From ae799967a4feb1f87905d1a64fe2acfd5eb02ad5 Mon Sep 17 00:00:00 2001 From: Miki Date: Mon, 24 Oct 2022 12:13:43 -0700 Subject: [PATCH] Manually backports Windows changes from #2601 (#2647) * [Windows] Replaces `rm -rf` with `remove.js` * [dev/build] Facilitates using zipped archives of node releases * [div/build] Introduces Windows as a platform * [dev/build] Corrects cleaning of platform specific build artifacts * [dev/build] Enhances the cleanup of downloaded node binaries * [opensearch-dashboards-plugin] Removes prohibition on installing plugins on Windows * [@osd/utils] Adds a method to standardize path references across platforms * [dev/build] Standardize paths in tests * [@osd/telemetry-tools] Normalizes the collection paths * [plugins/url-forwarding] Fixes the usage of `normalizePath` across node and browser * [@osd/pm] Allows symlink created for tests without elevated privileges on Windows * [@osd/opensearch] Allows usage of Windows snapshots in integration tests * [@osd/opensearch] Employs absolute paths in tests * [@osd/apm-config-loader] Employs absolute paths in tests * [core/server] Employs absolute and posix references to paths * [@osd/optimizer] Standardize paths in tests * [@osd/tests] Employs absolute paths in tests * [@osd/pm] Standardize paths in project trees * [plugins/telemetry] Accommodates the inability of Windows to create unreadable files for testing * [@osd/config-schema] Normalize paths in tests * [@osd/plugin-helpers] Standardize paths in tests * [@osd/plugin-generator] Standardize paths in tests * [Windows] Update changelog backport PR: https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2601 Signed-off-by: Miki --- CHANGELOG.md | 1 + package.json | 5 +- .../src/utils/get_config_file_paths.test.ts | 2 +- .../__snapshots__/schema_error.test.ts.snap | 2 +- .../src/errors/schema_error.test.ts | 10 ++-- packages/osd-opensearch-archiver/package.json | 6 +-- packages/osd-opensearch/src/artifact.js | 8 ++-- packages/osd-opensearch/src/artifact.test.js | 4 +- .../src/utils/decompress.test.js | 4 +- .../src/utils/extract_config_files.test.js | 3 +- .../utils/find_most_recently_changed.test.js | 3 +- .../osd-optimizer/src/common/bundle.test.ts | 6 ++- .../src/optimizer/get_changes.test.ts | 15 ++++-- .../src/optimizer/get_plugin_bundles.test.ts | 5 ++ .../integration_tests/generate_plugin.test.ts | 12 +++-- packages/osd-plugin-helpers/package.json | 2 +- .../src/integration_tests/build.test.ts | 12 +++-- packages/osd-pm/src/utils/projects.test.ts | 3 +- packages/osd-pm/src/utils/projects_tree.ts | 3 +- .../src/tools/ts_parser.ts | 4 +- .../osd-telemetry-tools/src/tools/utils.ts | 5 +- .../lib/suite_tracker.test.ts | 2 +- packages/osd-utils/src/path/index.ts | 26 +++++++++- scripts/remove.js | 31 ++++++++++++ src/cli_plugin/install/pack.test.js | 5 +- src/cli_plugin/install/settings.js | 4 +- src/cli_plugin/install/settings.test.js | 22 +++++++-- src/cli_plugin/install/zip.test.js | 4 +- .../server/metrics/collectors/cgroup.test.ts | 7 ++- .../discovery/plugins_discovery.test.ts | 5 +- .../integration_tests/plugins_service.test.ts | 4 +- src/core/server/plugins/plugin.test.ts | 3 +- src/core/server/plugins/plugin.ts | 4 +- .../server/plugins/plugins_service.test.ts | 3 +- src/dev/build/args.test.ts | 38 +++++++++++++++ src/dev/build/args.ts | 2 + src/dev/build/cli.ts | 7 +-- src/dev/build/lib/config.test.ts | 15 +++++- src/dev/build/lib/config.ts | 4 +- src/dev/build/lib/exec.test.ts | 6 ++- src/dev/build/lib/fs.ts | 39 ++++++++++++++- src/dev/build/lib/platform.ts | 1 + src/dev/build/tasks/clean_tasks.ts | 6 +-- .../tasks/nodejs/clean_node_builds_task.ts | 10 ++-- .../nodejs/extract_node_builds_task.test.ts | 19 ++++---- .../tasks/nodejs/extract_node_builds_task.ts | 9 +--- .../build/tasks/nodejs/node_download_info.ts | 2 +- .../usage/telemetry_usage_collector.test.ts | 11 ++++- .../public/forward_app/normalize_path.ts | 6 ++- .../plugins/osd_tp_run_pipeline/package.json | 2 +- .../plugins/app_link_test/package.json | 2 +- .../plugins/core_app_status/package.json | 2 +- .../plugins/core_plugin_a/package.json | 2 +- .../plugins/core_plugin_appleave/package.json | 2 +- .../plugins/core_plugin_b/package.json | 2 +- .../core_plugin_chromeless/package.json | 2 +- .../core_plugin_route_timeouts/package.json | 2 +- .../core_plugin_static_assets/package.json | 2 +- .../plugins/core_provider_plugin/package.json | 2 +- .../plugins/data_search/package.json | 2 +- .../doc_views_links_plugin/package.json | 4 +- .../plugins/doc_views_plugin/package.json | 2 +- .../plugins/index_patterns/package.json | 2 +- .../management_test_plugin/package.json | 2 +- .../opensearch_client_plugin/package.json | 2 +- .../osd_sample_panel_action/package.json | 2 +- .../plugins/osd_top_nav/package.json | 2 +- .../osd_tp_custom_visualizations/package.json | 2 +- .../plugins/rendering_plugin/package.json | 2 +- .../plugins/ui_settings_plugin/package.json | 2 +- yarn.lock | 47 ++++++++++--------- 71 files changed, 360 insertions(+), 141 deletions(-) create mode 100644 scripts/remove.js diff --git a/CHANGELOG.md b/CHANGELOG.md index cd06fc293cd..3b41338faf5 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -23,6 +23,7 @@ Inspired from [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) * [Multi DataSource] Add data source config to opensearch-dashboards-docker ([#2557](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2557)) * [Multi DataSource] Make text content dynamically translated & update unit tests ([#2570](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2570)) * [Vis Builder] Change classname prefix wiz to vb ([#2581](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2581/files)) +* [Windows] Facilitate building and running OSD and plugins on Windows platforms ([#2601](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2601)) ### 🐛 Bug Fixes * [Vis Builder] Fixes auto bounds for timeseries bar chart visualization ([2401](https://github.com/opensearch-project/OpenSearch-Dashboards/pull/2401)) diff --git a/package.json b/package.json index c922c2b9eb7..c2767ccf025 100644 --- a/package.json +++ b/package.json @@ -65,7 +65,7 @@ "makelogs": "node scripts/makelogs", "uiFramework:compileCss": "cd packages/osd-ui-framework && yarn compileCss", "osd:watch": "node scripts/opensearch_dashboards --dev --logging.json=false", - "build:types": "rm -rf ./target/types && tsc --p tsconfig.types.json", + "build:types": "node scripts/remove.js ./target/types && tsc --p tsconfig.types.json", "docs:acceptApiChanges": "node --max-old-space-size=6144 scripts/check_published_api_changes.js --accept", "osd:bootstrap": "node scripts/build_ts_refs && node scripts/register_git_hook", "spec_to_console": "node scripts/spec_to_console", @@ -410,6 +410,7 @@ "mutation-observer": "^1.0.3", "ngreact": "^0.5.1", "nock": "12.0.3", + "node-stream-zip": "^1.15.0", "normalize-path": "^3.0.0", "nyc": "^15.1.0", "pixelmatch": "^5.1.0", @@ -459,4 +460,4 @@ "node": "14.20.0", "yarn": "^1.21.1" } -} \ No newline at end of file +} diff --git a/packages/osd-apm-config-loader/src/utils/get_config_file_paths.test.ts b/packages/osd-apm-config-loader/src/utils/get_config_file_paths.test.ts index e730a4ef9fd..32bff7f2939 100644 --- a/packages/osd-apm-config-loader/src/utils/get_config_file_paths.test.ts +++ b/packages/osd-apm-config-loader/src/utils/get_config_file_paths.test.ts @@ -40,7 +40,7 @@ describe('getConfigurationFilePaths', () => { expect(getConfigurationFilePaths(argv)).toEqual([ resolve(cwd, join('.', 'relative-path')), - '/absolute-path', + resolve('/absolute-path'), ]); }); diff --git a/packages/osd-config-schema/src/errors/__snapshots__/schema_error.test.ts.snap b/packages/osd-config-schema/src/errors/__snapshots__/schema_error.test.ts.snap index c34dd719e65..38f81a0cc62 100644 --- a/packages/osd-config-schema/src/errors/__snapshots__/schema_error.test.ts.snap +++ b/packages/osd-config-schema/src/errors/__snapshots__/schema_error.test.ts.snap @@ -3,6 +3,6 @@ exports[`includes stack 1`] = ` "Error: test at new SchemaError (packages/osd-config-schema/src/errors/schema_error.ts:35:5) - at Object. (packages/osd-config-schema/src/errors/schema_error.test.ts:55:11) + at Object. (packages/osd-config-schema/src/errors/schema_error.test.ts:59:11) at new Promise ()" `; diff --git a/packages/osd-config-schema/src/errors/schema_error.test.ts b/packages/osd-config-schema/src/errors/schema_error.test.ts index c6ebd5d0dbd..9e7b5a89708 100644 --- a/packages/osd-config-schema/src/errors/schema_error.test.ts +++ b/packages/osd-config-schema/src/errors/schema_error.test.ts @@ -28,7 +28,7 @@ * under the License. */ -import { relative } from 'path'; +import { relative, sep } from 'path'; import { SchemaError } from '.'; /** @@ -37,7 +37,7 @@ import { SchemaError } from '.'; export const cleanStack = (stack: string) => stack .split('\n') - .filter((line) => !line.includes('node_modules/') && !line.includes('internal/')) + .filter((line) => !line.includes('node_modules' + sep) && !line.includes('internal/')) .map((line) => { const parts = /.*\((.*)\).?/.exec(line) || []; @@ -46,7 +46,11 @@ export const cleanStack = (stack: string) => } const path = parts[1]; - return line.replace(path, relative(process.cwd(), path)); + // Cannot use `standardize` from `@osd/utils + let relativePath = relative(process.cwd(), path); + if (process.platform === 'win32') relativePath = relativePath.replace(/\\/g, '/'); + + return line.replace(path, relativePath); }) .join('\n'); diff --git a/packages/osd-opensearch-archiver/package.json b/packages/osd-opensearch-archiver/package.json index e1c28cc4748..f130ae44138 100644 --- a/packages/osd-opensearch-archiver/package.json +++ b/packages/osd-opensearch-archiver/package.json @@ -7,8 +7,8 @@ "devOnly": true }, "scripts": { - "osd:bootstrap": "rm -rf target && tsc", - "osd:watch": "rm -rf target && tsc --watch" + "osd:bootstrap": "node ../../scripts/remove.js target && tsc", + "osd:watch": "node ../../scripts/remove.js target && tsc --watch" }, "dependencies": { "@osd/dev-utils": "1.0.0", @@ -17,4 +17,4 @@ "devDependencies": { "@types/elasticsearch": "^5.0.33" } -} \ No newline at end of file +} diff --git a/packages/osd-opensearch/src/artifact.js b/packages/osd-opensearch/src/artifact.js index 69f443245d4..b7d8857ba09 100644 --- a/packages/osd-opensearch/src/artifact.js +++ b/packages/osd-opensearch/src/artifact.js @@ -186,12 +186,14 @@ async function getArtifactSpecForSnapshotFromUrl(urlVersion, log) { // issue: https://github.com/opensearch-project/OpenSearch-Dashboards/issues/475 const platform = process.platform === 'win32' ? 'windows' : process.platform; const arch = process.arch === 'arm64' ? 'arm64' : 'x64'; - if (platform !== 'linux') { - throw createCliError(`Snapshots are only available for Linux`); + const extension = process.platform === 'win32' ? 'zip' : 'tar.gz'; + + if (platform !== 'linux' && platform !== 'windows') { + throw createCliError(`Snapshots are only available for Linux and Windows`); } const latestUrl = `${DAILY_SNAPSHOTS_BASE_URL}/${desiredVersion}-SNAPSHOT`; - const latestFile = `opensearch-min-${desiredVersion}-SNAPSHOT-${platform}-${arch}-latest.tar.gz`; + const latestFile = `opensearch-min-${desiredVersion}-SNAPSHOT-${platform}-${arch}-latest.${extension}`; const completeLatestUrl = `${latestUrl}/${latestFile}`; let { abc, resp } = await verifySnapshotUrl(completeLatestUrl, log); diff --git a/packages/osd-opensearch/src/artifact.test.js b/packages/osd-opensearch/src/artifact.test.js index b9c331517c7..1d5d0bdf330 100644 --- a/packages/osd-opensearch/src/artifact.test.js +++ b/packages/osd-opensearch/src/artifact.test.js @@ -163,10 +163,10 @@ describe('Artifact', () => { }); }); - it('should throw when on a non-Linux platform', async () => { + it('should throw when on a non-Linux or non-Windows platform', async () => { Object.defineProperties(process, { platform: { - value: 'win32', + value: 'darwin', }, arch: { value: ORIGINAL_ARCHITECTURE, diff --git a/packages/osd-opensearch/src/utils/decompress.test.js b/packages/osd-opensearch/src/utils/decompress.test.js index e9e163c3ebc..bf30b49eeba 100644 --- a/packages/osd-opensearch/src/utils/decompress.test.js +++ b/packages/osd-opensearch/src/utils/decompress.test.js @@ -52,8 +52,8 @@ beforeEach(() => { fs.copyFileSync(path.resolve(fixturesFolder, 'snapshot.tar.gz'), tarGzSnapshot); }); -afterEach(() => { - del.sync(tmpFolder, { force: true }); +afterEach(async () => { + await del(tmpFolder, { force: true }); }); test('zip strips root directory', async () => { diff --git a/packages/osd-opensearch/src/utils/extract_config_files.test.js b/packages/osd-opensearch/src/utils/extract_config_files.test.js index 3d73d821dbc..c9da144f6e3 100644 --- a/packages/osd-opensearch/src/utils/extract_config_files.test.js +++ b/packages/osd-opensearch/src/utils/extract_config_files.test.js @@ -36,6 +36,7 @@ jest.mock('fs', () => ({ const { extractConfigFiles } = require('./extract_config_files'); const fs = require('fs'); +const path = require('path'); afterEach(() => { jest.clearAllMocks(); @@ -55,7 +56,7 @@ test('copies file', () => { extractConfigFiles(['path=/data/foo.yml'], '/opensearch'); expect(fs.readFileSync.mock.calls[0][0]).toEqual('/data/foo.yml'); - expect(fs.writeFileSync.mock.calls[0][0]).toEqual('/opensearch/config/foo.yml'); + expect(fs.writeFileSync.mock.calls[0][0]).toEqual(path.resolve('/opensearch/config/foo.yml')); }); test('ignores file which does not exist', () => { diff --git a/packages/osd-opensearch/src/utils/find_most_recently_changed.test.js b/packages/osd-opensearch/src/utils/find_most_recently_changed.test.js index 235ce9fd669..10b3dd78ff9 100644 --- a/packages/osd-opensearch/src/utils/find_most_recently_changed.test.js +++ b/packages/osd-opensearch/src/utils/find_most_recently_changed.test.js @@ -27,6 +27,7 @@ * specific language governing permissions and limitations * under the License. */ +const path = require('path'); jest.mock('fs', () => ({ statSync: jest.fn().mockImplementation((path) => { @@ -57,7 +58,7 @@ const { findMostRecentlyChanged } = require('./find_most_recently_changed'); test('returns newest file', () => { const file = findMostRecentlyChanged('/data/*.yml'); - expect(file).toEqual('/data/newest.yml'); + expect(file).toEqual(path.resolve('/data/newest.yml')); }); afterAll(() => { diff --git a/packages/osd-optimizer/src/common/bundle.test.ts b/packages/osd-optimizer/src/common/bundle.test.ts index 16aa012cf91..ceb7eff4b1d 100644 --- a/packages/osd-optimizer/src/common/bundle.test.ts +++ b/packages/osd-optimizer/src/common/bundle.test.ts @@ -28,6 +28,7 @@ * under the License. */ +import { resolve } from 'path'; import { Bundle, BundleSpec, parseBundles } from './bundle'; jest.mock('fs'); @@ -88,13 +89,16 @@ it('provides the module count from the cache', () => { it('parses bundles from JSON specs', () => { const bundles = parseBundles(JSON.stringify([SPEC])); + let expectedCachePath = resolve('/foo/bar/target/.osd-optimizer-cache'); + // Cannot use `standardize` from `@osd/util` due to mocking of fs + if (process?.platform === 'win32') expectedCachePath = expectedCachePath.replace(/\\/g, '\\\\'); expect(bundles).toMatchInlineSnapshot(` Array [ Bundle { "banner": undefined, "cache": BundleCache { - "path": "/foo/bar/target/.osd-optimizer-cache", + "path": "${expectedCachePath}", "state": undefined, }, "contextDir": "/foo/bar", diff --git a/packages/osd-optimizer/src/optimizer/get_changes.test.ts b/packages/osd-optimizer/src/optimizer/get_changes.test.ts index 071bb8e1a26..44e1637d543 100644 --- a/packages/osd-optimizer/src/optimizer/get_changes.test.ts +++ b/packages/osd-optimizer/src/optimizer/get_changes.test.ts @@ -28,9 +28,12 @@ * under the License. */ +import path from 'path'; + jest.mock('execa'); import { getChanges } from './get_changes'; +import { standardize } from '@osd/dev-utils'; const execa: jest.Mock = jest.requireMock('execa'); @@ -56,12 +59,16 @@ it('parses git ls-files output', async () => { }; }); + const rootPath = path.resolve('/foo/bar/x/osd-optimizer') + path.sep; + const srcPath = path.join(rootPath, 'src') + path.sep; + const commonPath = path.join(srcPath, 'common') + path.sep; + await expect(getChanges('/foo/bar/x')).resolves.toMatchInlineSnapshot(` Map { - "/foo/bar/x/osd-optimizer/package.json" => "modified", - "/foo/bar/x/osd-optimizer/src/common/bundle.ts" => "modified", - "/foo/bar/x/osd-optimizer/src/common/bundles.ts" => "deleted", - "/foo/bar/x/osd-optimizer/src/get_bundle_definitions.test.ts" => "deleted", + "${standardize(rootPath, false, true)}package.json" => "modified", + "${standardize(commonPath, false, true)}bundle.ts" => "modified", + "${standardize(commonPath, false, true)}bundles.ts" => "deleted", + "${standardize(srcPath, false, true)}get_bundle_definitions.test.ts" => "deleted", } `); }); diff --git a/packages/osd-optimizer/src/optimizer/get_plugin_bundles.test.ts b/packages/osd-optimizer/src/optimizer/get_plugin_bundles.test.ts index 608b16a3661..28ee6179f01 100644 --- a/packages/osd-optimizer/src/optimizer/get_plugin_bundles.test.ts +++ b/packages/osd-optimizer/src/optimizer/get_plugin_bundles.test.ts @@ -31,10 +31,15 @@ import { createAbsolutePathSerializer } from '@osd/dev-utils'; import { getPluginBundles } from './get_plugin_bundles'; +import path from 'path'; expect.addSnapshotSerializer(createAbsolutePathSerializer('/repo', '')); expect.addSnapshotSerializer(createAbsolutePathSerializer('/output', '')); +expect.addSnapshotSerializer(createAbsolutePathSerializer(path.resolve('/output'), '')); expect.addSnapshotSerializer(createAbsolutePathSerializer('/outside/of/repo', '')); +expect.addSnapshotSerializer( + createAbsolutePathSerializer(path.resolve('/outside/of/repo'), '') +); it('returns a bundle for core and each plugin', () => { expect( diff --git a/packages/osd-plugin-generator/src/integration_tests/generate_plugin.test.ts b/packages/osd-plugin-generator/src/integration_tests/generate_plugin.test.ts index 51378b14470..45ec5a6986a 100644 --- a/packages/osd-plugin-generator/src/integration_tests/generate_plugin.test.ts +++ b/packages/osd-plugin-generator/src/integration_tests/generate_plugin.test.ts @@ -32,13 +32,17 @@ import Path from 'path'; import del from 'del'; import execa from 'execa'; -import { REPO_ROOT } from '@osd/utils'; -import { createAbsolutePathSerializer } from '@osd/dev-utils'; +import { REPO_ROOT, standardize, createAbsolutePathSerializer } from '@osd/dev-utils'; import globby from 'globby'; -const GENERATED_DIR = Path.resolve(REPO_ROOT, `plugins`); +// Has to be a posix reference because it is used to generate glob patterns +const GENERATED_DIR = standardize(Path.resolve(REPO_ROOT, `plugins`), true); -expect.addSnapshotSerializer(createAbsolutePathSerializer()); +expect.addSnapshotSerializer( + createAbsolutePathSerializer( + process?.platform === 'win32' ? standardize(REPO_ROOT, true) : REPO_ROOT + ) +); beforeEach(async () => { await del([`${GENERATED_DIR}/**`, `!${GENERATED_DIR}`, `!${GENERATED_DIR}/.gitignore`], { diff --git a/packages/osd-plugin-helpers/package.json b/packages/osd-plugin-helpers/package.json index 44719973018..3738aae36b1 100644 --- a/packages/osd-plugin-helpers/package.json +++ b/packages/osd-plugin-helpers/package.json @@ -12,7 +12,7 @@ "plugin-helpers": "bin/plugin-helpers.js" }, "scripts": { - "osd:bootstrap": "rm -rf target && tsc", + "osd:bootstrap": "node ../../scripts/remove.js && tsc", "osd:watch": "tsc --watch" }, "dependencies": { diff --git a/packages/osd-plugin-helpers/src/integration_tests/build.test.ts b/packages/osd-plugin-helpers/src/integration_tests/build.test.ts index 4dc550e5004..35195f9bc16 100644 --- a/packages/osd-plugin-helpers/src/integration_tests/build.test.ts +++ b/packages/osd-plugin-helpers/src/integration_tests/build.test.ts @@ -32,8 +32,12 @@ import Path from 'path'; import Fs from 'fs'; import execa from 'execa'; -import { REPO_ROOT } from '@osd/utils'; -import { createStripAnsiSerializer, createReplaceSerializer } from '@osd/dev-utils'; +import { + REPO_ROOT, + standardize, + createStripAnsiSerializer, + createReplaceSerializer, +} from '@osd/dev-utils'; import extract from 'extract-zip'; import del from 'del'; import globby from 'globby'; @@ -78,7 +82,7 @@ it('builds a generated plugin into a viable archive', async () => { expect(generateProc.all).toMatchInlineSnapshot(` " succ 🎉 - Your plugin has been created in plugins/foo_test_plugin + Your plugin has been created in ${standardize('plugins/foo_test_plugin', false, true)} " `); @@ -165,7 +169,7 @@ it('builds a non-semver generated plugin into a viable archive', async () => { expect(generateProc.all).toMatchInlineSnapshot(` " succ 🎉 - Your plugin has been created in plugins/foo_test_plugin + Your plugin has been created in ${standardize('plugins/foo_test_plugin', false, true)} " `); diff --git a/packages/osd-pm/src/utils/projects.test.ts b/packages/osd-pm/src/utils/projects.test.ts index 57935452feb..545b435a7e0 100644 --- a/packages/osd-pm/src/utils/projects.test.ts +++ b/packages/osd-pm/src/utils/projects.test.ts @@ -53,7 +53,8 @@ describe('#getProjects', () => { await promisify(symlink)( join(__dirname, '__fixtures__/symlinked-plugins/corge'), - join(rootPlugins, 'corge') + join(rootPlugins, 'corge'), + 'junction' // This parameter would only be used on Windows ); }); diff --git a/packages/osd-pm/src/utils/projects_tree.ts b/packages/osd-pm/src/utils/projects_tree.ts index 5a455f35ea6..41f9e433109 100644 --- a/packages/osd-pm/src/utils/projects_tree.ts +++ b/packages/osd-pm/src/utils/projects_tree.ts @@ -31,6 +31,7 @@ import chalk from 'chalk'; import path from 'path'; +import { standardize } from '@osd/utils'; import { Project } from './project'; const projectKey = Symbol('__project'); @@ -117,7 +118,7 @@ function createTreeStructure(tree: IProjectsTree): ITree { // `foo/bar/baz` instead. if (subtree.children && subtree.children.length === 1) { const child = subtree.children[0]; - const newName = chalk.dim(path.join(dir.toString(), child.name!)); + const newName = chalk.dim(standardize(path.join(dir.toString(), child.name!), true)); children.push({ children: child.children, diff --git a/packages/osd-telemetry-tools/src/tools/ts_parser.ts b/packages/osd-telemetry-tools/src/tools/ts_parser.ts index 2932bd76d47..31940dcfdfd 100644 --- a/packages/osd-telemetry-tools/src/tools/ts_parser.ts +++ b/packages/osd-telemetry-tools/src/tools/ts_parser.ts @@ -31,7 +31,7 @@ import * as ts from 'typescript'; import { createFailError } from '@osd/dev-utils'; import * as path from 'path'; -import { getProperty, getPropertyValue } from './utils'; +import { getProperty, getPropertyValue, normalizePath } from './utils'; import { getDescriptor, Descriptor } from './serializer'; export function* traverseNodes(maybeNodes: ts.Node | ts.Node[]): Generator { @@ -205,7 +205,7 @@ export function* parseUsageCollection( sourceFile: ts.SourceFile, program: ts.Program ): Generator { - const relativePath = path.relative(process.cwd(), sourceFile.fileName); + const relativePath = normalizePath(path.relative(process.cwd(), sourceFile.fileName), false); if (sourceHasUsageCollector(sourceFile)) { for (const node of traverseNodes(sourceFile)) { if (isMakeUsageCollectorFunction(node, sourceFile)) { diff --git a/packages/osd-telemetry-tools/src/tools/utils.ts b/packages/osd-telemetry-tools/src/tools/utils.ts index 3df213f8278..23717576947 100644 --- a/packages/osd-telemetry-tools/src/tools/utils.ts +++ b/packages/osd-telemetry-tools/src/tools/utils.ts @@ -311,6 +311,7 @@ export function difference(actual: any, expected: any) { return changes(actual, expected); } -export function normalizePath(inputPath: string) { - return normalize(path.relative('.', inputPath)); +export function normalizePath(inputPath: string, relativeToRoot: boolean = true) { + if (relativeToRoot) return normalize(path.relative('.', inputPath)); + return normalize(inputPath); } diff --git a/packages/osd-test/src/functional_test_runner/lib/suite_tracker.test.ts b/packages/osd-test/src/functional_test_runner/lib/suite_tracker.test.ts index f7c45727734..cc628b9de81 100644 --- a/packages/osd-test/src/functional_test_runner/lib/suite_tracker.test.ts +++ b/packages/osd-test/src/functional_test_runner/lib/suite_tracker.test.ts @@ -40,7 +40,7 @@ import { REPO_ROOT } from '@osd/dev-utils'; import { Lifecycle } from './lifecycle'; import { SuiteTracker } from './suite_tracker'; -const DEFAULT_TEST_METADATA_PATH = join(REPO_ROOT, 'target', 'test_metadata.json'); +const DEFAULT_TEST_METADATA_PATH = resolve(REPO_ROOT, 'target', 'test_metadata.json'); const MOCK_CONFIG_PATH = join('test', 'config.js'); const MOCK_TEST_PATH = join('test', 'apps', 'test.js'); const ENVS_TO_RESET = ['TEST_METADATA_PATH']; diff --git a/packages/osd-utils/src/path/index.ts b/packages/osd-utils/src/path/index.ts index c661b04fb6a..263d2d39ac3 100644 --- a/packages/osd-utils/src/path/index.ts +++ b/packages/osd-utils/src/path/index.ts @@ -28,7 +28,7 @@ * under the License. */ -import { join } from 'path'; +import { join, normalize } from 'path'; import { accessSync, constants } from 'fs'; import { TypeOf, schema } from '@osd/config-schema'; import { REPO_ROOT } from '../repo_root'; @@ -94,3 +94,27 @@ export const config = { data: schema.string({ defaultValue: () => getDataPath() }), }), }; + +/** + * Get a standardized reference to a path + * @param {string} path - the path to standardize + * @param {boolean} [usePosix=true] - produce a posix reference + * @param {boolean} [escapedBackslashes=true] - on Windows, double-backslash the reference + * @internal + */ +export const standardize = ( + path: string, + usePosix: boolean = true, + escapedBackslashes: boolean = true +) => { + /* Force os-dependant separators + * path.posix.normalize doesn't convert backslashes to slashes on Windows so we manually force it afterwards + */ + const normal = normalize(path); + + // Filter out in-browser executions as well as non-windows ones + if (process?.platform !== 'win32') return normal; + + if (usePosix) return normal.replace(/\\/g, '/'); + return escapedBackslashes ? normal.replace(/\\/g, '\\\\') : normal; +}; diff --git a/scripts/remove.js b/scripts/remove.js new file mode 100644 index 00000000000..cc3c6273937 --- /dev/null +++ b/scripts/remove.js @@ -0,0 +1,31 @@ +/* + * Copyright OpenSearch Contributors + * SPDX-License-Identifier: Apache-2.0 + */ + +/* eslint no-restricted-syntax: 0 */ +const del = require('del'); +const path = require('path'); + +if (!process.argv.includes(__filename)) { + console.error('Usage: node scripts/remove.js '); + process.exit(1); +} + +const toDeletes = process.argv + .slice(process.argv.indexOf(__filename + 1)) + .map((item) => path.resolve(item)); + +if (toDeletes.length === 0) { + console.warn('Nothing to delete'); + process.exit(0); +} + +(async () => { + const deletedPaths = await del(toDeletes); + if (deletedPaths === 0) { + console.warn('Nothing deleted'); + } else { + console.log('Deleted files and directories:\n\t', deletedPaths.join('\n\t')); + } +})(); diff --git a/src/cli_plugin/install/pack.test.js b/src/cli_plugin/install/pack.test.js index 5520e34bc3b..783593c6d9f 100644 --- a/src/cli_plugin/install/pack.test.js +++ b/src/cli_plugin/install/pack.test.js @@ -72,10 +72,11 @@ describe('opensearchDashboards cli', function () { Fs.mkdirSync(testWorkingPath, { recursive: true }); }); - afterEach(function () { + afterEach(async () => { logger.log.restore(); logger.error.restore(); - del.sync(workingPathRoot); + + await del(workingPathRoot); }); function copyReplyFile(filename) { diff --git a/src/cli_plugin/install/settings.js b/src/cli_plugin/install/settings.js index 3d7cdec3d62..2b0c34bfcd3 100644 --- a/src/cli_plugin/install/settings.js +++ b/src/cli_plugin/install/settings.js @@ -44,9 +44,7 @@ function generateUrls({ version, plugin }) { function generatePluginUrl(version, plugin) { const platform = process.platform === 'win32' ? 'windows' : process.platform; const arch = process.arch === 'arm64' ? 'arm64' : 'x64'; - if (platform !== 'linux') { - throw new Error('Plugins are only available for Linux'); - } + return `${LATEST_PLUGIN_BASE_URL}/${version}/latest/${platform}/${arch}/tar/builds/opensearch-dashboards/plugins/${plugin}-${version}.zip`; } diff --git a/src/cli_plugin/install/settings.test.js b/src/cli_plugin/install/settings.test.js index dc769496e9e..ac7cf94e676 100644 --- a/src/cli_plugin/install/settings.test.js +++ b/src/cli_plugin/install/settings.test.js @@ -137,7 +137,7 @@ describe('parse function', function () { `); }); - it('should throw when on a non-Linux platform', function () { + it('produces expected results on Windows', function () { Object.defineProperties(process, { platform: { value: 'win32', @@ -146,9 +146,23 @@ describe('parse function', function () { value: 'x64', }, }); - expect(() => parse(command, { ...defaultOptions }, osdPackage)).toThrow( - 'Plugins are only available for Linux' - ); + expect(parse(command, { ...defaultOptions }, osdPackage)).toMatchInlineSnapshot(` + Object { + "config": "", + "plugin": "plugin name", + "pluginDir": /plugins, + "quiet": false, + "silent": false, + "tempArchiveFile": /plugins/.plugin.installing/archive.part, + "timeout": 0, + "urls": Array [ + "plugin name", + "https://ci.opensearch.org/ci/dbc/distribution-build-opensearch-dashboards/1234/latest/windows/x64/tar/builds/opensearch-dashboards/plugins/plugin name-1234.zip", + ], + "version": 1234, + "workingPath": /plugins/.plugin.installing, + } + `); }); it('should not throw when on a non-x64 arch', function () { diff --git a/src/cli_plugin/install/zip.test.js b/src/cli_plugin/install/zip.test.js index f010acdd829..206b091c367 100644 --- a/src/cli_plugin/install/zip.test.js +++ b/src/cli_plugin/install/zip.test.js @@ -48,8 +48,8 @@ describe('opensearchDashboards cli', function () { tempPath = path.resolve(os.tmpdir(), randomDir); }); - afterEach(() => { - del.sync(tempPath, { force: true }); + afterEach(async () => { + await del(tempPath, { force: true }); }); describe('analyzeArchive', function () { diff --git a/src/core/server/metrics/collectors/cgroup.test.ts b/src/core/server/metrics/collectors/cgroup.test.ts index 633b3c8aeae..50fc952566b 100644 --- a/src/core/server/metrics/collectors/cgroup.test.ts +++ b/src/core/server/metrics/collectors/cgroup.test.ts @@ -31,6 +31,7 @@ import mockFs from 'mock-fs'; import { loggerMock } from '@osd/logging/target/mocks'; import { OsCgroupMetricsCollector } from './cgroup'; +import path from 'path'; describe('OsCgroupMetricsCollector', () => { afterEach(() => mockFs.restore()); @@ -140,10 +141,14 @@ throttled_time 666 const logger = loggerMock.create(); + const usagePath = + (process.platform === 'win32' ? '\\\\?\\' : '') + + path.resolve('/sys/fs/cgroup/cpuacct/groupname/cpuacct.usage'); + const collector = new OsCgroupMetricsCollector({ logger }); expect(await collector.collect()).toEqual({}); expect(logger.error).toHaveBeenCalledWith( - "cgroup metrics could not be read due to error: [Error: EACCES, permission denied '/sys/fs/cgroup/cpuacct/groupname/cpuacct.usage']" + `cgroup metrics could not be read due to error: [Error: EACCES, permission denied '${usagePath}']` ); }); }); diff --git a/src/core/server/plugins/discovery/plugins_discovery.test.ts b/src/core/server/plugins/discovery/plugins_discovery.test.ts index bc7480bb8ad..92b2cb71ef9 100644 --- a/src/core/server/plugins/discovery/plugins_discovery.test.ts +++ b/src/core/server/plugins/discovery/plugins_discovery.test.ts @@ -44,6 +44,7 @@ import { discover } from './plugins_discovery'; import { CoreContext } from '../../core_context'; const OPENSEARCH_DASHBOARDS_ROOT = process.cwd(); +const EXTENDED_PATH_PREFIX = process.platform === 'win32' ? '\\\\?\\' : ''; const Plugins = { invalid: () => ({ @@ -243,7 +244,7 @@ describe('plugins discovery system', () => { const srcPluginsPath = resolve(OPENSEARCH_DASHBOARDS_ROOT, 'src', 'plugins'); expect(errors).toEqual( expect.arrayContaining([ - `Error: EACCES, permission denied '${srcPluginsPath}' (invalid-search-path, ${srcPluginsPath})`, + `Error: EACCES, permission denied '${EXTENDED_PATH_PREFIX}${srcPluginsPath}' (invalid-search-path, ${srcPluginsPath})`, ]) ); }); @@ -278,7 +279,7 @@ describe('plugins discovery system', () => { const errorPath = manifestPath('plugin_a'); expect(errors).toEqual( expect.arrayContaining([ - `Error: EACCES, permission denied '${errorPath}' (missing-manifest, ${errorPath})`, + `Error: EACCES, permission denied '${EXTENDED_PATH_PREFIX}${errorPath}' (missing-manifest, ${errorPath})`, ]) ); }); diff --git a/src/core/server/plugins/integration_tests/plugins_service.test.ts b/src/core/server/plugins/integration_tests/plugins_service.test.ts index 29396d0acce..34310ea3de3 100644 --- a/src/core/server/plugins/integration_tests/plugins_service.test.ts +++ b/src/core/server/plugins/integration_tests/plugins_service.test.ts @@ -32,7 +32,7 @@ import { REPO_ROOT } from '@osd/dev-utils'; import { mockPackage, mockDiscover } from './plugins_service.test.mocks'; -import { join } from 'path'; +import { posix } from 'path'; import { PluginsService } from '../plugins_service'; import { ConfigPath, ConfigService, Env } from '../../config'; @@ -163,7 +163,7 @@ describe('PluginsService', () => { } as Plugin); jest.doMock( - join(pluginPath, 'server'), + posix.join(pluginPath, 'server'), () => ({ plugin: pluginInitializer, }), diff --git a/src/core/server/plugins/plugin.test.ts b/src/core/server/plugins/plugin.test.ts index 1858f7557ad..9543d379493 100644 --- a/src/core/server/plugins/plugin.test.ts +++ b/src/core/server/plugins/plugin.test.ts @@ -28,7 +28,7 @@ * under the License. */ -import { join } from 'path'; +import { posix } from 'path'; import { BehaviorSubject } from 'rxjs'; import { REPO_ROOT } from '@osd/dev-utils'; import { schema } from '@osd/config-schema'; @@ -47,6 +47,7 @@ import { InstanceInfo, } from './plugin_context'; +const { join } = posix; const mockPluginInitializer = jest.fn(); const logger = loggingSystemMock.create(); jest.doMock( diff --git a/src/core/server/plugins/plugin.ts b/src/core/server/plugins/plugin.ts index 7dbe4da4cc5..89a2aecc82f 100644 --- a/src/core/server/plugins/plugin.ts +++ b/src/core/server/plugins/plugin.ts @@ -28,7 +28,7 @@ * under the License. */ -import { join } from 'path'; +import { posix } from 'path'; import typeDetect from 'type-detect'; import { Subject } from 'rxjs'; import { first } from 'rxjs/operators'; @@ -45,6 +45,8 @@ import { } from './types'; import { CoreSetup, CoreStart } from '..'; +const { join } = posix; + /** * Lightweight wrapper around discovered plugin that is responsible for instantiating * plugin and dispatching proper context and dependencies into plugin's lifecycle hooks. diff --git a/src/core/server/plugins/plugins_service.test.ts b/src/core/server/plugins/plugins_service.test.ts index cc4ac5e65fa..cff5ae79b91 100644 --- a/src/core/server/plugins/plugins_service.test.ts +++ b/src/core/server/plugins/plugins_service.test.ts @@ -30,7 +30,7 @@ import { mockDiscover, mockPackage } from './plugins_service.test.mocks'; -import { resolve, join } from 'path'; +import { resolve, posix } from 'path'; import { BehaviorSubject, from } from 'rxjs'; import { schema } from '@osd/config-schema'; import { createAbsolutePathSerializer, REPO_ROOT } from '@osd/dev-utils'; @@ -48,6 +48,7 @@ import { config } from './plugins_config'; import { take } from 'rxjs/operators'; import { DiscoveredPlugin } from './types'; +const { join } = posix; const MockPluginsSystem: jest.Mock = PluginsSystem as any; let pluginsService: PluginsService; diff --git a/src/dev/build/args.test.ts b/src/dev/build/args.test.ts index 262305f6225..2304c560a68 100644 --- a/src/dev/build/args.test.ts +++ b/src/dev/build/args.test.ts @@ -62,6 +62,7 @@ it('build dist for current platform, without packages, by default', () => { "darwin": false, "linux": false, "linuxArm": false, + "windows": false, }, "versionQualifier": "", }, @@ -90,6 +91,7 @@ it('build dist for linux x64 platform, without packages, if --linux is passed', "darwin": false, "linux": true, "linuxArm": false, + "windows": false, }, "versionQualifier": "", }, @@ -118,6 +120,7 @@ it('build dist for linux arm64 platform, without packages, if --linux-arm is pas "darwin": false, "linux": false, "linuxArm": true, + "windows": false, }, "versionQualifier": "", }, @@ -146,6 +149,36 @@ it('build dist for darwin x64 platform, without packages, if --darwin is passed' "darwin": true, "linux": false, "linuxArm": false, + "windows": false, + }, + "versionQualifier": "", + }, + "log": , + "showHelp": false, + "unknownFlags": Array [], + } + `); +}); + +it('build dist for windows x64 platform, without packages, if --windows is passed', () => { + expect(readCliArgs(['node', 'scripts/build-platform', '--windows'])).toMatchInlineSnapshot(` + Object { + "buildOptions": Object { + "createArchives": true, + "createDebArmPackage": false, + "createDebPackage": false, + "createDockerPackage": false, + "createDockerUbiPackage": false, + "createRpmArmPackage": false, + "createRpmPackage": false, + "downloadFreshNode": true, + "isRelease": false, + "targetAllPlatforms": false, + "targetPlatforms": Object { + "darwin": false, + "linux": false, + "linuxArm": false, + "windows": true, }, "versionQualifier": "", }, @@ -174,6 +207,7 @@ it('builds packages if --all-platforms is passed', () => { "darwin": false, "linux": false, "linuxArm": false, + "windows": false, }, "versionQualifier": "", }, @@ -202,6 +236,7 @@ it('limits packages if --rpm passed with --all-platforms', () => { "darwin": false, "linux": false, "linuxArm": false, + "windows": false, }, "versionQualifier": "", }, @@ -230,6 +265,7 @@ it('limits packages if --deb passed with --all-platforms', () => { "darwin": false, "linux": false, "linuxArm": false, + "windows": false, }, "versionQualifier": "", }, @@ -259,6 +295,7 @@ it('limits packages if --docker passed with --all-platforms', () => { "darwin": false, "linux": false, "linuxArm": false, + "windows": false, }, "versionQualifier": "", }, @@ -288,6 +325,7 @@ it('limits packages if --docker passed with --skip-docker-ubi and --all-platform "darwin": false, "linux": false, "linuxArm": false, + "windows": false, }, "versionQualifier": "", }, diff --git a/src/dev/build/args.ts b/src/dev/build/args.ts index 7c16b6de539..7e131174e33 100644 --- a/src/dev/build/args.ts +++ b/src/dev/build/args.ts @@ -50,6 +50,7 @@ export function readCliArgs(argv: string[]) { 'verbose', 'debug', 'all-platforms', + 'windows', 'darwin', 'linux', 'linux-arm', @@ -130,6 +131,7 @@ export function readCliArgs(argv: string[]) { createDockerPackage: isOsPackageDesired('docker'), createDockerUbiPackage: isOsPackageDesired('docker') && !Boolean(flags['skip-docker-ubi']), targetPlatforms: { + windows: Boolean(flags.windows), darwin: Boolean(flags.darwin), linux: Boolean(flags.linux), linuxArm: Boolean(flags['linux-arm']), diff --git a/src/dev/build/cli.ts b/src/dev/build/cli.ts index 0153a1768c9..b075a6047ac 100644 --- a/src/dev/build/cli.ts +++ b/src/dev/build/cli.ts @@ -58,9 +58,10 @@ if (showHelp) { --skip-archives {dim Don't produce tar/zip archives} --skip-os-packages {dim Don't produce rpm/deb/docker packages} --all-platforms {dim Produce archives for all platforms, not just this one} - --linux {dim Produce archives for only linux x64 platform} - --linux-arm {dim Produce archives for only linux arm64 platform} - --darwin {dim Produce archives for only darwin x64 platform} + --linux {dim Produce archives only for linux x64 platform} + --linux-arm {dim Produce archives only for linux arm64 platform} + --darwin {dim Produce archives only for darwin x64 platform} + --windows {dim Produce archives only for windows x64 platform} --rpm {dim Only build the rpm package} --deb {dim Only build the deb package} --docker {dim Only build the docker image} diff --git a/src/dev/build/lib/config.test.ts b/src/dev/build/lib/config.test.ts index 57b9775bf3f..db96a8c18dd 100644 --- a/src/dev/build/lib/config.test.ts +++ b/src/dev/build/lib/config.test.ts @@ -30,7 +30,7 @@ import { resolve } from 'path'; -import { REPO_ROOT } from '@osd/utils'; +import { REPO_ROOT, standardize } from '@osd/utils'; import { createAbsolutePathSerializer } from '@osd/dev-utils'; import pkg from '../../../../package.json'; @@ -54,6 +54,7 @@ const setup = async ({ darwin: false, linux: false, linuxArm: false, + windows: false, }, }: { targetAllPlatforms?: boolean; @@ -61,6 +62,7 @@ const setup = async ({ darwin: boolean; linux: boolean; linuxArm: boolean; + windows: boolean; }; } = {}) => { return await Config.create({ @@ -87,7 +89,9 @@ describe('#getNodeVersion()', () => { describe('#getRepoRelativePath()', () => { it('converts an absolute path to relative path, from the root of the repo', async () => { const config = await setup(); - expect(config.getRepoRelativePath(__dirname)).toMatchInlineSnapshot(`"src/dev/build/lib"`); + expect(config.getRepoRelativePath(__dirname)).toMatchInlineSnapshot( + `"${standardize('src/dev/build/lib', false, true)}"` + ); }); }); @@ -115,6 +119,7 @@ describe('#hasSpecifiedPlatform', () => { darwin: true, linux: false, linuxArm: false, + windows: false, }, }); expect(config.hasSpecifiedPlatform() === true); @@ -127,6 +132,7 @@ describe('#hasSpecifiedPlatform', () => { darwin: false, linux: false, linuxArm: true, + windows: false, }, }); expect(config.hasSpecifiedPlatform() === true); @@ -139,6 +145,7 @@ describe('#hasSpecifiedPlatform', () => { darwin: false, linux: true, linuxArm: false, + windows: false, }, }); expect(config.hasSpecifiedPlatform() === true); @@ -205,6 +212,7 @@ describe('#getTargetPlatforms()', () => { darwin: true, linux: false, linuxArm: false, + windows: false, }, }); @@ -227,6 +235,7 @@ describe('#getTargetPlatforms()', () => { darwin: false, linux: true, linuxArm: false, + windows: false, }, }); @@ -249,6 +258,7 @@ describe('#getTargetPlatforms()', () => { darwin: false, linux: false, linuxArm: true, + windows: false, }, }); @@ -271,6 +281,7 @@ describe('#getTargetPlatforms()', () => { darwin: true, linux: false, linuxArm: true, + windows: false, }, }); diff --git a/src/dev/build/lib/config.ts b/src/dev/build/lib/config.ts index 2804a702be4..4f47a5ec8f5 100644 --- a/src/dev/build/lib/config.ts +++ b/src/dev/build/lib/config.ts @@ -143,6 +143,7 @@ export class Config { const platforms: Platform[] = []; if (this.targetPlatforms.darwin) platforms.push(this.getPlatform('darwin', 'x64')); if (this.targetPlatforms.linux) platforms.push(this.getPlatform('linux', 'x64')); + if (this.targetPlatforms.windows) platforms.push(this.getPlatform('win32', 'x64')); if (this.targetPlatforms.linuxArm) platforms.push(this.getPlatform('linux', 'arm64')); if (platforms.length > 0) return platforms; @@ -153,7 +154,7 @@ export class Config { /** * Return the list of Platforms we need/have node downloads for. We always * include the linux platform even if we aren't targeting linux so we can - * reliably get the LICENSE file, which isn't included in the windows version + * reliably get the LICENSE file. */ getNodePlatforms() { if (this.targetAllPlatforms) { @@ -164,6 +165,7 @@ export class Config { return [this.getPlatform('linux', 'x64')]; } + // ToDo: All node dists, including Windows, contain a LICENSE file; do we still need to do this? return [this.getPlatformForThisOs(), this.getPlatform('linux', 'x64')]; } diff --git a/src/dev/build/lib/exec.test.ts b/src/dev/build/lib/exec.test.ts index 2dc75b3a311..7257f7f88db 100644 --- a/src/dev/build/lib/exec.test.ts +++ b/src/dev/build/lib/exec.test.ts @@ -39,6 +39,8 @@ import { import { exec } from './exec'; +const escapedPathToNode = Path.sep === '\\' ? '\\\\node.exe' : '/node'; + const testWriter = new ToolingLogCollectingWriter(); const log = new ToolingLog(); log.setWriters([testWriter]); @@ -59,7 +61,7 @@ it('executes a command, logs the command, and logs the output', async () => { await exec(log, process.execPath, ['-e', 'console.log("hi")']); expect(testWriter.messages).toMatchInlineSnapshot(` Array [ - " debg $ /node -e console.log(\\"hi\\")", + " debg $ ${escapedPathToNode} -e console.log(\\"hi\\")", " debg hi", ] `); @@ -71,7 +73,7 @@ it('logs using level: option', async () => { }); expect(testWriter.messages).toMatchInlineSnapshot(` Array [ - " info $ /node -e console.log(\\"hi\\")", + " info $ ${escapedPathToNode} -e console.log(\\"hi\\")", " info hi", ] `); diff --git a/src/dev/build/lib/fs.ts b/src/dev/build/lib/fs.ts index ae846ef7d67..53fc241f772 100644 --- a/src/dev/build/lib/fs.ts +++ b/src/dev/build/lib/fs.ts @@ -36,6 +36,7 @@ import { createGunzip } from 'zlib'; import { inspect, promisify } from 'util'; import archiver from 'archiver'; +import * as StreamZip from 'node-stream-zip'; import vfs from 'vinyl-fs'; import File from 'vinyl'; import del from 'del'; @@ -183,7 +184,7 @@ export async function copyAll( destination: string, options: CopyAllOptions = {} ) { - const { select = ['**/*'], dot = false, time = Date.now() } = options; + const { select = ['**/*'], dot = false, time = Date.now() / 1000 } = options; assertAbsolute(sourceDir); assertAbsolute(destination); @@ -266,6 +267,38 @@ export async function gunzip(source: string, destination: string) { ); } +interface UnzipOptions { + strip?: boolean | number; +} + +export async function unzip(source: string, destination: string, options: UnzipOptions) { + assertAbsolute(source); + assertAbsolute(destination); + + await mkdirAsync(destination, { recursive: true }); + + const zip = new StreamZip.async({ file: source }); + + if (!options.strip || !isFinite(options.strip as number)) { + // Extract the entire archive + await zip.extract(null, destination); + } else { + const stripLevels = options.strip === true ? 1 : options.strip; + + // Find the directories that are `stripLevels` deep and extract them only + for (const entry of Object.values(await zip.entries())) { + if (!entry.isDirectory) continue; + + const pathDepth = entry.name.replace(/\/+$/, '').split('/').length; + if (stripLevels === pathDepth) { + await zip.extract(entry.name, destination); + } + } + } + + await zip.close(); +} + interface CompressTarOptions { createRootDirectory: boolean; source: string; @@ -325,3 +358,7 @@ export async function compressZip({ return fileCount; } + +export function normalizePath(loc: string) { + return sep === '\\' ? loc.replace(/\\/g, '/') : loc; +} diff --git a/src/dev/build/lib/platform.ts b/src/dev/build/lib/platform.ts index 6553bcd3b11..673356ec620 100644 --- a/src/dev/build/lib/platform.ts +++ b/src/dev/build/lib/platform.ts @@ -35,6 +35,7 @@ export interface TargetPlatforms { darwin: boolean; linuxArm: boolean; linux: boolean; + windows: boolean; } export class Platform { diff --git a/src/dev/build/tasks/clean_tasks.ts b/src/dev/build/tasks/clean_tasks.ts index 8b1d635cdde..c420a6b36b2 100644 --- a/src/dev/build/tasks/clean_tasks.ts +++ b/src/dev/build/tasks/clean_tasks.ts @@ -30,7 +30,7 @@ import minimatch from 'minimatch'; -import { deleteAll, deleteEmptyFolders, scanDelete, Task, GlobalTask } from '../lib'; +import { deleteAll, deleteEmptyFolders, scanDelete, Task, GlobalTask, normalizePath } from '../lib'; export const Clean: GlobalTask = { global: true, @@ -190,8 +190,8 @@ export const CleanExtraBinScripts: Task = { if (platform.isWindows()) { await deleteAll( [ - build.resolvePathForPlatform(platform, 'bin', '*'), - `!${build.resolvePathForPlatform(platform, 'bin', '*.bat')}`, + normalizePath(build.resolvePathForPlatform(platform, 'bin', '*')), + `!${normalizePath(build.resolvePathForPlatform(platform, 'bin', '*.bat'))}`, ], log ); diff --git a/src/dev/build/tasks/nodejs/clean_node_builds_task.ts b/src/dev/build/tasks/nodejs/clean_node_builds_task.ts index 490d71e6d70..938f7f43f69 100644 --- a/src/dev/build/tasks/nodejs/clean_node_builds_task.ts +++ b/src/dev/build/tasks/nodejs/clean_node_builds_task.ts @@ -28,7 +28,7 @@ * under the License. */ -import { deleteAll, Task } from '../../lib'; +import { deleteAll, normalizePath, Task } from '../../lib'; export const CleanNodeBuilds: Task = { description: 'Cleaning npm from node', @@ -37,9 +37,11 @@ export const CleanNodeBuilds: Task = { for (const platform of config.getTargetPlatforms()) { await deleteAll( [ - build.resolvePathForPlatform(platform, 'node/lib/node_modules'), - build.resolvePathForPlatform(platform, 'node/bin/npm'), - build.resolvePathForPlatform(platform, 'node/bin/npx'), + normalizePath(build.resolvePathForPlatform(platform, 'node/**/node_modules')), + normalizePath(build.resolvePathForPlatform(platform, 'node/**/npm*')), + normalizePath(build.resolvePathForPlatform(platform, 'node/**/npx*')), + normalizePath(build.resolvePathForPlatform(platform, 'node/**/corepack*')), + normalizePath(build.resolvePathForPlatform(platform, 'node/**/nodevars*')), ], log ); diff --git a/src/dev/build/tasks/nodejs/extract_node_builds_task.test.ts b/src/dev/build/tasks/nodejs/extract_node_builds_task.test.ts index 73e23ecdf27..6b3a066a1d2 100644 --- a/src/dev/build/tasks/nodejs/extract_node_builds_task.test.ts +++ b/src/dev/build/tasks/nodejs/extract_node_builds_task.test.ts @@ -69,6 +69,7 @@ async function setup() { linux: false, linuxArm: false, darwin: false, + windows: false, }, }); @@ -101,15 +102,6 @@ it('runs expected fs operations', async () => { expect(usedMethods).toMatchInlineSnapshot(` Object { - "copy": Array [ - Array [ - /.node_binaries//node.exe, - /.node_binaries//win32-x64/node.exe, - Object { - "clone": true, - }, - ], - ], "untar": Array [ Array [ /.node_binaries//node-v-linux-x64.tar.gz, @@ -133,6 +125,15 @@ it('runs expected fs operations', async () => { }, ], ], + "unzip": Array [ + Array [ + /.node_binaries//node-v-win-x64.zip, + /.node_binaries//win32-x64, + Object { + "strip": 1, + }, + ], + ], } `); }); diff --git a/src/dev/build/tasks/nodejs/extract_node_builds_task.ts b/src/dev/build/tasks/nodejs/extract_node_builds_task.ts index 8e915a8b4e4..8252ce2153f 100644 --- a/src/dev/build/tasks/nodejs/extract_node_builds_task.ts +++ b/src/dev/build/tasks/nodejs/extract_node_builds_task.ts @@ -28,9 +28,7 @@ * under the License. */ -import Path from 'path'; - -import { untar, GlobalTask, copy } from '../../lib'; +import { untar, unzip, GlobalTask } from '../../lib'; import { getNodeDownloadInfo } from './node_download_info'; export const ExtractNodeBuilds: GlobalTask = { @@ -41,10 +39,7 @@ export const ExtractNodeBuilds: GlobalTask = { config.getTargetPlatforms().map(async (platform) => { const { downloadPath, extractDir } = getNodeDownloadInfo(config, platform); if (platform.isWindows()) { - // windows executable is not extractable, it's just an .exe file - await copy(downloadPath, Path.resolve(extractDir, 'node.exe'), { - clone: true, - }); + await unzip(downloadPath, extractDir, { strip: 1 }); } else { await untar(downloadPath, extractDir, { strip: 1 }); } diff --git a/src/dev/build/tasks/nodejs/node_download_info.ts b/src/dev/build/tasks/nodejs/node_download_info.ts index 5b9006e89f7..86e0c680ab0 100644 --- a/src/dev/build/tasks/nodejs/node_download_info.ts +++ b/src/dev/build/tasks/nodejs/node_download_info.ts @@ -37,7 +37,7 @@ export function getNodeDownloadInfo(config: Config, platform: Platform) { const arch = platform.getNodeArch(); const downloadName = platform.isWindows() - ? 'win-x64/node.exe' + ? `node-v${version}-win-x64.zip` : `node-v${version}-${arch}.tar.gz`; const url = `https://nodejs.org/dist/v${version}/${downloadName}`; diff --git a/src/plugins/telemetry/server/collectors/usage/telemetry_usage_collector.test.ts b/src/plugins/telemetry/server/collectors/usage/telemetry_usage_collector.test.ts index 2cffae202a1..7e49c7d3244 100644 --- a/src/plugins/telemetry/server/collectors/usage/telemetry_usage_collector.test.ts +++ b/src/plugins/telemetry/server/collectors/usage/telemetry_usage_collector.test.ts @@ -51,8 +51,15 @@ describe('telemetry_usage_collector', () => { unreadable: resolve(tempDir, 'tests-telemetry_usage_collector-unreadable.yml'), valid: resolve(tempDir, 'telemetry.yml'), }; - const invalidFiles = [tempFiles.too_big, tempFiles.unreadable]; + const invalidFiles = [tempFiles.too_big]; const validFiles = [tempFiles.blank, tempFiles.empty, tempFiles.valid]; + // Windows cannot create the `unreadable` file as unreadable + if (process.platform === 'win32') { + validFiles.push(tempFiles.unreadable); + } else { + invalidFiles.push(tempFiles.unreadable); + } + const allFiles = Object.values(tempFiles); const expectedObject = { expected: 'value', @@ -98,7 +105,7 @@ describe('telemetry_usage_collector', () => { }); test('returns `true` file that has valid data', async () => { - expect(allFiles.filter(isFileReadable)).toEqual(validFiles); + expect(allFiles.filter(isFileReadable).sort()).toEqual(validFiles.sort()); }); }); diff --git a/src/plugins/url_forwarding/public/forward_app/normalize_path.ts b/src/plugins/url_forwarding/public/forward_app/normalize_path.ts index 88f3a1d5335..aae41809d76 100644 --- a/src/plugins/url_forwarding/public/forward_app/normalize_path.ts +++ b/src/plugins/url_forwarding/public/forward_app/normalize_path.ts @@ -28,11 +28,13 @@ * under the License. */ -import { normalize } from 'path'; +import { normalize, posix } from 'path'; export function normalizePath(path: string) { + // `normalize` in path-browserify is an implementation of `posix.normalize` + const normalizeFunc = posix?.normalize || normalize; // resolve ../ within the path - const normalizedPath = normalize(path); + const normalizedPath = normalizeFunc(path); // strip any leading slashes and dots and replace with single leading slash return normalizedPath.replace(/(\.?\.?\/?)*/, '/'); } diff --git a/test/interpreter_functional/plugins/osd_tp_run_pipeline/package.json b/test/interpreter_functional/plugins/osd_tp_run_pipeline/package.json index 80275e41e04..45476309224 100644 --- a/test/interpreter_functional/plugins/osd_tp_run_pipeline/package.json +++ b/test/interpreter_functional/plugins/osd_tp_run_pipeline/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "@elastic/eui": "npm:@opensearch-project/oui@1.0.0", diff --git a/test/plugin_functional/plugins/app_link_test/package.json b/test/plugin_functional/plugins/app_link_test/package.json index 8b28e62e31b..dd07b4de638 100644 --- a/test/plugin_functional/plugins/app_link_test/package.json +++ b/test/plugin_functional/plugins/app_link_test/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_app_status/package.json b/test/plugin_functional/plugins/core_app_status/package.json index 0304da467b4..524e33d8dfb 100644 --- a/test/plugin_functional/plugins/core_app_status/package.json +++ b/test/plugin_functional/plugins/core_app_status/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_plugin_a/package.json b/test/plugin_functional/plugins/core_plugin_a/package.json index 53ea6306f2a..b57d5783c77 100644 --- a/test/plugin_functional/plugins/core_plugin_a/package.json +++ b/test/plugin_functional/plugins/core_plugin_a/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_plugin_appleave/package.json b/test/plugin_functional/plugins/core_plugin_appleave/package.json index 69e7caea397..5caa1a70f8d 100644 --- a/test/plugin_functional/plugins/core_plugin_appleave/package.json +++ b/test/plugin_functional/plugins/core_plugin_appleave/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_plugin_b/package.json b/test/plugin_functional/plugins/core_plugin_b/package.json index 56ec66f867f..d37ffd582e6 100644 --- a/test/plugin_functional/plugins/core_plugin_b/package.json +++ b/test/plugin_functional/plugins/core_plugin_b/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_plugin_chromeless/package.json b/test/plugin_functional/plugins/core_plugin_chromeless/package.json index 33a247924d0..0c444aaf80c 100644 --- a/test/plugin_functional/plugins/core_plugin_chromeless/package.json +++ b/test/plugin_functional/plugins/core_plugin_chromeless/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_plugin_route_timeouts/package.json b/test/plugin_functional/plugins/core_plugin_route_timeouts/package.json index 974d9398dd6..1b03b60ad38 100644 --- a/test/plugin_functional/plugins/core_plugin_route_timeouts/package.json +++ b/test/plugin_functional/plugins/core_plugin_route_timeouts/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_plugin_static_assets/package.json b/test/plugin_functional/plugins/core_plugin_static_assets/package.json index 5b50b579549..e44a09af12c 100644 --- a/test/plugin_functional/plugins/core_plugin_static_assets/package.json +++ b/test/plugin_functional/plugins/core_plugin_static_assets/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/core_provider_plugin/package.json b/test/plugin_functional/plugins/core_provider_plugin/package.json index 068d9b0e638..778d9363e71 100644 --- a/test/plugin_functional/plugins/core_provider_plugin/package.json +++ b/test/plugin_functional/plugins/core_provider_plugin/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/data_search/package.json b/test/plugin_functional/plugins/data_search/package.json index fcd6ba5260f..056a79f2139 100644 --- a/test/plugin_functional/plugins/data_search/package.json +++ b/test/plugin_functional/plugins/data_search/package.json @@ -7,7 +7,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/doc_views_links_plugin/package.json b/test/plugin_functional/plugins/doc_views_links_plugin/package.json index 92cfca07815..7cc258622ae 100644 --- a/test/plugin_functional/plugins/doc_views_links_plugin/package.json +++ b/test/plugin_functional/plugins/doc_views_links_plugin/package.json @@ -9,9 +9,9 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" } -} \ No newline at end of file +} diff --git a/test/plugin_functional/plugins/doc_views_plugin/package.json b/test/plugin_functional/plugins/doc_views_plugin/package.json index 4f0aa8b8ae4..67018cec9d9 100644 --- a/test/plugin_functional/plugins/doc_views_plugin/package.json +++ b/test/plugin_functional/plugins/doc_views_plugin/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/index_patterns/package.json b/test/plugin_functional/plugins/index_patterns/package.json index 114131058ec..3b88f3bf393 100644 --- a/test/plugin_functional/plugins/index_patterns/package.json +++ b/test/plugin_functional/plugins/index_patterns/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/management_test_plugin/package.json b/test/plugin_functional/plugins/management_test_plugin/package.json index cd0b7eb62b8..b20971f403a 100644 --- a/test/plugin_functional/plugins/management_test_plugin/package.json +++ b/test/plugin_functional/plugins/management_test_plugin/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/opensearch_client_plugin/package.json b/test/plugin_functional/plugins/opensearch_client_plugin/package.json index fc7aab14306..77d31a85f8f 100644 --- a/test/plugin_functional/plugins/opensearch_client_plugin/package.json +++ b/test/plugin_functional/plugins/opensearch_client_plugin/package.json @@ -7,7 +7,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/osd_sample_panel_action/package.json b/test/plugin_functional/plugins/osd_sample_panel_action/package.json index b1847e7d35f..34ebf31d78f 100644 --- a/test/plugin_functional/plugins/osd_sample_panel_action/package.json +++ b/test/plugin_functional/plugins/osd_sample_panel_action/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "@elastic/eui": "npm:@opensearch-project/oui@1.0.0", diff --git a/test/plugin_functional/plugins/osd_top_nav/package.json b/test/plugin_functional/plugins/osd_top_nav/package.json index 49076bfe626..a1a244da27c 100644 --- a/test/plugin_functional/plugins/osd_top_nav/package.json +++ b/test/plugin_functional/plugins/osd_top_nav/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/osd_tp_custom_visualizations/package.json b/test/plugin_functional/plugins/osd_tp_custom_visualizations/package.json index e1f3698fdd3..18961a35fda 100644 --- a/test/plugin_functional/plugins/osd_tp_custom_visualizations/package.json +++ b/test/plugin_functional/plugins/osd_tp_custom_visualizations/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "@elastic/eui": "npm:@opensearch-project/oui@1.0.0", diff --git a/test/plugin_functional/plugins/rendering_plugin/package.json b/test/plugin_functional/plugins/rendering_plugin/package.json index bb651872f1a..2548cfef508 100644 --- a/test/plugin_functional/plugins/rendering_plugin/package.json +++ b/test/plugin_functional/plugins/rendering_plugin/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/test/plugin_functional/plugins/ui_settings_plugin/package.json b/test/plugin_functional/plugins/ui_settings_plugin/package.json index f167bfc6994..db9bedec26d 100644 --- a/test/plugin_functional/plugins/ui_settings_plugin/package.json +++ b/test/plugin_functional/plugins/ui_settings_plugin/package.json @@ -9,7 +9,7 @@ "license": "Apache-2.0", "scripts": { "osd": "node ../../../../scripts/osd.js", - "build": "rm -rf './target' && tsc" + "build": "node ../../scripts/remove.js './target' && tsc" }, "devDependencies": { "typescript": "4.0.2" diff --git a/yarn.lock b/yarn.lock index fe16ed3b99b..601676740b5 100644 --- a/yarn.lock +++ b/yarn.lock @@ -9257,7 +9257,7 @@ glob@7.1.3: once "^1.3.0" path-is-absolute "^1.0.0" -glob@7.1.7, glob@~7.1.6: +glob@7.1.7, glob@~7.1.1, glob@~7.1.6: version "7.1.7" resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.7.tgz#3b193e9233f01d42d0b3f78294bbeeb418f94a90" integrity sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ== @@ -11911,10 +11911,10 @@ leaflet-responsive-popup@0.6.4: resolved "https://registry.yarnpkg.com/leaflet-responsive-popup/-/leaflet-responsive-popup-0.6.4.tgz#b93d9368ef9f96d6dc911cf5b96d90e08601c6b3" integrity sha512-2D8G9aQA6NHkulDBPN9kqbUCkCpWQQ6dF0xFL11AuEIWIbsL4UC/ZPP5m8GYM0dpU6YTlmyyCh1Tz+cls5Q4dg== -"leaflet-vega@npm:@amoo-miki/leaflet-vega@0.8.7": - version "0.8.7" - resolved "https://registry.yarnpkg.com/@amoo-miki/leaflet-vega/-/leaflet-vega-0.8.7.tgz#8faca1b4b8e2ef7d48667ac6faad9204f4da7153" - integrity sha512-T4M5yziwj3Fi9Adsbce+cdWqPjON0BRwEjwqLlPMoirU1vhifA6YKrlZkVzJrK0IIm+hdfMCLkBz33gD8fdxzQ== +"leaflet-vega@npm:@amoo-miki/leaflet-vega@0.8.8": + version "0.8.8" + resolved "https://registry.yarnpkg.com/@amoo-miki/leaflet-vega/-/leaflet-vega-0.8.8.tgz#675abf37d72fbea859755e982f4fd19dea776557" + integrity sha512-W2gGgFDxzy/XUx+fQJfz0NYVXsKl7V+G6QywiMcOV5NEodDId9c60up7NNf+cfM7ggpo+5BuLqrKmosuGO1CsA== dependencies: vega-spec-injector "^0.0.2" @@ -12335,7 +12335,7 @@ lodash.uniq@^4.5.0: resolved "https://registry.yarnpkg.com/lodash.uniq/-/lodash.uniq-4.5.0.tgz#d0225373aeb652adc1bc82e4945339a842754773" integrity sha1-0CJTc662Uq3BvILklFM5qEJ1R3M= -lodash@4.17.21, lodash@^4.0.1, lodash@^4.10.0, lodash@^4.17.10, lodash@^4.17.11, lodash@^4.17.13, lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.19, lodash@^4.17.21, lodash@^4.17.4, lodash@^4.7.0, lodash@~4.17.15, lodash@~4.17.19, lodash@~4.17.21: +lodash@4.17.21, lodash@^4.0.0, lodash@^4.0.1, lodash@^4.10.0, lodash@^4.17.10, lodash@^4.17.11, lodash@^4.17.13, lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.19, lodash@^4.17.21, lodash@^4.17.4, lodash@^4.7.0, lodash@~4.17.10, lodash@~4.17.15, lodash@~4.17.19, lodash@~4.17.21: version "4.17.21" resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== @@ -12821,7 +12821,7 @@ minimatch@3.0.4: dependencies: brace-expansion "^1.1.7" -minimatch@~3.0.4: +minimatch@~3.0.2, minimatch@~3.0.4: version "3.0.8" resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.8.tgz#5e6a59bd11e2ab0de1cfb843eb2d82e546c321c1" integrity sha512-6FsRAQsxQ61mw+qP1ZzbL9Bc78x2p5OqNgNpnoAFLTrX8n5Kxph0CsnhmKKNXTWjXqU5L0pGPR7hYk+XWZr60Q== @@ -13103,6 +13103,11 @@ nan@^2.12.1, nan@^2.14.1, nan@^2.14.2: resolved "https://registry.yarnpkg.com/nan/-/nan-2.15.0.tgz#3f34a473ff18e15c1b5626b62903b5ad6e665fee" integrity sha512-8ZtvEnA2c5aYCZYd1cvgdnU6cqwixRoYg70xPLWUws5ORTa/lnw+u4amixRS/Ac5U5mQVgp9pnlSUnbNWFaWZQ== +nan@^2.13.2: + version "2.17.0" + resolved "https://registry.yarnpkg.com/nan/-/nan-2.17.0.tgz#c0150a2368a182f033e9aa5195ec76ea41a199cb" + integrity sha512-2ZTgtl0nJsO0KQCjEpxcIr5D+Yv90plTitZt9JBfQvVJDS5seMl3FOvsh3+9CoYWXf/1l5OaZzzF6nDm4cagaQ== + nano-css@^5.2.1: version "5.3.4" resolved "https://registry.yarnpkg.com/nano-css/-/nano-css-5.3.4.tgz#40af6a83a76f84204f346e8ccaa9169cdae9167b" @@ -13266,7 +13271,7 @@ node-gyp-build@^4.2.3: resolved "https://registry.yarnpkg.com/node-gyp-build/-/node-gyp-build-4.3.0.tgz#9f256b03e5826150be39c764bf51e993946d71a3" integrity sha512-iWjXZvmboq0ja1pUGULQBexmxq8CV4xBhX7VDOTbL7ZR4FOowwY/VOtRxBN/yKxmdGoIp4j5ysNT4u3S2pDQ3Q== -node-gyp@^7.0.0: +node-gyp@^7.0.0, node-gyp@^7.1.0: version "7.1.2" resolved "https://registry.yarnpkg.com/node-gyp/-/node-gyp-7.1.2.tgz#21a810aebb187120251c3bcec979af1587b188ae" integrity sha512-CbpcIo7C3eMu3dL1c3d0xw449fHIGALIJsRP4DDPHpyiW8vcriNY7ubh9TE4zEKfSxscY7PjeFnshE7h75ynjQ== @@ -13364,6 +13369,11 @@ node-sass@^6.0.1: stdout-stream "^1.4.0" "true-case-path" "^1.0.2" +node-stream-zip@^1.15.0: + version "1.15.0" + resolved "https://registry.yarnpkg.com/node-stream-zip/-/node-stream-zip-1.15.0.tgz#158adb88ed8004c6c49a396b50a6a5de3bca33ea" + integrity sha512-LN4fydt9TqhZhThkZIVQnF9cwjU3qmUH9h78Mx/K7d3VvfRqqwthLwJEUOEL0QPZ0XQmNN7be5Ggit5+4dq3Bw== + nopt@^2.2.0: version "2.2.1" resolved "https://registry.yarnpkg.com/nopt/-/nopt-2.2.1.tgz#2aa09b7d1768487b3b89a9c5aa52335bff0baea7" @@ -13466,7 +13476,7 @@ npm-run-path@^4.0.0, npm-run-path@^4.0.1: dependencies: path-key "^3.0.0" -npmlog@^4.1.2: +npmlog@^4.0.0, npmlog@^4.1.2: version "4.1.2" resolved "https://registry.yarnpkg.com/npmlog/-/npmlog-4.1.2.tgz#08a7f2a8bf734604779a9efa4ad5cc717abb954b" integrity sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg== @@ -15518,7 +15528,7 @@ replace-ext@^1.0.0: resolved "https://registry.yarnpkg.com/replace-ext/-/replace-ext-1.0.1.tgz#2d6d996d04a15855d967443631dd5f77825b016a" integrity sha512-yD5BHCe7quCgBph4rMQ+0KkIRKwWCrHDOX1p1Gp6HwjPM5kVoCdKGNhN7ydqqsX6lJEnQDKZ/tFMiEdQ1dvPEw== -request@^2.88.2: +request@^2.88.0, request@^2.88.2: version "2.88.2" resolved "https://registry.yarnpkg.com/request/-/request-2.88.2.tgz#d73c918731cb5a87da047e207234146f664d12b3" integrity sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw== @@ -15879,13 +15889,6 @@ sass-loader@^10.2.0: schema-utils "^3.0.0" semver "^7.3.2" -sass@~1.26.11: - version "1.26.12" - resolved "https://registry.yarnpkg.com/sass/-/sass-1.26.12.tgz#79eddaa1773fff32ccf19e00d1ce380fc2afc7d0" - integrity sha512-hmSwtBOWoS9zwe0yAS+QmaseVCUELiGV22gXHDR7+9stEsVuEuxfY1GhC8XmUpC+Ir3Hwq7NxSUNbnmkznnF7g== - dependencies: - chokidar ">=2.0.0 <4.0.0" - sax@1.2.1: version "1.2.1" resolved "https://registry.yarnpkg.com/sax/-/sax-1.2.1.tgz#7b8e656190b228e81a66aea748480d828cd2d37a" @@ -18377,10 +18380,10 @@ vega-hierarchy@~4.1.0: vega-dataflow "^5.7.3" vega-util "^1.15.2" -"vega-interpreter@npm:@amoo-miki/vega-forced-csp-compliant-interpreter@1.0.5": - version "1.0.5" - resolved "https://registry.yarnpkg.com/@amoo-miki/vega-forced-csp-compliant-interpreter/-/vega-forced-csp-compliant-interpreter-1.0.5.tgz#49970be9b00ca7e45ced0617fbf373c77a28aab4" - integrity sha512-lfeU77lVoUbSCC6N1ywdKg+I6K08xpkd82TLon+LebtKyC8aLCe7P5Dd/89zAPyFwRyobKftHu8z0xpV7R7a4Q== +"vega-interpreter@npm:@amoo-miki/vega-forced-csp-compliant-interpreter@1.0.6": + version "1.0.6" + resolved "https://registry.yarnpkg.com/@amoo-miki/vega-forced-csp-compliant-interpreter/-/vega-forced-csp-compliant-interpreter-1.0.6.tgz#5cffdf12b7fe12dc936194edd9e8519506c38716" + integrity sha512-9S5nTTVd8JVKobcWp5iwirIeePiamwH1J9uSZPuG5kcF0TUBvGu++ERKjNdst5Qck7e4R6/7vjx2wVf58XUarg== vega-label@~1.2.0: version "1.2.0" @@ -19304,7 +19307,7 @@ yargs-unparser@1.6.0: lodash "^4.17.15" yargs "^13.3.0" -yargs@13.3.2, yargs@^13.3.0: +yargs@13.3.2, yargs@^13.3.0, yargs@^13.3.2: version "13.3.2" resolved "https://registry.yarnpkg.com/yargs/-/yargs-13.3.2.tgz#ad7ffefec1aa59565ac915f82dccb38a9c31a2dd" integrity sha512-AX3Zw5iPruN5ie6xGRIDgqkT+ZhnRlZMLMHAs8tg7nRruy2Nb+i5o9bwghAogtM08q1dpr2LVoS8KSTMYpWXUw==