From e2e51cd483caac7a646d059fcf75e8280ce48b6f Mon Sep 17 00:00:00 2001 From: josephjclark Date: Fri, 19 Apr 2024 15:40:01 +0100 Subject: [PATCH] CLI: autoinstall for metadata (#673) * cli: support autoinstall in metadata command * Fixing:#192 * added integration tests * added integration tests * completed all requested changes * changeset * version: cli@1.2.3 --------- Co-authored-by: Satyam Mattoo <96661612+SatyamMattoo@users.noreply.github.com> --- integration-tests/cli/test/metadata.test.ts | 14 +++++++ packages/cli/CHANGELOG.md | 6 +++ packages/cli/package.json | 2 +- packages/cli/src/metadata/handler.ts | 8 +++- .../test/metadata/should-autoinstall.test.ts | 38 +++++++++++++++++++ 5 files changed, 66 insertions(+), 2 deletions(-) create mode 100644 packages/cli/test/metadata/should-autoinstall.test.ts diff --git a/integration-tests/cli/test/metadata.test.ts b/integration-tests/cli/test/metadata.test.ts index 7be1413dc..b5ae39a60 100644 --- a/integration-tests/cli/test/metadata.test.ts +++ b/integration-tests/cli/test/metadata.test.ts @@ -126,3 +126,17 @@ test.serial('does not log credentials', async (t) => { t.regex(logString, /(pin_number)/i); t.notRegex(logString, new RegExp(sensitiveValue), 'i'); }); + +// This test should auto-install the common adaptor but then happily fail to generate metadata +test.serial( + `openfn metadata -f -S "${state}" -a common --log-json --log info`, + async (t) => { + const { stdout } = await run(t.title); + + t.regex(stdout, /Generating metadata/); + t.regex(stdout, /Installing packages.../); + t.regex(stdout, /Installed @openfn\/language-common@/); + t.regex(stdout, /Installation complete in \d+\.\d+s/); + t.regex(stdout, /No metadata helper found/); + } +); \ No newline at end of file diff --git a/packages/cli/CHANGELOG.md b/packages/cli/CHANGELOG.md index fb693c786..5f72ca82b 100644 --- a/packages/cli/CHANGELOG.md +++ b/packages/cli/CHANGELOG.md @@ -1,5 +1,11 @@ # @openfn/cli +## 1.2.3 + +### Patch Changes + +- 1dffdfc: support autoinstall in the metadata command + ## 1.2.2 ### Patch Changes diff --git a/packages/cli/package.json b/packages/cli/package.json index 151d8a32d..0c06a81cc 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -1,6 +1,6 @@ { "name": "@openfn/cli", - "version": "1.2.2", + "version": "1.2.3", "description": "CLI devtools for the openfn toolchain.", "engines": { "node": ">=18", diff --git a/packages/cli/src/metadata/handler.ts b/packages/cli/src/metadata/handler.ts index eb050acf4..e68681228 100644 --- a/packages/cli/src/metadata/handler.ts +++ b/packages/cli/src/metadata/handler.ts @@ -4,6 +4,7 @@ import loadState from '../util/load-state'; import cache from './cache'; import { getModuleEntryPoint } from '@openfn/runtime'; import { ExecutionPlan } from '@openfn/lexicon'; +import { install } from '../repo/handler'; // Add extra, uh, metadata to the, uh, metadata object const decorateMetadata = (metadata: any) => { @@ -48,6 +49,8 @@ export const getAdaptorPath = async ( return adaptorPath; }; +export const shouldAutoinstall = (adaptor: string): boolean => adaptor?.length > 0 && !adaptor.startsWith('/') && !adaptor.includes('='); + const metadataHandler = async (options: MetadataOpts, logger: Logger) => { const { repoDir, adaptors } = options; const adaptor = adaptors[0]; @@ -81,7 +84,10 @@ const metadataHandler = async (options: MetadataOpts, logger: Logger) => { } try { - // Import the adaptor + if (shouldAutoinstall(adaptor)) { + await install({ packages: [adaptor], repoDir }, logger); + } + const adaptorPath = await getAdaptorPath(adaptor, logger, options.repoDir); const mod = await import(adaptorPath!); diff --git a/packages/cli/test/metadata/should-autoinstall.test.ts b/packages/cli/test/metadata/should-autoinstall.test.ts new file mode 100644 index 000000000..c60a965ac --- /dev/null +++ b/packages/cli/test/metadata/should-autoinstall.test.ts @@ -0,0 +1,38 @@ +import test from 'ava'; +import { shouldAutoinstall } from '../../src/metadata/handler' + +test('should return false when no adaptor is provided', (t) => { + const adaptor = ''; + const result = shouldAutoinstall(adaptor); + t.false(result); +}); + +test('should return false for adaptors with "test=" prefix', (t) => { + const adaptor = 'test=/repo/modules/test'; + const result = shouldAutoinstall(adaptor); + t.false(result); +}); + +test('should return false for adaptors that are full module paths', (t) => { + const adaptor = '/repo/modules/test'; + const result = shouldAutoinstall(adaptor); + t.false(result) +}); + +test('should return true for adaptors with a name', (t) => { + const adaptor = 'common'; + const result = shouldAutoinstall(adaptor); + t.true(result); +}); + +test('should return true for adaptors with a name and version', (t) => { + const adaptor = '@openfn/language-common@1.0.0'; + const result = shouldAutoinstall(adaptor); + t.true(result); +}); + +test('should return false for adaptors that are full paths', (t) => { + const adaptor = '@openfn/language-common'; + const result = shouldAutoinstall(adaptor); + t.true(result); +}); \ No newline at end of file