mirror of
https://github.com/elastic/kibana.git
synced 2025-06-27 18:51:07 -04:00
[Content Management] Maps onboard (#153304)
This commit is contained in:
parent
045b58fe5b
commit
42a893db40
61 changed files with 1094 additions and 300 deletions
|
@ -64,52 +64,52 @@ export interface ServicesDefinition {
|
||||||
export interface ServiceTransforms {
|
export interface ServiceTransforms {
|
||||||
get: {
|
get: {
|
||||||
in: {
|
in: {
|
||||||
options: ObjectTransforms;
|
options: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
out: {
|
out: {
|
||||||
result: ObjectTransforms;
|
result: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
bulkGet: {
|
bulkGet: {
|
||||||
in: {
|
in: {
|
||||||
options: ObjectTransforms;
|
options: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
out: {
|
out: {
|
||||||
result: ObjectTransforms;
|
result: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
create: {
|
create: {
|
||||||
in: {
|
in: {
|
||||||
data: ObjectTransforms;
|
data: ObjectTransforms<any, any, any, any>;
|
||||||
options: ObjectTransforms;
|
options: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
out: {
|
out: {
|
||||||
result: ObjectTransforms;
|
result: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
update: {
|
update: {
|
||||||
in: {
|
in: {
|
||||||
data: ObjectTransforms;
|
data: ObjectTransforms<any, any, any, any>;
|
||||||
options: ObjectTransforms;
|
options: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
out: {
|
out: {
|
||||||
result: ObjectTransforms;
|
result: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
delete: {
|
delete: {
|
||||||
in: {
|
in: {
|
||||||
options: ObjectTransforms;
|
options: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
out: {
|
out: {
|
||||||
result: ObjectTransforms;
|
result: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
search: {
|
search: {
|
||||||
in: {
|
in: {
|
||||||
options: ObjectTransforms;
|
options: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
out: {
|
out: {
|
||||||
result: ObjectTransforms;
|
result: ObjectTransforms<any, any, any, any>;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,12 +9,7 @@
|
||||||
import { schema } from '@kbn/config-schema';
|
import { schema } from '@kbn/config-schema';
|
||||||
import { initTransform } from './object_transform';
|
import { initTransform } from './object_transform';
|
||||||
|
|
||||||
import type {
|
import type { ObjectMigrationDefinition, Version, VersionableObject } from './types';
|
||||||
ObjectMigrationDefinition,
|
|
||||||
ObjectTransforms,
|
|
||||||
Version,
|
|
||||||
VersionableObject,
|
|
||||||
} from './types';
|
|
||||||
|
|
||||||
interface FooV1 {
|
interface FooV1 {
|
||||||
fullName: string;
|
fullName: string;
|
||||||
|
@ -58,7 +53,7 @@ const fooMigrationDef: ObjectMigrationDefinition = {
|
||||||
|
|
||||||
const setup = <UpIn = unknown, UpOut = unknown, DownIn = unknown, DownOut = unknown>(
|
const setup = <UpIn = unknown, UpOut = unknown, DownIn = unknown, DownOut = unknown>(
|
||||||
browserVersion: Version
|
browserVersion: Version
|
||||||
): ObjectTransforms<UpIn, UpOut, DownIn, DownOut> => {
|
) => {
|
||||||
const transformsFactory = initTransform<UpIn, UpOut, DownIn, DownOut>(browserVersion);
|
const transformsFactory = initTransform<UpIn, UpOut, DownIn, DownOut>(browserVersion);
|
||||||
return transformsFactory(fooMigrationDef);
|
return transformsFactory(fooMigrationDef);
|
||||||
};
|
};
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
* Side Public License, v 1.
|
* Side Public License, v 1.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { ObjectMigrationDefinition, ObjectTransform, ObjectTransforms, Version } from './types';
|
import { ObjectMigrationDefinition, ObjectTransform, Version } from './types';
|
||||||
import { validateObj, validateVersion } from './utils';
|
import { validateObj, validateVersion } from './utils';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -97,11 +97,8 @@ const getTransformFns = <I = unknown, O = unknown>(
|
||||||
*/
|
*/
|
||||||
export const initTransform =
|
export const initTransform =
|
||||||
<UpIn = unknown, UpOut = unknown, DownIn = unknown, DownOut = unknown>(requestVersion: Version) =>
|
<UpIn = unknown, UpOut = unknown, DownIn = unknown, DownOut = unknown>(requestVersion: Version) =>
|
||||||
(
|
(migrationDefinition: ObjectMigrationDefinition) => {
|
||||||
migrationDefinition: ObjectMigrationDefinition
|
|
||||||
): ObjectTransforms<UpIn, UpOut, DownIn, DownOut> => {
|
|
||||||
const { latestVersion } = getVersionsMeta(migrationDefinition);
|
const { latestVersion } = getVersionsMeta(migrationDefinition);
|
||||||
|
|
||||||
const getVersion = (v: Version | 'latest'): Version => (v === 'latest' ? latestVersion : v);
|
const getVersion = (v: Version | 'latest'): Version => (v === 'latest' ? latestVersion : v);
|
||||||
|
|
||||||
const validateFn = (value: unknown, version: number = requestVersion) => {
|
const validateFn = (value: unknown, version: number = requestVersion) => {
|
||||||
|
@ -120,7 +117,11 @@ export const initTransform =
|
||||||
};
|
};
|
||||||
|
|
||||||
return {
|
return {
|
||||||
up: (obj, to = 'latest', { validate = true }: { validate?: boolean } = {}) => {
|
up: <I = UpIn, O = UpOut>(
|
||||||
|
obj: I,
|
||||||
|
to: number | 'latest' = 'latest',
|
||||||
|
{ validate = true }: { validate?: boolean } = {}
|
||||||
|
) => {
|
||||||
try {
|
try {
|
||||||
if (!migrationDefinition[requestVersion]) {
|
if (!migrationDefinition[requestVersion]) {
|
||||||
return {
|
return {
|
||||||
|
@ -145,16 +146,12 @@ export const initTransform =
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
const fns = getTransformFns<UpIn, UpOut>(
|
const fns = getTransformFns<I, O>(requestVersion, targetVersion, migrationDefinition);
|
||||||
requestVersion,
|
|
||||||
targetVersion,
|
|
||||||
migrationDefinition
|
|
||||||
);
|
|
||||||
|
|
||||||
const value = fns.reduce((acc, fn) => {
|
const value = fns.reduce((acc, fn) => {
|
||||||
const res = fn(acc as unknown as UpIn);
|
const res = fn(acc as unknown as I);
|
||||||
return res;
|
return res;
|
||||||
}, obj as unknown as UpOut);
|
}, obj as unknown as O);
|
||||||
|
|
||||||
return { value, error: null };
|
return { value, error: null };
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
|
@ -164,7 +161,11 @@ export const initTransform =
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
down: (obj, from = 'latest', { validate = true }: { validate?: boolean } = {}) => {
|
down: <I = DownIn, O = DownOut>(
|
||||||
|
obj: I,
|
||||||
|
from: number | 'latest' = 'latest',
|
||||||
|
{ validate = true }: { validate?: boolean } = {}
|
||||||
|
) => {
|
||||||
try {
|
try {
|
||||||
if (!migrationDefinition[requestVersion]) {
|
if (!migrationDefinition[requestVersion]) {
|
||||||
return {
|
return {
|
||||||
|
@ -189,16 +190,12 @@ export const initTransform =
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const fns = getTransformFns<DownIn, DownOut>(
|
const fns = getTransformFns<I, O>(fromVersion, requestVersion, migrationDefinition);
|
||||||
fromVersion,
|
|
||||||
requestVersion,
|
|
||||||
migrationDefinition
|
|
||||||
);
|
|
||||||
|
|
||||||
const value = fns.reduce((acc, fn) => {
|
const value = fns.reduce((acc, fn) => {
|
||||||
const res = fn(acc as unknown as DownIn);
|
const res = fn(acc as unknown as I);
|
||||||
return res;
|
return res;
|
||||||
}, obj as unknown as DownOut);
|
}, obj as unknown as O);
|
||||||
|
|
||||||
return { value: value as any, error: null };
|
return { value: value as any, error: null };
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
|
|
|
@ -42,21 +42,21 @@ export interface ObjectTransforms<
|
||||||
DownIn = unknown,
|
DownIn = unknown,
|
||||||
DownOut = unknown
|
DownOut = unknown
|
||||||
> {
|
> {
|
||||||
up: (
|
up: <I = UpIn, O = UpOut>(
|
||||||
obj: UpIn,
|
obj: I,
|
||||||
version?: Version | 'latest',
|
version?: Version | 'latest',
|
||||||
options?: {
|
options?: {
|
||||||
/** Validate the object _before_ up transform */
|
/** Validate the object _before_ up transform */
|
||||||
validate?: boolean;
|
validate?: boolean;
|
||||||
}
|
}
|
||||||
) => TransformReturn<UpOut>;
|
) => TransformReturn<O>;
|
||||||
down: (
|
down: <I = DownIn, O = DownOut>(
|
||||||
obj: DownIn,
|
obj: DownIn,
|
||||||
version?: Version | 'latest',
|
version?: Version | 'latest',
|
||||||
options?: {
|
options?: {
|
||||||
/** Validate the object _before_ down transform */
|
/** Validate the object _before_ down transform */
|
||||||
validate?: boolean;
|
validate?: boolean;
|
||||||
}
|
}
|
||||||
) => TransformReturn<DownOut>;
|
) => TransformReturn<O>;
|
||||||
validate: (obj: any, version?: Version) => ValidationError | null;
|
validate: (obj: any, version?: Version) => ValidationError | null;
|
||||||
}
|
}
|
||||||
|
|
|
@ -34,11 +34,11 @@ export class RpcClient implements CrudClient {
|
||||||
constructor(private http: { post: HttpSetup['post'] }) {}
|
constructor(private http: { post: HttpSetup['post'] }) {}
|
||||||
|
|
||||||
public get<I extends GetIn = GetIn, O = unknown, M = unknown>(input: I) {
|
public get<I extends GetIn = GetIn, O = unknown, M = unknown>(input: I) {
|
||||||
return this.sendMessage<GetResponse<O, M>>('get', input).then((r) => r.item);
|
return this.sendMessage<GetResponse<O, M>>('get', input).then((r) => r.result);
|
||||||
}
|
}
|
||||||
|
|
||||||
public bulkGet<I extends BulkGetIn = BulkGetIn, O = unknown, M = unknown>(input: I) {
|
public bulkGet<I extends BulkGetIn = BulkGetIn, O = unknown, M = unknown>(input: I) {
|
||||||
return this.sendMessage<BulkGetResponse<O, M>>('bulkGet', input).then((r) => r.items);
|
return this.sendMessage<BulkGetResponse<O, M>>('bulkGet', input).then((r) => r.result);
|
||||||
}
|
}
|
||||||
|
|
||||||
public create<I extends CreateIn = CreateIn, O = unknown, M = unknown>(input: I) {
|
public create<I extends CreateIn = CreateIn, O = unknown, M = unknown>(input: I) {
|
||||||
|
|
|
@ -165,7 +165,7 @@ describe('Content Core', () => {
|
||||||
const { fooContentCrud, ctx, cleanUp } = setup({ registerFooType: true });
|
const { fooContentCrud, ctx, cleanUp } = setup({ registerFooType: true });
|
||||||
|
|
||||||
const res = await fooContentCrud!.get(ctx, '1');
|
const res = await fooContentCrud!.get(ctx, '1');
|
||||||
expect(res.item.item).toBeUndefined();
|
expect(res.result.item).toBeUndefined();
|
||||||
|
|
||||||
cleanUp();
|
cleanUp();
|
||||||
});
|
});
|
||||||
|
@ -176,7 +176,7 @@ describe('Content Core', () => {
|
||||||
const res = await fooContentCrud!.get(ctx, '1', { forwardInResponse: { foo: 'bar' } });
|
const res = await fooContentCrud!.get(ctx, '1', { forwardInResponse: { foo: 'bar' } });
|
||||||
expect(res).toEqual({
|
expect(res).toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
item: {
|
result: {
|
||||||
item: {
|
item: {
|
||||||
// Options forwared in response
|
// Options forwared in response
|
||||||
options: { foo: 'bar' },
|
options: { foo: 'bar' },
|
||||||
|
@ -191,7 +191,7 @@ describe('Content Core', () => {
|
||||||
const { fooContentCrud, ctx, cleanUp } = setup({ registerFooType: true });
|
const { fooContentCrud, ctx, cleanUp } = setup({ registerFooType: true });
|
||||||
|
|
||||||
const res = await fooContentCrud!.bulkGet(ctx, ['1', '2']);
|
const res = await fooContentCrud!.bulkGet(ctx, ['1', '2']);
|
||||||
expect(res.items).toEqual({
|
expect(res.result).toEqual({
|
||||||
hits: [{ item: undefined }, { item: undefined }],
|
hits: [{ item: undefined }, { item: undefined }],
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -207,7 +207,7 @@ describe('Content Core', () => {
|
||||||
|
|
||||||
expect(res).toEqual({
|
expect(res).toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
items: {
|
result: {
|
||||||
hits: [
|
hits: [
|
||||||
{
|
{
|
||||||
item: {
|
item: {
|
||||||
|
@ -230,7 +230,7 @@ describe('Content Core', () => {
|
||||||
const { fooContentCrud, ctx, cleanUp } = setup({ registerFooType: true });
|
const { fooContentCrud, ctx, cleanUp } = setup({ registerFooType: true });
|
||||||
|
|
||||||
const res = await fooContentCrud!.get(ctx, '1234');
|
const res = await fooContentCrud!.get(ctx, '1234');
|
||||||
expect(res.item.item).toBeUndefined();
|
expect(res.result.item).toBeUndefined();
|
||||||
await fooContentCrud!.create(
|
await fooContentCrud!.create(
|
||||||
ctx,
|
ctx,
|
||||||
{ title: 'Hello' },
|
{ title: 'Hello' },
|
||||||
|
@ -238,7 +238,7 @@ describe('Content Core', () => {
|
||||||
);
|
);
|
||||||
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
item: {
|
result: {
|
||||||
item: {
|
item: {
|
||||||
id: '1234',
|
id: '1234',
|
||||||
title: 'Hello',
|
title: 'Hello',
|
||||||
|
@ -256,7 +256,7 @@ describe('Content Core', () => {
|
||||||
await fooContentCrud!.update(ctx, '1234', { title: 'changed' });
|
await fooContentCrud!.update(ctx, '1234', { title: 'changed' });
|
||||||
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
item: {
|
result: {
|
||||||
item: {
|
item: {
|
||||||
id: '1234',
|
id: '1234',
|
||||||
title: 'changed',
|
title: 'changed',
|
||||||
|
@ -292,7 +292,7 @@ describe('Content Core', () => {
|
||||||
|
|
||||||
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
item: {
|
result: {
|
||||||
item: {
|
item: {
|
||||||
id: '1234',
|
id: '1234',
|
||||||
title: 'changed',
|
title: 'changed',
|
||||||
|
@ -309,14 +309,14 @@ describe('Content Core', () => {
|
||||||
await fooContentCrud!.create(ctx, { title: 'Hello' }, { id: '1234' });
|
await fooContentCrud!.create(ctx, { title: 'Hello' }, { id: '1234' });
|
||||||
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
item: {
|
result: {
|
||||||
item: expect.any(Object),
|
item: expect.any(Object),
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
await fooContentCrud!.delete(ctx, '1234');
|
await fooContentCrud!.delete(ctx, '1234');
|
||||||
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
expect(fooContentCrud!.get(ctx, '1234')).resolves.toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
item: {
|
result: {
|
||||||
item: undefined,
|
item: undefined,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
|
@ -19,12 +19,12 @@ import type { ContentStorage, StorageContext } from './types';
|
||||||
|
|
||||||
export interface GetResponse<T = unknown, M = void> {
|
export interface GetResponse<T = unknown, M = void> {
|
||||||
contentTypeId: string;
|
contentTypeId: string;
|
||||||
item: GetResult<T, M>;
|
result: GetResult<T, M>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface BulkGetResponse<T = unknown, M = void> {
|
export interface BulkGetResponse<T = unknown, M = void> {
|
||||||
contentTypeId: string;
|
contentTypeId: string;
|
||||||
items: BulkGetResult<T, M>;
|
result: BulkGetResult<T, M>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CreateItemResponse<T = unknown, M = void> {
|
export interface CreateItemResponse<T = unknown, M = void> {
|
||||||
|
@ -89,7 +89,7 @@ export class ContentCrud<T = unknown> {
|
||||||
options,
|
options,
|
||||||
});
|
});
|
||||||
|
|
||||||
return { contentTypeId: this.contentTypeId, item };
|
return { contentTypeId: this.contentTypeId, result: item };
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
this.eventBus.emit({
|
this.eventBus.emit({
|
||||||
type: 'getItemError',
|
type: 'getItemError',
|
||||||
|
@ -128,7 +128,7 @@ export class ContentCrud<T = unknown> {
|
||||||
|
|
||||||
return {
|
return {
|
||||||
contentTypeId: this.contentTypeId,
|
contentTypeId: this.contentTypeId,
|
||||||
items,
|
result: items,
|
||||||
};
|
};
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
this.eventBus.emit({
|
this.eventBus.emit({
|
||||||
|
|
|
@ -206,7 +206,7 @@ describe('RPC -> bulkGet()', () => {
|
||||||
|
|
||||||
expect(result).toEqual({
|
expect(result).toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
items: expected,
|
result: expected,
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(storage.bulkGet).toHaveBeenCalledWith(
|
expect(storage.bulkGet).toHaveBeenCalledWith(
|
||||||
|
|
|
@ -161,7 +161,7 @@ describe('RPC -> get()', () => {
|
||||||
|
|
||||||
expect(result).toEqual({
|
expect(result).toEqual({
|
||||||
contentTypeId: FOO_CONTENT_ID,
|
contentTypeId: FOO_CONTENT_ID,
|
||||||
item: expected,
|
result: expected,
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(storage.get).toHaveBeenCalledWith(
|
expect(storage.get).toHaveBeenCalledWith(
|
||||||
|
|
|
@ -7,15 +7,16 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { omit } from 'lodash';
|
import { omit } from 'lodash';
|
||||||
|
import { schema } from '@kbn/config-schema';
|
||||||
|
import { ContentManagementServiceDefinitionVersioned } from '@kbn/object-versioning';
|
||||||
|
|
||||||
|
import type { SearchQuery } from '../../../common';
|
||||||
import { validate } from '../../utils';
|
import { validate } from '../../utils';
|
||||||
import { ContentRegistry } from '../../core/registry';
|
import { ContentRegistry } from '../../core/registry';
|
||||||
import { createMockedStorage } from '../../core/mocks';
|
import { createMockedStorage } from '../../core/mocks';
|
||||||
import { EventBus } from '../../core/event_bus';
|
import { EventBus } from '../../core/event_bus';
|
||||||
import { search } from './search';
|
|
||||||
import { ContentManagementServiceDefinitionVersioned } from '@kbn/object-versioning';
|
|
||||||
import { schema } from '@kbn/config-schema';
|
|
||||||
import { getServiceObjectTransformFactory } from '../services_transforms_factory';
|
import { getServiceObjectTransformFactory } from '../services_transforms_factory';
|
||||||
|
import { search } from './search';
|
||||||
|
|
||||||
const { fn, schemas } = search;
|
const { fn, schemas } = search;
|
||||||
|
|
||||||
|
@ -34,7 +35,12 @@ const FOO_CONTENT_ID = 'foo';
|
||||||
|
|
||||||
describe('RPC -> search()', () => {
|
describe('RPC -> search()', () => {
|
||||||
describe('Input/Output validation', () => {
|
describe('Input/Output validation', () => {
|
||||||
const query = { text: 'hello' };
|
const query: SearchQuery = {
|
||||||
|
text: 'hello',
|
||||||
|
tags: { included: ['abc'], excluded: ['def'] },
|
||||||
|
cursor: '1',
|
||||||
|
limit: 50,
|
||||||
|
};
|
||||||
const validInput = { contentTypeId: 'foo', version: 1, query };
|
const validInput = { contentTypeId: 'foo', version: 1, query };
|
||||||
|
|
||||||
test('should validate that a contentTypeId and "query" object is passed', () => {
|
test('should validate that a contentTypeId and "query" object is passed', () => {
|
||||||
|
@ -63,6 +69,10 @@ describe('RPC -> search()', () => {
|
||||||
input: { ...validInput, query: 123 }, // query is not an object
|
input: { ...validInput, query: 123 }, // query is not an object
|
||||||
expectedError: '[query]: expected a plain object value, but found [number] instead.',
|
expectedError: '[query]: expected a plain object value, but found [number] instead.',
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
input: { ...validInput, query: { tags: { included: 123 } } }, // invalid query
|
||||||
|
expectedError: '[query.tags.included]: expected value of type [array] but got [number]',
|
||||||
|
},
|
||||||
{
|
{
|
||||||
input: { ...validInput, unknown: 'foo' },
|
input: { ...validInput, unknown: 'foo' },
|
||||||
expectedError: '[unknown]: definition for this key is missing',
|
expectedError: '[unknown]: definition for this key is missing',
|
||||||
|
|
|
@ -30,7 +30,7 @@ export interface VisualizationListItem {
|
||||||
export interface VisualizationsAppExtension {
|
export interface VisualizationsAppExtension {
|
||||||
docTypes: string[];
|
docTypes: string[];
|
||||||
searchFields?: string[];
|
searchFields?: string[];
|
||||||
toListItem: (savedObject: SimpleSavedObject) => VisualizationListItem;
|
toListItem: (savedObject: SimpleSavedObject<any>) => VisualizationListItem;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface VisTypeAlias {
|
export interface VisTypeAlias {
|
||||||
|
|
19
x-pack/plugins/maps/common/content_management/cm_services.ts
Normal file
19
x-pack/plugins/maps/common/content_management/cm_services.ts
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
import type {
|
||||||
|
ContentManagementServicesDefinition as ServicesDefinition,
|
||||||
|
Version,
|
||||||
|
} from '@kbn/object-versioning';
|
||||||
|
|
||||||
|
// We export the versionned service definition from this file and not the barrel to avoid adding
|
||||||
|
// the schemas in the "public" js bundle
|
||||||
|
|
||||||
|
import { serviceDefinition as v1 } from './v1/cm_services';
|
||||||
|
|
||||||
|
export const cmServicesDefinition: { [version: Version]: ServicesDefinition } = {
|
||||||
|
1: v1,
|
||||||
|
};
|
|
@ -5,12 +5,6 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* eslint-disable @typescript-eslint/consistent-type-definitions */
|
export const LATEST_VERSION = 1;
|
||||||
|
|
||||||
export type MapSavedObjectAttributes = {
|
export const CONTENT_ID = 'map';
|
||||||
title: string;
|
|
||||||
description?: string;
|
|
||||||
mapStateJSON?: string;
|
|
||||||
layerListJSON?: string;
|
|
||||||
uiStateJSON?: string;
|
|
||||||
};
|
|
34
x-pack/plugins/maps/common/content_management/index.ts
Normal file
34
x-pack/plugins/maps/common/content_management/index.ts
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
export { LATEST_VERSION, CONTENT_ID } from './constants';
|
||||||
|
|
||||||
|
export type { MapContentType } from './types';
|
||||||
|
|
||||||
|
export type {
|
||||||
|
MapAttributes,
|
||||||
|
MapItem,
|
||||||
|
PartialMapItem,
|
||||||
|
MapGetIn,
|
||||||
|
MapGetOut,
|
||||||
|
MapCreateIn,
|
||||||
|
MapCreateOut,
|
||||||
|
CreateOptions,
|
||||||
|
MapUpdateIn,
|
||||||
|
MapUpdateOut,
|
||||||
|
UpdateOptions,
|
||||||
|
MapDeleteIn,
|
||||||
|
MapDeleteOut,
|
||||||
|
MapSearchIn,
|
||||||
|
MapSearchOptions,
|
||||||
|
MapSearchOut,
|
||||||
|
} from './latest';
|
||||||
|
|
||||||
|
// Today "v1" === "latest" so the export under MapV1 namespace is not really useful
|
||||||
|
// We leave it as a reference for future version when it will be needed to export/support older types
|
||||||
|
// in the UIs.
|
||||||
|
export * as MapV1 from './v1';
|
9
x-pack/plugins/maps/common/content_management/latest.ts
Normal file
9
x-pack/plugins/maps/common/content_management/latest.ts
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
// Latest version is 1
|
||||||
|
export * from './v1';
|
8
x-pack/plugins/maps/common/content_management/types.ts
Normal file
8
x-pack/plugins/maps/common/content_management/types.ts
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
export type MapContentType = 'map';
|
137
x-pack/plugins/maps/common/content_management/v1/cm_services.ts
Normal file
137
x-pack/plugins/maps/common/content_management/v1/cm_services.ts
Normal file
|
@ -0,0 +1,137 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
import { schema } from '@kbn/config-schema';
|
||||||
|
import type { ContentManagementServicesDefinition as ServicesDefinition } from '@kbn/object-versioning';
|
||||||
|
|
||||||
|
const apiError = schema.object({
|
||||||
|
error: schema.string(),
|
||||||
|
message: schema.string(),
|
||||||
|
statusCode: schema.number(),
|
||||||
|
metadata: schema.object({}, { unknowns: 'allow' }),
|
||||||
|
});
|
||||||
|
|
||||||
|
const referenceSchema = schema.object(
|
||||||
|
{
|
||||||
|
name: schema.maybe(schema.string()),
|
||||||
|
type: schema.string(),
|
||||||
|
id: schema.string(),
|
||||||
|
},
|
||||||
|
{ unknowns: 'forbid' }
|
||||||
|
);
|
||||||
|
|
||||||
|
const referencesSchema = schema.arrayOf(referenceSchema);
|
||||||
|
|
||||||
|
const mapAttributesSchema = schema.object(
|
||||||
|
{
|
||||||
|
title: schema.string(),
|
||||||
|
description: schema.maybe(schema.string()),
|
||||||
|
mapStateJSON: schema.maybe(schema.string()),
|
||||||
|
layerListJSON: schema.maybe(schema.string()),
|
||||||
|
uiStateJSON: schema.maybe(schema.string()),
|
||||||
|
},
|
||||||
|
{ unknowns: 'forbid' }
|
||||||
|
);
|
||||||
|
|
||||||
|
const mapSavedObjectSchema = schema.object(
|
||||||
|
{
|
||||||
|
id: schema.string(),
|
||||||
|
type: schema.string(),
|
||||||
|
version: schema.maybe(schema.string()),
|
||||||
|
createdAt: schema.maybe(schema.string()),
|
||||||
|
updatedAt: schema.maybe(schema.string()),
|
||||||
|
error: schema.maybe(apiError),
|
||||||
|
attributes: mapAttributesSchema,
|
||||||
|
references: referencesSchema,
|
||||||
|
namespaces: schema.maybe(schema.arrayOf(schema.string())),
|
||||||
|
originId: schema.maybe(schema.string()),
|
||||||
|
},
|
||||||
|
{ unknowns: 'allow' }
|
||||||
|
);
|
||||||
|
|
||||||
|
const getResultSchema = schema.object(
|
||||||
|
{
|
||||||
|
item: mapSavedObjectSchema,
|
||||||
|
meta: schema.object(
|
||||||
|
{
|
||||||
|
outcome: schema.oneOf([
|
||||||
|
schema.literal('exactMatch'),
|
||||||
|
schema.literal('aliasMatch'),
|
||||||
|
schema.literal('conflict'),
|
||||||
|
]),
|
||||||
|
aliasTargetId: schema.maybe(schema.string()),
|
||||||
|
aliasPurpose: schema.maybe(
|
||||||
|
schema.oneOf([
|
||||||
|
schema.literal('savedObjectConversion'),
|
||||||
|
schema.literal('savedObjectImport'),
|
||||||
|
])
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{ unknowns: 'forbid' }
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{ unknowns: 'forbid' }
|
||||||
|
);
|
||||||
|
|
||||||
|
const createOptionsSchema = schema.object({
|
||||||
|
references: schema.maybe(referencesSchema),
|
||||||
|
});
|
||||||
|
|
||||||
|
// Content management service definition.
|
||||||
|
// We need it for BWC support between different versions of the content
|
||||||
|
export const serviceDefinition: ServicesDefinition = {
|
||||||
|
get: {
|
||||||
|
out: {
|
||||||
|
result: {
|
||||||
|
schema: getResultSchema,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
create: {
|
||||||
|
in: {
|
||||||
|
options: {
|
||||||
|
schema: createOptionsSchema,
|
||||||
|
},
|
||||||
|
data: {
|
||||||
|
schema: mapAttributesSchema,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
out: {
|
||||||
|
result: {
|
||||||
|
schema: schema.object(
|
||||||
|
{
|
||||||
|
item: mapSavedObjectSchema,
|
||||||
|
},
|
||||||
|
{ unknowns: 'forbid' }
|
||||||
|
),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
update: {
|
||||||
|
in: {
|
||||||
|
options: {
|
||||||
|
schema: createOptionsSchema, // same schema as "create"
|
||||||
|
},
|
||||||
|
data: {
|
||||||
|
schema: mapAttributesSchema,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
search: {
|
||||||
|
in: {
|
||||||
|
options: {
|
||||||
|
schema: schema.maybe(
|
||||||
|
schema.object(
|
||||||
|
{
|
||||||
|
onlyTitle: schema.maybe(schema.boolean()),
|
||||||
|
},
|
||||||
|
{ unknowns: 'forbid' }
|
||||||
|
)
|
||||||
|
),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
25
x-pack/plugins/maps/common/content_management/v1/index.ts
Normal file
25
x-pack/plugins/maps/common/content_management/v1/index.ts
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
export type {
|
||||||
|
MapAttributes,
|
||||||
|
MapItem,
|
||||||
|
PartialMapItem,
|
||||||
|
MapGetIn,
|
||||||
|
MapGetOut,
|
||||||
|
MapCreateIn,
|
||||||
|
MapCreateOut,
|
||||||
|
CreateOptions,
|
||||||
|
MapUpdateIn,
|
||||||
|
MapUpdateOut,
|
||||||
|
UpdateOptions,
|
||||||
|
MapDeleteIn,
|
||||||
|
MapDeleteOut,
|
||||||
|
MapSearchIn,
|
||||||
|
MapSearchOptions,
|
||||||
|
MapSearchOut,
|
||||||
|
} from './types';
|
110
x-pack/plugins/maps/common/content_management/v1/types.ts
Normal file
110
x-pack/plugins/maps/common/content_management/v1/types.ts
Normal file
|
@ -0,0 +1,110 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
import type {
|
||||||
|
GetIn,
|
||||||
|
GetResult,
|
||||||
|
CreateIn,
|
||||||
|
CreateResult,
|
||||||
|
SearchIn,
|
||||||
|
SearchResult,
|
||||||
|
UpdateIn,
|
||||||
|
UpdateResult,
|
||||||
|
DeleteIn,
|
||||||
|
DeleteResult,
|
||||||
|
} from '@kbn/content-management-plugin/common';
|
||||||
|
import { MapContentType } from '../types';
|
||||||
|
|
||||||
|
interface Reference {
|
||||||
|
type: string;
|
||||||
|
id: string;
|
||||||
|
name: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* eslint-disable-next-line @typescript-eslint/consistent-type-definitions */
|
||||||
|
export type MapAttributes = {
|
||||||
|
title: string;
|
||||||
|
description?: string;
|
||||||
|
mapStateJSON?: string;
|
||||||
|
layerListJSON?: string;
|
||||||
|
uiStateJSON?: string;
|
||||||
|
};
|
||||||
|
|
||||||
|
export interface MapItem {
|
||||||
|
id: string;
|
||||||
|
type: string;
|
||||||
|
version?: string;
|
||||||
|
createdAt?: string;
|
||||||
|
updatedAt?: string;
|
||||||
|
error?: {
|
||||||
|
error: string;
|
||||||
|
message: string;
|
||||||
|
statusCode: number;
|
||||||
|
metadata?: Record<string, unknown>;
|
||||||
|
};
|
||||||
|
attributes: MapAttributes;
|
||||||
|
references: Reference[];
|
||||||
|
namespaces?: string[];
|
||||||
|
originId?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export type PartialMapItem = Omit<MapItem, 'attributes' | 'references'> & {
|
||||||
|
attributes: Partial<MapAttributes>;
|
||||||
|
references: Reference[] | undefined;
|
||||||
|
};
|
||||||
|
|
||||||
|
// ----------- GET --------------
|
||||||
|
|
||||||
|
export type MapGetIn = GetIn<MapContentType>;
|
||||||
|
|
||||||
|
export type MapGetOut = GetResult<
|
||||||
|
MapItem,
|
||||||
|
{
|
||||||
|
outcome: 'exactMatch' | 'aliasMatch' | 'conflict';
|
||||||
|
aliasTargetId?: string;
|
||||||
|
aliasPurpose?: 'savedObjectConversion' | 'savedObjectImport';
|
||||||
|
}
|
||||||
|
>;
|
||||||
|
|
||||||
|
// ----------- CREATE --------------
|
||||||
|
|
||||||
|
export interface CreateOptions {
|
||||||
|
/** Array of referenced saved objects. */
|
||||||
|
references?: Reference[];
|
||||||
|
}
|
||||||
|
|
||||||
|
export type MapCreateIn = CreateIn<MapContentType, MapAttributes, CreateOptions>;
|
||||||
|
|
||||||
|
export type MapCreateOut = CreateResult<MapItem>;
|
||||||
|
|
||||||
|
// ----------- UPDATE --------------
|
||||||
|
|
||||||
|
export interface UpdateOptions {
|
||||||
|
/** Array of referenced saved objects. */
|
||||||
|
references?: Reference[];
|
||||||
|
}
|
||||||
|
|
||||||
|
export type MapUpdateIn = UpdateIn<MapContentType, MapAttributes, UpdateOptions>;
|
||||||
|
|
||||||
|
export type MapUpdateOut = UpdateResult<PartialMapItem>;
|
||||||
|
|
||||||
|
// ----------- DELETE --------------
|
||||||
|
|
||||||
|
export type MapDeleteIn = DeleteIn<MapContentType>;
|
||||||
|
|
||||||
|
export type MapDeleteOut = DeleteResult;
|
||||||
|
|
||||||
|
// ----------- SEARCH --------------
|
||||||
|
|
||||||
|
export interface MapSearchOptions {
|
||||||
|
/** Flag to indicate to only search the text on the "title" field */
|
||||||
|
onlyTitle?: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
export type MapSearchIn = SearchIn<MapContentType, MapSearchOptions>;
|
||||||
|
|
||||||
|
export type MapSearchOut = SearchResult<MapItem>;
|
|
@ -7,7 +7,7 @@
|
||||||
|
|
||||||
import { EmbeddableRegistryDefinition } from '@kbn/embeddable-plugin/common';
|
import { EmbeddableRegistryDefinition } from '@kbn/embeddable-plugin/common';
|
||||||
import { MapEmbeddablePersistableState } from './types';
|
import { MapEmbeddablePersistableState } from './types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
import { extractReferences } from '../migrations/references';
|
import { extractReferences } from '../migrations/references';
|
||||||
|
|
||||||
export const extract: EmbeddableRegistryDefinition['extract'] = (state) => {
|
export const extract: EmbeddableRegistryDefinition['extract'] = (state) => {
|
||||||
|
@ -21,7 +21,7 @@ export const extract: EmbeddableRegistryDefinition['extract'] = (state) => {
|
||||||
|
|
||||||
// by-value embeddable
|
// by-value embeddable
|
||||||
const { attributes, references } = extractReferences({
|
const { attributes, references } = extractReferences({
|
||||||
attributes: typedState.attributes as MapSavedObjectAttributes,
|
attributes: typedState.attributes as MapAttributes,
|
||||||
});
|
});
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
|
|
||||||
import type { EmbeddableRegistryDefinition } from '@kbn/embeddable-plugin/common';
|
import type { EmbeddableRegistryDefinition } from '@kbn/embeddable-plugin/common';
|
||||||
import type { MapEmbeddablePersistableState } from './types';
|
import type { MapEmbeddablePersistableState } from './types';
|
||||||
import type { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
import { extractReferences, injectReferences } from '../migrations/references';
|
import { extractReferences, injectReferences } from '../migrations/references';
|
||||||
|
|
||||||
export const inject: EmbeddableRegistryDefinition['inject'] = (state, references) => {
|
export const inject: EmbeddableRegistryDefinition['inject'] = (state, references) => {
|
||||||
|
@ -23,7 +23,7 @@ export const inject: EmbeddableRegistryDefinition['inject'] = (state, references
|
||||||
// run embeddable state through extract logic to ensure any state with hard coded ids is replace with refNames
|
// run embeddable state through extract logic to ensure any state with hard coded ids is replace with refNames
|
||||||
// refName generation will produce consistent values allowing inject logic to then replace refNames with current ids.
|
// refName generation will produce consistent values allowing inject logic to then replace refNames with current ids.
|
||||||
const { attributes: attributesWithNoHardCodedIds } = extractReferences({
|
const { attributes: attributesWithNoHardCodedIds } = extractReferences({
|
||||||
attributes: typedState.attributes as MapSavedObjectAttributes,
|
attributes: typedState.attributes as MapAttributes,
|
||||||
});
|
});
|
||||||
|
|
||||||
const { attributes: attributesWithInjectedIds } = injectReferences({
|
const { attributes: attributesWithInjectedIds } = injectReferences({
|
||||||
|
|
|
@ -5,18 +5,14 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
import { JoinDescriptor, LayerDescriptor, VectorLayerDescriptor } from '../descriptor_types';
|
import { JoinDescriptor, LayerDescriptor, VectorLayerDescriptor } from '../descriptor_types';
|
||||||
import { SOURCE_TYPES } from '../constants';
|
import { SOURCE_TYPES } from '../constants';
|
||||||
|
|
||||||
// enforce type property on joins. It's possible older saved-objects do not have this correctly filled in
|
// enforce type property on joins. It's possible older saved-objects do not have this correctly filled in
|
||||||
// e.g. sample-data was missing the right.type field.
|
// e.g. sample-data was missing the right.type field.
|
||||||
// This is just to be safe.
|
// This is just to be safe.
|
||||||
export function addTypeToTermJoin({
|
export function addTypeToTermJoin({ attributes }: { attributes: MapAttributes }): MapAttributes {
|
||||||
attributes,
|
|
||||||
}: {
|
|
||||||
attributes: MapSavedObjectAttributes;
|
|
||||||
}): MapSavedObjectAttributes {
|
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,7 +21,7 @@ import {
|
||||||
LayerDescriptor,
|
LayerDescriptor,
|
||||||
VectorLayerDescriptor,
|
VectorLayerDescriptor,
|
||||||
} from '../descriptor_types';
|
} from '../descriptor_types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
const GROUP_BY_DELIMITER = '_groupby_';
|
const GROUP_BY_DELIMITER = '_groupby_';
|
||||||
|
|
||||||
|
@ -53,11 +53,7 @@ function parseLegacyAggKey(legacyAggKey: string): { aggType: AGG_TYPE; aggFieldN
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function migrateJoinAggKey({
|
export function migrateJoinAggKey({ attributes }: { attributes: MapAttributes }): MapAttributes {
|
||||||
attributes,
|
|
||||||
}: {
|
|
||||||
attributes: MapSavedObjectAttributes;
|
|
||||||
}): MapSavedObjectAttributes {
|
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,16 +7,16 @@
|
||||||
|
|
||||||
import { Filter } from '@kbn/es-query';
|
import { Filter } from '@kbn/es-query';
|
||||||
import { MigrateFunction } from '@kbn/kibana-utils-plugin/common';
|
import { MigrateFunction } from '@kbn/kibana-utils-plugin/common';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
export function migrateDataPersistedState(
|
export function migrateDataPersistedState(
|
||||||
{
|
{
|
||||||
attributes,
|
attributes,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
},
|
},
|
||||||
filterMigration: MigrateFunction<Filter[], Filter[]>
|
filterMigration: MigrateFunction<Filter[], Filter[]>
|
||||||
): MapSavedObjectAttributes {
|
): MapAttributes {
|
||||||
let mapState: { filters: Filter[] } = { filters: [] };
|
let mapState: { filters: Filter[] } = { filters: [] };
|
||||||
if (attributes.mapStateJSON) {
|
if (attributes.mapStateJSON) {
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -8,16 +8,16 @@
|
||||||
import type { Serializable } from '@kbn/utility-types';
|
import type { Serializable } from '@kbn/utility-types';
|
||||||
import type { DataViewSpec } from '@kbn/data-plugin/common';
|
import type { DataViewSpec } from '@kbn/data-plugin/common';
|
||||||
import { MigrateFunction } from '@kbn/kibana-utils-plugin/common';
|
import { MigrateFunction } from '@kbn/kibana-utils-plugin/common';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
export function migrateDataViewsPersistedState(
|
export function migrateDataViewsPersistedState(
|
||||||
{
|
{
|
||||||
attributes,
|
attributes,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
},
|
},
|
||||||
migration: MigrateFunction<Serializable, Serializable>
|
migration: MigrateFunction<Serializable, Serializable>
|
||||||
): MapSavedObjectAttributes {
|
): MapAttributes {
|
||||||
let mapState: { adHocDataViews?: DataViewSpec[] } = { adHocDataViews: [] };
|
let mapState: { adHocDataViews?: DataViewSpec[] } = { adHocDataViews: [] };
|
||||||
if (attributes.mapStateJSON) {
|
if (attributes.mapStateJSON) {
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -12,7 +12,7 @@ import {
|
||||||
LayerDescriptor,
|
LayerDescriptor,
|
||||||
VectorStyleDescriptor,
|
VectorStyleDescriptor,
|
||||||
} from '../descriptor_types';
|
} from '../descriptor_types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
const COLOR_STYLES = [
|
const COLOR_STYLES = [
|
||||||
VECTOR_STYLES.FILL_COLOR,
|
VECTOR_STYLES.FILL_COLOR,
|
||||||
|
@ -53,8 +53,8 @@ function migrateColorProperty(
|
||||||
export function migrateOtherCategoryColor({
|
export function migrateOtherCategoryColor({
|
||||||
attributes,
|
attributes,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
}): MapSavedObjectAttributes {
|
}): MapAttributes {
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,15 +5,11 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
import { LayerDescriptor } from '../descriptor_types';
|
import { LayerDescriptor } from '../descriptor_types';
|
||||||
|
|
||||||
// In 7.14, attribution added to the layer_descriptor. Prior to 7.14, 2 sources, WMS and TMS, had attribution on source descriptor.
|
// In 7.14, attribution added to the layer_descriptor. Prior to 7.14, 2 sources, WMS and TMS, had attribution on source descriptor.
|
||||||
export function moveAttribution({
|
export function moveAttribution({ attributes }: { attributes: MapAttributes }): MapAttributes {
|
||||||
attributes,
|
|
||||||
}: {
|
|
||||||
attributes: MapSavedObjectAttributes;
|
|
||||||
}): MapSavedObjectAttributes {
|
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
|
|
||||||
import type { DataViewSpec } from '@kbn/data-plugin/common';
|
import type { DataViewSpec } from '@kbn/data-plugin/common';
|
||||||
import { SavedObjectReference } from '@kbn/core/types';
|
import { SavedObjectReference } from '@kbn/core/types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
import { LayerDescriptor, VectorLayerDescriptor } from '../descriptor_types';
|
import { LayerDescriptor, VectorLayerDescriptor } from '../descriptor_types';
|
||||||
|
|
||||||
interface IndexPatternReferenceDescriptor {
|
interface IndexPatternReferenceDescriptor {
|
||||||
|
@ -21,7 +21,7 @@ export function extractReferences({
|
||||||
attributes,
|
attributes,
|
||||||
references = [],
|
references = [],
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
references?: SavedObjectReference[];
|
references?: SavedObjectReference[];
|
||||||
}) {
|
}) {
|
||||||
if (!attributes.layerListJSON) {
|
if (!attributes.layerListJSON) {
|
||||||
|
@ -119,7 +119,7 @@ export function injectReferences({
|
||||||
attributes,
|
attributes,
|
||||||
references,
|
references,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
references: SavedObjectReference[];
|
references: SavedObjectReference[];
|
||||||
}) {
|
}) {
|
||||||
if (!attributes.layerListJSON) {
|
if (!attributes.layerListJSON) {
|
||||||
|
|
|
@ -5,13 +5,13 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
export function removeBoundsFromSavedObject({
|
export function removeBoundsFromSavedObject({
|
||||||
attributes,
|
attributes,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
}): MapSavedObjectAttributes {
|
}): MapAttributes {
|
||||||
const newAttributes = { ...attributes };
|
const newAttributes = { ...attributes };
|
||||||
// @ts-expect-error
|
// @ts-expect-error
|
||||||
// This removes an unused parameter from pre 7.8=< saved objects
|
// This removes an unused parameter from pre 7.8=< saved objects
|
||||||
|
|
|
@ -7,18 +7,14 @@
|
||||||
|
|
||||||
import { LAYER_TYPE } from '../constants';
|
import { LAYER_TYPE } from '../constants';
|
||||||
import { LayerDescriptor } from '../descriptor_types';
|
import { LayerDescriptor } from '../descriptor_types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
// LAYER_TYPE constants renamed in 8.1 to provide more distinguishable names that better refect layer.
|
// LAYER_TYPE constants renamed in 8.1 to provide more distinguishable names that better refect layer.
|
||||||
// TILED_VECTOR replaced with MVT_VECTOR
|
// TILED_VECTOR replaced with MVT_VECTOR
|
||||||
// VECTOR_TILE replaced with EMS_VECTOR_TILE
|
// VECTOR_TILE replaced with EMS_VECTOR_TILE
|
||||||
// VECTOR replaced with GEOJSON_VECTOR
|
// VECTOR replaced with GEOJSON_VECTOR
|
||||||
// TILE replaced with RASTER_TILE
|
// TILE replaced with RASTER_TILE
|
||||||
export function renameLayerTypes({
|
export function renameLayerTypes({ attributes }: { attributes: MapAttributes }): MapAttributes {
|
||||||
attributes,
|
|
||||||
}: {
|
|
||||||
attributes: MapSavedObjectAttributes;
|
|
||||||
}): MapSavedObjectAttributes {
|
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,7 +8,7 @@
|
||||||
import _ from 'lodash';
|
import _ from 'lodash';
|
||||||
import { SOURCE_TYPES, SCALING_TYPES } from '../constants';
|
import { SOURCE_TYPES, SCALING_TYPES } from '../constants';
|
||||||
import { LayerDescriptor, ESSearchSourceDescriptor } from '../descriptor_types';
|
import { LayerDescriptor, ESSearchSourceDescriptor } from '../descriptor_types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
function isEsDocumentSource(layerDescriptor: LayerDescriptor) {
|
function isEsDocumentSource(layerDescriptor: LayerDescriptor) {
|
||||||
const sourceType = _.get(layerDescriptor, 'sourceDescriptor.type');
|
const sourceType = _.get(layerDescriptor, 'sourceDescriptor.type');
|
||||||
|
@ -18,8 +18,8 @@ function isEsDocumentSource(layerDescriptor: LayerDescriptor) {
|
||||||
export function migrateUseTopHitsToScalingType({
|
export function migrateUseTopHitsToScalingType({
|
||||||
attributes,
|
attributes,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
}): MapSavedObjectAttributes {
|
}): MapAttributes {
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,13 +5,13 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
export function setDefaultAutoFitToBounds({
|
export function setDefaultAutoFitToBounds({
|
||||||
attributes,
|
attributes,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
}): MapSavedObjectAttributes {
|
}): MapAttributes {
|
||||||
if (!attributes || !attributes.mapStateJSON) {
|
if (!attributes || !attributes.mapStateJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
|
|
||||||
import { SOURCE_TYPES } from '../constants';
|
import { SOURCE_TYPES } from '../constants';
|
||||||
import { LayerDescriptor, EMSTMSSourceDescriptor } from '../descriptor_types';
|
import { LayerDescriptor, EMSTMSSourceDescriptor } from '../descriptor_types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
// LightModeDefault added to EMSTMSSourceDescriptor in 8.0.0
|
// LightModeDefault added to EMSTMSSourceDescriptor in 8.0.0
|
||||||
// to avoid changing auto selected light mode tiles for maps created < 8.0.0
|
// to avoid changing auto selected light mode tiles for maps created < 8.0.0
|
||||||
|
@ -16,8 +16,8 @@ import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
||||||
export function setEmsTmsDefaultModes({
|
export function setEmsTmsDefaultModes({
|
||||||
attributes,
|
attributes,
|
||||||
}: {
|
}: {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
}): MapSavedObjectAttributes {
|
}): MapAttributes {
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return attributes;
|
return attributes;
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,7 +8,7 @@
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
import mapSavedObjects from './test_resources/sample_map_saved_objects.json';
|
import mapSavedObjects from './test_resources/sample_map_saved_objects.json';
|
||||||
import { LayerStatsCollector } from './layer_stats_collector';
|
import { LayerStatsCollector } from './layer_stats_collector';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
const expecteds = [
|
const expecteds = [
|
||||||
{
|
{
|
||||||
|
@ -69,7 +69,7 @@ const expecteds = [
|
||||||
];
|
];
|
||||||
|
|
||||||
const testsToRun = mapSavedObjects.map(
|
const testsToRun = mapSavedObjects.map(
|
||||||
(savedObject: { attributes: MapSavedObjectAttributes }, index: number) => {
|
(savedObject: { attributes: MapAttributes }, index: number) => {
|
||||||
const { attributes } = savedObject;
|
const { attributes } = savedObject;
|
||||||
return [attributes, expecteds[index]] as const;
|
return [attributes, expecteds[index]] as const;
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,7 +19,7 @@ import {
|
||||||
LayerDescriptor,
|
LayerDescriptor,
|
||||||
VectorLayerDescriptor,
|
VectorLayerDescriptor,
|
||||||
} from '../descriptor_types';
|
} from '../descriptor_types';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
import { EMS_BASEMAP_KEYS, JOIN_KEYS, LAYER_KEYS, RESOLUTION_KEYS, SCALING_KEYS } from './types';
|
import { EMS_BASEMAP_KEYS, JOIN_KEYS, LAYER_KEYS, RESOLUTION_KEYS, SCALING_KEYS } from './types';
|
||||||
|
|
||||||
export class LayerStatsCollector {
|
export class LayerStatsCollector {
|
||||||
|
@ -34,7 +34,7 @@ export class LayerStatsCollector {
|
||||||
private _layerTypeCounts: { [key: string]: number } = {};
|
private _layerTypeCounts: { [key: string]: number } = {};
|
||||||
private _sourceIds: Set<string> = new Set();
|
private _sourceIds: Set<string> = new Set();
|
||||||
|
|
||||||
constructor(attributes: MapSavedObjectAttributes) {
|
constructor(attributes: MapAttributes) {
|
||||||
if (!attributes || !attributes.layerListJSON) {
|
if (!attributes || !attributes.layerListJSON) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,7 +8,7 @@
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
import mapSavedObjects from './test_resources/sample_map_saved_objects.json';
|
import mapSavedObjects from './test_resources/sample_map_saved_objects.json';
|
||||||
import { MapSettingsCollector } from './map_settings_collector';
|
import { MapSettingsCollector } from './map_settings_collector';
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
|
|
||||||
const expecteds = [
|
const expecteds = [
|
||||||
{
|
{
|
||||||
|
@ -30,7 +30,7 @@ const expecteds = [
|
||||||
];
|
];
|
||||||
|
|
||||||
const testsToRun = mapSavedObjects.map(
|
const testsToRun = mapSavedObjects.map(
|
||||||
(savedObject: { attributes: MapSavedObjectAttributes }, index: number) => {
|
(savedObject: { attributes: MapAttributes }, index: number) => {
|
||||||
const { attributes } = savedObject;
|
const { attributes } = savedObject;
|
||||||
return [attributes, expecteds[index]] as const;
|
return [attributes, expecteds[index]] as const;
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,13 +5,13 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { MapSavedObjectAttributes } from '../map_saved_object_type';
|
import type { MapAttributes } from '../content_management';
|
||||||
import { MapSettings } from '../descriptor_types';
|
import { MapSettings } from '../descriptor_types';
|
||||||
|
|
||||||
export class MapSettingsCollector {
|
export class MapSettingsCollector {
|
||||||
private _customIconsCount: number = 0;
|
private _customIconsCount: number = 0;
|
||||||
|
|
||||||
constructor(attributes: MapSavedObjectAttributes) {
|
constructor(attributes: MapAttributes) {
|
||||||
if (!attributes || !attributes.mapStateJSON) {
|
if (!attributes || !attributes.mapStateJSON) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
|
@ -29,7 +29,8 @@
|
||||||
"mapsEms",
|
"mapsEms",
|
||||||
"savedObjects",
|
"savedObjects",
|
||||||
"share",
|
"share",
|
||||||
"presentationUtil"
|
"presentationUtil",
|
||||||
|
"contentManagement"
|
||||||
],
|
],
|
||||||
"optionalPlugins": [
|
"optionalPlugins": [
|
||||||
"cloud",
|
"cloud",
|
||||||
|
|
|
@ -0,0 +1,67 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
import { i18n } from '@kbn/i18n';
|
||||||
|
import { OverlayStart } from '@kbn/core/public';
|
||||||
|
|
||||||
|
import { mapsClient } from './maps_client';
|
||||||
|
|
||||||
|
const rejectErrorMessage = i18n.translate('xpack.maps.saveDuplicateRejectedDescription', {
|
||||||
|
defaultMessage: 'Save with duplicate title confirmation was rejected',
|
||||||
|
});
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
title: string;
|
||||||
|
id?: string;
|
||||||
|
getDisplayName: () => string;
|
||||||
|
onTitleDuplicate: () => void;
|
||||||
|
lastSavedTitle: string;
|
||||||
|
copyOnSave: boolean;
|
||||||
|
isTitleDuplicateConfirmed: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface Context {
|
||||||
|
overlays: OverlayStart;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const checkForDuplicateTitle = async (
|
||||||
|
{
|
||||||
|
id,
|
||||||
|
title,
|
||||||
|
lastSavedTitle,
|
||||||
|
copyOnSave,
|
||||||
|
isTitleDuplicateConfirmed,
|
||||||
|
getDisplayName,
|
||||||
|
onTitleDuplicate,
|
||||||
|
}: Props,
|
||||||
|
{ overlays }: Context
|
||||||
|
) => {
|
||||||
|
if (isTitleDuplicateConfirmed) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (title === lastSavedTitle && !copyOnSave) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
const { hits } = await mapsClient.search(
|
||||||
|
{
|
||||||
|
text: `"${title}"`,
|
||||||
|
limit: 10,
|
||||||
|
},
|
||||||
|
{ onlyTitle: true }
|
||||||
|
);
|
||||||
|
|
||||||
|
const existing = hits.find((obj) => obj.attributes.title.toLowerCase() === title.toLowerCase());
|
||||||
|
|
||||||
|
if (!existing || existing.id === id) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
onTitleDuplicate();
|
||||||
|
return Promise.reject(new Error(rejectErrorMessage));
|
||||||
|
};
|
10
x-pack/plugins/maps/public/content_management/index.ts
Normal file
10
x-pack/plugins/maps/public/content_management/index.ts
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
export { mapsClient } from './maps_client';
|
||||||
|
|
||||||
|
export { checkForDuplicateTitle } from './duplicate_title_check';
|
71
x-pack/plugins/maps/public/content_management/maps_client.ts
Normal file
71
x-pack/plugins/maps/public/content_management/maps_client.ts
Normal file
|
@ -0,0 +1,71 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
import type { SearchQuery } from '@kbn/content-management-plugin/common';
|
||||||
|
|
||||||
|
import type {
|
||||||
|
MapGetIn,
|
||||||
|
MapGetOut,
|
||||||
|
MapCreateIn,
|
||||||
|
MapCreateOut,
|
||||||
|
MapUpdateIn,
|
||||||
|
MapUpdateOut,
|
||||||
|
MapDeleteIn,
|
||||||
|
MapDeleteOut,
|
||||||
|
MapSearchIn,
|
||||||
|
MapSearchOut,
|
||||||
|
MapSearchOptions,
|
||||||
|
} from '../../common/content_management';
|
||||||
|
import { getContentManagement } from '../kibana_services';
|
||||||
|
|
||||||
|
const get = async (id: string) => {
|
||||||
|
return getContentManagement().client.get<MapGetIn, MapGetOut>({
|
||||||
|
contentTypeId: 'map',
|
||||||
|
id,
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const create = async ({ data, options }: Omit<MapCreateIn, 'contentTypeId'>) => {
|
||||||
|
const res = await getContentManagement().client.create<MapCreateIn, MapCreateOut>({
|
||||||
|
contentTypeId: 'map',
|
||||||
|
data,
|
||||||
|
options,
|
||||||
|
});
|
||||||
|
return res;
|
||||||
|
};
|
||||||
|
|
||||||
|
const update = async ({ id, data, options }: Omit<MapUpdateIn, 'contentTypeId'>) => {
|
||||||
|
const res = await getContentManagement().client.update<MapUpdateIn, MapUpdateOut>({
|
||||||
|
contentTypeId: 'map',
|
||||||
|
id,
|
||||||
|
data,
|
||||||
|
options,
|
||||||
|
});
|
||||||
|
return res;
|
||||||
|
};
|
||||||
|
|
||||||
|
const deleteMap = async (id: string) => {
|
||||||
|
await getContentManagement().client.delete<MapDeleteIn, MapDeleteOut>({
|
||||||
|
contentTypeId: 'map',
|
||||||
|
id,
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const search = async (query: SearchQuery = {}, options?: MapSearchOptions) => {
|
||||||
|
return getContentManagement().client.search<MapSearchIn, MapSearchOut>({
|
||||||
|
contentTypeId: 'map',
|
||||||
|
query,
|
||||||
|
options,
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
export const mapsClient = {
|
||||||
|
get,
|
||||||
|
create,
|
||||||
|
update,
|
||||||
|
delete: deleteMap,
|
||||||
|
search,
|
||||||
|
};
|
|
@ -11,7 +11,7 @@ import { getControlledBy, MapEmbeddable } from './map_embeddable';
|
||||||
import { buildExistsFilter, disableFilter, pinFilter, toggleFilterNegated } from '@kbn/es-query';
|
import { buildExistsFilter, disableFilter, pinFilter, toggleFilterNegated } from '@kbn/es-query';
|
||||||
import type { DataViewFieldBase, DataViewBase } from '@kbn/es-query';
|
import type { DataViewFieldBase, DataViewBase } from '@kbn/es-query';
|
||||||
import { MapEmbeddableConfig, MapEmbeddableInput } from './types';
|
import { MapEmbeddableConfig, MapEmbeddableInput } from './types';
|
||||||
import { MapSavedObjectAttributes } from '../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../common/content_management';
|
||||||
|
|
||||||
jest.mock('../kibana_services', () => {
|
jest.mock('../kibana_services', () => {
|
||||||
return {
|
return {
|
||||||
|
@ -66,7 +66,7 @@ jest.mock('../routes/map_page', () => {
|
||||||
class MockSavedMap {
|
class MockSavedMap {
|
||||||
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
||||||
private _store = require('../reducers/store').createMapStore();
|
private _store = require('../reducers/store').createMapStore();
|
||||||
private _attributes: MapSavedObjectAttributes = {
|
private _attributes: MapAttributes = {
|
||||||
title: 'myMap',
|
title: 'myMap',
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -15,7 +15,7 @@ import {
|
||||||
} from '@kbn/embeddable-plugin/public';
|
} from '@kbn/embeddable-plugin/public';
|
||||||
import type { Filter, Query, TimeRange } from '@kbn/es-query';
|
import type { Filter, Query, TimeRange } from '@kbn/es-query';
|
||||||
import { MapCenterAndZoom, MapExtent, MapSettings } from '../../common/descriptor_types';
|
import { MapCenterAndZoom, MapExtent, MapSettings } from '../../common/descriptor_types';
|
||||||
import { MapSavedObjectAttributes } from '../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../common/content_management';
|
||||||
|
|
||||||
export interface MapEmbeddableConfig {
|
export interface MapEmbeddableConfig {
|
||||||
editable: boolean;
|
editable: boolean;
|
||||||
|
@ -37,7 +37,7 @@ interface MapEmbeddableState {
|
||||||
isMovementSynchronized?: boolean;
|
isMovementSynchronized?: boolean;
|
||||||
}
|
}
|
||||||
export type MapByValueInput = {
|
export type MapByValueInput = {
|
||||||
attributes: MapSavedObjectAttributes;
|
attributes: MapAttributes;
|
||||||
} & EmbeddableInput &
|
} & EmbeddableInput &
|
||||||
MapEmbeddableState;
|
MapEmbeddableState;
|
||||||
export type MapByReferenceInput = SavedObjectEmbeddableInput & MapEmbeddableState;
|
export type MapByReferenceInput = SavedObjectEmbeddableInput & MapEmbeddableState;
|
||||||
|
|
|
@ -44,7 +44,6 @@ export const getHttp = () => coreStart.http;
|
||||||
export const getExecutionContextService = () => coreStart.executionContext;
|
export const getExecutionContextService = () => coreStart.executionContext;
|
||||||
export const getTimeFilter = () => pluginsStart.data.query.timefilter.timefilter;
|
export const getTimeFilter = () => pluginsStart.data.query.timefilter.timefilter;
|
||||||
export const getToasts = () => coreStart.notifications.toasts;
|
export const getToasts = () => coreStart.notifications.toasts;
|
||||||
export const getSavedObjectsClient = () => coreStart.savedObjects.client;
|
|
||||||
export const getCoreChrome = () => coreStart.chrome;
|
export const getCoreChrome = () => coreStart.chrome;
|
||||||
export const getDevToolsCapabilities = () => coreStart.application.capabilities.dev_tools;
|
export const getDevToolsCapabilities = () => coreStart.application.capabilities.dev_tools;
|
||||||
export const getMapsCapabilities = () => coreStart.application.capabilities.maps;
|
export const getMapsCapabilities = () => coreStart.application.capabilities.maps;
|
||||||
|
@ -68,6 +67,7 @@ export const getSpacesApi = () => pluginsStart.spaces;
|
||||||
export const getTheme = () => coreStart.theme;
|
export const getTheme = () => coreStart.theme;
|
||||||
export const getApplication = () => coreStart.application;
|
export const getApplication = () => coreStart.application;
|
||||||
export const getUsageCollection = () => pluginsStart.usageCollection;
|
export const getUsageCollection = () => pluginsStart.usageCollection;
|
||||||
|
export const getContentManagement = () => pluginsStart.contentManagement;
|
||||||
export const isScreenshotMode = () => {
|
export const isScreenshotMode = () => {
|
||||||
return pluginsStart.screenshotMode ? pluginsStart.screenshotMode.isScreenshotMode() : false;
|
return pluginsStart.screenshotMode ? pluginsStart.screenshotMode.isScreenshotMode() : false;
|
||||||
};
|
};
|
||||||
|
|
|
@ -8,12 +8,13 @@
|
||||||
import { SavedObjectReference } from '@kbn/core/types';
|
import { SavedObjectReference } from '@kbn/core/types';
|
||||||
import type { ResolvedSimpleSavedObject } from '@kbn/core/public';
|
import type { ResolvedSimpleSavedObject } from '@kbn/core/public';
|
||||||
import { AttributeService } from '@kbn/embeddable-plugin/public';
|
import { AttributeService } from '@kbn/embeddable-plugin/public';
|
||||||
import { checkForDuplicateTitle, OnSaveProps } from '@kbn/saved-objects-plugin/public';
|
import type { OnSaveProps } from '@kbn/saved-objects-plugin/public';
|
||||||
import { MapSavedObjectAttributes } from '../common/map_saved_object_type';
|
import type { MapAttributes } from '../common/content_management';
|
||||||
import { MAP_SAVED_OBJECT_TYPE } from '../common/constants';
|
import { MAP_SAVED_OBJECT_TYPE } from '../common/constants';
|
||||||
import { getMapEmbeddableDisplayName } from '../common/i18n_getters';
|
import { getMapEmbeddableDisplayName } from '../common/i18n_getters';
|
||||||
import { getCoreOverlays, getEmbeddableService, getSavedObjectsClient } from './kibana_services';
|
import { getCoreOverlays, getEmbeddableService } from './kibana_services';
|
||||||
import { extractReferences, injectReferences } from '../common/migrations/references';
|
import { extractReferences, injectReferences } from '../common/migrations/references';
|
||||||
|
import { mapsClient, checkForDuplicateTitle } from './content_management';
|
||||||
import { MapByValueInput, MapByReferenceInput } from './embeddable/types';
|
import { MapByValueInput, MapByReferenceInput } from './embeddable/types';
|
||||||
|
|
||||||
export interface SharingSavedObjectProps {
|
export interface SharingSavedObjectProps {
|
||||||
|
@ -23,7 +24,7 @@ export interface SharingSavedObjectProps {
|
||||||
sourceId?: string;
|
sourceId?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
type MapDoc = MapSavedObjectAttributes & {
|
type MapDoc = MapAttributes & {
|
||||||
references?: SavedObjectReference[];
|
references?: SavedObjectReference[];
|
||||||
};
|
};
|
||||||
export interface MapUnwrapMetaInfo {
|
export interface MapUnwrapMetaInfo {
|
||||||
|
@ -62,19 +63,12 @@ export function getMapAttributeService(): MapAttributeService {
|
||||||
references: savedObjectClientReferences,
|
references: savedObjectClientReferences,
|
||||||
});
|
});
|
||||||
|
|
||||||
const savedObject = await (savedObjectId
|
const {
|
||||||
? getSavedObjectsClient().update<MapSavedObjectAttributes>(
|
item: { id },
|
||||||
MAP_SAVED_OBJECT_TYPE,
|
} = await (savedObjectId
|
||||||
savedObjectId,
|
? mapsClient.update({ id: savedObjectId, data: updatedAttributes, options: { references } })
|
||||||
updatedAttributes,
|
: mapsClient.create({ data: updatedAttributes, options: { references } }));
|
||||||
{ references }
|
return { id };
|
||||||
)
|
|
||||||
: getSavedObjectsClient().create<MapSavedObjectAttributes>(
|
|
||||||
MAP_SAVED_OBJECT_TYPE,
|
|
||||||
updatedAttributes,
|
|
||||||
{ references }
|
|
||||||
));
|
|
||||||
return { id: savedObject.id };
|
|
||||||
},
|
},
|
||||||
unwrapMethod: async (
|
unwrapMethod: async (
|
||||||
savedObjectId: string
|
savedObjectId: string
|
||||||
|
@ -83,14 +77,9 @@ export function getMapAttributeService(): MapAttributeService {
|
||||||
metaInfo: MapUnwrapMetaInfo;
|
metaInfo: MapUnwrapMetaInfo;
|
||||||
}> => {
|
}> => {
|
||||||
const {
|
const {
|
||||||
saved_object: savedObject,
|
item: savedObject,
|
||||||
outcome,
|
meta: { outcome, aliasPurpose, aliasTargetId },
|
||||||
alias_target_id: aliasTargetId,
|
} = await mapsClient.get(savedObjectId);
|
||||||
alias_purpose: aliasPurpose,
|
|
||||||
} = await getSavedObjectsClient().resolve<MapSavedObjectAttributes>(
|
|
||||||
MAP_SAVED_OBJECT_TYPE,
|
|
||||||
savedObjectId
|
|
||||||
);
|
|
||||||
|
|
||||||
if (savedObject.error) {
|
if (savedObject.error) {
|
||||||
throw savedObject.error;
|
throw savedObject.error;
|
||||||
|
@ -118,13 +107,11 @@ export function getMapAttributeService(): MapAttributeService {
|
||||||
title: props.newTitle,
|
title: props.newTitle,
|
||||||
copyOnSave: false,
|
copyOnSave: false,
|
||||||
lastSavedTitle: '',
|
lastSavedTitle: '',
|
||||||
getEsType: () => MAP_SAVED_OBJECT_TYPE,
|
isTitleDuplicateConfirmed: props.isTitleDuplicateConfirmed,
|
||||||
getDisplayName: getMapEmbeddableDisplayName,
|
getDisplayName: getMapEmbeddableDisplayName,
|
||||||
|
onTitleDuplicate: props.onTitleDuplicate,
|
||||||
},
|
},
|
||||||
props.isTitleDuplicateConfirmed,
|
|
||||||
props.onTitleDuplicate,
|
|
||||||
{
|
{
|
||||||
savedObjectsClient: getSavedObjectsClient(),
|
|
||||||
overlays: getCoreOverlays(),
|
overlays: getCoreOverlays(),
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
|
@ -7,8 +7,7 @@
|
||||||
|
|
||||||
import { i18n } from '@kbn/i18n';
|
import { i18n } from '@kbn/i18n';
|
||||||
import type { VisualizationsSetup, VisualizationStage } from '@kbn/visualizations-plugin/public';
|
import type { VisualizationsSetup, VisualizationStage } from '@kbn/visualizations-plugin/public';
|
||||||
import type { SimpleSavedObject } from '@kbn/core/public';
|
import type { MapItem } from '../common/content_management';
|
||||||
import type { MapSavedObjectAttributes } from '../common/map_saved_object_type';
|
|
||||||
import {
|
import {
|
||||||
APP_ID,
|
APP_ID,
|
||||||
APP_ICON,
|
APP_ICON,
|
||||||
|
@ -37,9 +36,8 @@ export function getMapsVisTypeAlias(visualizations: VisualizationsSetup) {
|
||||||
visualizations: {
|
visualizations: {
|
||||||
docTypes: [MAP_SAVED_OBJECT_TYPE],
|
docTypes: [MAP_SAVED_OBJECT_TYPE],
|
||||||
searchFields: ['title^3'],
|
searchFields: ['title^3'],
|
||||||
toListItem(savedObject: SimpleSavedObject) {
|
toListItem(mapItem: MapItem) {
|
||||||
const { id, type, updatedAt, attributes } =
|
const { id, type, updatedAt, attributes } = mapItem;
|
||||||
savedObject as SimpleSavedObject<MapSavedObjectAttributes>;
|
|
||||||
const { title, description } = attributes;
|
const { title, description } = attributes;
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|
|
@ -33,7 +33,6 @@ import type { DataPublicPluginSetup, DataPublicPluginStart } from '@kbn/data-plu
|
||||||
import type { UnifiedSearchPublicPluginStart } from '@kbn/unified-search-plugin/public';
|
import type { UnifiedSearchPublicPluginStart } from '@kbn/unified-search-plugin/public';
|
||||||
import type { LicensingPluginSetup, LicensingPluginStart } from '@kbn/licensing-plugin/public';
|
import type { LicensingPluginSetup, LicensingPluginStart } from '@kbn/licensing-plugin/public';
|
||||||
import type { FileUploadPluginStart } from '@kbn/file-upload-plugin/public';
|
import type { FileUploadPluginStart } from '@kbn/file-upload-plugin/public';
|
||||||
import type { SavedObjectsStart } from '@kbn/saved-objects-plugin/public';
|
|
||||||
import type { PresentationUtilPluginStart } from '@kbn/presentation-util-plugin/public';
|
import type { PresentationUtilPluginStart } from '@kbn/presentation-util-plugin/public';
|
||||||
import type { SavedObjectTaggingPluginStart } from '@kbn/saved-objects-tagging-plugin/public';
|
import type { SavedObjectTaggingPluginStart } from '@kbn/saved-objects-tagging-plugin/public';
|
||||||
import type { ChartsPluginStart } from '@kbn/charts-plugin/public';
|
import type { ChartsPluginStart } from '@kbn/charts-plugin/public';
|
||||||
|
@ -42,6 +41,11 @@ import type { SpacesPluginStart } from '@kbn/spaces-plugin/public';
|
||||||
import type { CloudSetup } from '@kbn/cloud-plugin/public';
|
import type { CloudSetup } from '@kbn/cloud-plugin/public';
|
||||||
import type { LensPublicSetup } from '@kbn/lens-plugin/public';
|
import type { LensPublicSetup } from '@kbn/lens-plugin/public';
|
||||||
import { ScreenshotModePluginSetup } from '@kbn/screenshot-mode-plugin/public';
|
import { ScreenshotModePluginSetup } from '@kbn/screenshot-mode-plugin/public';
|
||||||
|
import type {
|
||||||
|
ContentManagementPublicSetup,
|
||||||
|
ContentManagementPublicStart,
|
||||||
|
} from '@kbn/content-management-plugin/public';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
createRegionMapFn,
|
createRegionMapFn,
|
||||||
GEOHASH_GRID,
|
GEOHASH_GRID,
|
||||||
|
@ -80,6 +84,7 @@ import { setIsCloudEnabled, setMapAppConfig, setStartServices } from './kibana_s
|
||||||
import { MapInspectorView, VectorTileInspectorView } from './inspector';
|
import { MapInspectorView, VectorTileInspectorView } from './inspector';
|
||||||
|
|
||||||
import { setupLensChoroplethChart } from './lens';
|
import { setupLensChoroplethChart } from './lens';
|
||||||
|
import { CONTENT_ID, LATEST_VERSION } from '../common/content_management';
|
||||||
|
|
||||||
export interface MapsPluginSetupDependencies {
|
export interface MapsPluginSetupDependencies {
|
||||||
cloud?: CloudSetup;
|
cloud?: CloudSetup;
|
||||||
|
@ -94,6 +99,7 @@ export interface MapsPluginSetupDependencies {
|
||||||
licensing: LicensingPluginSetup;
|
licensing: LicensingPluginSetup;
|
||||||
usageCollection?: UsageCollectionSetup;
|
usageCollection?: UsageCollectionSetup;
|
||||||
screenshotMode?: ScreenshotModePluginSetup;
|
screenshotMode?: ScreenshotModePluginSetup;
|
||||||
|
contentManagement: ContentManagementPublicSetup;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface MapsPluginStartDependencies {
|
export interface MapsPluginStartDependencies {
|
||||||
|
@ -109,13 +115,13 @@ export interface MapsPluginStartDependencies {
|
||||||
uiActions: UiActionsStart;
|
uiActions: UiActionsStart;
|
||||||
share: SharePluginStart;
|
share: SharePluginStart;
|
||||||
visualizations: VisualizationsStart;
|
visualizations: VisualizationsStart;
|
||||||
savedObjects: SavedObjectsStart;
|
|
||||||
dashboard: DashboardStart;
|
dashboard: DashboardStart;
|
||||||
savedObjectsTagging?: SavedObjectTaggingPluginStart;
|
savedObjectsTagging?: SavedObjectTaggingPluginStart;
|
||||||
presentationUtil: PresentationUtilPluginStart;
|
presentationUtil: PresentationUtilPluginStart;
|
||||||
security?: SecurityPluginStart;
|
security?: SecurityPluginStart;
|
||||||
spaces?: SpacesPluginStart;
|
spaces?: SpacesPluginStart;
|
||||||
mapsEms: MapsEmsPluginPublicStart;
|
mapsEms: MapsEmsPluginPublicStart;
|
||||||
|
contentManagement: ContentManagementPublicStart;
|
||||||
screenshotMode?: ScreenshotModePluginSetup;
|
screenshotMode?: ScreenshotModePluginSetup;
|
||||||
usageCollection?: UsageCollectionSetup;
|
usageCollection?: UsageCollectionSetup;
|
||||||
}
|
}
|
||||||
|
@ -201,6 +207,14 @@ export class MapsPlugin
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
plugins.contentManagement.registry.register({
|
||||||
|
id: CONTENT_ID,
|
||||||
|
version: {
|
||||||
|
latest: LATEST_VERSION,
|
||||||
|
},
|
||||||
|
name: getAppTitle(),
|
||||||
|
});
|
||||||
|
|
||||||
setupLensChoroplethChart(core, plugins.expressions, plugins.lens);
|
setupLensChoroplethChart(core, plugins.expressions, plugins.lens);
|
||||||
|
|
||||||
// register wrapper around legacy tile_map and region_map visualizations
|
// register wrapper around legacy tile_map and region_map visualizations
|
||||||
|
|
|
@ -10,9 +10,10 @@ import { i18n } from '@kbn/i18n';
|
||||||
import { Redirect } from 'react-router-dom';
|
import { Redirect } from 'react-router-dom';
|
||||||
import { EmbeddableStateTransfer } from '@kbn/embeddable-plugin/public';
|
import { EmbeddableStateTransfer } from '@kbn/embeddable-plugin/public';
|
||||||
import { ScopedHistory } from '@kbn/core/public';
|
import { ScopedHistory } from '@kbn/core/public';
|
||||||
import { getSavedObjectsClient, getToasts } from '../../kibana_services';
|
import { getToasts } from '../../kibana_services';
|
||||||
import { MapsListView } from './maps_list_view';
|
import { MapsListView } from './maps_list_view';
|
||||||
import { APP_ID, MAP_SAVED_OBJECT_TYPE } from '../../../common/constants';
|
import { APP_ID } from '../../../common/constants';
|
||||||
|
import { mapsClient } from '../../content_management';
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
history: ScopedHistory;
|
history: ScopedHistory;
|
||||||
|
@ -38,13 +39,9 @@ export class LoadListAndRender extends Component<Props> {
|
||||||
|
|
||||||
async _loadMapsList() {
|
async _loadMapsList() {
|
||||||
try {
|
try {
|
||||||
const results = await getSavedObjectsClient().find({
|
const results = await mapsClient.search({ limit: 1 });
|
||||||
type: MAP_SAVED_OBJECT_TYPE,
|
|
||||||
perPage: 1,
|
|
||||||
fields: ['title'],
|
|
||||||
});
|
|
||||||
if (this._isMounted) {
|
if (this._isMounted) {
|
||||||
this.setState({ mapsLoaded: true, hasSavedMaps: !!results.savedObjects.length });
|
this.setState({ mapsLoaded: true, hasSavedMaps: !!results.hits.length });
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
if (this._isMounted) {
|
if (this._isMounted) {
|
||||||
|
|
|
@ -5,37 +5,29 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import React from 'react';
|
import React, { useCallback, memo } from 'react';
|
||||||
import { SavedObjectReference } from '@kbn/core/types';
|
|
||||||
import type { SavedObjectsFindOptionsReference, ScopedHistory } from '@kbn/core/public';
|
import type { SavedObjectsFindOptionsReference, ScopedHistory } from '@kbn/core/public';
|
||||||
import { METRIC_TYPE } from '@kbn/analytics';
|
import { METRIC_TYPE } from '@kbn/analytics';
|
||||||
import { i18n } from '@kbn/i18n';
|
import { i18n } from '@kbn/i18n';
|
||||||
import { TableListView } from '@kbn/content-management-table-list';
|
import { TableListView } from '@kbn/content-management-table-list';
|
||||||
import type { UserContentCommonSchema } from '@kbn/content-management-table-list';
|
import type { UserContentCommonSchema } from '@kbn/content-management-table-list';
|
||||||
import { SimpleSavedObject } from '@kbn/core-saved-objects-api-browser';
|
|
||||||
import { APP_ID, getEditPath, MAP_PATH, MAP_SAVED_OBJECT_TYPE } from '../../../common/constants';
|
import type { MapItem } from '../../../common/content_management';
|
||||||
|
import { APP_ID, getEditPath, MAP_PATH } from '../../../common/constants';
|
||||||
import {
|
import {
|
||||||
getMapsCapabilities,
|
getMapsCapabilities,
|
||||||
getCoreChrome,
|
getCoreChrome,
|
||||||
getExecutionContextService,
|
getExecutionContextService,
|
||||||
getNavigateToApp,
|
getNavigateToApp,
|
||||||
getSavedObjectsClient,
|
|
||||||
getUiSettings,
|
getUiSettings,
|
||||||
getUsageCollection,
|
getUsageCollection,
|
||||||
} from '../../kibana_services';
|
} from '../../kibana_services';
|
||||||
import { getAppTitle } from '../../../common/i18n_getters';
|
import { getAppTitle } from '../../../common/i18n_getters';
|
||||||
import { MapSavedObjectAttributes } from '../../../common/map_saved_object_type';
|
import { mapsClient } from '../../content_management';
|
||||||
|
|
||||||
const SAVED_OBJECTS_LIMIT_SETTING = 'savedObjects:listingLimit';
|
const SAVED_OBJECTS_LIMIT_SETTING = 'savedObjects:listingLimit';
|
||||||
const SAVED_OBJECTS_PER_PAGE_SETTING = 'savedObjects:perPage';
|
const SAVED_OBJECTS_PER_PAGE_SETTING = 'savedObjects:perPage';
|
||||||
|
|
||||||
interface MapItem {
|
|
||||||
id: string;
|
|
||||||
title: string;
|
|
||||||
description?: string;
|
|
||||||
references?: SavedObjectReference[];
|
|
||||||
}
|
|
||||||
|
|
||||||
interface MapUserContent extends UserContentCommonSchema {
|
interface MapUserContent extends UserContentCommonSchema {
|
||||||
type: string;
|
type: string;
|
||||||
attributes: {
|
attributes: {
|
||||||
|
@ -51,59 +43,26 @@ function navigateToNewMap() {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
const toTableListViewSavedObject = (
|
const toTableListViewSavedObject = (mapItem: MapItem): MapUserContent => {
|
||||||
savedObject: SimpleSavedObject<MapSavedObjectAttributes>
|
|
||||||
): MapUserContent => {
|
|
||||||
return {
|
return {
|
||||||
...savedObject,
|
...mapItem,
|
||||||
updatedAt: savedObject.updatedAt!,
|
updatedAt: mapItem.updatedAt!,
|
||||||
attributes: {
|
attributes: {
|
||||||
...savedObject.attributes,
|
...mapItem.attributes,
|
||||||
title: savedObject.attributes.title ?? '',
|
title: mapItem.attributes.title ?? '',
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
async function findMaps(
|
async function deleteMaps(items: Array<{ id: string }>) {
|
||||||
searchTerm: string,
|
await Promise.all(items.map(({ id }) => mapsClient.delete(id)));
|
||||||
{
|
|
||||||
references,
|
|
||||||
referencesToExclude,
|
|
||||||
}: {
|
|
||||||
references?: SavedObjectsFindOptionsReference[];
|
|
||||||
referencesToExclude?: SavedObjectsFindOptionsReference[];
|
|
||||||
} = {}
|
|
||||||
) {
|
|
||||||
const resp = await getSavedObjectsClient().find<MapSavedObjectAttributes>({
|
|
||||||
type: MAP_SAVED_OBJECT_TYPE,
|
|
||||||
search: searchTerm ? `${searchTerm}*` : undefined,
|
|
||||||
perPage: getUiSettings().get(SAVED_OBJECTS_LIMIT_SETTING),
|
|
||||||
page: 1,
|
|
||||||
searchFields: ['title^3', 'description'],
|
|
||||||
defaultSearchOperator: 'AND',
|
|
||||||
fields: ['description', 'title'],
|
|
||||||
hasReference: references,
|
|
||||||
hasNoReference: referencesToExclude,
|
|
||||||
});
|
|
||||||
|
|
||||||
return {
|
|
||||||
total: resp.total,
|
|
||||||
hits: resp.savedObjects.map(toTableListViewSavedObject),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
async function deleteMaps(items: object[]) {
|
|
||||||
const deletions = items.map((item) => {
|
|
||||||
return getSavedObjectsClient().delete(MAP_SAVED_OBJECT_TYPE, (item as MapItem).id);
|
|
||||||
});
|
|
||||||
await Promise.all(deletions);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
history: ScopedHistory;
|
history: ScopedHistory;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function MapsListView(props: Props) {
|
function MapsListViewComp({ history }: Props) {
|
||||||
getExecutionContextService().set({
|
getExecutionContextService().set({
|
||||||
type: 'application',
|
type: 'application',
|
||||||
name: APP_ID,
|
name: APP_ID,
|
||||||
|
@ -117,6 +76,42 @@ export function MapsListView(props: Props) {
|
||||||
getCoreChrome().docTitle.change(getAppTitle());
|
getCoreChrome().docTitle.change(getAppTitle());
|
||||||
getCoreChrome().setBreadcrumbs([{ text: getAppTitle() }]);
|
getCoreChrome().setBreadcrumbs([{ text: getAppTitle() }]);
|
||||||
|
|
||||||
|
const findMaps = useCallback(
|
||||||
|
async (
|
||||||
|
searchTerm: string,
|
||||||
|
{
|
||||||
|
references = [],
|
||||||
|
referencesToExclude = [],
|
||||||
|
}: {
|
||||||
|
references?: SavedObjectsFindOptionsReference[];
|
||||||
|
referencesToExclude?: SavedObjectsFindOptionsReference[];
|
||||||
|
} = {}
|
||||||
|
) => {
|
||||||
|
return mapsClient
|
||||||
|
.search({
|
||||||
|
text: searchTerm ? `${searchTerm}*` : undefined,
|
||||||
|
limit: getUiSettings().get(SAVED_OBJECTS_LIMIT_SETTING),
|
||||||
|
tags: {
|
||||||
|
included: references.map(({ id }) => id),
|
||||||
|
excluded: referencesToExclude.map(({ id }) => id),
|
||||||
|
},
|
||||||
|
})
|
||||||
|
.then(({ hits, pagination: { total } }) => {
|
||||||
|
return {
|
||||||
|
total,
|
||||||
|
hits: hits.map(toTableListViewSavedObject),
|
||||||
|
};
|
||||||
|
})
|
||||||
|
.catch((e) => {
|
||||||
|
return {
|
||||||
|
total: 0,
|
||||||
|
hits: [],
|
||||||
|
};
|
||||||
|
});
|
||||||
|
},
|
||||||
|
[]
|
||||||
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<TableListView<MapUserContent>
|
<TableListView<MapUserContent>
|
||||||
id="map"
|
id="map"
|
||||||
|
@ -134,7 +129,9 @@ export function MapsListView(props: Props) {
|
||||||
defaultMessage: 'maps',
|
defaultMessage: 'maps',
|
||||||
})}
|
})}
|
||||||
tableListTitle={getAppTitle()}
|
tableListTitle={getAppTitle()}
|
||||||
onClickTitle={({ id }) => props.history.push(getEditPath(id))}
|
onClickTitle={({ id }) => history.push(getEditPath(id))}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export const MapsListView = memo(MapsListViewComp);
|
||||||
|
|
|
@ -11,7 +11,7 @@ import { i18n } from '@kbn/i18n';
|
||||||
import { EmbeddableStateTransfer } from '@kbn/embeddable-plugin/public';
|
import { EmbeddableStateTransfer } from '@kbn/embeddable-plugin/public';
|
||||||
import { ScopedHistory } from '@kbn/core/public';
|
import { ScopedHistory } from '@kbn/core/public';
|
||||||
import { OnSaveProps } from '@kbn/saved-objects-plugin/public';
|
import { OnSaveProps } from '@kbn/saved-objects-plugin/public';
|
||||||
import { MapSavedObjectAttributes } from '../../../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../../../common/content_management';
|
||||||
import { APP_ID, MAP_PATH, MAP_SAVED_OBJECT_TYPE } from '../../../../common/constants';
|
import { APP_ID, MAP_PATH, MAP_SAVED_OBJECT_TYPE } from '../../../../common/constants';
|
||||||
import { createMapStore, MapStore, MapStoreState } from '../../../reducers/store';
|
import { createMapStore, MapStore, MapStoreState } from '../../../reducers/store';
|
||||||
import { MapSettings } from '../../../../common/descriptor_types';
|
import { MapSettings } from '../../../../common/descriptor_types';
|
||||||
|
@ -71,7 +71,7 @@ function setMapSettingsFromEncodedState(settings: Partial<MapSettings>) {
|
||||||
}
|
}
|
||||||
|
|
||||||
export class SavedMap {
|
export class SavedMap {
|
||||||
private _attributes: MapSavedObjectAttributes | null = null;
|
private _attributes: MapAttributes | null = null;
|
||||||
private _sharingSavedObjectProps: SharingSavedObjectProps | null = null;
|
private _sharingSavedObjectProps: SharingSavedObjectProps | null = null;
|
||||||
private readonly _defaultLayers: LayerDescriptor[];
|
private readonly _defaultLayers: LayerDescriptor[];
|
||||||
private readonly _embeddableId?: string;
|
private readonly _embeddableId?: string;
|
||||||
|
@ -385,7 +385,7 @@ export class SavedMap {
|
||||||
return this._attributes.title !== undefined ? this._attributes.title : '';
|
return this._attributes.title !== undefined ? this._attributes.title : '';
|
||||||
}
|
}
|
||||||
|
|
||||||
public getAttributes(): MapSavedObjectAttributes {
|
public getAttributes(): MapAttributes {
|
||||||
if (!this._attributes) {
|
if (!this._attributes) {
|
||||||
throw new Error('Invalid usage, must await whenReady before calling getAttributes');
|
throw new Error('Invalid usage, must await whenReady before calling getAttributes');
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,6 @@ import React from 'react';
|
||||||
import { i18n } from '@kbn/i18n';
|
import { i18n } from '@kbn/i18n';
|
||||||
import { Adapters } from '@kbn/inspector-plugin/public';
|
import { Adapters } from '@kbn/inspector-plugin/public';
|
||||||
import {
|
import {
|
||||||
checkForDuplicateTitle,
|
|
||||||
SavedObjectSaveModalOrigin,
|
SavedObjectSaveModalOrigin,
|
||||||
OnSaveProps,
|
OnSaveProps,
|
||||||
showSaveModal,
|
showSaveModal,
|
||||||
|
@ -24,14 +23,13 @@ import {
|
||||||
getMapsCapabilities,
|
getMapsCapabilities,
|
||||||
getIsAllowByValueEmbeddables,
|
getIsAllowByValueEmbeddables,
|
||||||
getInspector,
|
getInspector,
|
||||||
getSavedObjectsClient,
|
|
||||||
getCoreOverlays,
|
getCoreOverlays,
|
||||||
getSavedObjectsTagging,
|
getSavedObjectsTagging,
|
||||||
getPresentationUtilContext,
|
getPresentationUtilContext,
|
||||||
} from '../../kibana_services';
|
} from '../../kibana_services';
|
||||||
import { MAP_SAVED_OBJECT_TYPE } from '../../../common/constants';
|
|
||||||
import { SavedMap } from './saved_map';
|
import { SavedMap } from './saved_map';
|
||||||
import { getMapEmbeddableDisplayName } from '../../../common/i18n_getters';
|
import { getMapEmbeddableDisplayName } from '../../../common/i18n_getters';
|
||||||
|
import { checkForDuplicateTitle } from '../../content_management';
|
||||||
|
|
||||||
const SavedObjectSaveModalDashboard = withSuspense(LazySavedObjectSaveModalDashboard);
|
const SavedObjectSaveModalDashboard = withSuspense(LazySavedObjectSaveModalDashboard);
|
||||||
|
|
||||||
|
@ -180,13 +178,11 @@ export function getTopNavConfig({
|
||||||
title: props.newTitle,
|
title: props.newTitle,
|
||||||
copyOnSave: props.newCopyOnSave,
|
copyOnSave: props.newCopyOnSave,
|
||||||
lastSavedTitle: savedMap.getSavedObjectId() ? savedMap.getTitle() : '',
|
lastSavedTitle: savedMap.getSavedObjectId() ? savedMap.getTitle() : '',
|
||||||
getEsType: () => MAP_SAVED_OBJECT_TYPE,
|
isTitleDuplicateConfirmed: props.isTitleDuplicateConfirmed,
|
||||||
getDisplayName: getMapEmbeddableDisplayName,
|
getDisplayName: getMapEmbeddableDisplayName,
|
||||||
|
onTitleDuplicate: props.onTitleDuplicate,
|
||||||
},
|
},
|
||||||
props.isTitleDuplicateConfirmed,
|
|
||||||
props.onTitleDuplicate,
|
|
||||||
{
|
{
|
||||||
savedObjectsClient: getSavedObjectsClient(),
|
|
||||||
overlays: getCoreOverlays(),
|
overlays: getCoreOverlays(),
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
8
x-pack/plugins/maps/server/content_management/index.ts
Normal file
8
x-pack/plugins/maps/server/content_management/index.ts
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
|
||||||
|
export { MapsStorage } from './maps_storage';
|
313
x-pack/plugins/maps/server/content_management/maps_storage.ts
Normal file
313
x-pack/plugins/maps/server/content_management/maps_storage.ts
Normal file
|
@ -0,0 +1,313 @@
|
||||||
|
/*
|
||||||
|
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||||
|
* or more contributor license agreements. Licensed under the Elastic License
|
||||||
|
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||||
|
* 2.0.
|
||||||
|
*/
|
||||||
|
import Boom from '@hapi/boom';
|
||||||
|
import type { SearchQuery } from '@kbn/content-management-plugin/common';
|
||||||
|
import type { ContentStorage, StorageContext } from '@kbn/content-management-plugin/server';
|
||||||
|
import type {
|
||||||
|
SavedObject,
|
||||||
|
SavedObjectReference,
|
||||||
|
SavedObjectsFindOptions,
|
||||||
|
} from '@kbn/core-saved-objects-api-server';
|
||||||
|
|
||||||
|
import { CONTENT_ID } from '../../common/content_management';
|
||||||
|
import { cmServicesDefinition } from '../../common/content_management/cm_services';
|
||||||
|
import type {
|
||||||
|
MapItem,
|
||||||
|
PartialMapItem,
|
||||||
|
MapContentType,
|
||||||
|
MapAttributes,
|
||||||
|
MapGetOut,
|
||||||
|
MapCreateIn,
|
||||||
|
MapCreateOut,
|
||||||
|
CreateOptions,
|
||||||
|
MapUpdateIn,
|
||||||
|
MapUpdateOut,
|
||||||
|
UpdateOptions,
|
||||||
|
MapDeleteOut,
|
||||||
|
MapSearchOptions,
|
||||||
|
MapSearchOut,
|
||||||
|
} from '../../common/content_management';
|
||||||
|
|
||||||
|
const savedObjectClientFromRequest = async (ctx: StorageContext) => {
|
||||||
|
if (!ctx.requestHandlerContext) {
|
||||||
|
throw new Error('Storage context.requestHandlerContext missing.');
|
||||||
|
}
|
||||||
|
|
||||||
|
const { savedObjects } = await ctx.requestHandlerContext.core;
|
||||||
|
return savedObjects.client;
|
||||||
|
};
|
||||||
|
|
||||||
|
type PartialSavedObject<T> = Omit<SavedObject<Partial<T>>, 'references'> & {
|
||||||
|
references: SavedObjectReference[] | undefined;
|
||||||
|
};
|
||||||
|
|
||||||
|
function savedObjectToMapItem(savedObject: SavedObject<MapAttributes>, partial: false): MapItem;
|
||||||
|
|
||||||
|
function savedObjectToMapItem(
|
||||||
|
savedObject: PartialSavedObject<MapAttributes>,
|
||||||
|
partial: true
|
||||||
|
): PartialMapItem;
|
||||||
|
|
||||||
|
function savedObjectToMapItem(
|
||||||
|
savedObject: SavedObject<MapAttributes> | PartialSavedObject<MapAttributes>
|
||||||
|
): MapItem | PartialMapItem {
|
||||||
|
const {
|
||||||
|
id,
|
||||||
|
type,
|
||||||
|
updated_at: updatedAt,
|
||||||
|
created_at: createdAt,
|
||||||
|
attributes: { title, description, layerListJSON, mapStateJSON, uiStateJSON },
|
||||||
|
references,
|
||||||
|
error,
|
||||||
|
namespaces,
|
||||||
|
} = savedObject;
|
||||||
|
|
||||||
|
return {
|
||||||
|
id,
|
||||||
|
type,
|
||||||
|
updatedAt,
|
||||||
|
createdAt,
|
||||||
|
attributes: {
|
||||||
|
title,
|
||||||
|
description,
|
||||||
|
layerListJSON,
|
||||||
|
mapStateJSON,
|
||||||
|
uiStateJSON,
|
||||||
|
},
|
||||||
|
references,
|
||||||
|
error,
|
||||||
|
namespaces,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
const SO_TYPE: MapContentType = 'map';
|
||||||
|
|
||||||
|
export class MapsStorage implements ContentStorage<MapItem, PartialMapItem> {
|
||||||
|
constructor() {}
|
||||||
|
|
||||||
|
async get(ctx: StorageContext, id: string): Promise<MapGetOut> {
|
||||||
|
const {
|
||||||
|
utils: { getTransforms },
|
||||||
|
version: { request: requestVersion },
|
||||||
|
} = ctx;
|
||||||
|
const transforms = getTransforms(cmServicesDefinition, requestVersion);
|
||||||
|
const soClient = await savedObjectClientFromRequest(ctx);
|
||||||
|
|
||||||
|
// Save data in DB
|
||||||
|
const {
|
||||||
|
saved_object: savedObject,
|
||||||
|
alias_purpose: aliasPurpose,
|
||||||
|
alias_target_id: aliasTargetId,
|
||||||
|
outcome,
|
||||||
|
} = await soClient.resolve<MapAttributes>(SO_TYPE, id);
|
||||||
|
|
||||||
|
const response: MapGetOut = {
|
||||||
|
item: savedObjectToMapItem(savedObject, false),
|
||||||
|
meta: {
|
||||||
|
aliasPurpose,
|
||||||
|
aliasTargetId,
|
||||||
|
outcome,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
// Validate DB response and DOWN transform to the request version
|
||||||
|
const { value, error: resultError } = transforms.get.out.result.down<MapGetOut, MapGetOut>(
|
||||||
|
response
|
||||||
|
);
|
||||||
|
|
||||||
|
if (resultError) {
|
||||||
|
throw Boom.badRequest(`Invalid response. ${resultError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
async bulkGet(): Promise<never> {
|
||||||
|
// Not implemented. Maps does not use bulkGet
|
||||||
|
throw new Error(`[bulkGet] has not been implemented. See MapsStorage class.`);
|
||||||
|
}
|
||||||
|
|
||||||
|
async create(
|
||||||
|
ctx: StorageContext,
|
||||||
|
data: MapCreateIn['data'],
|
||||||
|
options: CreateOptions
|
||||||
|
): Promise<MapCreateOut> {
|
||||||
|
const {
|
||||||
|
utils: { getTransforms },
|
||||||
|
version: { request: requestVersion },
|
||||||
|
} = ctx;
|
||||||
|
const transforms = getTransforms(cmServicesDefinition, requestVersion);
|
||||||
|
|
||||||
|
// Validate input (data & options) & UP transform them to the latest version
|
||||||
|
const { value: dataToLatest, error: dataError } = transforms.create.in.data.up<
|
||||||
|
MapAttributes,
|
||||||
|
MapAttributes
|
||||||
|
>(data);
|
||||||
|
if (dataError) {
|
||||||
|
throw Boom.badRequest(`Invalid data. ${dataError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
const { value: optionsToLatest, error: optionsError } = transforms.create.in.options.up<
|
||||||
|
CreateOptions,
|
||||||
|
CreateOptions
|
||||||
|
>(options);
|
||||||
|
if (optionsError) {
|
||||||
|
throw Boom.badRequest(`Invalid options. ${optionsError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Save data in DB
|
||||||
|
const soClient = await savedObjectClientFromRequest(ctx);
|
||||||
|
const savedObject = await soClient.create<MapAttributes>(
|
||||||
|
SO_TYPE,
|
||||||
|
dataToLatest,
|
||||||
|
optionsToLatest
|
||||||
|
);
|
||||||
|
|
||||||
|
// Validate DB response and DOWN transform to the request version
|
||||||
|
const { value, error: resultError } = transforms.create.out.result.down<
|
||||||
|
MapCreateOut,
|
||||||
|
MapCreateOut
|
||||||
|
>({
|
||||||
|
item: savedObjectToMapItem(savedObject, false),
|
||||||
|
});
|
||||||
|
|
||||||
|
if (resultError) {
|
||||||
|
throw Boom.badRequest(`Invalid response. ${resultError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
async update(
|
||||||
|
ctx: StorageContext,
|
||||||
|
id: string,
|
||||||
|
data: MapUpdateIn['data'],
|
||||||
|
options: UpdateOptions
|
||||||
|
): Promise<MapUpdateOut> {
|
||||||
|
const {
|
||||||
|
utils: { getTransforms },
|
||||||
|
version: { request: requestVersion },
|
||||||
|
} = ctx;
|
||||||
|
const transforms = getTransforms(cmServicesDefinition, requestVersion);
|
||||||
|
|
||||||
|
// Validate input (data & options) & UP transform them to the latest version
|
||||||
|
const { value: dataToLatest, error: dataError } = transforms.update.in.data.up<
|
||||||
|
MapAttributes,
|
||||||
|
MapAttributes
|
||||||
|
>(data);
|
||||||
|
if (dataError) {
|
||||||
|
throw Boom.badRequest(`Invalid data. ${dataError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
const { value: optionsToLatest, error: optionsError } = transforms.update.in.options.up<
|
||||||
|
CreateOptions,
|
||||||
|
CreateOptions
|
||||||
|
>(options);
|
||||||
|
if (optionsError) {
|
||||||
|
throw Boom.badRequest(`Invalid options. ${optionsError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Save data in DB
|
||||||
|
const soClient = await savedObjectClientFromRequest(ctx);
|
||||||
|
const partialSavedObject = await soClient.update<MapAttributes>(
|
||||||
|
SO_TYPE,
|
||||||
|
id,
|
||||||
|
dataToLatest,
|
||||||
|
optionsToLatest
|
||||||
|
);
|
||||||
|
|
||||||
|
// Validate DB response and DOWN transform to the request version
|
||||||
|
const { value, error: resultError } = transforms.update.out.result.down<
|
||||||
|
MapUpdateOut,
|
||||||
|
MapUpdateOut
|
||||||
|
>({
|
||||||
|
item: savedObjectToMapItem(partialSavedObject, true),
|
||||||
|
});
|
||||||
|
|
||||||
|
if (resultError) {
|
||||||
|
throw Boom.badRequest(`Invalid response. ${resultError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
async delete(ctx: StorageContext, id: string): Promise<MapDeleteOut> {
|
||||||
|
const soClient = await savedObjectClientFromRequest(ctx);
|
||||||
|
await soClient.delete(SO_TYPE, id);
|
||||||
|
return { success: true };
|
||||||
|
}
|
||||||
|
|
||||||
|
async search(
|
||||||
|
ctx: StorageContext,
|
||||||
|
query: SearchQuery,
|
||||||
|
options: MapSearchOptions = {}
|
||||||
|
): Promise<MapSearchOut> {
|
||||||
|
const {
|
||||||
|
utils: { getTransforms },
|
||||||
|
version: { request: requestVersion },
|
||||||
|
} = ctx;
|
||||||
|
const transforms = getTransforms(cmServicesDefinition, requestVersion);
|
||||||
|
const soClient = await savedObjectClientFromRequest(ctx);
|
||||||
|
|
||||||
|
// Validate and UP transform the options
|
||||||
|
const { value: optionsToLatest, error: optionsError } = transforms.search.in.options.up<
|
||||||
|
MapSearchOptions,
|
||||||
|
MapSearchOptions
|
||||||
|
>(options);
|
||||||
|
if (optionsError) {
|
||||||
|
throw Boom.badRequest(`Invalid payload. ${optionsError.message}`);
|
||||||
|
}
|
||||||
|
const { onlyTitle = false } = optionsToLatest;
|
||||||
|
|
||||||
|
const { included, excluded } = query.tags ?? {};
|
||||||
|
const hasReference: SavedObjectsFindOptions['hasReference'] = included
|
||||||
|
? included.map((id) => ({
|
||||||
|
id,
|
||||||
|
type: 'tag',
|
||||||
|
}))
|
||||||
|
: undefined;
|
||||||
|
|
||||||
|
const hasNoReference: SavedObjectsFindOptions['hasNoReference'] = excluded
|
||||||
|
? excluded.map((id) => ({
|
||||||
|
id,
|
||||||
|
type: 'tag',
|
||||||
|
}))
|
||||||
|
: undefined;
|
||||||
|
|
||||||
|
const soQuery: SavedObjectsFindOptions = {
|
||||||
|
type: CONTENT_ID,
|
||||||
|
search: query.text,
|
||||||
|
perPage: query.limit,
|
||||||
|
page: query.cursor ? +query.cursor : undefined,
|
||||||
|
defaultSearchOperator: 'AND',
|
||||||
|
searchFields: onlyTitle ? ['title'] : ['title^3', 'description'],
|
||||||
|
fields: ['description', 'title'],
|
||||||
|
hasReference,
|
||||||
|
hasNoReference,
|
||||||
|
};
|
||||||
|
|
||||||
|
// Execute the query in the DB
|
||||||
|
const response = await soClient.find<MapAttributes>(soQuery);
|
||||||
|
|
||||||
|
// Validate the response and DOWN transform to the request version
|
||||||
|
const { value, error: resultError } = transforms.search.out.result.down<
|
||||||
|
MapSearchOut,
|
||||||
|
MapSearchOut
|
||||||
|
>({
|
||||||
|
hits: response.saved_objects.map((so) => savedObjectToMapItem(so, false)),
|
||||||
|
pagination: {
|
||||||
|
total: response.total,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
if (resultError) {
|
||||||
|
throw Boom.badRequest(`Invalid response. ${resultError.message}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
}
|
|
@ -6,7 +6,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import type { SerializableRecord } from '@kbn/utility-types';
|
import type { SerializableRecord } from '@kbn/utility-types';
|
||||||
import { MapSavedObjectAttributes } from '../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../common/content_management';
|
||||||
import { moveAttribution } from '../../common/migrations/move_attribution';
|
import { moveAttribution } from '../../common/migrations/move_attribution';
|
||||||
import { migrateOtherCategoryColor } from '../../common/migrations/migrate_other_category_color';
|
import { migrateOtherCategoryColor } from '../../common/migrations/migrate_other_category_color';
|
||||||
import { setEmsTmsDefaultModes } from '../../common/migrations/set_ems_tms_default_modes';
|
import { setEmsTmsDefaultModes } from '../../common/migrations/set_ems_tms_default_modes';
|
||||||
|
@ -25,7 +25,7 @@ export const embeddableMigrations = {
|
||||||
try {
|
try {
|
||||||
return {
|
return {
|
||||||
...state,
|
...state,
|
||||||
attributes: moveAttribution(state as { attributes: MapSavedObjectAttributes }),
|
attributes: moveAttribution(state as { attributes: MapAttributes }),
|
||||||
} as SerializableRecord;
|
} as SerializableRecord;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
// Do not fail migration
|
// Do not fail migration
|
||||||
|
@ -37,7 +37,7 @@ export const embeddableMigrations = {
|
||||||
try {
|
try {
|
||||||
return {
|
return {
|
||||||
...state,
|
...state,
|
||||||
attributes: setEmsTmsDefaultModes(state as { attributes: MapSavedObjectAttributes }),
|
attributes: setEmsTmsDefaultModes(state as { attributes: MapAttributes }),
|
||||||
} as SerializableRecord;
|
} as SerializableRecord;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
// Do not fail migration
|
// Do not fail migration
|
||||||
|
@ -47,7 +47,7 @@ export const embeddableMigrations = {
|
||||||
},
|
},
|
||||||
'8.0.1': (state: SerializableRecord) => {
|
'8.0.1': (state: SerializableRecord) => {
|
||||||
try {
|
try {
|
||||||
const { attributes } = extractReferences(state as { attributes: MapSavedObjectAttributes });
|
const { attributes } = extractReferences(state as { attributes: MapAttributes });
|
||||||
return {
|
return {
|
||||||
...state,
|
...state,
|
||||||
attributes,
|
attributes,
|
||||||
|
@ -62,7 +62,7 @@ export const embeddableMigrations = {
|
||||||
try {
|
try {
|
||||||
return {
|
return {
|
||||||
...state,
|
...state,
|
||||||
attributes: renameLayerTypes(state as { attributes: MapSavedObjectAttributes }),
|
attributes: renameLayerTypes(state as { attributes: MapAttributes }),
|
||||||
} as SerializableRecord;
|
} as SerializableRecord;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
// Do not fail migration
|
// Do not fail migration
|
||||||
|
@ -74,7 +74,7 @@ export const embeddableMigrations = {
|
||||||
try {
|
try {
|
||||||
return {
|
return {
|
||||||
...state,
|
...state,
|
||||||
attributes: migrateOtherCategoryColor(state as { attributes: MapSavedObjectAttributes }),
|
attributes: migrateOtherCategoryColor(state as { attributes: MapAttributes }),
|
||||||
} as SerializableRecord;
|
} as SerializableRecord;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
// Do not fail migration
|
// Do not fail migration
|
||||||
|
|
|
@ -8,16 +8,16 @@
|
||||||
import { asyncForEach } from '@kbn/std';
|
import { asyncForEach } from '@kbn/std';
|
||||||
import type { ISavedObjectsRepository, SavedObject } from '@kbn/core/server';
|
import type { ISavedObjectsRepository, SavedObject } from '@kbn/core/server';
|
||||||
import { MAP_SAVED_OBJECT_TYPE } from '../../common/constants';
|
import { MAP_SAVED_OBJECT_TYPE } from '../../common/constants';
|
||||||
import type { MapSavedObjectAttributes } from '../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../common/content_management';
|
||||||
|
|
||||||
export async function findMaps(
|
export async function findMaps(
|
||||||
savedObjectsClient: Pick<ISavedObjectsRepository, 'find'>,
|
savedObjectsClient: Pick<ISavedObjectsRepository, 'find'>,
|
||||||
callback: (savedObject: SavedObject<MapSavedObjectAttributes>) => Promise<void>
|
callback: (savedObject: SavedObject<MapAttributes>) => Promise<void>
|
||||||
) {
|
) {
|
||||||
let nextPage = 1;
|
let nextPage = 1;
|
||||||
let hasMorePages = false;
|
let hasMorePages = false;
|
||||||
do {
|
do {
|
||||||
const results = await savedObjectsClient.find<MapSavedObjectAttributes>({
|
const results = await savedObjectsClient.find<MapAttributes>({
|
||||||
type: MAP_SAVED_OBJECT_TYPE,
|
type: MAP_SAVED_OBJECT_TYPE,
|
||||||
page: nextPage,
|
page: nextPage,
|
||||||
});
|
});
|
||||||
|
|
|
@ -5,7 +5,7 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { MapSavedObjectAttributes } from '../../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../../common/content_management';
|
||||||
import {
|
import {
|
||||||
EMS_BASEMAP_KEYS,
|
EMS_BASEMAP_KEYS,
|
||||||
JOIN_KEYS,
|
JOIN_KEYS,
|
||||||
|
@ -38,7 +38,7 @@ export class MapStatsCollector {
|
||||||
private _customIconsCountStats: ClusterCountStats | undefined;
|
private _customIconsCountStats: ClusterCountStats | undefined;
|
||||||
private _sourceCountStats: ClusterCountStats | undefined;
|
private _sourceCountStats: ClusterCountStats | undefined;
|
||||||
|
|
||||||
push(attributes: MapSavedObjectAttributes) {
|
push(attributes: MapAttributes) {
|
||||||
if (!attributes || !attributes.mapStateJSON || !attributes.layerListJSON) {
|
if (!attributes || !attributes.mapStateJSON || !attributes.layerListJSON) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,6 +17,8 @@ import {
|
||||||
import { HomeServerPluginSetup } from '@kbn/home-plugin/server';
|
import { HomeServerPluginSetup } from '@kbn/home-plugin/server';
|
||||||
import { DataViewPersistableStateService } from '@kbn/data-views-plugin/common';
|
import { DataViewPersistableStateService } from '@kbn/data-views-plugin/common';
|
||||||
import type { EMSSettings } from '@kbn/maps-ems-plugin/server';
|
import type { EMSSettings } from '@kbn/maps-ems-plugin/server';
|
||||||
|
|
||||||
|
import { CONTENT_ID, LATEST_VERSION } from '../common/content_management';
|
||||||
import { getEcommerceSavedObjects } from './sample_data/ecommerce_saved_objects';
|
import { getEcommerceSavedObjects } from './sample_data/ecommerce_saved_objects';
|
||||||
import { getFlightsSavedObjects } from './sample_data/flights_saved_objects';
|
import { getFlightsSavedObjects } from './sample_data/flights_saved_objects';
|
||||||
import { getWebLogsSavedObjects } from './sample_data/web_logs_saved_objects';
|
import { getWebLogsSavedObjects } from './sample_data/web_logs_saved_objects';
|
||||||
|
@ -30,6 +32,7 @@ import { setupEmbeddable } from './embeddable';
|
||||||
import { setupSavedObjects } from './saved_objects';
|
import { setupSavedObjects } from './saved_objects';
|
||||||
import { registerIntegrations } from './register_integrations';
|
import { registerIntegrations } from './register_integrations';
|
||||||
import { StartDeps, SetupDeps } from './types';
|
import { StartDeps, SetupDeps } from './types';
|
||||||
|
import { MapsStorage } from './content_management';
|
||||||
|
|
||||||
export class MapsPlugin implements Plugin {
|
export class MapsPlugin implements Plugin {
|
||||||
readonly _initializerContext: PluginInitializerContext<MapsXPackConfig>;
|
readonly _initializerContext: PluginInitializerContext<MapsXPackConfig>;
|
||||||
|
@ -150,7 +153,7 @@ export class MapsPlugin implements Plugin {
|
||||||
DataViewPersistableStateService
|
DataViewPersistableStateService
|
||||||
);
|
);
|
||||||
|
|
||||||
const { usageCollection, home, features, customIntegrations } = plugins;
|
const { usageCollection, home, features, customIntegrations, contentManagement } = plugins;
|
||||||
const config$ = this._initializerContext.config.create();
|
const config$ = this._initializerContext.config.create();
|
||||||
|
|
||||||
const emsSettings = plugins.mapsEms.createEMSSettings();
|
const emsSettings = plugins.mapsEms.createEMSSettings();
|
||||||
|
@ -199,6 +202,14 @@ export class MapsPlugin implements Plugin {
|
||||||
setupSavedObjects(core, getFilterMigrations, getDataViewMigrations);
|
setupSavedObjects(core, getFilterMigrations, getDataViewMigrations);
|
||||||
registerMapsUsageCollector(usageCollection);
|
registerMapsUsageCollector(usageCollection);
|
||||||
|
|
||||||
|
contentManagement.register({
|
||||||
|
id: CONTENT_ID,
|
||||||
|
storage: new MapsStorage(),
|
||||||
|
version: {
|
||||||
|
latest: LATEST_VERSION,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
setupEmbeddable(plugins.embeddable, getFilterMigrations, getDataViewMigrations);
|
setupEmbeddable(plugins.embeddable, getFilterMigrations, getDataViewMigrations);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|
|
@ -21,12 +21,12 @@ import { addTypeToTermJoin } from '../../common/migrations/add_type_to_termjoin'
|
||||||
import { moveAttribution } from '../../common/migrations/move_attribution';
|
import { moveAttribution } from '../../common/migrations/move_attribution';
|
||||||
import { setEmsTmsDefaultModes } from '../../common/migrations/set_ems_tms_default_modes';
|
import { setEmsTmsDefaultModes } from '../../common/migrations/set_ems_tms_default_modes';
|
||||||
import { renameLayerTypes } from '../../common/migrations/rename_layer_types';
|
import { renameLayerTypes } from '../../common/migrations/rename_layer_types';
|
||||||
import type { MapSavedObjectAttributes } from '../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../common/content_management';
|
||||||
|
|
||||||
function logMigrationWarning(
|
function logMigrationWarning(
|
||||||
context: SavedObjectMigrationContext,
|
context: SavedObjectMigrationContext,
|
||||||
errorMsg: string,
|
errorMsg: string,
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>
|
||||||
) {
|
) {
|
||||||
context.log.warn(
|
context.log.warn(
|
||||||
`map migration failed (${context.migrationVersion}). ${errorMsg}. attributes: ${JSON.stringify(
|
`map migration failed (${context.migrationVersion}). ${errorMsg}. attributes: ${JSON.stringify(
|
||||||
|
@ -44,7 +44,7 @@ function logMigrationWarning(
|
||||||
*/
|
*/
|
||||||
export const savedObjectMigrations = {
|
export const savedObjectMigrations = {
|
||||||
'7.2.0': (
|
'7.2.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -61,7 +61,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.4.0': (
|
'7.4.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -77,7 +77,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.5.0': (
|
'7.5.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -93,7 +93,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.6.0': (
|
'7.6.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -110,7 +110,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.7.0': (
|
'7.7.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -127,7 +127,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.8.0': (
|
'7.8.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -143,7 +143,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.9.0': (
|
'7.9.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -159,7 +159,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.10.0': (
|
'7.10.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -175,7 +175,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.12.0': (
|
'7.12.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -191,7 +191,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'7.14.0': (
|
'7.14.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -207,7 +207,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'8.0.0': (
|
'8.0.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -223,7 +223,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'8.1.0': (
|
'8.1.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
@ -239,7 +239,7 @@ export const savedObjectMigrations = {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'8.4.0': (
|
'8.4.0': (
|
||||||
doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>,
|
doc: SavedObjectUnsanitizedDoc<MapAttributes>,
|
||||||
context: SavedObjectMigrationContext
|
context: SavedObjectMigrationContext
|
||||||
) => {
|
) => {
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -11,9 +11,10 @@ import type { SavedObjectMigrationMap } from '@kbn/core/server';
|
||||||
import { MigrateFunctionsObject } from '@kbn/kibana-utils-plugin/common';
|
import { MigrateFunctionsObject } from '@kbn/kibana-utils-plugin/common';
|
||||||
import { mergeSavedObjectMigrationMaps } from '@kbn/core/server';
|
import { mergeSavedObjectMigrationMaps } from '@kbn/core/server';
|
||||||
import { APP_ICON, getFullPath } from '../../common/constants';
|
import { APP_ICON, getFullPath } from '../../common/constants';
|
||||||
|
import { CONTENT_ID } from '../../common/content_management';
|
||||||
import { migrateDataPersistedState } from '../../common/migrations/migrate_data_persisted_state';
|
import { migrateDataPersistedState } from '../../common/migrations/migrate_data_persisted_state';
|
||||||
import { migrateDataViewsPersistedState } from '../../common/migrations/migrate_data_view_persisted_state';
|
import { migrateDataViewsPersistedState } from '../../common/migrations/migrate_data_view_persisted_state';
|
||||||
import type { MapSavedObjectAttributes } from '../../common/map_saved_object_type';
|
import type { MapAttributes } from '../../common/content_management';
|
||||||
import { savedObjectMigrations } from './saved_object_migrations';
|
import { savedObjectMigrations } from './saved_object_migrations';
|
||||||
|
|
||||||
export function setupSavedObjects(
|
export function setupSavedObjects(
|
||||||
|
@ -21,8 +22,8 @@ export function setupSavedObjects(
|
||||||
getFilterMigrations: () => MigrateFunctionsObject,
|
getFilterMigrations: () => MigrateFunctionsObject,
|
||||||
getDataViewMigrations: () => MigrateFunctionsObject
|
getDataViewMigrations: () => MigrateFunctionsObject
|
||||||
) {
|
) {
|
||||||
core.savedObjects.registerType<MapSavedObjectAttributes>({
|
core.savedObjects.registerType<MapAttributes>({
|
||||||
name: 'map',
|
name: CONTENT_ID,
|
||||||
hidden: false,
|
hidden: false,
|
||||||
namespaceType: 'multiple-isolated',
|
namespaceType: 'multiple-isolated',
|
||||||
convertToMultiNamespaceTypeVersion: '8.0.0',
|
convertToMultiNamespaceTypeVersion: '8.0.0',
|
||||||
|
@ -71,7 +72,7 @@ export const getMapsFilterMigrations = (
|
||||||
): MigrateFunctionsObject =>
|
): MigrateFunctionsObject =>
|
||||||
mapValues(
|
mapValues(
|
||||||
filterMigrations,
|
filterMigrations,
|
||||||
(filterMigration) => (doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>) => {
|
(filterMigration) => (doc: SavedObjectUnsanitizedDoc<MapAttributes>) => {
|
||||||
try {
|
try {
|
||||||
const attributes = migrateDataPersistedState(doc, filterMigration);
|
const attributes = migrateDataPersistedState(doc, filterMigration);
|
||||||
|
|
||||||
|
@ -93,20 +94,17 @@ export const getMapsFilterMigrations = (
|
||||||
export const getMapsDataViewMigrations = (
|
export const getMapsDataViewMigrations = (
|
||||||
migrations: MigrateFunctionsObject
|
migrations: MigrateFunctionsObject
|
||||||
): MigrateFunctionsObject =>
|
): MigrateFunctionsObject =>
|
||||||
mapValues(
|
mapValues(migrations, (migration) => (doc: SavedObjectUnsanitizedDoc<MapAttributes>) => {
|
||||||
migrations,
|
try {
|
||||||
(migration) => (doc: SavedObjectUnsanitizedDoc<MapSavedObjectAttributes>) => {
|
const attributes = migrateDataViewsPersistedState(doc, migration);
|
||||||
try {
|
|
||||||
const attributes = migrateDataViewsPersistedState(doc, migration);
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
...doc,
|
...doc,
|
||||||
attributes,
|
attributes,
|
||||||
};
|
};
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
// Do not fail migration
|
// Do not fail migration
|
||||||
// Maps application can display error when saved object is viewed
|
// Maps application can display error when saved object is viewed
|
||||||
return doc;
|
return doc;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
);
|
});
|
||||||
|
|
|
@ -16,6 +16,7 @@ import {
|
||||||
PluginStart as DataPluginStart,
|
PluginStart as DataPluginStart,
|
||||||
} from '@kbn/data-plugin/server';
|
} from '@kbn/data-plugin/server';
|
||||||
import { CustomIntegrationsPluginSetup } from '@kbn/custom-integrations-plugin/server';
|
import { CustomIntegrationsPluginSetup } from '@kbn/custom-integrations-plugin/server';
|
||||||
|
import type { ContentManagementServerSetup } from '@kbn/content-management-plugin/server';
|
||||||
|
|
||||||
export interface SetupDeps {
|
export interface SetupDeps {
|
||||||
data: DataPluginSetup;
|
data: DataPluginSetup;
|
||||||
|
@ -26,6 +27,7 @@ export interface SetupDeps {
|
||||||
mapsEms: MapsEmsPluginServerSetup;
|
mapsEms: MapsEmsPluginServerSetup;
|
||||||
embeddable: EmbeddableSetup;
|
embeddable: EmbeddableSetup;
|
||||||
customIntegrations: CustomIntegrationsPluginSetup;
|
customIntegrations: CustomIntegrationsPluginSetup;
|
||||||
|
contentManagement: ContentManagementServerSetup;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface StartDeps {
|
export interface StartDeps {
|
||||||
|
|
|
@ -56,7 +56,6 @@
|
||||||
"@kbn/mapbox-gl",
|
"@kbn/mapbox-gl",
|
||||||
"@kbn/core-execution-context-common",
|
"@kbn/core-execution-context-common",
|
||||||
"@kbn/chart-icons",
|
"@kbn/chart-icons",
|
||||||
"@kbn/core-saved-objects-api-browser",
|
|
||||||
"@kbn/ui-theme",
|
"@kbn/ui-theme",
|
||||||
"@kbn/monaco",
|
"@kbn/monaco",
|
||||||
"@kbn/safer-lodash-set",
|
"@kbn/safer-lodash-set",
|
||||||
|
@ -64,6 +63,9 @@
|
||||||
"@kbn/config-schema",
|
"@kbn/config-schema",
|
||||||
"@kbn/controls-plugin",
|
"@kbn/controls-plugin",
|
||||||
"@kbn/shared-ux-router",
|
"@kbn/shared-ux-router",
|
||||||
|
"@kbn/content-management-plugin",
|
||||||
|
"@kbn/core-saved-objects-api-server",
|
||||||
|
"@kbn/object-versioning",
|
||||||
"@kbn/field-types",
|
"@kbn/field-types",
|
||||||
],
|
],
|
||||||
"exclude": [
|
"exclude": [
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue