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

Merge main changes to Feature-Anywhere branch #4295

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
45 commits
Select commit Hold shift + click to select a range
e74ab2d
Fix header icon (#3910) (#3915)
opensearch-trigger-bot[bot] Apr 22, 2023
ef2cb84
Add server side private IP blocking for data source endpoints validat…
kristenTian Apr 24, 2023
a947240
Docs (Jest): Update jest documentation links (#3931)
joshuarrrr Apr 24, 2023
b97a4b5
Revert "[CCI] Replace jquery usage in console plugin with native meth…
joshuarrrr Apr 24, 2023
0e34c3c
[BUG][Dashboard listing] push to history if dashboard otherwise nav (…
kavilla Apr 25, 2023
66aa122
remove jquery console release note for https://github.com/opensearch-…
joshuarrrr Apr 25, 2023
755f16b
[CCI] Update js-yaml to v4.0.5 (#3770)
andreymyssak Apr 25, 2023
ac2ee3a
Update README.md (#3788)
vagimeli Apr 26, 2023
a8ace28
Bump yaml to 2.2.2 (#3947)
manasvinibs Apr 27, 2023
ca0bb8f
Bump `joi` to v14 to avoid the possibility of prototype poisoning in …
AMoo-Miki May 2, 2023
f5a978d
[Doc] Add communication guide (#3837)
joshuarrrr May 3, 2023
5ea0cbe
Temporarily hardcode chromedriver to 112.0.0 to enable all ftr tests …
ananzh May 5, 2023
6e352ff
Fix wording and duplicate code in embeddable example plugin (#3911)
abbyhu2000 May 5, 2023
0188d05
[CI] setup Chrome and utilize binary path (#3997)
kavilla May 11, 2023
8121c9d
[Dashboards listing] fix listing limit (#4021)
kavilla May 15, 2023
0e25f2e
[CCI] Fix EUI/OUI type errors (#3798)
Nicksqain May 15, 2023
87e7951
Fix bottom bar visibility using create portal (#3336) (#3978)
SergeyMyssak May 16, 2023
69b1854
Adds threshold to code coverage changes for project (#4040)
ashwin-pc May 16, 2023
873b7f3
Updates PR template for screenshots and test instructions (#4042)
ashwin-pc May 16, 2023
2c33d57
Replace re2 with RegExp in timeline and add unit tests (#3908)
ananzh May 16, 2023
b04e657
[Console] [CCI] Remove unused ul element and its custom styling. (#3993)
curq May 17, 2023
c5058a3
Add 1.3.10 release note (#4060) (#4063)
opensearch-trigger-bot[bot] May 18, 2023
e737790
[Multiple Datasource] Support Amazon OpenSearch Serverless (#3957)
zhongnansu May 19, 2023
83d7b5b
Remove Sass from `tile_map` plugin (#4110)
BSFishy May 23, 2023
61ea841
Design for New Saved Object Service Interface for Custom Repository (…
bandinib-amzn May 23, 2023
1524784
enhance grouping for context menu options (#3924)
sikhote May 24, 2023
6399a6c
Adding Tao and Zilong to MAINTAINERS (#4137)
zengyan-amazon May 25, 2023
574f119
[MD]Update data-test-subj for functional tests & fix bug in edit flow…
zhongnansu May 25, 2023
1c0ffee
Add support for Node.js >=14.20.1 <19 (#4071)
AMoo-Miki May 26, 2023
ec41f59
Remove timeline application (#3971)
ananzh May 26, 2023
bd7d707
Use `exec` in the CLI shell scripts to prevent new process creation (…
AMoo-Miki May 26, 2023
4978786
chore (lychee): Add company.net to exclusion list (#4171)
joshuarrrr May 30, 2023
20c928f
Bundle Node 14 as a fallback for operating systems that cannot run No…
AMoo-Miki May 30, 2023
821ad73
Refactor authentication description message (#4179)
zhongnansu May 31, 2023
da501e4
[CI] skip checksum verification for cypress tests (#4188)
kavilla May 31, 2023
f017eaa
Adds plugin manifest config to define OpenSearch plugin dependency an…
manasvinibs Jun 1, 2023
efbcb69
[Table Visualization] Remove custom styling for text-align:center in …
curq Jun 1, 2023
bb0c98f
Add new MAINTAINERS to CODEOWNERS file (#4199)
Flyingliuhub Jun 1, 2023
5ffb3d8
Add 2.8.0 release notes (#4204)
kavilla Jun 1, 2023
487cd36
Chore(CHANGELOG): Update with 2.7, 2.8 releases (#3890)
joshuarrrr Jun 2, 2023
5c5de03
[Saved Object Service] Adds Repository Factory Provider (#4149)
bandinib-amzn Jun 5, 2023
cb27336
add category option for context menus (#4144)
sikhote Jun 6, 2023
55b293a
[CCI] Add bluebird replaces for src/plugins/saved_objects (#4026)
Nicksqain Jun 8, 2023
2322c53
Validate and correct change log after 2.8 release (#4275)
zhongnansu Jun 10, 2023
99f7c37
Merge remote-tracking branch 'origin/main' into main-merge
lezzago Jun 15, 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
2 changes: 1 addition & 1 deletion .github/CODEOWNERS
Validating CODEOWNERS rules …
Original file line number Diff line number Diff line change
@@ -1 +1 @@
* @ananzh @kavilla @seanneumann @AMoo-Miki @ashwin-pc @joshuarrrr @abbyhu2000 @zengyan-amazon @kristenTian @zhongnansu @manasvinibs
* @ananzh @kavilla @seanneumann @AMoo-Miki @ashwin-pc @joshuarrrr @abbyhu2000 @zengyan-amazon @kristenTian @zhongnansu @manasvinibs @ZilongX @Flyingliuhub
7 changes: 5 additions & 2 deletions .github/workflows/cypress_workflow.yml
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,10 @@ env:
START_CMD: 'node ../scripts/opensearch_dashboards --dev --no-base-path --no-watch'
OPENSEARCH_SNAPSHOT_CMD: 'node ../scripts/opensearch snapshot'
SPEC: 'cypress/integration/core-opensearch-dashboards/opensearch-dashboards/**/*.js,'
CYPRESS_ENV: 'env CYPRESS_VISBUILDER_ENABLED=true CYPRESS_DATASOURCE_MANAGEMENT_ENABLED=false'
CYPRESS_BROWSER: 'chromium'
CYPRESS_VISBUILDER_ENABLED: true
CYPRESS_DATASOURCE_MANAGEMENT_ENABLED: false
OSD_SNAPSHOT_SKIP_VERIFY_CHECKSUM: true

jobs:
cypress-tests:
Expand Down Expand Up @@ -76,7 +79,7 @@ jobs:
working-directory: ${{ env.FTR_PATH }}
start: ${{ env.OPENSEARCH_SNAPSHOT_CMD }}, ${{ env.START_CMD }}
wait-on: 'http://localhost:9200, http://localhost:5601'
command: ${{ env.CYPRESS_ENV }} yarn cypress:run-without-security --browser chromium --spec ${{ env.SPEC }}
command: yarn cypress:run-without-security --browser ${{ env.CYPRESS_BROWSER }} --spec ${{ env.SPEC }}

# Screenshots are only captured on failure, will change this once we do visual regression tests
- uses: actions/upload-artifact@v3
Expand Down
742 changes: 521 additions & 221 deletions CHANGELOG.md

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ import { PanelViewWithSharingLong } from './panel_view_with_sharing_long';
import { PanelEdit } from './panel_edit';
import { PanelEditWithDrilldowns } from './panel_edit_with_drilldowns';
import { PanelEditWithDrilldownsAndContextActions } from './panel_edit_with_drilldowns_and_context_actions';
import { PanelGroupOptionsAndContextActions } from './panel_group_options_and_context_actions';

export const ContextMenuExamples: React.FC = () => {
return (
Expand All @@ -59,7 +60,6 @@ export const ContextMenuExamples: React.FC = () => {
<PanelViewWithSharingLong />
</EuiFlexItem>
</EuiFlexGroup>

<EuiFlexGroup>
<EuiFlexItem>
<PanelEdit />
Expand All @@ -71,6 +71,11 @@ export const ContextMenuExamples: React.FC = () => {
<PanelEditWithDrilldownsAndContextActions />
</EuiFlexItem>
</EuiFlexGroup>
<EuiFlexGroup>
<EuiFlexItem>
<PanelGroupOptionsAndContextActions />
</EuiFlexItem>
</EuiFlexGroup>
</EuiText>
);
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
/*
* Copyright OpenSearch Contributors
* SPDX-License-Identifier: Apache-2.0
*/

import * as React from 'react';
import { EuiButton, EuiContextMenu, EuiPopover } from '@elastic/eui';
import useAsync from 'react-use/lib/useAsync';
import { buildContextMenuForActions, Action } from '../../../../src/plugins/ui_actions/public';
import { sampleAction } from './util';

export const PanelGroupOptionsAndContextActions: React.FC = () => {
const [open, setOpen] = React.useState(false);

const context = {};
const trigger: any = 'TEST_TRIGGER';
const drilldownGrouping: Action['grouping'] = [
{
id: 'drilldowns',
getDisplayName: () => 'Uncategorized group',
getIconType: () => 'popout',
order: 20,
},
];
const exampleGroup: Action['grouping'] = [
{
id: 'example',
getDisplayName: () => 'Example group',
getIconType: () => 'cloudStormy',
order: 20,
category: 'visAug',
},
];
const alertingGroup: Action['grouping'] = [
{
id: 'alerting',
getDisplayName: () => 'Alerting',
getIconType: () => 'cloudStormy',
order: 20,
category: 'visAug',
},
];
const anomaliesGroup: Action['grouping'] = [
{
id: 'anomalies',
getDisplayName: () => 'Anomalies',
getIconType: () => 'cloudStormy',
order: 30,
category: 'visAug',
},
];
const actions = [
sampleAction('test-1', 100, 'Edit visualization', 'pencil'),
sampleAction('test-2', 99, 'Clone panel', 'partial'),

sampleAction('test-9', 10, 'Create drilldown', 'plusInCircle', drilldownGrouping),
sampleAction('test-10', 9, 'Manage drilldowns', 'list', drilldownGrouping),

sampleAction('test-11', 10, 'Example action', 'dashboardApp', exampleGroup),
sampleAction('test-11', 10, 'Alertin action 1', 'dashboardApp', alertingGroup),
sampleAction('test-12', 9, 'Alertin action 2', 'dashboardApp', alertingGroup),
sampleAction('test-13', 8, 'Anomalies 1', 'cloudStormy', anomaliesGroup),
sampleAction('test-14', 7, 'Anomalies 2', 'link', anomaliesGroup),
];

const panels = useAsync(() =>
buildContextMenuForActions({
actions: actions.map((action) => ({ action, context, trigger })),
})
);

return (
<EuiPopover
button={<EuiButton onClick={() => setOpen((x) => !x)}>Grouping with categories</EuiButton>}
isOpen={open}
panelPaddingSize="none"
anchorPosition="downLeft"
closePopover={() => setOpen(false)}
>
<EuiContextMenu initialPanelId={'mainMenu'} panels={panels.value} />
</EuiPopover>
);
};
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,13 @@

### 🐛 Bug Fixes

- [TSVB] Fix the link to "serial differencing aggregation" documentation ([#3503](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3503))

### 📝 Documentation

- Update jest documentation links ([#3939](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3939))

### 🛠 Maintenance

- Add threshold to code coverage changes for project ([#4050](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/4050))
- Temporarily hardcode chromedriver to 112.0.0 to enable all ftr tests ([#4039]())
- Temporarily hardcode chromedriver to 112.0.0 to enable all ftr tests ([#4039](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/4039))
- Update MAINTAINERS.md and CODEOWNERS ([#3938](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3938))
- Add opensearch-dashboards-docker-dev to .gitignore ([#3781](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3781))
35 changes: 35 additions & 0 deletions release-notes/opensearch-dashboards.release-notes-2.8.0.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
## Version 2.8.0 Release Notes

### Deprecations

- Remove timeline application ([#3971](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3971))

### 🛡 Security

- [CVE-2023-2251] Bump `yaml` to `2.2.2` ([#3947](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3947))

### 📈 Features/Enhancements

- [Multiple Datasource] Support Amazon OpenSearch Serverless ([#3957](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3957))
- Add support for Node.js >=14.20.1 <19 ([#4071](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/4071))
- Bundle Node.js 14 as a fallback for operating systems that cannot run Node.js 18 ([#4151](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/4151))
- Enhance grouping for context menus ([#3924](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3924))

### 🐛 Bug Fixes

- [BUG] Fix bottom bar visibility using createPortal ([#3978](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3978))
- [Dashboards Listing] Fix listing limit to utilize `savedObjects:listingLimit` instead of `savedObjects:perPage` ([#4021](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/4021))

### 🚞 Infrastructure

- Install chrome driver for functional tests from path set by environment variable `TEST_BROWSER_BINARY_PATH`([#3997](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3997))
- Add threshold to code coverage config to prevent workflow failures ([#4040](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/4040))
- [CI] Skip checksum verification on OpenSearch snapshot for cypress tests ([#4188](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/4188))

### 🛠 Maintenance

- Use `exec` in the CLI shell scripts to prevent new process creation ([#3955](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/3955))

## 🎉 Welcome

Thank you to all the first-time contributors who made this release possible: @sikhote, @SergeyMyssak!
1 change: 1 addition & 0 deletions src/core/public/plugins/plugins_service.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,7 @@ function createManifest(
version: 'some-version',
configPath: ['path'],
requiredPlugins: required,
requiredOpenSearchPlugins: optional,
optionalPlugins: optional,
requiredBundles: [],
};
Expand Down
1 change: 1 addition & 0 deletions src/core/server/legacy/legacy_service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -275,6 +275,7 @@ export class LegacyService implements CoreService {
addClientWrapper: setupDeps.core.savedObjects.addClientWrapper,
registerType: setupDeps.core.savedObjects.registerType,
getImportExportObjectLimit: setupDeps.core.savedObjects.getImportExportObjectLimit,
setRepositoryFactoryProvider: setupDeps.core.savedObjects.setRepositoryFactoryProvider,
},
status: {
isStatusPageAnonymous: setupDeps.core.status.isStatusPageAnonymous,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -247,6 +247,79 @@ test('return error when manifest contains unrecognized properties', async () =>
});
});

describe('requiredOpenSearchPlugins', () => {
test('return error when plugin `requiredOpenSearchPlugins` is a string and not an array of string', async () => {
mockReadFilePromise.mockResolvedValue(
Buffer.from(
JSON.stringify({
id: 'id1',
version: '7.0.0',
server: true,
requiredOpenSearchPlugins: 'abc',
})
)
);

await expect(parseManifest(pluginPath, packageInfo, logger)).rejects.toMatchObject({
message: `The "requiredOpenSearchPlugins" in plugin manifest for "id1" should be an array of strings. (invalid-manifest, ${pluginManifestPath})`,
type: PluginDiscoveryErrorType.InvalidManifest,
path: pluginManifestPath,
});
});

test('return error when `requiredOpenSearchPlugins` is not a string', async () => {
mockReadFilePromise.mockResolvedValue(
Buffer.from(JSON.stringify({ id: 'id2', version: '7.0.0', requiredOpenSearchPlugins: 2 }))
);

await expect(parseManifest(pluginPath, packageInfo, logger)).rejects.toMatchObject({
message: `The "requiredOpenSearchPlugins" in plugin manifest for "id2" should be an array of strings. (invalid-manifest, ${pluginManifestPath})`,
type: PluginDiscoveryErrorType.InvalidManifest,
path: pluginManifestPath,
});
});

test('return error when plugin requiredOpenSearchPlugins is an array that contains non-string values', async () => {
mockReadFilePromise.mockResolvedValue(
Buffer.from(
JSON.stringify({ id: 'id3', version: '7.0.0', requiredOpenSearchPlugins: ['plugin1', 2] })
)
);

await expect(parseManifest(pluginPath, packageInfo, logger)).rejects.toMatchObject({
message: `The "requiredOpenSearchPlugins" in plugin manifest for "id3" should be an array of strings. (invalid-manifest, ${pluginManifestPath})`,
type: PluginDiscoveryErrorType.InvalidManifest,
path: pluginManifestPath,
});
});

test('Happy path when plugin `requiredOpenSearchPlugins` is an array of string', async () => {
mockReadFilePromise.mockResolvedValue(
Buffer.from(
JSON.stringify({
id: 'id1',
version: '7.0.0',
server: true,
requiredOpenSearchPlugins: ['plugin1', 'plugin2'],
})
)
);

await expect(parseManifest(pluginPath, packageInfo, logger)).resolves.toEqual({
id: 'id1',
configPath: 'id_1',
version: '7.0.0',
opensearchDashboardsVersion: '7.0.0',
optionalPlugins: [],
requiredPlugins: [],
requiredOpenSearchPlugins: ['plugin1', 'plugin2'],
requiredBundles: [],
server: true,
ui: false,
});
});
});

describe('configPath', () => {
test('falls back to plugin id if not specified', async () => {
mockReadFilePromise.mockResolvedValue(
Expand Down Expand Up @@ -301,6 +374,7 @@ test('set defaults for all missing optional fields', async () => {
opensearchDashboardsVersion: '7.0.0',
optionalPlugins: [],
requiredPlugins: [],
requiredOpenSearchPlugins: [],
requiredBundles: [],
server: true,
ui: false,
Expand All @@ -317,6 +391,7 @@ test('return all set optional fields as they are in manifest', async () => {
opensearchDashboardsVersion: '7.0.0',
requiredPlugins: ['some-required-plugin', 'some-required-plugin-2'],
optionalPlugins: ['some-optional-plugin'],
requiredOpenSearchPlugins: ['test-opensearch-plugin-1', 'test-opensearch-plugin-2'],
ui: true,
})
)
Expand All @@ -330,6 +405,7 @@ test('return all set optional fields as they are in manifest', async () => {
optionalPlugins: ['some-optional-plugin'],
requiredBundles: [],
requiredPlugins: ['some-required-plugin', 'some-required-plugin-2'],
requiredOpenSearchPlugins: ['test-opensearch-plugin-1', 'test-opensearch-plugin-2'],
server: false,
ui: true,
});
Expand All @@ -344,6 +420,7 @@ test('return manifest when plugin expected OpenSearch Dashboards version matches
version: 'some-version',
opensearchDashboardsVersion: '7.0.0-alpha2',
requiredPlugins: ['some-required-plugin'],
requiredOpenSearchPlugins: [],
server: true,
})
)
Expand All @@ -356,6 +433,7 @@ test('return manifest when plugin expected OpenSearch Dashboards version matches
opensearchDashboardsVersion: '7.0.0-alpha2',
optionalPlugins: [],
requiredPlugins: ['some-required-plugin'],
requiredOpenSearchPlugins: [],
requiredBundles: [],
server: true,
ui: false,
Expand Down Expand Up @@ -383,6 +461,7 @@ test('return manifest when plugin expected OpenSearch Dashboards version is `ope
opensearchDashboardsVersion: 'opensearchDashboards',
optionalPlugins: [],
requiredPlugins: ['some-required-plugin'],
requiredOpenSearchPlugins: [],
requiredBundles: [],
server: true,
ui: true,
Expand Down
26 changes: 26 additions & 0 deletions src/core/server/plugins/discovery/plugin_manifest_parser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ const KNOWN_MANIFEST_FIELDS = (() => {
version: true,
configPath: true,
requiredPlugins: true,
requiredOpenSearchPlugins: true,
optionalPlugins: true,
ui: true,
server: true,
Expand Down Expand Up @@ -156,6 +157,28 @@ export async function parseManifest(
);
}

if (
manifest.requiredOpenSearchPlugins !== undefined &&
(!Array.isArray(manifest.requiredOpenSearchPlugins) ||
!manifest.requiredOpenSearchPlugins.every((plugin) => typeof plugin === 'string'))
) {
throw PluginDiscoveryError.invalidManifest(
manifestPath,
new Error(
`The "requiredOpenSearchPlugins" in plugin manifest for "${manifest.id}" should be an array of strings.`
)
);
}

if (
Array.isArray(manifest.requiredOpenSearchPlugins) &&
manifest.requiredOpenSearchPlugins.length > 0
) {
log.info(
`Plugin ${manifest.id} has a dependency on following OpenSearch plugin(s): "${manifest.requiredOpenSearchPlugins}".`
);
}

const expectedOpenSearchDashboardsVersion =
typeof manifest.opensearchDashboardsVersion === 'string' && manifest.opensearchDashboardsVersion
? manifest.opensearchDashboardsVersion
Expand Down Expand Up @@ -198,6 +221,9 @@ export async function parseManifest(
opensearchDashboardsVersion: expectedOpenSearchDashboardsVersion,
configPath: manifest.configPath || snakeCase(manifest.id),
requiredPlugins: Array.isArray(manifest.requiredPlugins) ? manifest.requiredPlugins : [],
requiredOpenSearchPlugins: Array.isArray(manifest.requiredOpenSearchPlugins)
? manifest.requiredOpenSearchPlugins
: [],
optionalPlugins: Array.isArray(manifest.optionalPlugins) ? manifest.optionalPlugins : [],
requiredBundles: Array.isArray(manifest.requiredBundles) ? manifest.requiredBundles : [],
ui: includesUiPlugin,
Expand Down
Loading
Loading