From 41ba7e290455ba958956885be9755cb1cd41069f Mon Sep 17 00:00:00 2001 From: Julien Oculi Date: Sat, 15 Jun 2024 16:14:05 +0200 Subject: [PATCH] build: :construction_worker: add script to add remote deno packages as local deno workspaces --- deno.json | 3 +- scripts/add_package.ts | 78 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 80 insertions(+), 1 deletion(-) create mode 100644 scripts/add_package.ts diff --git a/deno.json b/deno.json index 8159ad4..b2a10fa 100644 --- a/deno.json +++ b/deno.json @@ -8,7 +8,8 @@ "build": "deno run -A dev.ts build", "preview": "deno run -A main.ts", "update": "deno run -A -r https://fresh.deno.dev/update .", - "serve": "deno task preview" + "serve": "deno task preview", + "dev:add_package": "deno run --allow-net --allow-read=./deno.json --allow-write=./deno.json,./packages --allow-run=git,deno ./scripts/add_package.ts" }, "fmt": { "singleQuote": true, diff --git a/scripts/add_package.ts b/scripts/add_package.ts new file mode 100644 index 0000000..ca09fdd --- /dev/null +++ b/scripts/add_package.ts @@ -0,0 +1,78 @@ +import { join } from '$std/path/join.ts' +import { ensureDir } from '$std/fs/mod.ts' +import denoJson from '../deno.json' with { type: 'json' } + +// Get package from cli +const baseRepo = 'https://git.cohabit.fr/' +const packageRepoAndTag = Deno.args[0] +const match = packageRepoAndTag.match(/(?@\w+\/\w+)@(?\d\.\d\.\d.*)/) + +// Parse name and version tag +if (match === null || match.groups === undefined) { + throw new SyntaxError('usage: deno task $task_name @scope/name@x.x.x') +} +const { name, tag } = match.groups +const repoUrl = new URL(`${name.slice(1)}.git`, baseRepo) + +// Setup destination and remove old versions +const fsName = name.replace('/', '.') +const packageBase = join(Deno.cwd(), 'packages') +const destinationBase = join(packageBase, fsName) +const destinationCurrent = `${destinationBase}@${tag}` + +// Create base dir if needed +await ensureDir(packageBase) + +// Remove old versions +for await (const entry of Deno.readDir(packageBase)) { + if (entry.isDirectory && entry.name.startsWith(fsName)) { + Deno.remove(join(packageBase, entry.name), { + recursive: true, + }) + } +} + +// Clone repo @ tag +const git = new Deno.Command('git', { + args: [ + 'clone', + repoUrl.href, + '--branch', + tag, + '--single-branch', + '--depth', + '1', + destinationCurrent, + ], + stderr: 'inherit', + stdout: 'inherit', +}) +await git.output() + +// Get workspaces +// @ts-ignore maybe undefined +const workspaces: string[] = denoJson['workspaces'] ?? [] +// Update deno.json +const newDenoJson = { + ...denoJson, + imports: { + ...denoJson.imports, + [`${name}/`]: `./packages/${fsName}@${tag}/`, + }, + workspaces: [ + ...workspaces.filter((workspace) => + workspace.startsWith(`packages/${fsName}`) === false + ), + `packages/${fsName}@${tag}`, + ], +} + +// Update deno.json file +await Deno.writeTextFile('../deno.json', JSON.stringify(newDenoJson)) + +const denoFmt = new Deno.Command('deno', { + args: ['fmt', 'deno.json'], + stderr: 'inherit', + stdout: 'inherit', +}) +await denoFmt.output()