Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Change public objects logic & Search with ACL control #71

Merged
Merged
Show file tree
Hide file tree
Changes from 22 commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
3cfdc38
feat: update public workspace
SuZhou-Joe Aug 1, 2023
8f3b29f
refractor: change public objects logic
SuZhou-Joe Aug 2, 2023
e09a887
feat: create public workspace when service start
SuZhou-Joe Aug 3, 2023
93885d8
feat: some modify
SuZhou-Joe Aug 3, 2023
e20d6ea
feature: some optimize and create workspace when ui settings is open
SuZhou-Joe Aug 3, 2023
f1c4ed5
feat: update
SuZhou-Joe Aug 3, 2023
e9bf305
feat: update
SuZhou-Joe Aug 3, 2023
e9c9a4e
feat: update
SuZhou-Joe Aug 3, 2023
15ff5db
feat: update
SuZhou-Joe Aug 3, 2023
59c01f9
temp: submit
SuZhou-Joe Aug 4, 2023
6648bd0
feat: update
SuZhou-Joe Aug 8, 2023
6cd39d4
feat: update
SuZhou-Joe Aug 8, 2023
a8ed9d3
feat: update
SuZhou-Joe Aug 8, 2023
bb65ed5
feat: update
SuZhou-Joe Aug 8, 2023
5c2634a
feat: update query dsl
SuZhou-Joe Aug 9, 2023
ecc4b57
feat: use same constants
SuZhou-Joe Aug 9, 2023
c487141
feat: make it run
SuZhou-Joe Aug 9, 2023
1b2bf54
feat: remove dashboard admin
SuZhou-Joe Aug 9, 2023
59c0c9f
feat: modify query DSL
SuZhou-Joe Aug 9, 2023
ffbf2c4
feat: modify query DSL
SuZhou-Joe Aug 9, 2023
dbd7f8f
feat: modify query DSL
SuZhou-Joe Aug 9, 2023
3217788
feat: list principals route
SuZhou-Joe Aug 9, 2023
a93c2ac
feat: optimize query DSL
SuZhou-Joe Aug 9, 2023
47f8bd5
feat: change public logic
SuZhou-Joe Aug 9, 2023
8375910
feat: update
SuZhou-Joe Aug 9, 2023
0c53ece
feat: update
SuZhou-Joe Aug 9, 2023
2579883
feat: remove init
SuZhou-Joe Aug 9, 2023
384449d
feat: add judgement when workspaceList is empty
SuZhou-Joe Aug 9, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
45 changes: 33 additions & 12 deletions src/core/public/saved_objects/saved_objects_client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ import {

import { SimpleSavedObject } from './simple_saved_object';
import { HttpFetchOptions, HttpSetup } from '../http';
import { PUBLIC_WORKSPACE } from '../../utils';

type SavedObjectsFindOptions = Omit<
SavedObjectFindOptionsServer,
Expand Down Expand Up @@ -184,7 +185,11 @@ const getObjectsToFetch = (queue: BatchQueueEntry[]): ObjectTypeAndId[] => {
export class SavedObjectsClient {
private http: HttpSetup;
private batchQueue: BatchQueueEntry[];
private currentWorkspaceId?: string;
/**
* if currentWorkspaceId is undefined, it means
* we should not carry out workspace info when doing any operation.
*/
private currentWorkspaceId: string | undefined;

/**
* Throttled processing of get requests into bulk requests at 100ms interval
Expand Down Expand Up @@ -229,11 +234,11 @@ export class SavedObjectsClient {
this.batchQueue = [];
}

private async _getCurrentWorkspace(): Promise<string | null> {
return this.currentWorkspaceId || null;
private _getCurrentWorkspace(): string | undefined {
return this.currentWorkspaceId;
}

public async setCurrentWorkspace(workspaceId: string): Promise<boolean> {
public setCurrentWorkspace(workspaceId: string): boolean {
this.currentWorkspaceId = workspaceId;
return true;
}
Expand All @@ -259,7 +264,13 @@ export class SavedObjectsClient {
const query = {
overwrite: options.overwrite,
};
const currentWorkspaceId = await this._getCurrentWorkspace();
const currentWorkspaceId = this._getCurrentWorkspace();
let finalWorkspaces;
if (options.hasOwnProperty('workspaces')) {
finalWorkspaces = options.workspaces;
} else if (typeof currentWorkspaceId === 'string') {
finalWorkspaces = [currentWorkspaceId];
}

const createRequest: Promise<SavedObject<T>> = this.savedObjectsFetch(path, {
method: 'POST',
Expand All @@ -268,9 +279,9 @@ export class SavedObjectsClient {
attributes,
migrationVersion: options.migrationVersion,
references: options.references,
...(options.workspaces || currentWorkspaceId
...(finalWorkspaces
? {
workspaces: options.workspaces || [currentWorkspaceId],
workspaces: finalWorkspaces,
}
: {}),
}),
Expand Down Expand Up @@ -366,14 +377,24 @@ export class SavedObjectsClient {
queryDSL: 'queryDSL',
};

const workspaces = [
...(options.workspaces || [await this._getCurrentWorkspace()]),
'public',
].filter((item) => item);
const currentWorkspaceId = this._getCurrentWorkspace();
let finalWorkspaces;
if (options.hasOwnProperty('workspaces')) {
finalWorkspaces = options.workspaces;
} else if (typeof currentWorkspaceId === 'string') {
finalWorkspaces =
currentWorkspaceId === PUBLIC_WORKSPACE
SuZhou-Joe marked this conversation as resolved.
Show resolved Hide resolved
? undefined
: [PUBLIC_WORKSPACE, currentWorkspaceId];
}

const renamedQuery = renameKeys<SavedObjectsFindOptions, any>(renameMap, {
...options,
workspaces,
...(finalWorkspaces
? {
workspaces: finalWorkspaces,
}
: {}),
});
const query = pick.apply(null, [renamedQuery, ...Object.values<string>(renameMap)]) as Partial<
Record<string, any>
Expand Down
6 changes: 5 additions & 1 deletion src/core/public/utils/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,4 +32,8 @@ export { shareWeakReplay } from './share_weak_replay';
export { Sha256 } from './crypto';
export { MountWrapper, mountReactNode } from './mount';
export { getWorkspaceIdFromUrl, WORKSPACE_TYPE } from './workspace';
export { WORKSPACE_PATH_PREFIX } from '../../utils';
export {
WORKSPACE_PATH_PREFIX,
PUBLIC_WORKSPACE,
WORKSPACE_FEATURE_FLAG_KEY_IN_UI_SETTINGS,
} from '../../utils';
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

import { InternalHttpServiceSetup } from '../../../http';
import { SavedObjectsPermissionControlContract } from '../client';
import { registerListRoute } from './principals';
import { registerValidateRoute } from './validate';

export function registerPermissionCheckRoutes({
Expand All @@ -17,4 +18,5 @@ export function registerPermissionCheckRoutes({
const router = http.createRouter('/api/saved_objects_permission_control/');

registerValidateRoute(router, permissionControl);
registerListRoute(router, permissionControl);
}
4 changes: 2 additions & 2 deletions src/core/server/saved_objects/routes/share.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { exportSavedObjectsToStream } from '../export';
import { validateObjects } from './utils';
import { collectSavedObjects } from '../import/collect_saved_objects';
import { WORKSPACE_TYPE } from '../../workspaces';
import { GLOBAL_WORKSPACE_ID } from '../../workspaces/constants';
import { PUBLIC_WORKSPACE } from '../../../utils/constants';

const SHARE_LIMIT = 10000;

Expand Down Expand Up @@ -73,7 +73,7 @@ export const registerShareRoute = (router: IRouter) => {
(obj) =>
obj.workspaces &&
obj.workspaces.length > 0 &&
!obj.workspaces.includes(GLOBAL_WORKSPACE_ID)
!obj.workspaces.includes(PUBLIC_WORKSPACE)
)
.map((obj) => ({ id: obj.id, type: obj.type, workspaces: obj.workspaces }));

Expand Down
6 changes: 3 additions & 3 deletions src/core/server/saved_objects/service/lib/repository.ts
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ import {
FIND_DEFAULT_PER_PAGE,
SavedObjectsUtils,
} from './utils';
import { GLOBAL_WORKSPACE_ID } from '../../../workspaces/constants';
import { PUBLIC_WORKSPACE } from '../../../../utils/constants';

// BEWARE: The SavedObjectClient depends on the implementation details of the SavedObjectsRepository
// so any breaking changes to this repository are considered breaking changes to the SavedObjectsClient.
Expand Down Expand Up @@ -1299,7 +1299,7 @@ export class SavedObjectsRepository {
if (
obj.workspaces &&
obj.workspaces.length > 0 &&
!obj.workspaces.includes(GLOBAL_WORKSPACE_ID)
!obj.workspaces.includes(PUBLIC_WORKSPACE)
) {
return intersection(obj.workspaces, options.workspaces).length === 0;
}
Expand Down Expand Up @@ -1352,7 +1352,7 @@ export class SavedObjectsRepository {
params: {
time,
workspaces,
globalWorkspaceId: GLOBAL_WORKSPACE_ID,
globalWorkspaceId: PUBLIC_WORKSPACE,
},
},
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -142,14 +142,6 @@ function getClauseForWorkspace(workspace: string) {
};
}

if (workspace === 'public') {
return {
bool: {
must_not: [{ exists: { field: 'workspaces' } }],
},
};
}

return {
bool: {
must: [{ term: { workspaces: workspace } }],
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,6 @@
*/

import { Permissions } from '../permission_control/acl';

import { ISavedObjectsRepository } from './lib';
import {
SavedObject,
Expand Down
4 changes: 3 additions & 1 deletion src/core/server/server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -262,7 +262,9 @@ export class Server {
opensearch: opensearchStart,
savedObjects: savedObjectsStart,
});
await this.workspaces.start();
await this.workspaces.start({
savedObjects: savedObjectsStart,
});

this.coreStart = {
capabilities: capabilitiesStart,
Expand Down
26 changes: 26 additions & 0 deletions src/core/server/ui_settings/settings/workspace.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
/*
* Copyright OpenSearch Contributors
* SPDX-License-Identifier: Apache-2.0
*/

import { schema } from '@osd/config-schema';
import { i18n } from '@osd/i18n';
import { UiSettingsParams } from '../../../types';
import { WORKSPACE_FEATURE_FLAG_KEY_IN_UI_SETTINGS } from '../../../utils';

export const getWorkspaceSettings = (): Record<string, UiSettingsParams> => {
return {
[WORKSPACE_FEATURE_FLAG_KEY_IN_UI_SETTINGS]: {
name: i18n.translate('core.ui_settings.params.workspace.enableWorkspaceTitle', {
defaultMessage: 'Enable Workspace',
}),
value: false,
requiresPageReload: true,
description: i18n.translate('core.ui_settings.params.workspace.enableWorkspaceTitle', {
defaultMessage: 'Enable or disable OpenSearch Dashboards Workspace',
}),
category: ['workspace'],
schema: schema.boolean(),
},
};
};
1 change: 0 additions & 1 deletion src/core/server/workspaces/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,3 @@
*/

export const WORKSPACE_TYPE = 'workspace';
export const GLOBAL_WORKSPACE_ID = 'public';
Original file line number Diff line number Diff line change
Expand Up @@ -214,26 +214,57 @@ export class WorkspaceSavedObjectsClientWrapper {
);
if (options.workspaces) {
const isEveryWorkspaceIsPermitted = options.workspaces.every((item) =>
// TODO modify this line to use permittedWorkspaceIds if public workspace is also a workspace
['public', ...(permittedWorkspaceIds || [])]?.includes(item)
(permittedWorkspaceIds || []).includes(item)
);
if (!isEveryWorkspaceIsPermitted) {
throw generateWorkspacePermissionError();
}
} else {
const queryDSL = ACL.genereateGetPermittedSavedObjectsQueryDSL(
[
PermissionMode.LibraryRead,
PermissionMode.LibraryWrite,
PermissionMode.Management,
PermissionMode.Read,
PermissionMode.Write,
],
[PermissionMode.Read, PermissionMode.Write],
principals,
options.type
);
options.workspaces = permittedWorkspaceIds;
options.queryDSL = queryDSL;
options.workspaces = undefined;
/**
* Select all the docs that
* 1. ACL matches read or write permission OR
* 2. workspaces matches library_read or library_write or management OR
* 3. Advanced settings
*/
options.queryDSL = {
SuZhou-Joe marked this conversation as resolved.
Show resolved Hide resolved
query: {
bool: {
filter: [
{
bool: {
should: [
{
bool: {
SuZhou-Joe marked this conversation as resolved.
Show resolved Hide resolved
must: {
term: {
type: 'config',
},
},
},
},
queryDSL.query,
{
bool: {
should: permittedWorkspaceIds?.map((item) => ({
terms: {
workspaces: [item],
SuZhou-Joe marked this conversation as resolved.
Show resolved Hide resolved
},
})),
},
},
],
},
},
],
},
},
};
}
}

Expand Down
Loading
Loading