Remove final legacy dependencies from Header UI (#38175)
* Remove final legacy dependencies from Header UI * Address @eliperelman comments * Move files for x-pack move
This commit is contained in:
parent
48c5df2e98
commit
5941436e1b
|
@ -0,0 +1,25 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavControl](./kibana-plugin-public.chromenavcontrol.md)
|
||||
|
||||
## ChromeNavControl interface
|
||||
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
export interface ChromeNavControl
|
||||
```
|
||||
|
||||
## Properties
|
||||
|
||||
| Property | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| [order](./kibana-plugin-public.chromenavcontrol.order.md) | <code>number</code> | |
|
||||
|
||||
## Methods
|
||||
|
||||
| Method | Description |
|
||||
| --- | --- |
|
||||
| [mount(targetDomElement)](./kibana-plugin-public.chromenavcontrol.mount.md) | |
|
||||
|
|
@ -0,0 +1,22 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavControl](./kibana-plugin-public.chromenavcontrol.md) > [mount](./kibana-plugin-public.chromenavcontrol.mount.md)
|
||||
|
||||
## ChromeNavControl.mount() method
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
mount(targetDomElement: HTMLElement): () => void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| targetDomElement | <code>HTMLElement</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`() => void`
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavControl](./kibana-plugin-public.chromenavcontrol.md) > [order](./kibana-plugin-public.chromenavcontrol.order.md)
|
||||
|
||||
## ChromeNavControl.order property
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
order?: number;
|
||||
```
|
|
@ -0,0 +1,35 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavControls](./kibana-plugin-public.chromenavcontrols.md)
|
||||
|
||||
## ChromeNavControls interface
|
||||
|
||||
[APIs](./kibana-plugin-public.chromenavcontrols.md) for registering new controls to be displayed in the navigation bar.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
export interface ChromeNavControls
|
||||
```
|
||||
|
||||
## Methods
|
||||
|
||||
| Method | Description |
|
||||
| --- | --- |
|
||||
| [registerLeft(navControl)](./kibana-plugin-public.chromenavcontrols.registerleft.md) | Register a nav control to be presented on the left side of the chrome header. |
|
||||
| [registerRight(navControl)](./kibana-plugin-public.chromenavcontrols.registerright.md) | Register a nav control to be presented on the right side of the chrome header. |
|
||||
|
||||
## Example
|
||||
|
||||
Register a left-side nav control rendered with React.
|
||||
|
||||
```jsx
|
||||
chrome.navControls.registerLeft({
|
||||
mount(targetDomElement) {
|
||||
ReactDOM.mount(<MyControl />, targetDomElement);
|
||||
return () => ReactDOM.unmountComponentAtNode(targetDomElement);
|
||||
}
|
||||
})
|
||||
|
||||
```
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavControls](./kibana-plugin-public.chromenavcontrols.md) > [registerLeft](./kibana-plugin-public.chromenavcontrols.registerleft.md)
|
||||
|
||||
## ChromeNavControls.registerLeft() method
|
||||
|
||||
Register a nav control to be presented on the left side of the chrome header.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
registerLeft(navControl: ChromeNavControl): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| navControl | <code>ChromeNavControl</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavControls](./kibana-plugin-public.chromenavcontrols.md) > [registerRight](./kibana-plugin-public.chromenavcontrols.registerright.md)
|
||||
|
||||
## ChromeNavControls.registerRight() method
|
||||
|
||||
Register a nav control to be presented on the right side of the chrome header.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
registerRight(navControl: ChromeNavControl): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| navControl | <code>ChromeNavControl</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,23 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [enableForcedAppSwitcherNavigation](./kibana-plugin-public.chromenavlinks.enableforcedappswitchernavigation.md)
|
||||
|
||||
## ChromeNavLinks.enableForcedAppSwitcherNavigation() method
|
||||
|
||||
Enable forced navigation mode, which will trigger a page refresh when a nav link is clicked and only the hash is updated.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
enableForcedAppSwitcherNavigation(): void;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
||||
## Remarks
|
||||
|
||||
This is only necessary when rendering the status page in place of another app, as links to that app will set the current URL and change the hash, but the routes for the correct are not loaded so nothing will happen. https://github.com/elastic/kibana/pull/29770
|
||||
|
||||
Used only by status\_page plugin
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [get](./kibana-plugin-public.chromenavlinks.get.md)
|
||||
|
||||
## ChromeNavLinks.get() method
|
||||
|
||||
Get the state of a navlink at this point in time.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
get(id: string): ChromeNavLink | undefined;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| id | <code>string</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`ChromeNavLink | undefined`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [getAll](./kibana-plugin-public.chromenavlinks.getall.md)
|
||||
|
||||
## ChromeNavLinks.getAll() method
|
||||
|
||||
Get the current state of all navlinks.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getAll(): Array<Readonly<ChromeNavLink>>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Array<Readonly<ChromeNavLink>>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [getForceAppSwitcherNavigation$](./kibana-plugin-public.chromenavlinks.getforceappswitchernavigation$.md)
|
||||
|
||||
## ChromeNavLinks.getForceAppSwitcherNavigation$() method
|
||||
|
||||
An observable of the forced app switcher state.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getForceAppSwitcherNavigation$(): Observable<boolean>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<boolean>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [getNavLinks$](./kibana-plugin-public.chromenavlinks.getnavlinks$.md)
|
||||
|
||||
## ChromeNavLinks.getNavLinks$() method
|
||||
|
||||
Get an observable for a sorted list of navlinks.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getNavLinks$(): Observable<Array<Readonly<ChromeNavLink>>>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<Array<Readonly<ChromeNavLink>>>`
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [has](./kibana-plugin-public.chromenavlinks.has.md)
|
||||
|
||||
## ChromeNavLinks.has() method
|
||||
|
||||
Check whether or not a navlink exists.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
has(id: string): boolean;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| id | <code>string</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`boolean`
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md)
|
||||
|
||||
## ChromeNavLinks interface
|
||||
|
||||
[APIs](./kibana-plugin-public.chromenavlinks.md) for manipulating nav links.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
export interface ChromeNavLinks
|
||||
```
|
||||
|
||||
## Methods
|
||||
|
||||
| Method | Description |
|
||||
| --- | --- |
|
||||
| [enableForcedAppSwitcherNavigation()](./kibana-plugin-public.chromenavlinks.enableforcedappswitchernavigation.md) | Enable forced navigation mode, which will trigger a page refresh when a nav link is clicked and only the hash is updated. |
|
||||
| [get(id)](./kibana-plugin-public.chromenavlinks.get.md) | Get the state of a navlink at this point in time. |
|
||||
| [getAll()](./kibana-plugin-public.chromenavlinks.getall.md) | Get the current state of all navlinks. |
|
||||
| [getForceAppSwitcherNavigation$()](./kibana-plugin-public.chromenavlinks.getforceappswitchernavigation$.md) | An observable of the forced app switcher state. |
|
||||
| [getNavLinks$()](./kibana-plugin-public.chromenavlinks.getnavlinks$.md) | Get an observable for a sorted list of navlinks. |
|
||||
| [has(id)](./kibana-plugin-public.chromenavlinks.has.md) | Check whether or not a navlink exists. |
|
||||
| [showOnly(id)](./kibana-plugin-public.chromenavlinks.showonly.md) | Remove all navlinks except the one matching the given id. |
|
||||
| [update(id, values)](./kibana-plugin-public.chromenavlinks.update.md) | Update the navlink for the given id with the updated attributes. Returns the updated navlink or <code>undefined</code> if it does not exist. |
|
||||
|
|
@ -0,0 +1,28 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [showOnly](./kibana-plugin-public.chromenavlinks.showonly.md)
|
||||
|
||||
## ChromeNavLinks.showOnly() method
|
||||
|
||||
Remove all navlinks except the one matching the given id.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
showOnly(id: string): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| id | <code>string</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
||||
## Remarks
|
||||
|
||||
NOTE: this is not reversible.
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) > [update](./kibana-plugin-public.chromenavlinks.update.md)
|
||||
|
||||
## ChromeNavLinks.update() method
|
||||
|
||||
Update the navlink for the given id with the updated attributes. Returns the updated navlink or `undefined` if it does not exist.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
update(id: string, values: ChromeNavLinkUpdateableFields): ChromeNavLink | undefined;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| id | <code>string</code> | |
|
||||
| values | <code>ChromeNavLinkUpdateableFields</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`ChromeNavLink | undefined`
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeNavLinkUpdateableFields](./kibana-plugin-public.chromenavlinkupdateablefields.md)
|
||||
|
||||
## ChromeNavLinkUpdateableFields type
|
||||
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
export declare type ChromeNavLinkUpdateableFields = Partial<Pick<ChromeNavLink, 'active' | 'disabled' | 'hidden' | 'url' | 'subUrlBase'>>;
|
||||
```
|
|
@ -0,0 +1,34 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessed](./kibana-plugin-public.chromerecentlyaccessed.md) > [add](./kibana-plugin-public.chromerecentlyaccessed.add.md)
|
||||
|
||||
## ChromeRecentlyAccessed.add() method
|
||||
|
||||
Adds a new item to the recently accessed history.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
add(link: string, label: string, id: string): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| link | <code>string</code> | |
|
||||
| label | <code>string</code> | |
|
||||
| id | <code>string</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
||||
## Example
|
||||
|
||||
|
||||
```js
|
||||
chrome.recentlyAccessed.add('/app/map/1234', 'Map 1234', '1234');
|
||||
|
||||
```
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessed](./kibana-plugin-public.chromerecentlyaccessed.md) > [get$](./kibana-plugin-public.chromerecentlyaccessed.get$.md)
|
||||
|
||||
## ChromeRecentlyAccessed.get$() method
|
||||
|
||||
Gets an Observable of the array of recently accessed history.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
get$(): Observable<ChromeRecentlyAccessedHistoryItem[]>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<ChromeRecentlyAccessedHistoryItem[]>`
|
||||
|
||||
## Example
|
||||
|
||||
|
||||
```js
|
||||
chrome.recentlyAccessed.get$().subscribe(console.log);
|
||||
|
||||
```
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessed](./kibana-plugin-public.chromerecentlyaccessed.md) > [get](./kibana-plugin-public.chromerecentlyaccessed.get.md)
|
||||
|
||||
## ChromeRecentlyAccessed.get() method
|
||||
|
||||
Gets an Array of the current recently accessed history.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
get(): ChromeRecentlyAccessedHistoryItem[];
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`ChromeRecentlyAccessedHistoryItem[]`
|
||||
|
||||
## Example
|
||||
|
||||
|
||||
```js
|
||||
chrome.recentlyAccessed.get().forEach(console.log);
|
||||
|
||||
```
|
||||
|
|
@ -0,0 +1,22 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessed](./kibana-plugin-public.chromerecentlyaccessed.md)
|
||||
|
||||
## ChromeRecentlyAccessed interface
|
||||
|
||||
[APIs](./kibana-plugin-public.chromerecentlyaccessed.md) for recently accessed history.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
export interface ChromeRecentlyAccessed
|
||||
```
|
||||
|
||||
## Methods
|
||||
|
||||
| Method | Description |
|
||||
| --- | --- |
|
||||
| [add(link, label, id)](./kibana-plugin-public.chromerecentlyaccessed.add.md) | Adds a new item to the recently accessed history. |
|
||||
| [get()](./kibana-plugin-public.chromerecentlyaccessed.get.md) | Gets an Array of the current recently accessed history. |
|
||||
| [get$()](./kibana-plugin-public.chromerecentlyaccessed.get$.md) | Gets an Observable of the array of recently accessed history. |
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessedHistoryItem](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.md) > [id](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.id.md)
|
||||
|
||||
## ChromeRecentlyAccessedHistoryItem.id property
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
id: string;
|
||||
```
|
|
@ -0,0 +1,11 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessedHistoryItem](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.md) > [label](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.label.md)
|
||||
|
||||
## ChromeRecentlyAccessedHistoryItem.label property
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
label: string;
|
||||
```
|
|
@ -0,0 +1,11 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessedHistoryItem](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.md) > [link](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.link.md)
|
||||
|
||||
## ChromeRecentlyAccessedHistoryItem.link property
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
link: string;
|
||||
```
|
|
@ -0,0 +1,21 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeRecentlyAccessedHistoryItem](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.md)
|
||||
|
||||
## ChromeRecentlyAccessedHistoryItem interface
|
||||
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
export interface ChromeRecentlyAccessedHistoryItem
|
||||
```
|
||||
|
||||
## Properties
|
||||
|
||||
| Property | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| [id](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.id.md) | <code>string</code> | |
|
||||
| [label](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.label.md) | <code>string</code> | |
|
||||
| [link](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.link.md) | <code>string</code> | |
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [addApplicationClass](./kibana-plugin-public.chromestart.addapplicationclass.md)
|
||||
|
||||
## ChromeStart.addApplicationClass() method
|
||||
|
||||
Add a className that should be set on the application container.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
addApplicationClass(className: string): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| className | <code>string</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [getApplicationClasses$](./kibana-plugin-public.chromestart.getapplicationclasses$.md)
|
||||
|
||||
## ChromeStart.getApplicationClasses$() method
|
||||
|
||||
Get the current set of classNames that will be set on the application container.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getApplicationClasses$(): Observable<string[]>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<string[]>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [getBadge$](./kibana-plugin-public.chromestart.getbadge$.md)
|
||||
|
||||
## ChromeStart.getBadge$() method
|
||||
|
||||
Get an observable of the current badge
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getBadge$(): Observable<ChromeBadge | undefined>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<ChromeBadge | undefined>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [getBrand$](./kibana-plugin-public.chromestart.getbrand$.md)
|
||||
|
||||
## ChromeStart.getBrand$() method
|
||||
|
||||
Get an observable of the current brand information.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getBrand$(): Observable<ChromeBrand>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<ChromeBrand>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [getBreadcrumbs$](./kibana-plugin-public.chromestart.getbreadcrumbs$.md)
|
||||
|
||||
## ChromeStart.getBreadcrumbs$() method
|
||||
|
||||
Get an observable of the current list of breadcrumbs
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getBreadcrumbs$(): Observable<ChromeBreadcrumb[]>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<ChromeBreadcrumb[]>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [getHelpExtension$](./kibana-plugin-public.chromestart.gethelpextension$.md)
|
||||
|
||||
## ChromeStart.getHelpExtension$() method
|
||||
|
||||
Get an observable of the current custom help conttent
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getHelpExtension$(): Observable<ChromeHelpExtension | undefined>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<ChromeHelpExtension | undefined>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [getIsCollapsed$](./kibana-plugin-public.chromestart.getiscollapsed$.md)
|
||||
|
||||
## ChromeStart.getIsCollapsed$() method
|
||||
|
||||
Get an observable of the current collapsed state of the chrome.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getIsCollapsed$(): Observable<boolean>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<boolean>`
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [getIsVisible$](./kibana-plugin-public.chromestart.getisvisible$.md)
|
||||
|
||||
## ChromeStart.getIsVisible$() method
|
||||
|
||||
Get an observable of the current visibility state of the chrome.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
getIsVisible$(): Observable<boolean>;
|
||||
```
|
||||
<b>Returns:</b>
|
||||
|
||||
`Observable<boolean>`
|
||||
|
|
@ -2,11 +2,40 @@
|
|||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md)
|
||||
|
||||
## ChromeStart type
|
||||
## ChromeStart interface
|
||||
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
export declare type ChromeStart = ReturnType<ChromeService['start']>;
|
||||
export interface ChromeStart
|
||||
```
|
||||
|
||||
## Properties
|
||||
|
||||
| Property | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| [navControls](./kibana-plugin-public.chromestart.navcontrols.md) | <code>ChromeNavControls</code> | [APIs](./kibana-plugin-public.chromenavcontrols.md) for registering new controls to be displayed in the navigation bar. |
|
||||
| [navLinks](./kibana-plugin-public.chromestart.navlinks.md) | <code>ChromeNavLinks</code> | [APIs](./kibana-plugin-public.chromenavlinks.md) for manipulating nav links. |
|
||||
| [recentlyAccessed](./kibana-plugin-public.chromestart.recentlyaccessed.md) | <code>ChromeRecentlyAccessed</code> | [APIs](./kibana-plugin-public.chromerecentlyaccessed.md) for recently accessed history. |
|
||||
|
||||
## Methods
|
||||
|
||||
| Method | Description |
|
||||
| --- | --- |
|
||||
| [addApplicationClass(className)](./kibana-plugin-public.chromestart.addapplicationclass.md) | Add a className that should be set on the application container. |
|
||||
| [getApplicationClasses$()](./kibana-plugin-public.chromestart.getapplicationclasses$.md) | Get the current set of classNames that will be set on the application container. |
|
||||
| [getBadge$()](./kibana-plugin-public.chromestart.getbadge$.md) | Get an observable of the current badge |
|
||||
| [getBrand$()](./kibana-plugin-public.chromestart.getbrand$.md) | Get an observable of the current brand information. |
|
||||
| [getBreadcrumbs$()](./kibana-plugin-public.chromestart.getbreadcrumbs$.md) | Get an observable of the current list of breadcrumbs |
|
||||
| [getHelpExtension$()](./kibana-plugin-public.chromestart.gethelpextension$.md) | Get an observable of the current custom help conttent |
|
||||
| [getIsCollapsed$()](./kibana-plugin-public.chromestart.getiscollapsed$.md) | Get an observable of the current collapsed state of the chrome. |
|
||||
| [getIsVisible$()](./kibana-plugin-public.chromestart.getisvisible$.md) | Get an observable of the current visibility state of the chrome. |
|
||||
| [removeApplicationClass(className)](./kibana-plugin-public.chromestart.removeapplicationclass.md) | Remove a className added with <code>addApplicationClass()</code>. If className is unknown it is ignored. |
|
||||
| [setBadge(badge)](./kibana-plugin-public.chromestart.setbadge.md) | Override the current badge |
|
||||
| [setBrand(brand)](./kibana-plugin-public.chromestart.setbrand.md) | Set the brand configuration. |
|
||||
| [setBreadcrumbs(newBreadcrumbs)](./kibana-plugin-public.chromestart.setbreadcrumbs.md) | Override the current set of breadcrumbs |
|
||||
| [setHelpExtension(helpExtension)](./kibana-plugin-public.chromestart.sethelpextension.md) | Override the current set of custom help content |
|
||||
| [setIsCollapsed(isCollapsed)](./kibana-plugin-public.chromestart.setiscollapsed.md) | Set the collapsed state of the chrome navigation. |
|
||||
| [setIsVisible(isVisible)](./kibana-plugin-public.chromestart.setisvisible.md) | Set the temporary visibility for the chrome. This does nothing if the chrome is hidden by default and should be used to hide the chrome for things like full-screen modes with an exit button. |
|
||||
|
||||
|
|
|
@ -0,0 +1,13 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [navControls](./kibana-plugin-public.chromestart.navcontrols.md)
|
||||
|
||||
## ChromeStart.navControls property
|
||||
|
||||
[APIs](./kibana-plugin-public.chromenavcontrols.md) for registering new controls to be displayed in the navigation bar.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
navControls: ChromeNavControls;
|
||||
```
|
|
@ -0,0 +1,13 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [navLinks](./kibana-plugin-public.chromestart.navlinks.md)
|
||||
|
||||
## ChromeStart.navLinks property
|
||||
|
||||
[APIs](./kibana-plugin-public.chromenavlinks.md) for manipulating nav links.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
navLinks: ChromeNavLinks;
|
||||
```
|
|
@ -0,0 +1,13 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [recentlyAccessed](./kibana-plugin-public.chromestart.recentlyaccessed.md)
|
||||
|
||||
## ChromeStart.recentlyAccessed property
|
||||
|
||||
[APIs](./kibana-plugin-public.chromerecentlyaccessed.md) for recently accessed history.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
recentlyAccessed: ChromeRecentlyAccessed;
|
||||
```
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [removeApplicationClass](./kibana-plugin-public.chromestart.removeapplicationclass.md)
|
||||
|
||||
## ChromeStart.removeApplicationClass() method
|
||||
|
||||
Remove a className added with `addApplicationClass()`<!-- -->. If className is unknown it is ignored.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
removeApplicationClass(className: string): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| className | <code>string</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [setBadge](./kibana-plugin-public.chromestart.setbadge.md)
|
||||
|
||||
## ChromeStart.setBadge() method
|
||||
|
||||
Override the current badge
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
setBadge(badge?: ChromeBadge): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| badge | <code>ChromeBadge</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,39 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [setBrand](./kibana-plugin-public.chromestart.setbrand.md)
|
||||
|
||||
## ChromeStart.setBrand() method
|
||||
|
||||
Set the brand configuration.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
setBrand(brand: ChromeBrand): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| brand | <code>ChromeBrand</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
||||
## Remarks
|
||||
|
||||
Normally the `logo` property will be rendered as the CSS background for the home link in the chrome navigation, but when the page is rendered in a small window the `smallLogo` will be used and rendered at about 45px wide.
|
||||
|
||||
## Example
|
||||
|
||||
|
||||
```js
|
||||
chrome.setBrand({
|
||||
logo: 'url(/plugins/app/logo.png) center no-repeat'
|
||||
smallLogo: 'url(/plugins/app/logo-small.png) center no-repeat'
|
||||
})
|
||||
|
||||
```
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [setBreadcrumbs](./kibana-plugin-public.chromestart.setbreadcrumbs.md)
|
||||
|
||||
## ChromeStart.setBreadcrumbs() method
|
||||
|
||||
Override the current set of breadcrumbs
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
setBreadcrumbs(newBreadcrumbs: ChromeBreadcrumb[]): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| newBreadcrumbs | <code>ChromeBreadcrumb[]</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [setHelpExtension](./kibana-plugin-public.chromestart.sethelpextension.md)
|
||||
|
||||
## ChromeStart.setHelpExtension() method
|
||||
|
||||
Override the current set of custom help content
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
setHelpExtension(helpExtension?: ChromeHelpExtension): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| helpExtension | <code>ChromeHelpExtension</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [setIsCollapsed](./kibana-plugin-public.chromestart.setiscollapsed.md)
|
||||
|
||||
## ChromeStart.setIsCollapsed() method
|
||||
|
||||
Set the collapsed state of the chrome navigation.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
setIsCollapsed(isCollapsed: boolean): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| isCollapsed | <code>boolean</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
|
||||
|
||||
[Home](./index.md) > [kibana-plugin-public](./kibana-plugin-public.md) > [ChromeStart](./kibana-plugin-public.chromestart.md) > [setIsVisible](./kibana-plugin-public.chromestart.setisvisible.md)
|
||||
|
||||
## ChromeStart.setIsVisible() method
|
||||
|
||||
Set the temporary visibility for the chrome. This does nothing if the chrome is hidden by default and should be used to hide the chrome for things like full-screen modes with an exit button.
|
||||
|
||||
<b>Signature:</b>
|
||||
|
||||
```typescript
|
||||
setIsVisible(isVisible: boolean): void;
|
||||
```
|
||||
|
||||
## Parameters
|
||||
|
||||
| Parameter | Type | Description |
|
||||
| --- | --- | --- |
|
||||
| isVisible | <code>boolean</code> | |
|
||||
|
||||
<b>Returns:</b>
|
||||
|
||||
`void`
|
||||
|
|
@ -27,7 +27,13 @@ The plugin integrates with the core system via lifecycle events: `setup`<!-- -->
|
|||
| [ChromeBadge](./kibana-plugin-public.chromebadge.md) | |
|
||||
| [ChromeBrand](./kibana-plugin-public.chromebrand.md) | |
|
||||
| [ChromeBreadcrumb](./kibana-plugin-public.chromebreadcrumb.md) | |
|
||||
| [ChromeNavControl](./kibana-plugin-public.chromenavcontrol.md) | |
|
||||
| [ChromeNavControls](./kibana-plugin-public.chromenavcontrols.md) | [APIs](./kibana-plugin-public.chromenavcontrols.md) for registering new controls to be displayed in the navigation bar. |
|
||||
| [ChromeNavLink](./kibana-plugin-public.chromenavlink.md) | |
|
||||
| [ChromeNavLinks](./kibana-plugin-public.chromenavlinks.md) | [APIs](./kibana-plugin-public.chromenavlinks.md) for manipulating nav links. |
|
||||
| [ChromeRecentlyAccessed](./kibana-plugin-public.chromerecentlyaccessed.md) | [APIs](./kibana-plugin-public.chromerecentlyaccessed.md) for recently accessed history. |
|
||||
| [ChromeRecentlyAccessedHistoryItem](./kibana-plugin-public.chromerecentlyaccessedhistoryitem.md) | |
|
||||
| [ChromeStart](./kibana-plugin-public.chromestart.md) | |
|
||||
| [CoreSetup](./kibana-plugin-public.coresetup.md) | Core services exposed to the <code>Plugin</code> setup lifecycle |
|
||||
| [CoreStart](./kibana-plugin-public.corestart.md) | Core services exposed to the <code>Plugin</code> start lifecycle |
|
||||
| [ErrorToastOptions](./kibana-plugin-public.errortoastoptions.md) | |
|
||||
|
@ -50,7 +56,7 @@ The plugin integrates with the core system via lifecycle events: `setup`<!-- -->
|
|||
| Type Alias | Description |
|
||||
| --- | --- |
|
||||
| [ChromeHelpExtension](./kibana-plugin-public.chromehelpextension.md) | |
|
||||
| [ChromeStart](./kibana-plugin-public.chromestart.md) | |
|
||||
| [ChromeNavLinkUpdateableFields](./kibana-plugin-public.chromenavlinkupdateablefields.md) | |
|
||||
| [HttpSetup](./kibana-plugin-public.httpsetup.md) | |
|
||||
| [HttpStart](./kibana-plugin-public.httpstart.md) | |
|
||||
| [PluginInitializer](./kibana-plugin-public.plugininitializer.md) | The <code>plugin</code> export at the root of a plugin's <code>public</code> directory should conform to this interface. |
|
||||
|
|
|
@ -275,6 +275,7 @@
|
|||
"@microsoft/api-extractor": "7.1.8",
|
||||
"@octokit/rest": "^15.10.0",
|
||||
"@percy/agent": "^0.1.16",
|
||||
"@trust/webcrypto": "^0.9.2",
|
||||
"@types/angular": "1.6.50",
|
||||
"@types/angular-mocks": "^1.7.0",
|
||||
"@types/babel__core": "^7.1.0",
|
||||
|
@ -374,6 +375,7 @@
|
|||
"eslint-plugin-react-hooks": "1.6.0",
|
||||
"exit-hook": "^2.1.0",
|
||||
"faker": "1.1.0",
|
||||
"fast-text-encoding": "^1.0.0",
|
||||
"fetch-mock": "7.3.3",
|
||||
"geckodriver": "1.16.2",
|
||||
"getopts": "^2.2.4",
|
||||
|
|
|
@ -37,6 +37,17 @@ const createStartContractMock = () => {
|
|||
enableForcedAppSwitcherNavigation: jest.fn(),
|
||||
getForceAppSwitcherNavigation$: jest.fn(),
|
||||
},
|
||||
recentlyAccessed: {
|
||||
add: jest.fn(),
|
||||
get: jest.fn(),
|
||||
get$: jest.fn(),
|
||||
},
|
||||
navControls: {
|
||||
registerLeft: jest.fn(),
|
||||
registerRight: jest.fn(),
|
||||
getLeft$: jest.fn(),
|
||||
getRight$: jest.fn(),
|
||||
},
|
||||
setBrand: jest.fn(),
|
||||
getBrand$: jest.fn(),
|
||||
setIsVisible: jest.fn(),
|
||||
|
@ -69,7 +80,7 @@ const createMock = () => {
|
|||
start: jest.fn(),
|
||||
stop: jest.fn(),
|
||||
};
|
||||
mocked.start.mockReturnValue(createStartContractMock());
|
||||
mocked.start.mockResolvedValue(createStartContractMock());
|
||||
return mocked;
|
||||
};
|
||||
|
||||
|
|
|
@ -24,6 +24,7 @@ import { applicationServiceMock } from '../application/application_service.mock'
|
|||
import { httpServiceMock } from '../http/http_service.mock';
|
||||
import { injectedMetadataServiceMock } from '../injected_metadata/injected_metadata_service.mock';
|
||||
import { notificationServiceMock } from '../notifications/notifications_service.mock';
|
||||
import { ChromeService } from './chrome_service';
|
||||
|
||||
const store = new Map();
|
||||
(window as any).localStorage = {
|
||||
|
@ -32,14 +33,12 @@ const store = new Map();
|
|||
removeItem: (key: string) => store.delete(String(key)),
|
||||
};
|
||||
|
||||
import { ChromeService } from './chrome_service';
|
||||
|
||||
function defaultStartDeps(): any {
|
||||
return {
|
||||
application: applicationServiceMock.createStartContract(),
|
||||
http: httpServiceMock.createStartContract(),
|
||||
notifications: notificationServiceMock.createStartContract(),
|
||||
injectedMetadata: injectedMetadataServiceMock.createStartContract(),
|
||||
notifications: notificationServiceMock.createStartContract(),
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -48,11 +47,11 @@ beforeEach(() => {
|
|||
});
|
||||
|
||||
describe('start', () => {
|
||||
it('adds legacy browser warning if browserSupportsCsp is disabled and warnLegacyBrowsers is enabled', () => {
|
||||
it('adds legacy browser warning if browserSupportsCsp is disabled and warnLegacyBrowsers is enabled', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: false });
|
||||
const startDeps = defaultStartDeps();
|
||||
startDeps.injectedMetadata.getCspConfig.mockReturnValue({ warnLegacyBrowsers: true });
|
||||
service.start(startDeps);
|
||||
await service.start(startDeps);
|
||||
expect(startDeps.notifications.toasts.addWarning.mock.calls).toMatchInlineSnapshot(`
|
||||
Array [
|
||||
Array [
|
||||
|
@ -62,26 +61,26 @@ Array [
|
|||
`);
|
||||
});
|
||||
|
||||
it('does not add legacy browser warning if browser supports CSP', () => {
|
||||
it('does not add legacy browser warning if browser supports CSP', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const startDeps = defaultStartDeps();
|
||||
startDeps.injectedMetadata.getCspConfig.mockReturnValue({ warnLegacyBrowsers: true });
|
||||
service.start(startDeps);
|
||||
await service.start(startDeps);
|
||||
expect(startDeps.notifications.toasts.addWarning).not.toBeCalled();
|
||||
});
|
||||
|
||||
it('does not add legacy browser warning if warnLegacyBrowsers is disabled', () => {
|
||||
it('does not add legacy browser warning if warnLegacyBrowsers is disabled', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: false });
|
||||
const startDeps = defaultStartDeps();
|
||||
startDeps.injectedMetadata.getCspConfig.mockReturnValue({ warnLegacyBrowsers: false });
|
||||
service.start(startDeps);
|
||||
await service.start(startDeps);
|
||||
expect(startDeps.notifications.toasts.addWarning).not.toBeCalled();
|
||||
});
|
||||
|
||||
describe('brand', () => {
|
||||
it('updates/emits the brand as it changes', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getBrand$()
|
||||
.pipe(toArray())
|
||||
|
@ -115,7 +114,7 @@ Array [
|
|||
describe('visibility', () => {
|
||||
it('updates/emits the visibility', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getIsVisible$()
|
||||
.pipe(toArray())
|
||||
|
@ -140,7 +139,7 @@ Array [
|
|||
window.history.pushState(undefined, '', '#/home?a=b&embed=true');
|
||||
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getIsVisible$()
|
||||
.pipe(toArray())
|
||||
|
@ -165,7 +164,7 @@ Array [
|
|||
describe('is collapsed', () => {
|
||||
it('updates/emits isCollapsed', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getIsCollapsed$()
|
||||
.pipe(toArray())
|
||||
|
@ -188,7 +187,7 @@ Array [
|
|||
|
||||
it('only stores true in localStorage', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
|
||||
start.setIsCollapsed(true);
|
||||
expect(store.size).toBe(1);
|
||||
|
@ -201,7 +200,7 @@ Array [
|
|||
describe('application classes', () => {
|
||||
it('updates/emits the application classes', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getApplicationClasses$()
|
||||
.pipe(toArray())
|
||||
|
@ -253,7 +252,7 @@ Array [
|
|||
describe('badge', () => {
|
||||
it('updates/emits the current badge', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getBadge$()
|
||||
.pipe(toArray())
|
||||
|
@ -284,7 +283,7 @@ Array [
|
|||
describe('breadcrumbs', () => {
|
||||
it('updates/emits the current set of breadcrumbs', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getBreadcrumbs$()
|
||||
.pipe(toArray())
|
||||
|
@ -326,7 +325,7 @@ Array [
|
|||
describe('help extension', () => {
|
||||
it('updates/emits the current help extension', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = start
|
||||
.getHelpExtension$()
|
||||
.pipe(toArray())
|
||||
|
@ -350,7 +349,7 @@ Array [
|
|||
describe('stop', () => {
|
||||
it('completes applicationClass$, isCollapsed$, breadcrumbs$, isVisible$, and brand$ observables', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
const promise = Rx.combineLatest(
|
||||
start.getBrand$(),
|
||||
start.getApplicationClasses$(),
|
||||
|
@ -366,7 +365,7 @@ describe('stop', () => {
|
|||
|
||||
it('completes immediately if service already stopped', async () => {
|
||||
const service = new ChromeService({ browserSupportsCsp: true });
|
||||
const start = service.start(defaultStartDeps());
|
||||
const start = await service.start(defaultStartDeps());
|
||||
service.stop();
|
||||
|
||||
await expect(
|
||||
|
|
|
@ -20,15 +20,21 @@
|
|||
import * as Url from 'url';
|
||||
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import * as Rx from 'rxjs';
|
||||
import { BehaviorSubject, Observable, ReplaySubject } from 'rxjs';
|
||||
import { map, takeUntil } from 'rxjs/operators';
|
||||
import { IconType } from '@elastic/eui';
|
||||
|
||||
import { InjectedMetadataStart } from '../injected_metadata';
|
||||
import { NotificationsStart } from '../notifications';
|
||||
import { NavLinksService } from './nav_links/nav_links_service';
|
||||
import { ApplicationStart } from '../application';
|
||||
import { HttpStart } from '../http';
|
||||
|
||||
import { ChromeNavLinks, NavLinksService } from './nav_links';
|
||||
import { ChromeRecentlyAccessed, RecentlyAccessedService } from './recently_accessed';
|
||||
import { NavControlsService, ChromeNavControls } from './nav_controls';
|
||||
|
||||
export { ChromeNavControls, ChromeRecentlyAccessed };
|
||||
|
||||
const IS_COLLAPSED_KEY = 'core.chrome.isCollapsed';
|
||||
|
||||
function isEmbedParamInHash() {
|
||||
|
@ -72,24 +78,31 @@ interface StartDeps {
|
|||
|
||||
/** @internal */
|
||||
export class ChromeService {
|
||||
private readonly stop$ = new Rx.ReplaySubject(1);
|
||||
private readonly stop$ = new ReplaySubject(1);
|
||||
private readonly browserSupportsCsp: boolean;
|
||||
private readonly navControls = new NavControlsService();
|
||||
private readonly navLinks = new NavLinksService();
|
||||
private readonly recentlyAccessed = new RecentlyAccessedService();
|
||||
|
||||
public constructor({ browserSupportsCsp }: ConstructorParams) {
|
||||
this.browserSupportsCsp = browserSupportsCsp;
|
||||
}
|
||||
|
||||
public start({ application, http, injectedMetadata, notifications }: StartDeps) {
|
||||
public async start({
|
||||
application,
|
||||
http,
|
||||
injectedMetadata,
|
||||
notifications,
|
||||
}: StartDeps): Promise<ChromeStart> {
|
||||
const FORCE_HIDDEN = isEmbedParamInHash();
|
||||
|
||||
const brand$ = new Rx.BehaviorSubject<ChromeBrand>({});
|
||||
const isVisible$ = new Rx.BehaviorSubject(true);
|
||||
const isCollapsed$ = new Rx.BehaviorSubject(!!localStorage.getItem(IS_COLLAPSED_KEY));
|
||||
const applicationClasses$ = new Rx.BehaviorSubject<Set<string>>(new Set());
|
||||
const helpExtension$ = new Rx.BehaviorSubject<ChromeHelpExtension | undefined>(undefined);
|
||||
const breadcrumbs$ = new Rx.BehaviorSubject<ChromeBreadcrumb[]>([]);
|
||||
const badge$ = new Rx.BehaviorSubject<ChromeBadge | undefined>(undefined);
|
||||
const brand$ = new BehaviorSubject<ChromeBrand>({});
|
||||
const isVisible$ = new BehaviorSubject(true);
|
||||
const isCollapsed$ = new BehaviorSubject(!!localStorage.getItem(IS_COLLAPSED_KEY));
|
||||
const applicationClasses$ = new BehaviorSubject<Set<string>>(new Set());
|
||||
const helpExtension$ = new BehaviorSubject<ChromeHelpExtension | undefined>(undefined);
|
||||
const breadcrumbs$ = new BehaviorSubject<ChromeBreadcrumb[]>([]);
|
||||
const badge$ = new BehaviorSubject<ChromeBadge | undefined>(undefined);
|
||||
|
||||
if (!this.browserSupportsCsp && injectedMetadata.getCspConfig().warnLegacyBrowsers) {
|
||||
notifications.toasts.addWarning(
|
||||
|
@ -100,22 +113,12 @@ export class ChromeService {
|
|||
}
|
||||
|
||||
return {
|
||||
navControls: this.navControls.start(),
|
||||
navLinks: this.navLinks.start({ application, http }),
|
||||
recentlyAccessed: await this.recentlyAccessed.start({ http }),
|
||||
|
||||
getBrand$: () => brand$.pipe(takeUntil(this.stop$)),
|
||||
|
||||
/**
|
||||
* Set the brand configuration. Normally the `logo` property will be rendered as the
|
||||
* CSS background for the home link in the chrome navigation, but when the page is
|
||||
* rendered in a small window the `smallLogo` will be used and rendered at about
|
||||
* 45px wide.
|
||||
*
|
||||
* example:
|
||||
*
|
||||
* chrome.setBrand({
|
||||
* logo: 'url(/plugins/app/logo.png) center no-repeat'
|
||||
* smallLogo: 'url(/plugins/app/logo-small.png) center no-repeat'
|
||||
* })
|
||||
*
|
||||
*/
|
||||
setBrand: (brand: ChromeBrand) => {
|
||||
brand$.next(
|
||||
Object.freeze({
|
||||
|
@ -125,32 +128,18 @@ export class ChromeService {
|
|||
);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get an observable of the current brand information.
|
||||
*/
|
||||
getBrand$: () => brand$.pipe(takeUntil(this.stop$)),
|
||||
|
||||
/**
|
||||
* Set the temporary visibility for the chrome. This does nothing if the chrome is hidden
|
||||
* by default and should be used to hide the chrome for things like full-screen modes
|
||||
* with an exit button.
|
||||
*/
|
||||
setIsVisible: (visibility: boolean) => {
|
||||
isVisible$.next(visibility);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get an observable of the current visibility state of the chrome.
|
||||
*/
|
||||
getIsVisible$: () =>
|
||||
isVisible$.pipe(
|
||||
map(visibility => (FORCE_HIDDEN ? false : visibility)),
|
||||
takeUntil(this.stop$)
|
||||
),
|
||||
|
||||
/**
|
||||
* Set the collapsed state of the chrome navigation.
|
||||
*/
|
||||
setIsVisible: (visibility: boolean) => {
|
||||
isVisible$.next(visibility);
|
||||
},
|
||||
|
||||
getIsCollapsed$: () => isCollapsed$.pipe(takeUntil(this.stop$)),
|
||||
|
||||
setIsCollapsed: (isCollapsed: boolean) => {
|
||||
isCollapsed$.next(isCollapsed);
|
||||
if (isCollapsed) {
|
||||
|
@ -160,69 +149,38 @@ export class ChromeService {
|
|||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Get an observable of the current collapsed state of the chrome.
|
||||
*/
|
||||
getIsCollapsed$: () => isCollapsed$.pipe(takeUntil(this.stop$)),
|
||||
getApplicationClasses$: () =>
|
||||
applicationClasses$.pipe(
|
||||
map(set => [...set]),
|
||||
takeUntil(this.stop$)
|
||||
),
|
||||
|
||||
/**
|
||||
* Add a className that should be set on the application container.
|
||||
*/
|
||||
addApplicationClass: (className: string) => {
|
||||
const update = new Set([...applicationClasses$.getValue()]);
|
||||
update.add(className);
|
||||
applicationClasses$.next(update);
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove a className added with `addApplicationClass()`. If className is unknown it is ignored.
|
||||
*/
|
||||
removeApplicationClass: (className: string) => {
|
||||
const update = new Set([...applicationClasses$.getValue()]);
|
||||
update.delete(className);
|
||||
applicationClasses$.next(update);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the current set of classNames that will be set on the application container.
|
||||
*/
|
||||
getApplicationClasses$: () =>
|
||||
applicationClasses$.pipe(
|
||||
map(set => [...set]),
|
||||
takeUntil(this.stop$)
|
||||
),
|
||||
/**
|
||||
* Get an observable of the current badge
|
||||
*/
|
||||
getBadge$: () => badge$.pipe(takeUntil(this.stop$)),
|
||||
|
||||
/**
|
||||
* Override the current badge
|
||||
*/
|
||||
setBadge: (badge: ChromeBadge | undefined) => {
|
||||
setBadge: (badge: ChromeBadge) => {
|
||||
badge$.next(badge);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get an observable of the current list of breadcrumbs
|
||||
*/
|
||||
getBreadcrumbs$: () => breadcrumbs$.pipe(takeUntil(this.stop$)),
|
||||
|
||||
/**
|
||||
* Override the current set of breadcrumbs
|
||||
*/
|
||||
setBreadcrumbs: (newBreadcrumbs: ChromeBreadcrumb[]) => {
|
||||
breadcrumbs$.next(newBreadcrumbs);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get an observable of the current custom help conttent
|
||||
*/
|
||||
getHelpExtension$: () => helpExtension$.pipe(takeUntil(this.stop$)),
|
||||
|
||||
/**
|
||||
* Override the current set of breadcrumbs
|
||||
*/
|
||||
setHelpExtension: (helpExtension?: ChromeHelpExtension) => {
|
||||
helpExtension$.next(helpExtension);
|
||||
},
|
||||
|
@ -236,4 +194,103 @@ export class ChromeService {
|
|||
}
|
||||
|
||||
/** @public */
|
||||
export type ChromeStart = ReturnType<ChromeService['start']>;
|
||||
export interface ChromeStart {
|
||||
/** {@inheritdoc ChromeNavLinks} */
|
||||
navLinks: ChromeNavLinks;
|
||||
/** {@inheritdoc ChromeNavControls} */
|
||||
navControls: ChromeNavControls;
|
||||
/** {@inheritdoc ChromeRecentlyAccessed} */
|
||||
recentlyAccessed: ChromeRecentlyAccessed;
|
||||
|
||||
/**
|
||||
* Get an observable of the current brand information.
|
||||
*/
|
||||
getBrand$(): Observable<ChromeBrand>;
|
||||
|
||||
/**
|
||||
* Set the brand configuration.
|
||||
*
|
||||
* @remarks
|
||||
* Normally the `logo` property will be rendered as the
|
||||
* CSS background for the home link in the chrome navigation, but when the page is
|
||||
* rendered in a small window the `smallLogo` will be used and rendered at about
|
||||
* 45px wide.
|
||||
*
|
||||
* @example
|
||||
* ```js
|
||||
* chrome.setBrand({
|
||||
* logo: 'url(/plugins/app/logo.png) center no-repeat'
|
||||
* smallLogo: 'url(/plugins/app/logo-small.png) center no-repeat'
|
||||
* })
|
||||
* ```
|
||||
*
|
||||
*/
|
||||
setBrand(brand: ChromeBrand): void;
|
||||
|
||||
/**
|
||||
* Get an observable of the current visibility state of the chrome.
|
||||
*/
|
||||
getIsVisible$(): Observable<boolean>;
|
||||
|
||||
/**
|
||||
* Set the temporary visibility for the chrome. This does nothing if the chrome is hidden
|
||||
* by default and should be used to hide the chrome for things like full-screen modes
|
||||
* with an exit button.
|
||||
*/
|
||||
setIsVisible(isVisible: boolean): void;
|
||||
|
||||
/**
|
||||
* Get an observable of the current collapsed state of the chrome.
|
||||
*/
|
||||
getIsCollapsed$(): Observable<boolean>;
|
||||
|
||||
/**
|
||||
* Set the collapsed state of the chrome navigation.
|
||||
*/
|
||||
setIsCollapsed(isCollapsed: boolean): void;
|
||||
|
||||
/**
|
||||
* Get the current set of classNames that will be set on the application container.
|
||||
*/
|
||||
getApplicationClasses$(): Observable<string[]>;
|
||||
|
||||
/**
|
||||
* Add a className that should be set on the application container.
|
||||
*/
|
||||
addApplicationClass(className: string): void;
|
||||
|
||||
/**
|
||||
* Remove a className added with `addApplicationClass()`. If className is unknown it is ignored.
|
||||
*/
|
||||
removeApplicationClass(className: string): void;
|
||||
|
||||
/**
|
||||
* Get an observable of the current badge
|
||||
*/
|
||||
getBadge$(): Observable<ChromeBadge | undefined>;
|
||||
|
||||
/**
|
||||
* Override the current badge
|
||||
*/
|
||||
setBadge(badge?: ChromeBadge): void;
|
||||
|
||||
/**
|
||||
* Get an observable of the current list of breadcrumbs
|
||||
*/
|
||||
getBreadcrumbs$(): Observable<ChromeBreadcrumb[]>;
|
||||
|
||||
/**
|
||||
* Override the current set of breadcrumbs
|
||||
*/
|
||||
setBreadcrumbs(newBreadcrumbs: ChromeBreadcrumb[]): void;
|
||||
|
||||
/**
|
||||
* Get an observable of the current custom help conttent
|
||||
*/
|
||||
getHelpExtension$(): Observable<ChromeHelpExtension | undefined>;
|
||||
|
||||
/**
|
||||
* Override the current set of custom help content
|
||||
*/
|
||||
setHelpExtension(helpExtension?: ChromeHelpExtension): void;
|
||||
}
|
||||
|
|
|
@ -25,4 +25,6 @@ export {
|
|||
ChromeBrand,
|
||||
ChromeHelpExtension,
|
||||
} from './chrome_service';
|
||||
export { ChromeNavLink } from './nav_links';
|
||||
export { ChromeNavLink, ChromeNavLinks, ChromeNavLinkUpdateableFields } from './nav_links';
|
||||
export { ChromeRecentlyAccessed, ChromeRecentlyAccessedHistoryItem } from './recently_accessed';
|
||||
export { ChromeNavControl, ChromeNavControls } from './nav_controls';
|
||||
|
|
20
src/core/public/chrome/nav_controls/index.ts
Normal file
20
src/core/public/chrome/nav_controls/index.ts
Normal file
|
@ -0,0 +1,20 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
export * from './nav_controls_service';
|
|
@ -0,0 +1,87 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { NavControlsService } from './nav_controls_service';
|
||||
import { take } from 'rxjs/operators';
|
||||
|
||||
describe('RecentlyAccessed#start()', () => {
|
||||
const getStart = () => {
|
||||
return new NavControlsService().start();
|
||||
};
|
||||
|
||||
describe('left side', () => {
|
||||
it('allows registration', async () => {
|
||||
const navControls = getStart();
|
||||
const nc = { mount: jest.fn() };
|
||||
navControls.registerLeft(nc);
|
||||
expect(
|
||||
await navControls
|
||||
.getLeft$()
|
||||
.pipe(take(1))
|
||||
.toPromise()
|
||||
).toEqual([nc]);
|
||||
});
|
||||
|
||||
it('sorts controls by order property', async () => {
|
||||
const navControls = getStart();
|
||||
const nc1 = { mount: jest.fn(), order: 10 };
|
||||
const nc2 = { mount: jest.fn(), order: 0 };
|
||||
const nc3 = { mount: jest.fn(), order: 20 };
|
||||
navControls.registerLeft(nc1);
|
||||
navControls.registerLeft(nc2);
|
||||
navControls.registerLeft(nc3);
|
||||
expect(
|
||||
await navControls
|
||||
.getLeft$()
|
||||
.pipe(take(1))
|
||||
.toPromise()
|
||||
).toEqual([nc2, nc1, nc3]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('right side', () => {
|
||||
it('allows registration', async () => {
|
||||
const navControls = getStart();
|
||||
const nc = { mount: jest.fn() };
|
||||
navControls.registerRight(nc);
|
||||
expect(
|
||||
await navControls
|
||||
.getRight$()
|
||||
.pipe(take(1))
|
||||
.toPromise()
|
||||
).toEqual([nc]);
|
||||
});
|
||||
|
||||
it('sorts controls by order property', async () => {
|
||||
const navControls = getStart();
|
||||
const nc1 = { mount: jest.fn(), order: 10 };
|
||||
const nc2 = { mount: jest.fn(), order: 0 };
|
||||
const nc3 = { mount: jest.fn(), order: 20 };
|
||||
navControls.registerRight(nc1);
|
||||
navControls.registerRight(nc2);
|
||||
navControls.registerRight(nc3);
|
||||
expect(
|
||||
await navControls
|
||||
.getRight$()
|
||||
.pipe(take(1))
|
||||
.toPromise()
|
||||
).toEqual([nc2, nc1, nc3]);
|
||||
});
|
||||
});
|
||||
});
|
86
src/core/public/chrome/nav_controls/nav_controls_service.ts
Normal file
86
src/core/public/chrome/nav_controls/nav_controls_service.ts
Normal file
|
@ -0,0 +1,86 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { sortBy } from 'lodash';
|
||||
import { BehaviorSubject, ReplaySubject } from 'rxjs';
|
||||
import { map, takeUntil } from 'rxjs/operators';
|
||||
|
||||
/** @public */
|
||||
export interface ChromeNavControl {
|
||||
order?: number;
|
||||
mount(targetDomElement: HTMLElement): () => void;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@link ChromeNavControls | APIs} for registering new controls to be displayed in the navigation bar.
|
||||
*
|
||||
* @example
|
||||
* Register a left-side nav control rendered with React.
|
||||
* ```jsx
|
||||
* chrome.navControls.registerLeft({
|
||||
* mount(targetDomElement) {
|
||||
* ReactDOM.mount(<MyControl />, targetDomElement);
|
||||
* return () => ReactDOM.unmountComponentAtNode(targetDomElement);
|
||||
* }
|
||||
* })
|
||||
* ```
|
||||
*
|
||||
* @public
|
||||
*/
|
||||
export interface ChromeNavControls {
|
||||
/** Register a nav control to be presented on the left side of the chrome header. */
|
||||
registerLeft(navControl: ChromeNavControl): void;
|
||||
/** Register a nav control to be presented on the right side of the chrome header. */
|
||||
registerRight(navControl: ChromeNavControl): void;
|
||||
}
|
||||
|
||||
/** @internal */
|
||||
export class NavControlsService {
|
||||
private readonly stop$ = new ReplaySubject(1);
|
||||
|
||||
public start() {
|
||||
const navControlsLeft$ = new BehaviorSubject<ReadonlySet<ChromeNavControl>>(new Set());
|
||||
const navControlsRight$ = new BehaviorSubject<ReadonlySet<ChromeNavControl>>(new Set());
|
||||
|
||||
return {
|
||||
// In the future, registration should be moved to the setup phase. This
|
||||
// is not possible until the legacy nav controls are no longer supported.
|
||||
registerLeft: (navControl: ChromeNavControl) =>
|
||||
navControlsLeft$.next(new Set([...navControlsLeft$.value.values(), navControl])),
|
||||
|
||||
registerRight: (navControl: ChromeNavControl) =>
|
||||
navControlsRight$.next(new Set([...navControlsRight$.value.values(), navControl])),
|
||||
|
||||
getLeft$: () =>
|
||||
navControlsLeft$.pipe(
|
||||
map(controls => sortBy([...controls.values()], 'order')),
|
||||
takeUntil(this.stop$)
|
||||
),
|
||||
getRight$: () =>
|
||||
navControlsRight$.pipe(
|
||||
map(controls => sortBy([...controls.values()], 'order')),
|
||||
takeUntil(this.stop$)
|
||||
),
|
||||
};
|
||||
}
|
||||
|
||||
public stop() {
|
||||
this.stop$.next();
|
||||
}
|
||||
}
|
|
@ -17,5 +17,5 @@
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
export { ChromeNavLink } from './nav_link';
|
||||
export { NavLinksService } from './nav_links_service';
|
||||
export { ChromeNavLink, ChromeNavLinkUpdateableFields } from './nav_link';
|
||||
export { ChromeNavLinks, NavLinksService } from './nav_links_service';
|
||||
|
|
|
@ -109,7 +109,8 @@ export interface ChromeNavLink {
|
|||
readonly url?: string;
|
||||
}
|
||||
|
||||
export type NavLinkUpdateableFields = Partial<
|
||||
/** @public */
|
||||
export type ChromeNavLinkUpdateableFields = Partial<
|
||||
Pick<ChromeNavLink, 'active' | 'disabled' | 'hidden' | 'url' | 'subUrlBase'>
|
||||
>;
|
||||
|
||||
|
@ -126,7 +127,7 @@ export class NavLinkWrapper {
|
|||
this.properties = Object.freeze(properties);
|
||||
}
|
||||
|
||||
public update(newProps: NavLinkUpdateableFields) {
|
||||
public update(newProps: ChromeNavLinkUpdateableFields) {
|
||||
// Enforce limited properties at runtime for JS code
|
||||
newProps = pick(newProps, ['active', 'disabled', 'hidden', 'url', 'subUrlBase']);
|
||||
return new NavLinkWrapper({ ...this.properties, ...newProps });
|
||||
|
|
|
@ -18,9 +18,9 @@
|
|||
*/
|
||||
|
||||
import { sortBy } from 'lodash';
|
||||
import { BehaviorSubject, ReplaySubject } from 'rxjs';
|
||||
import { BehaviorSubject, ReplaySubject, Observable } from 'rxjs';
|
||||
import { map, takeUntil } from 'rxjs/operators';
|
||||
import { NavLinkWrapper, NavLinkUpdateableFields } from './nav_link';
|
||||
import { NavLinkWrapper, ChromeNavLinkUpdateableFields, ChromeNavLink } from './nav_link';
|
||||
import { ApplicationStart } from '../../application';
|
||||
import { HttpStart } from '../../http';
|
||||
|
||||
|
@ -29,10 +29,76 @@ interface StartDeps {
|
|||
http: HttpStart;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@link ChromeNavLinks | APIs} for manipulating nav links.
|
||||
*
|
||||
* @public
|
||||
*/
|
||||
export interface ChromeNavLinks {
|
||||
/**
|
||||
* Get an observable for a sorted list of navlinks.
|
||||
*/
|
||||
getNavLinks$(): Observable<Array<Readonly<ChromeNavLink>>>;
|
||||
|
||||
/**
|
||||
* Get the state of a navlink at this point in time.
|
||||
* @param id
|
||||
*/
|
||||
get(id: string): ChromeNavLink | undefined;
|
||||
|
||||
/**
|
||||
* Get the current state of all navlinks.
|
||||
*/
|
||||
getAll(): Array<Readonly<ChromeNavLink>>;
|
||||
|
||||
/**
|
||||
* Check whether or not a navlink exists.
|
||||
* @param id
|
||||
*/
|
||||
has(id: string): boolean;
|
||||
|
||||
/**
|
||||
* Remove all navlinks except the one matching the given id.
|
||||
*
|
||||
* @remarks
|
||||
* NOTE: this is not reversible.
|
||||
*
|
||||
* @param id
|
||||
*/
|
||||
showOnly(id: string): void;
|
||||
|
||||
/**
|
||||
* Update the navlink for the given id with the updated attributes.
|
||||
* Returns the updated navlink or `undefined` if it does not exist.
|
||||
* @param id
|
||||
* @param values
|
||||
*/
|
||||
update(id: string, values: ChromeNavLinkUpdateableFields): ChromeNavLink | undefined;
|
||||
|
||||
/**
|
||||
* Enable forced navigation mode, which will trigger a page refresh
|
||||
* when a nav link is clicked and only the hash is updated.
|
||||
*
|
||||
* @remarks
|
||||
* This is only necessary when rendering the status page in place of another
|
||||
* app, as links to that app will set the current URL and change the hash, but
|
||||
* the routes for the correct are not loaded so nothing will happen.
|
||||
* https://github.com/elastic/kibana/pull/29770
|
||||
*
|
||||
* Used only by status_page plugin
|
||||
*/
|
||||
enableForcedAppSwitcherNavigation(): void;
|
||||
|
||||
/**
|
||||
* An observable of the forced app switcher state.
|
||||
*/
|
||||
getForceAppSwitcherNavigation$(): Observable<boolean>;
|
||||
}
|
||||
|
||||
export class NavLinksService {
|
||||
private readonly stop$ = new ReplaySubject(1);
|
||||
|
||||
public start({ application, http }: StartDeps) {
|
||||
public start({ application, http }: StartDeps): ChromeNavLinks {
|
||||
const navLinks$ = new BehaviorSubject<ReadonlyMap<string, NavLinkWrapper>>(
|
||||
new Map(
|
||||
application.availableApps.map(
|
||||
|
@ -51,9 +117,6 @@ export class NavLinksService {
|
|||
const forceAppSwitcherNavigation$ = new BehaviorSubject(false);
|
||||
|
||||
return {
|
||||
/**
|
||||
* Get an observable for a sorted list of navlinks.
|
||||
*/
|
||||
getNavLinks$: () => {
|
||||
return navLinks$.pipe(
|
||||
map(sortNavLinks),
|
||||
|
@ -61,35 +124,19 @@ export class NavLinksService {
|
|||
);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the state of a navlink at this point in time.
|
||||
* @param id
|
||||
*/
|
||||
get(id: string) {
|
||||
const link = navLinks$.value.get(id);
|
||||
return link && link.properties;
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the current state of all navlinks.
|
||||
*/
|
||||
getAll() {
|
||||
return sortNavLinks(navLinks$.value);
|
||||
},
|
||||
|
||||
/**
|
||||
* Check whether or not a navlink exists.
|
||||
* @param id
|
||||
*/
|
||||
has(id: string) {
|
||||
return navLinks$.value.has(id);
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove all navlinks except the one matching the given id.
|
||||
* NOTE: this is not reversible.
|
||||
* @param id
|
||||
*/
|
||||
showOnly(id: string) {
|
||||
if (!this.has(id)) {
|
||||
return;
|
||||
|
@ -98,13 +145,7 @@ export class NavLinksService {
|
|||
navLinks$.next(new Map([...navLinks$.value.entries()].filter(([linkId]) => linkId === id)));
|
||||
},
|
||||
|
||||
/**
|
||||
* Update the navlink for the given id with the updated attributes.
|
||||
* Returns the updated navlink or `undefined` if it does not exist.
|
||||
* @param id
|
||||
* @param values
|
||||
*/
|
||||
update(id: string, values: NavLinkUpdateableFields) {
|
||||
update(id: string, values: ChromeNavLinkUpdateableFields) {
|
||||
if (!this.has(id)) {
|
||||
return;
|
||||
}
|
||||
|
@ -123,23 +164,10 @@ export class NavLinksService {
|
|||
return this.get(id);
|
||||
},
|
||||
|
||||
/**
|
||||
* Enable forced navigation mode, which will trigger a page refresh
|
||||
* when a nav link is clicked and only the hash is updated. This is only
|
||||
* necessary when rendering the status page in place of another app, as
|
||||
* links to that app will set the current URL and change the hash, but
|
||||
* the routes for the correct are not loaded so nothing will happen.
|
||||
* https://github.com/elastic/kibana/pull/29770
|
||||
*
|
||||
* Used only by status_page plugin
|
||||
*/
|
||||
enableForcedAppSwitcherNavigation() {
|
||||
forceAppSwitcherNavigation$.next(true);
|
||||
},
|
||||
|
||||
/**
|
||||
* An observable of the forced app switcher state.
|
||||
*/
|
||||
getForceAppSwitcherNavigation$() {
|
||||
return forceAppSwitcherNavigation$.asObservable();
|
||||
},
|
||||
|
|
|
@ -20,16 +20,16 @@
|
|||
import { createLogKey } from './create_log_key';
|
||||
|
||||
describe('createLogKey', () => {
|
||||
it('should create a key starting with "kibana.history"', () => {
|
||||
expect(createLogKey('foo', 'bar')).toMatch(/^kibana\.history/);
|
||||
it('should create a key starting with "kibana.history"', async () => {
|
||||
expect(await createLogKey('foo', 'bar')).toMatch(/^kibana\.history/);
|
||||
});
|
||||
|
||||
it('should include a hashed suffix of the identifier when present', () => {
|
||||
it('should include a hashed suffix of the identifier when present', async () => {
|
||||
const expectedSuffix = `/N4rLtula/QIYB+3If6bXDONEO5CnqBPrlURto+/j7k=`;
|
||||
expect(createLogKey('foo', 'bar')).toMatch(`kibana.history.foo-${expectedSuffix}`);
|
||||
expect(await createLogKey('foo', 'bar')).toMatch(`kibana.history.foo-${expectedSuffix}`);
|
||||
});
|
||||
|
||||
it('should not include a hashed suffix if the identifier is not present', () => {
|
||||
expect(createLogKey('foo')).toEqual('kibana.history.foo');
|
||||
it('should not include a hashed suffix if the identifier is not present', async () => {
|
||||
expect(await createLogKey('foo')).toEqual('kibana.history.foo');
|
||||
});
|
||||
});
|
|
@ -17,15 +17,17 @@
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
import { Sha256 } from '../crypto';
|
||||
|
||||
export function createLogKey(type: string, optionalIdentifier: string) {
|
||||
export async function createLogKey(type: string, optionalIdentifier?: string) {
|
||||
const baseKey = `kibana.history.${type}`;
|
||||
|
||||
if (!optionalIdentifier) {
|
||||
return baseKey;
|
||||
}
|
||||
|
||||
const protectedIdentifier = new Sha256().update(optionalIdentifier, 'utf8').digest('base64');
|
||||
const encoder = new TextEncoder();
|
||||
const data = encoder.encode(optionalIdentifier);
|
||||
const buffer = await window.crypto.subtle.digest({ name: 'SHA-256' }, data);
|
||||
const protectedIdentifier = btoa(String.fromCharCode(...new Uint8Array(buffer)));
|
||||
|
||||
return `${baseKey}-${protectedIdentifier}`;
|
||||
}
|
24
src/core/public/chrome/recently_accessed/index.ts
Normal file
24
src/core/public/chrome/recently_accessed/index.ts
Normal file
|
@ -0,0 +1,24 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
export {
|
||||
ChromeRecentlyAccessed,
|
||||
ChromeRecentlyAccessedHistoryItem,
|
||||
RecentlyAccessedService,
|
||||
} from './recently_accessed_service';
|
140
src/core/public/chrome/recently_accessed/persisted_log.test.ts
Normal file
140
src/core/public/chrome/recently_accessed/persisted_log.test.ts
Normal file
|
@ -0,0 +1,140 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { PersistedLog } from './persisted_log';
|
||||
|
||||
const createMockStorage = () => ({
|
||||
clear: jest.fn(),
|
||||
getItem: jest.fn(),
|
||||
key: jest.fn(),
|
||||
removeItem: jest.fn(),
|
||||
setItem: jest.fn(),
|
||||
length: 0,
|
||||
});
|
||||
|
||||
jest.mock('ui/chrome', () => {
|
||||
return {
|
||||
getBasePath: () => `/some/base/path`,
|
||||
};
|
||||
});
|
||||
|
||||
const historyName = 'testHistory';
|
||||
const historyLimit = 10;
|
||||
const payload = [
|
||||
{ first: 'clark', last: 'kent' },
|
||||
{ first: 'peter', last: 'parker' },
|
||||
{ first: 'bruce', last: 'wayne' },
|
||||
];
|
||||
|
||||
describe('PersistedLog', () => {
|
||||
let storage = createMockStorage();
|
||||
beforeEach(() => {
|
||||
storage = createMockStorage();
|
||||
});
|
||||
|
||||
describe('expected API', () => {
|
||||
test('has expected methods', () => {
|
||||
const log = new PersistedLog(historyName, { maxLength: 10 }, storage);
|
||||
|
||||
expect(typeof log.add).toBe('function');
|
||||
expect(typeof log.get).toBe('function');
|
||||
});
|
||||
});
|
||||
|
||||
describe('internal functionality', () => {
|
||||
test('reads from storage', () => {
|
||||
// @ts-ignore
|
||||
const log = new PersistedLog(historyName, { maxLength: 10 }, storage);
|
||||
|
||||
expect(storage.getItem).toHaveBeenCalledTimes(1);
|
||||
expect(storage.getItem).toHaveBeenCalledWith(historyName);
|
||||
});
|
||||
|
||||
test('writes to storage', () => {
|
||||
const log = new PersistedLog(historyName, { maxLength: 10 }, storage);
|
||||
const newItem = { first: 'diana', last: 'prince' };
|
||||
|
||||
const data = log.add(newItem);
|
||||
|
||||
expect(storage.setItem).toHaveBeenCalledTimes(1);
|
||||
expect(data).toEqual([newItem]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('persisting data', () => {
|
||||
test('fetches records from storage', () => {
|
||||
storage.getItem.mockReturnValue(JSON.stringify(payload));
|
||||
const log = new PersistedLog(historyName, { maxLength: 10 }, storage);
|
||||
|
||||
const items = log.get();
|
||||
expect(items.length).toBe(3);
|
||||
expect(items).toEqual(payload);
|
||||
});
|
||||
|
||||
test('prepends new records', () => {
|
||||
storage.getItem.mockReturnValue(JSON.stringify(payload.slice(0)));
|
||||
const log = new PersistedLog(historyName, { maxLength: 10 }, storage);
|
||||
const newItem = { first: 'selina', last: 'kyle' };
|
||||
|
||||
const items = log.add(newItem);
|
||||
expect(items.length).toBe(payload.length + 1);
|
||||
expect(items[0]).toEqual(newItem);
|
||||
});
|
||||
});
|
||||
|
||||
describe('stack options', () => {
|
||||
test('should observe the maxLength option', () => {
|
||||
const bulkData = [];
|
||||
|
||||
for (let i = 0; i < historyLimit; i++) {
|
||||
bulkData.push(['record ' + i]);
|
||||
}
|
||||
storage.getItem.mockReturnValue(JSON.stringify(bulkData));
|
||||
|
||||
const log = new PersistedLog(historyName, { maxLength: historyLimit }, storage);
|
||||
log.add(['new array 1']);
|
||||
const items = log.add(['new array 2']);
|
||||
|
||||
expect(items.length).toBe(historyLimit);
|
||||
});
|
||||
|
||||
test('should observe the filterDuplicates option', () => {
|
||||
storage.getItem.mockReturnValue(JSON.stringify(payload.slice(0)));
|
||||
const log = new PersistedLog(historyName, { maxLength: 10 }, storage);
|
||||
const newItem = payload[1];
|
||||
|
||||
const items = log.add(newItem);
|
||||
expect(items.length).toBe(payload.length);
|
||||
});
|
||||
|
||||
test('should truncate the list upon initialization if too long', () => {
|
||||
storage.getItem.mockReturnValue(JSON.stringify(payload.slice(0)));
|
||||
const log = new PersistedLog(historyName, { maxLength: 1 }, storage);
|
||||
const items = log.get();
|
||||
expect(items.length).toBe(1);
|
||||
});
|
||||
|
||||
test('should allow a maxLength of 0', () => {
|
||||
storage.getItem.mockReturnValue(JSON.stringify(payload.slice(0)));
|
||||
const log = new PersistedLog(historyName, { maxLength: 0 }, storage);
|
||||
const items = log.get();
|
||||
expect(items.length).toBe(0);
|
||||
});
|
||||
});
|
||||
});
|
86
src/core/public/chrome/recently_accessed/persisted_log.ts
Normal file
86
src/core/public/chrome/recently_accessed/persisted_log.ts
Normal file
|
@ -0,0 +1,86 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { cloneDeep, isEqual, take } from 'lodash';
|
||||
import * as Rx from 'rxjs';
|
||||
import { map } from 'rxjs/operators';
|
||||
|
||||
interface PersistedLogOptions<T = any> {
|
||||
maxLength: number | string;
|
||||
isEqual?: (oldItem: T, newItem: T) => boolean;
|
||||
}
|
||||
|
||||
export class PersistedLog<T = any> {
|
||||
private name: string;
|
||||
private maxLength: number;
|
||||
private isEqual: (oldItem: T, newItem: T) => boolean;
|
||||
private storage: Storage;
|
||||
|
||||
private items$: Rx.BehaviorSubject<T[]>;
|
||||
|
||||
constructor(name: string, options: PersistedLogOptions<T>, storage = localStorage) {
|
||||
this.name = name;
|
||||
this.maxLength =
|
||||
typeof options.maxLength === 'string'
|
||||
? (this.maxLength = parseInt(options.maxLength, 10))
|
||||
: options.maxLength;
|
||||
this.isEqual = options.isEqual || isEqual;
|
||||
this.storage = storage;
|
||||
this.items$ = new Rx.BehaviorSubject<T[]>(this.loadItems());
|
||||
|
||||
if (this.maxLength !== undefined && !isNaN(this.maxLength)) {
|
||||
this.items$.next(take(this.items$.value, this.maxLength));
|
||||
}
|
||||
}
|
||||
|
||||
public add(val: T) {
|
||||
if (val == null) {
|
||||
return this.items$.value;
|
||||
}
|
||||
|
||||
const nextItems = [
|
||||
val,
|
||||
// remove any duplicate items
|
||||
...[...this.items$.value].filter(item => !this.isEqual(item, val)),
|
||||
].slice(0, this.maxLength); // truncate
|
||||
|
||||
// Persist the stack to storage
|
||||
this.storage.setItem(this.name, JSON.stringify(nextItems));
|
||||
// Notify subscribers
|
||||
this.items$.next(nextItems);
|
||||
|
||||
return nextItems;
|
||||
}
|
||||
|
||||
public get() {
|
||||
return cloneDeep(this.items$.value);
|
||||
}
|
||||
|
||||
public get$() {
|
||||
return this.items$.pipe(map(items => cloneDeep(items)));
|
||||
}
|
||||
|
||||
private loadItems() {
|
||||
try {
|
||||
return JSON.parse(this.storage.getItem(this.name) || '[]');
|
||||
} catch {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,143 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { httpServiceMock } from '../../http/http_service.mock';
|
||||
import { RecentlyAccessedService } from './recently_accessed_service';
|
||||
import { Subject } from 'rxjs';
|
||||
import { takeUntil, bufferCount } from 'rxjs/operators';
|
||||
|
||||
// Maybe this should be moved to our global jest polyfills?
|
||||
class LocalStorageMock implements Storage {
|
||||
private store = new Map<string, string>();
|
||||
|
||||
clear() {
|
||||
this.store.clear();
|
||||
}
|
||||
|
||||
getItem(key: string) {
|
||||
return this.store.get(key) || null;
|
||||
}
|
||||
|
||||
setItem(key: string, value: any) {
|
||||
this.store.set(key, value.toString());
|
||||
}
|
||||
|
||||
removeItem(key: string) {
|
||||
this.store.delete(key);
|
||||
}
|
||||
|
||||
key(index: number) {
|
||||
return [...this.store.keys()][index] || null;
|
||||
}
|
||||
|
||||
get length() {
|
||||
return this.store.size;
|
||||
}
|
||||
}
|
||||
|
||||
describe('RecentlyAccessed#start()', () => {
|
||||
let originalLocalStorage: Storage;
|
||||
beforeAll(() => {
|
||||
originalLocalStorage = window.localStorage;
|
||||
// @ts-ignore
|
||||
window.localStorage = new LocalStorageMock();
|
||||
});
|
||||
beforeEach(() => localStorage.clear());
|
||||
// @ts-ignore
|
||||
afterAll(() => (window.localStorage = originalLocalStorage));
|
||||
|
||||
const getStart = async () => {
|
||||
const http = httpServiceMock.createStartContract();
|
||||
const recentlyAccessed = await new RecentlyAccessedService().start({ http });
|
||||
return { http, recentlyAccessed };
|
||||
};
|
||||
|
||||
it('allows adding and getting items', async () => {
|
||||
const { recentlyAccessed } = await getStart();
|
||||
recentlyAccessed.add('/app/item1', 'Item 1', 'item1');
|
||||
recentlyAccessed.add('/app/item2', 'Item 2', 'item2');
|
||||
expect(recentlyAccessed.get()).toEqual([
|
||||
{ link: '/app/item2', label: 'Item 2', id: 'item2' },
|
||||
{ link: '/app/item1', label: 'Item 1', id: 'item1' },
|
||||
]);
|
||||
});
|
||||
|
||||
it('persists data to localStorage', async () => {
|
||||
const { recentlyAccessed: ra1 } = await getStart();
|
||||
ra1.add('/app/item1', 'Item 1', 'item1');
|
||||
ra1.add('/app/item2', 'Item 2', 'item2');
|
||||
|
||||
const { recentlyAccessed: ra2 } = await getStart();
|
||||
expect(ra2.get()).toEqual([
|
||||
{ link: '/app/item2', label: 'Item 2', id: 'item2' },
|
||||
{ link: '/app/item1', label: 'Item 1', id: 'item1' },
|
||||
]);
|
||||
});
|
||||
|
||||
it('de-duplicates the list', async () => {
|
||||
const { recentlyAccessed } = await getStart();
|
||||
recentlyAccessed.add('/app/item1', 'Item 1', 'item1');
|
||||
recentlyAccessed.add('/app/item2', 'Item 2', 'item2');
|
||||
recentlyAccessed.add('/app/item1', 'Item 1', 'item1');
|
||||
expect(recentlyAccessed.get()).toEqual([
|
||||
{ link: '/app/item1', label: 'Item 1', id: 'item1' },
|
||||
{ link: '/app/item2', label: 'Item 2', id: 'item2' },
|
||||
]);
|
||||
});
|
||||
|
||||
it('exposes an observable', async () => {
|
||||
const { recentlyAccessed } = await getStart();
|
||||
const stop$ = new Subject();
|
||||
const observedValues$ = recentlyAccessed
|
||||
.get$()
|
||||
.pipe(
|
||||
bufferCount(3),
|
||||
takeUntil(stop$)
|
||||
)
|
||||
.toPromise();
|
||||
recentlyAccessed.add('/app/item1', 'Item 1', 'item1');
|
||||
recentlyAccessed.add('/app/item2', 'Item 2', 'item2');
|
||||
stop$.next();
|
||||
|
||||
expect(await observedValues$).toMatchInlineSnapshot(`
|
||||
Array [
|
||||
Array [],
|
||||
Array [
|
||||
Object {
|
||||
"id": "item1",
|
||||
"label": "Item 1",
|
||||
"link": "/app/item1",
|
||||
},
|
||||
],
|
||||
Array [
|
||||
Object {
|
||||
"id": "item2",
|
||||
"label": "Item 2",
|
||||
"link": "/app/item2",
|
||||
},
|
||||
Object {
|
||||
"id": "item1",
|
||||
"label": "Item 1",
|
||||
"link": "/app/item1",
|
||||
},
|
||||
],
|
||||
]
|
||||
`);
|
||||
});
|
||||
});
|
|
@ -0,0 +1,102 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
import { Observable } from 'rxjs';
|
||||
|
||||
import { PersistedLog } from './persisted_log';
|
||||
import { createLogKey } from './create_log_key';
|
||||
import { HttpSetup } from '../../http';
|
||||
|
||||
/** @public */
|
||||
export interface ChromeRecentlyAccessedHistoryItem {
|
||||
link: string;
|
||||
label: string;
|
||||
id: string;
|
||||
}
|
||||
|
||||
interface StartDeps {
|
||||
http: HttpSetup;
|
||||
}
|
||||
|
||||
/** @internal */
|
||||
export class RecentlyAccessedService {
|
||||
async start({ http }: StartDeps): Promise<ChromeRecentlyAccessed> {
|
||||
const logKey = await createLogKey('recentlyAccessed', http.basePath.get());
|
||||
const history = new PersistedLog<ChromeRecentlyAccessedHistoryItem>(logKey, {
|
||||
maxLength: 20,
|
||||
isEqual: (oldItem, newItem) => oldItem.id === newItem.id,
|
||||
});
|
||||
|
||||
return {
|
||||
/** Adds a new item to the history. */
|
||||
add: (link: string, label: string, id: string) => {
|
||||
history.add({
|
||||
link,
|
||||
label,
|
||||
id,
|
||||
});
|
||||
},
|
||||
|
||||
/** Gets the current array of history items. */
|
||||
get: () => history.get(),
|
||||
|
||||
/** Gets an observable of the current array of history items. */
|
||||
get$: () => history.get$(),
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* {@link ChromeRecentlyAccessed | APIs} for recently accessed history.
|
||||
* @public
|
||||
*/
|
||||
export interface ChromeRecentlyAccessed {
|
||||
/**
|
||||
* Adds a new item to the recently accessed history.
|
||||
*
|
||||
* @example
|
||||
* ```js
|
||||
* chrome.recentlyAccessed.add('/app/map/1234', 'Map 1234', '1234');
|
||||
* ```
|
||||
*
|
||||
* @param link a relative URL to the resource (not including the {@link HttpStart.basePath | `http.basePath`})
|
||||
* @param label the label to display in the UI
|
||||
* @param id a unique string used to de-duplicate the recently accessed llist.
|
||||
*/
|
||||
add(link: string, label: string, id: string): void;
|
||||
|
||||
/**
|
||||
* Gets an Array of the current recently accessed history.
|
||||
*
|
||||
* @example
|
||||
* ```js
|
||||
* chrome.recentlyAccessed.get().forEach(console.log);
|
||||
* ```
|
||||
*/
|
||||
get(): ChromeRecentlyAccessedHistoryItem[];
|
||||
|
||||
/**
|
||||
* Gets an Observable of the array of recently accessed history.
|
||||
*
|
||||
* @example
|
||||
* ```js
|
||||
* chrome.recentlyAccessed.get$().subscribe(console.log);
|
||||
* ```
|
||||
*/
|
||||
get$(): Observable<ChromeRecentlyAccessedHistoryItem[]>;
|
||||
}
|
|
@ -40,8 +40,14 @@ import {
|
|||
ChromeBrand,
|
||||
ChromeBreadcrumb,
|
||||
ChromeHelpExtension,
|
||||
ChromeNavControl,
|
||||
ChromeNavControls,
|
||||
ChromeNavLink,
|
||||
ChromeNavLinks,
|
||||
ChromeNavLinkUpdateableFields,
|
||||
ChromeStart,
|
||||
ChromeRecentlyAccessed,
|
||||
ChromeRecentlyAccessedHistoryItem,
|
||||
} from './chrome';
|
||||
import { FatalErrorsSetup, FatalErrorInfo } from './fatal_errors';
|
||||
import { HttpServiceBase, HttpSetup, HttpStart, HttpInterceptor } from './http';
|
||||
|
@ -137,7 +143,13 @@ export {
|
|||
ChromeBreadcrumb,
|
||||
ChromeBrand,
|
||||
ChromeHelpExtension,
|
||||
ChromeNavControl,
|
||||
ChromeNavControls,
|
||||
ChromeNavLink,
|
||||
ChromeNavLinks,
|
||||
ChromeNavLinkUpdateableFields,
|
||||
ChromeRecentlyAccessed,
|
||||
ChromeRecentlyAccessedHistoryItem,
|
||||
I18nStart,
|
||||
LegacyNavLink,
|
||||
Plugin,
|
||||
|
|
|
@ -75,6 +75,20 @@ export interface ChromeBreadcrumb {
|
|||
// @public (undocumented)
|
||||
export type ChromeHelpExtension = (element: HTMLDivElement) => (() => void);
|
||||
|
||||
// @public (undocumented)
|
||||
export interface ChromeNavControl {
|
||||
// (undocumented)
|
||||
mount(targetDomElement: HTMLElement): () => void;
|
||||
// (undocumented)
|
||||
order?: number;
|
||||
}
|
||||
|
||||
// @public
|
||||
export interface ChromeNavControls {
|
||||
registerLeft(navControl: ChromeNavControl): void;
|
||||
registerRight(navControl: ChromeNavControl): void;
|
||||
}
|
||||
|
||||
// @public (undocumented)
|
||||
export interface ChromeNavLink {
|
||||
readonly active?: boolean;
|
||||
|
@ -92,10 +106,60 @@ export interface ChromeNavLink {
|
|||
readonly url?: string;
|
||||
}
|
||||
|
||||
// Warning: (ae-forgotten-export) The symbol "ChromeService" needs to be exported by the entry point index.d.ts
|
||||
//
|
||||
// @public
|
||||
export interface ChromeNavLinks {
|
||||
enableForcedAppSwitcherNavigation(): void;
|
||||
get(id: string): ChromeNavLink | undefined;
|
||||
getAll(): Array<Readonly<ChromeNavLink>>;
|
||||
getForceAppSwitcherNavigation$(): Observable<boolean>;
|
||||
getNavLinks$(): Observable<Array<Readonly<ChromeNavLink>>>;
|
||||
has(id: string): boolean;
|
||||
showOnly(id: string): void;
|
||||
update(id: string, values: ChromeNavLinkUpdateableFields): ChromeNavLink | undefined;
|
||||
}
|
||||
|
||||
// @public (undocumented)
|
||||
export type ChromeStart = ReturnType<ChromeService['start']>;
|
||||
export type ChromeNavLinkUpdateableFields = Partial<Pick<ChromeNavLink, 'active' | 'disabled' | 'hidden' | 'url' | 'subUrlBase'>>;
|
||||
|
||||
// @public
|
||||
export interface ChromeRecentlyAccessed {
|
||||
// Warning: (ae-unresolved-link) The @link reference could not be resolved: No member was found with name "basePath"
|
||||
add(link: string, label: string, id: string): void;
|
||||
get$(): Observable<ChromeRecentlyAccessedHistoryItem[]>;
|
||||
get(): ChromeRecentlyAccessedHistoryItem[];
|
||||
}
|
||||
|
||||
// @public (undocumented)
|
||||
export interface ChromeRecentlyAccessedHistoryItem {
|
||||
// (undocumented)
|
||||
id: string;
|
||||
// (undocumented)
|
||||
label: string;
|
||||
// (undocumented)
|
||||
link: string;
|
||||
}
|
||||
|
||||
// @public (undocumented)
|
||||
export interface ChromeStart {
|
||||
addApplicationClass(className: string): void;
|
||||
getApplicationClasses$(): Observable<string[]>;
|
||||
getBadge$(): Observable<ChromeBadge | undefined>;
|
||||
getBrand$(): Observable<ChromeBrand>;
|
||||
getBreadcrumbs$(): Observable<ChromeBreadcrumb[]>;
|
||||
getHelpExtension$(): Observable<ChromeHelpExtension | undefined>;
|
||||
getIsCollapsed$(): Observable<boolean>;
|
||||
getIsVisible$(): Observable<boolean>;
|
||||
navControls: ChromeNavControls;
|
||||
navLinks: ChromeNavLinks;
|
||||
recentlyAccessed: ChromeRecentlyAccessed;
|
||||
removeApplicationClass(className: string): void;
|
||||
setBadge(badge?: ChromeBadge): void;
|
||||
setBrand(brand: ChromeBrand): void;
|
||||
setBreadcrumbs(newBreadcrumbs: ChromeBreadcrumb[]): void;
|
||||
setHelpExtension(helpExtension?: ChromeHelpExtension): void;
|
||||
setIsCollapsed(isCollapsed: boolean): void;
|
||||
setIsVisible(isVisible: boolean): void;
|
||||
}
|
||||
|
||||
// @internal (undocumented)
|
||||
export interface CoreContext {
|
||||
|
|
|
@ -26,3 +26,7 @@ const MutationObserver = require('mutation-observer');
|
|||
Object.defineProperty(window, 'MutationObserver', { value: MutationObserver });
|
||||
|
||||
require('whatwg-fetch');
|
||||
|
||||
// TextEncoder + TextDecoder
|
||||
require('fast-text-encoding');
|
||||
window.crypto = require('@trust/webcrypto');
|
||||
|
|
|
@ -54,8 +54,6 @@ import { i18n } from '@kbn/i18n';
|
|||
import { InjectedIntl, injectI18n } from '@kbn/i18n/react';
|
||||
import chrome from 'ui/chrome';
|
||||
import { HelpExtension } from 'ui/chrome';
|
||||
import { RecentlyAccessedHistoryItem } from 'ui/persisted_log';
|
||||
import { ChromeHeaderNavControlsRegistry } from 'ui/registry/chrome_header_nav_controls';
|
||||
import { relativeToAbsolute } from 'ui/url/relative_to_absolute';
|
||||
|
||||
import { HeaderBadge } from './header_badge';
|
||||
|
@ -63,22 +61,13 @@ import { HeaderBreadcrumbs } from './header_breadcrumbs';
|
|||
import { HeaderHelpMenu } from './header_help_menu';
|
||||
import { HeaderNavControls } from './header_nav_controls';
|
||||
|
||||
import { NavControlSide } from '../';
|
||||
import { ChromeBadge, ChromeBreadcrumb, ChromeNavLink } from '../../../../../../../core/public';
|
||||
|
||||
interface Props {
|
||||
appTitle?: string;
|
||||
badge$: Rx.Observable<ChromeBadge | undefined>;
|
||||
breadcrumbs$: Rx.Observable<ChromeBreadcrumb[]>;
|
||||
homeHref: string;
|
||||
isVisible: boolean;
|
||||
navLinks$: Rx.Observable<ChromeNavLink[]>;
|
||||
recentlyAccessed$: Rx.Observable<RecentlyAccessedHistoryItem[]>;
|
||||
forceAppSwitcherNavigation$: Rx.Observable<boolean>;
|
||||
helpExtension$: Rx.Observable<HelpExtension>;
|
||||
navControls: ChromeHeaderNavControlsRegistry;
|
||||
intl: InjectedIntl;
|
||||
}
|
||||
import {
|
||||
ChromeBadge,
|
||||
ChromeBreadcrumb,
|
||||
ChromeNavLink,
|
||||
ChromeRecentlyAccessedHistoryItem,
|
||||
ChromeNavControl,
|
||||
} from '../../../../../../../core/public';
|
||||
|
||||
// Providing a buffer between the limit and the cut off index
|
||||
// protects from truncating just the last couple (6) characters
|
||||
|
@ -87,7 +76,7 @@ const TRUNCATE_AT: number = 58;
|
|||
|
||||
function extendRecentlyAccessedHistoryItem(
|
||||
navLinks: ChromeNavLink[],
|
||||
recentlyAccessed: RecentlyAccessedHistoryItem
|
||||
recentlyAccessed: ChromeRecentlyAccessedHistoryItem
|
||||
) {
|
||||
const href = relativeToAbsolute(chrome.addBasePath(recentlyAccessed.link));
|
||||
const navLink = navLinks.find(nl => href.startsWith(nl.subUrlBase || nl.baseUrl));
|
||||
|
@ -142,10 +131,28 @@ function truncateRecentItemLabel(label: string): string {
|
|||
return label;
|
||||
}
|
||||
|
||||
interface Props {
|
||||
appTitle?: string;
|
||||
badge$: Rx.Observable<ChromeBadge | undefined>;
|
||||
breadcrumbs$: Rx.Observable<ChromeBreadcrumb[]>;
|
||||
homeHref: string;
|
||||
isVisible$: Rx.Observable<boolean>;
|
||||
navLinks$: Rx.Observable<ChromeNavLink[]>;
|
||||
recentlyAccessed$: Rx.Observable<ChromeRecentlyAccessedHistoryItem[]>;
|
||||
forceAppSwitcherNavigation$: Rx.Observable<boolean>;
|
||||
helpExtension$: Rx.Observable<HelpExtension>;
|
||||
navControlsLeft$: Rx.Observable<ReadonlyArray<ChromeNavControl>>;
|
||||
navControlsRight$: Rx.Observable<ReadonlyArray<ChromeNavControl>>;
|
||||
intl: InjectedIntl;
|
||||
}
|
||||
|
||||
interface State {
|
||||
navLinks: Array<ReturnType<typeof extendNavLink>>;
|
||||
recentlyAccessed: Array<ReturnType<typeof extendRecentlyAccessedHistoryItem>>;
|
||||
isVisible: boolean;
|
||||
navLinks: ReadonlyArray<ReturnType<typeof extendNavLink>>;
|
||||
recentlyAccessed: ReadonlyArray<ReturnType<typeof extendRecentlyAccessedHistoryItem>>;
|
||||
forceNavigation: boolean;
|
||||
navControlsLeft: ReadonlyArray<ChromeNavControl>;
|
||||
navControlsRight: ReadonlyArray<ChromeNavControl>;
|
||||
}
|
||||
|
||||
class HeaderUI extends Component<Props, State> {
|
||||
|
@ -156,25 +163,41 @@ class HeaderUI extends Component<Props, State> {
|
|||
super(props);
|
||||
|
||||
this.state = {
|
||||
isVisible: true,
|
||||
navLinks: [],
|
||||
recentlyAccessed: [],
|
||||
forceNavigation: false,
|
||||
navControlsLeft: [],
|
||||
navControlsRight: [],
|
||||
};
|
||||
}
|
||||
|
||||
public componentDidMount() {
|
||||
this.subscription = Rx.combineLatest(
|
||||
this.props.isVisible$,
|
||||
this.props.forceAppSwitcherNavigation$,
|
||||
this.props.navLinks$,
|
||||
this.props.recentlyAccessed$,
|
||||
this.props.forceAppSwitcherNavigation$
|
||||
this.props.navControlsLeft$,
|
||||
this.props.navControlsRight$
|
||||
).subscribe({
|
||||
next: ([navLinks, recentlyAccessed, forceNavigation]) => {
|
||||
next: ([
|
||||
isVisible,
|
||||
forceNavigation,
|
||||
navLinks,
|
||||
recentlyAccessed,
|
||||
navControlsLeft,
|
||||
navControlsRight,
|
||||
]) => {
|
||||
this.setState({
|
||||
isVisible,
|
||||
forceNavigation,
|
||||
navLinks: navLinks.map(navLink => extendNavLink(navLink)),
|
||||
recentlyAccessed: recentlyAccessed.map(ra =>
|
||||
extendRecentlyAccessedHistoryItem(navLinks, ra)
|
||||
),
|
||||
navControlsLeft,
|
||||
navControlsRight,
|
||||
});
|
||||
},
|
||||
});
|
||||
|
@ -214,24 +237,13 @@ class HeaderUI extends Component<Props, State> {
|
|||
}
|
||||
|
||||
public render() {
|
||||
const {
|
||||
appTitle,
|
||||
badge$,
|
||||
breadcrumbs$,
|
||||
isVisible,
|
||||
navControls,
|
||||
helpExtension$,
|
||||
intl,
|
||||
} = this.props;
|
||||
const { navLinks, recentlyAccessed } = this.state;
|
||||
const { appTitle, badge$, breadcrumbs$, helpExtension$, intl } = this.props;
|
||||
const { isVisible, navLinks, recentlyAccessed, navControlsLeft, navControlsRight } = this.state;
|
||||
|
||||
if (!isVisible) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const leftNavControls = navControls.bySide[NavControlSide.Left];
|
||||
const rightNavControls = navControls.bySide[NavControlSide.Right];
|
||||
|
||||
const navLinksArray = navLinks
|
||||
.filter(navLink => !navLink.hidden)
|
||||
.map(navLink => ({
|
||||
|
@ -289,7 +301,7 @@ class HeaderUI extends Component<Props, State> {
|
|||
|
||||
<EuiHeaderSectionItem border="right">{this.renderLogo()}</EuiHeaderSectionItem>
|
||||
|
||||
<HeaderNavControls navControls={leftNavControls} />
|
||||
<HeaderNavControls side="left" navControls={navControlsLeft} />
|
||||
</EuiHeaderSection>
|
||||
|
||||
<HeaderBreadcrumbs appTitle={appTitle} breadcrumbs$={breadcrumbs$} />
|
||||
|
@ -301,7 +313,7 @@ class HeaderUI extends Component<Props, State> {
|
|||
<HeaderHelpMenu helpExtension$={helpExtension$} />
|
||||
</EuiHeaderSectionItem>
|
||||
|
||||
<HeaderNavControls navControls={rightNavControls} />
|
||||
<HeaderNavControls side="right" navControls={navControlsRight} />
|
||||
</EuiHeaderSection>
|
||||
</EuiHeader>
|
||||
|
||||
|
|
|
@ -24,11 +24,12 @@ import {
|
|||
EuiHeaderSectionItem,
|
||||
} from '@elastic/eui';
|
||||
|
||||
import { NavControl } from '../';
|
||||
import { HeaderExtension } from './header_extension';
|
||||
import { ChromeNavControl } from '../../../../../../../core/public';
|
||||
|
||||
interface Props {
|
||||
navControls: NavControl[];
|
||||
navControls: ReadonlyArray<ChromeNavControl>;
|
||||
side: 'left' | 'right';
|
||||
}
|
||||
|
||||
export class HeaderNavControls extends Component<Props> {
|
||||
|
@ -42,12 +43,11 @@ export class HeaderNavControls extends Component<Props> {
|
|||
return navControls.map(this.renderNavControl);
|
||||
}
|
||||
|
||||
private renderNavControl = (navControl: NavControl) => (
|
||||
<EuiHeaderSectionItem
|
||||
key={navControl.name}
|
||||
border={navControl.side === 'left' ? 'right' : 'left'}
|
||||
>
|
||||
<HeaderExtension extension={navControl.render} />
|
||||
// It should be performant to use the index as the key since these are unlikely
|
||||
// to change while Kibana is running.
|
||||
private renderNavControl = (navControl: ChromeNavControl, index: number) => (
|
||||
<EuiHeaderSectionItem key={index} border={this.props.side === 'left' ? 'right' : 'left'}>
|
||||
<HeaderExtension extension={navControl.mount} />
|
||||
</EuiHeaderSectionItem>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -23,30 +23,44 @@ import { Header } from './components/header';
|
|||
import { wrapInI18nContext } from 'ui/i18n';
|
||||
import { chromeHeaderNavControlsRegistry } from 'ui/registry/chrome_header_nav_controls';
|
||||
import { npStart } from '../../../new_platform';
|
||||
import { NavControlSide } from '.';
|
||||
|
||||
const module = uiModules.get('kibana');
|
||||
|
||||
module.directive('headerGlobalNav', (reactDirective, chrome, Private, uiCapabilities) => {
|
||||
const { recentlyAccessed } = require('ui/persisted_log');
|
||||
module.directive('headerGlobalNav', (reactDirective, Private) => {
|
||||
const newPlatform = npStart.core;
|
||||
|
||||
// Continue to support legacy nav controls not registered with the NP.
|
||||
// NOTE: in future change this needs to be moved out of this directive.
|
||||
const navControls = Private(chromeHeaderNavControlsRegistry);
|
||||
const homeHref = chrome.addBasePath('/app/kibana#/home');
|
||||
(navControls.bySide[NavControlSide.Left] || [])
|
||||
.forEach(navControl => newPlatform.chrome.navControls.registerLeft({
|
||||
order: navControl.order,
|
||||
mount: navControl.render,
|
||||
}));
|
||||
(navControls.bySide[NavControlSide.Right] || [])
|
||||
.forEach(navControl => newPlatform.chrome.navControls.registerRight({
|
||||
order: navControl.order,
|
||||
mount: navControl.render,
|
||||
}));
|
||||
|
||||
return reactDirective(wrapInI18nContext(Header), [
|
||||
// scope accepted by directive, passed in as React props
|
||||
'appTitle',
|
||||
'isVisible',
|
||||
],
|
||||
{},
|
||||
// angular injected React props
|
||||
{
|
||||
badge$: chrome.badge.get$(),
|
||||
breadcrumbs$: chrome.breadcrumbs.get$(),
|
||||
helpExtension$: chrome.helpExtension.get$(),
|
||||
navLinks$: npStart.core.chrome.navLinks.getNavLinks$(),
|
||||
recentlyAccessed$: recentlyAccessed.get$(),
|
||||
forceAppSwitcherNavigation$: npStart.core.chrome.navLinks.getForceAppSwitcherNavigation$(),
|
||||
navControls,
|
||||
homeHref,
|
||||
uiCapabilities,
|
||||
isVisible$: newPlatform.chrome.getIsVisible$(),
|
||||
badge$: newPlatform.chrome.getBadge$(),
|
||||
breadcrumbs$: newPlatform.chrome.getBreadcrumbs$(),
|
||||
helpExtension$: newPlatform.chrome.getHelpExtension$(),
|
||||
navLinks$: newPlatform.chrome.navLinks.getNavLinks$(),
|
||||
forceAppSwitcherNavigation$: newPlatform.chrome.navLinks.getForceAppSwitcherNavigation$(),
|
||||
homeHref: newPlatform.http.basePath.prepend('/app/kibana#/home'),
|
||||
uiCapabilities: newPlatform.application.capabilities,
|
||||
recentlyAccessed$: newPlatform.chrome.recentlyAccessed.get$(),
|
||||
navControlsLeft$: newPlatform.chrome.navControls.getLeft$(),
|
||||
navControlsRight$: newPlatform.chrome.navControls.getRight$(),
|
||||
});
|
||||
});
|
||||
|
|
|
@ -3,7 +3,6 @@
|
|||
|
||||
<header-global-nav
|
||||
class="header-global-wrapper hide-for-sharing"
|
||||
is-visible="chrome.getVisible()"
|
||||
app-title="chrome.getAppTitle()"
|
||||
data-test-subj="headerGlobalNav"
|
||||
></header-global-nav>
|
||||
|
|
|
@ -17,6 +17,8 @@
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
import './change_time_filter.test.mocks';
|
||||
|
||||
jest.mock('ui/chrome',
|
||||
() => ({
|
||||
getBasePath: () => `/some/base/path`,
|
||||
|
|
|
@ -0,0 +1,28 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -21,4 +21,4 @@
|
|||
import './directive';
|
||||
|
||||
export { PersistedLog } from './persisted_log';
|
||||
export { recentlyAccessed, RecentlyAccessedHistoryItem } from './recently_accessed';
|
||||
export { recentlyAccessed } from './recently_accessed';
|
||||
|
|
|
@ -16,45 +16,7 @@
|
|||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
import chrome from 'ui/chrome';
|
||||
import { PersistedLog } from './';
|
||||
import { createLogKey } from './create_log_key';
|
||||
|
||||
export interface RecentlyAccessedHistoryItem {
|
||||
link: string;
|
||||
label: string;
|
||||
id: string;
|
||||
}
|
||||
import { npStart } from '../new_platform';
|
||||
|
||||
class RecentlyAccessed {
|
||||
public history: PersistedLog<RecentlyAccessedHistoryItem>;
|
||||
|
||||
constructor() {
|
||||
const logKey = createLogKey('recentlyAccessed', chrome.getBasePath());
|
||||
this.history = new PersistedLog(logKey, {
|
||||
maxLength: 20,
|
||||
filterDuplicates: true,
|
||||
isDuplicate: (oldItem, newItem) => {
|
||||
return oldItem.id === newItem.id;
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
public add(link: string, label: string, id: string) {
|
||||
this.history.add({
|
||||
link,
|
||||
label,
|
||||
id,
|
||||
});
|
||||
}
|
||||
|
||||
public get() {
|
||||
return this.history.get();
|
||||
}
|
||||
|
||||
public get$() {
|
||||
return this.history.get$();
|
||||
}
|
||||
}
|
||||
|
||||
export const recentlyAccessed = new RecentlyAccessed();
|
||||
export const recentlyAccessed = npStart.core.chrome.recentlyAccessed;
|
||||
|
|
|
@ -17,6 +17,8 @@
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
import './timefilter.test.mocks';
|
||||
|
||||
jest.mock('ui/chrome',
|
||||
() => ({
|
||||
getBasePath: () => `/some/base/path`,
|
||||
|
|
28
src/legacy/ui/public/timefilter/timefilter.test.mocks.ts
Normal file
28
src/legacy/ui/public/timefilter/timefilter.test.mocks.ts
Normal file
|
@ -0,0 +1,28 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -17,6 +17,8 @@
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
import './brush_event.test.mocks';
|
||||
|
||||
jest.mock('ui/chrome',
|
||||
() => ({
|
||||
getBasePath: () => `/some/base/path`,
|
||||
|
|
|
@ -0,0 +1,28 @@
|
|||
/*
|
||||
* Licensed to Elasticsearch B.V. under one or more contributor
|
||||
* license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright
|
||||
* ownership. Elasticsearch B.V. licenses this file to you under
|
||||
* the Apache License, Version 2.0 (the "License"); you may
|
||||
* not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -6,6 +6,7 @@
|
|||
|
||||
import jobConfig from '../../../../common/types/__mocks__/job_config_farequote';
|
||||
import mockAnnotations from './__mocks__/mock_annotations.json';
|
||||
import './annotations_table.test.mocks';
|
||||
|
||||
import { shallowWithIntl } from 'test_utils/enzyme_helpers';
|
||||
import React from 'react';
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -7,6 +7,7 @@
|
|||
import { shallow } from 'enzyme';
|
||||
import React from 'react';
|
||||
|
||||
import './job_list.test.mocks';
|
||||
import { DataFrameJobList } from './job_list';
|
||||
|
||||
describe('Data Frame: Job List <DataFrameJobList />', () => {
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -7,6 +7,7 @@
|
|||
import { shallow } from 'enzyme';
|
||||
import React from 'react';
|
||||
|
||||
import './page.test.mocks';
|
||||
import { Page } from './page';
|
||||
|
||||
describe('Data Frame: Job List <Page />', () => {
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import './explorer_chart_distribution.test.mocks';
|
||||
import { chartData as mockChartData } from './__mocks__/mock_chart_data_rare';
|
||||
import seriesConfig from './__mocks__/mock_series_config_rare.json';
|
||||
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -4,6 +4,7 @@
|
|||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import './explorer_chart_single_metric.test.mocks';
|
||||
import { chartData as mockChartData } from './__mocks__/mock_chart_data';
|
||||
import seriesConfig from './__mocks__/mock_series_config_filebeat.json';
|
||||
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -4,6 +4,7 @@
|
|||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import './explorer_chart_single_metric.test.mocks';
|
||||
import { chartData } from './__mocks__/mock_chart_data';
|
||||
import seriesConfig from './__mocks__/mock_series_config_filebeat.json';
|
||||
import seriesConfigRare from './__mocks__/mock_series_config_rare.json';
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -4,6 +4,7 @@
|
|||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import './explorer_charts_container_service.test.mocks';
|
||||
import _ from 'lodash';
|
||||
|
||||
import mockAnomalyChartRecords from './__mocks__/mock_anomaly_chart_records.json';
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -4,6 +4,7 @@
|
|||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import './explorer_swimlane.test.mocks';
|
||||
import mockOverallSwimlaneData from './__mocks__/mock_overall_swimlane.json';
|
||||
|
||||
import moment from 'moment-timezone';
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -6,6 +6,7 @@
|
|||
|
||||
//import mockOverallSwimlaneData from './__mocks__/mock_overall_swimlane.json';
|
||||
|
||||
import './timeseries_chart.test.mocks';
|
||||
import moment from 'moment-timezone';
|
||||
import { mountWithIntl } from 'test_utils/enzyme_helpers';
|
||||
import React from 'react';
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
|
@ -4,6 +4,7 @@
|
|||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import './chart_utils.test.mocks';
|
||||
import seriesConfig from '../explorer/explorer_charts/__mocks__/mock_series_config_filebeat';
|
||||
|
||||
// A copy of these mocks for ui/chrome and ui/timefilter are also
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License;
|
||||
* you may not use this file except in compliance with the Elastic License.
|
||||
*/
|
||||
|
||||
import { chromeServiceMock } from '../../../../../../src/core/public/mocks';
|
||||
|
||||
jest.doMock('ui/new_platform', () => ({
|
||||
npStart: {
|
||||
core: {
|
||||
chrome: chromeServiceMock.createStartContract(),
|
||||
},
|
||||
},
|
||||
}));
|
63
yarn.lock
63
yarn.lock
|
@ -3173,6 +3173,26 @@
|
|||
"@svgr/plugin-svgo" "^4.2.0"
|
||||
loader-utils "^1.2.3"
|
||||
|
||||
"@trust/keyto@^0.3.4":
|
||||
version "0.3.7"
|
||||
resolved "https://registry.yarnpkg.com/@trust/keyto/-/keyto-0.3.7.tgz#e251264e302a7a6be64a3e208dacb2ef6268c946"
|
||||
integrity sha512-t5kWWCTkPgg24JWVuCTPMx7l13F7YHdxBeJkT1vmoHjROgiOIEAN8eeY+iRmP1Hwsx+S7U55HyuqSsECr08a8A==
|
||||
dependencies:
|
||||
asn1.js "^5.0.1"
|
||||
base64url "^3.0.1"
|
||||
elliptic "^6.4.1"
|
||||
|
||||
"@trust/webcrypto@^0.9.2":
|
||||
version "0.9.2"
|
||||
resolved "https://registry.yarnpkg.com/@trust/webcrypto/-/webcrypto-0.9.2.tgz#c699d4c026a4446b04faa54d5389a81888ba713c"
|
||||
integrity sha512-5iMAVcGYKhqLJGjefB1nzuQSqUJTru0nG4CytpBT/GGp1Piz/MVnj2jORdYf4JBYzggCIa8WZUr2rchP2Ngn/w==
|
||||
dependencies:
|
||||
"@trust/keyto" "^0.3.4"
|
||||
base64url "^3.0.0"
|
||||
elliptic "^6.4.0"
|
||||
node-rsa "^0.4.0"
|
||||
text-encoding "^0.6.1"
|
||||
|
||||
"@turf/bbox@6.x":
|
||||
version "6.0.1"
|
||||
resolved "https://registry.yarnpkg.com/@turf/bbox/-/bbox-6.0.1.tgz#b966075771475940ee1c16be2a12cf389e6e923a"
|
||||
|
@ -5601,6 +5621,20 @@ asn1.js@^4.0.0:
|
|||
inherits "^2.0.1"
|
||||
minimalistic-assert "^1.0.0"
|
||||
|
||||
asn1.js@^5.0.1:
|
||||
version "5.0.1"
|
||||
resolved "https://registry.yarnpkg.com/asn1.js/-/asn1.js-5.0.1.tgz#7668b56416953f0ce3421adbb3893ace59c96f59"
|
||||
integrity sha512-aO8EaEgbgqq77IEw+1jfx5c9zTbzvkfuRBuZsSsPnTHMkmd5AI4J6OtITLZFa381jReeaQL67J0GBTUu0+ZTVw==
|
||||
dependencies:
|
||||
bn.js "^4.0.0"
|
||||
inherits "^2.0.1"
|
||||
minimalistic-assert "^1.0.0"
|
||||
|
||||
asn1@0.2.3:
|
||||
version "0.2.3"
|
||||
resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.3.tgz#dac8787713c9966849fc8180777ebe9c1ddf3b86"
|
||||
integrity sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=
|
||||
|
||||
asn1@~0.2.3:
|
||||
version "0.2.4"
|
||||
resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.4.tgz#8d2475dfab553bb33e77b54e59e880bb8ce23136"
|
||||
|
@ -6485,7 +6519,7 @@ base64id@1.0.0:
|
|||
resolved "https://registry.yarnpkg.com/base64id/-/base64id-1.0.0.tgz#47688cb99bb6804f0e06d3e763b1c32e57d8e6b6"
|
||||
integrity sha1-R2iMuZu2gE8OBtPnY7HDLlfY5rY=
|
||||
|
||||
base64url@^3.0.0:
|
||||
base64url@^3.0.0, base64url@^3.0.1:
|
||||
version "3.0.1"
|
||||
resolved "https://registry.yarnpkg.com/base64url/-/base64url-3.0.1.tgz#6399d572e2bc3f90a9a8b22d5dbb0a32d33f788d"
|
||||
integrity sha512-ir1UPr3dkwexU7FdV8qBBbNDRUhMmIekYMFZfi+C/sLNnRESKPl23nB9b2pltqfOQNnGzsDdId90AEtG5tCx4A==
|
||||
|
@ -10532,6 +10566,19 @@ elliptic@^6.0.0:
|
|||
minimalistic-assert "^1.0.0"
|
||||
minimalistic-crypto-utils "^1.0.0"
|
||||
|
||||
elliptic@^6.4.0, elliptic@^6.4.1:
|
||||
version "6.4.1"
|
||||
resolved "https://registry.yarnpkg.com/elliptic/-/elliptic-6.4.1.tgz#c2d0b7776911b86722c632c3c06c60f2f819939a"
|
||||
integrity sha512-BsXLz5sqX8OHcsh7CqBMztyXARmGQ3LWPtGjJi6DiJHq5C/qvi9P3OqgswKSDftbu8+IoI/QDTAm2fFnQ9SZSQ==
|
||||
dependencies:
|
||||
bn.js "^4.4.0"
|
||||
brorand "^1.0.1"
|
||||
hash.js "^1.0.0"
|
||||
hmac-drbg "^1.0.0"
|
||||
inherits "^2.0.1"
|
||||
minimalistic-assert "^1.0.0"
|
||||
minimalistic-crypto-utils "^1.0.0"
|
||||
|
||||
emoji-regex@^7.0.1, emoji-regex@^7.0.2:
|
||||
version "7.0.3"
|
||||
resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-7.0.3.tgz#933a04052860c85e83c122479c4748a8e4c72156"
|
||||
|
@ -11925,6 +11972,11 @@ fast-safe-stringify@^2.0.4:
|
|||
resolved "https://registry.yarnpkg.com/fast-safe-stringify/-/fast-safe-stringify-2.0.6.tgz#04b26106cc56681f51a044cfc0d76cf0008ac2c2"
|
||||
integrity sha512-q8BZ89jjc+mz08rSxROs8VsrBBcn1SIw1kq9NjolL509tkABRk9io01RAjSaEv1Xb2uFLt8VtRiZbGp5H8iDtg==
|
||||
|
||||
fast-text-encoding@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.yarnpkg.com/fast-text-encoding/-/fast-text-encoding-1.0.0.tgz#3e5ce8293409cfaa7177a71b9ca84e1b1e6f25ef"
|
||||
integrity sha512-R9bHCvweUxxwkDwhjav5vxpFvdPGlVngtqmx4pIZfSUhM/Q4NiIUHB456BAf+Q1Nwu3HEZYONtu+Rya+af4jiQ==
|
||||
|
||||
fastparse@^1.1.1:
|
||||
version "1.1.1"
|
||||
resolved "https://registry.yarnpkg.com/fastparse/-/fastparse-1.1.1.tgz#d1e2643b38a94d7583b479060e6c4affc94071f8"
|
||||
|
@ -19562,6 +19614,13 @@ node-releases@^1.1.3:
|
|||
dependencies:
|
||||
semver "^5.3.0"
|
||||
|
||||
node-rsa@^0.4.0:
|
||||
version "0.4.2"
|
||||
resolved "https://registry.yarnpkg.com/node-rsa/-/node-rsa-0.4.2.tgz#d6391729ec16a830ed5a38042b3157d2d5d72530"
|
||||
integrity sha1-1jkXKewWqDDtWjgEKzFX0tXXJTA=
|
||||
dependencies:
|
||||
asn1 "0.2.3"
|
||||
|
||||
node-sass@^4.9.4:
|
||||
version "4.9.4"
|
||||
resolved "https://registry.yarnpkg.com/node-sass/-/node-sass-4.9.4.tgz#349bd7f1c89422ffe7e1e4b60f2055a69fbc5512"
|
||||
|
@ -26227,7 +26286,7 @@ test-exclude@^5.0.0:
|
|||
read-pkg-up "^4.0.0"
|
||||
require-main-filename "^1.0.1"
|
||||
|
||||
text-encoding@^0.6.4:
|
||||
text-encoding@^0.6.1, text-encoding@^0.6.4:
|
||||
version "0.6.4"
|
||||
resolved "https://registry.yarnpkg.com/text-encoding/-/text-encoding-0.6.4.tgz#e399a982257a276dae428bb92845cb71bdc26d19"
|
||||
integrity sha1-45mpgiV6J22uQou5KEXLcb3CbRk=
|
||||
|
|
Loading…
Reference in a new issue