diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index d7c03e8..4f7410c 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -2,31 +2,35 @@ name: Publish to npm on: push: - branches: - - main + branches: [main] + +permissions: + contents: write + packages: write jobs: publish: runs-on: ubuntu-latest steps: - - name: Checkout repository - uses: actions/checkout@v3 - - - name: Setup Node.js - uses: actions/setup-node@v3 + - uses: actions/checkout@v3 with: - node-version: 16 + fetch-depth: 0 + - uses: actions/setup-node@v3 + with: + node-version: 20.8.1 registry-url: https://registry.npmjs.org always-auth: true - + - uses: pnpm/action-setup@v2 + with: + version: 8 - name: Install dependencies - run: npm install - - - name: Build the project - run: npm run build - - # Semantic versioning is applied manually; CI does not commit any version changes. - - name: Publish package + run: pnpm install + - name: Build + run: pnpm run build + - name: Release + run: pnpm semantic-release env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} - run: npm publish --access public --tag latest \ No newline at end of file + + # Semantic versioning is applied manually; CI does not commit any version changes. \ No newline at end of file diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..0522c18 --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,22 @@ +# [1.1.0](https://github.com/johnlindquist/worktree-cli/compare/v1.0.0...v1.1.0) (2025-03-20) + + +### Features + +* create worktrees in sibling directories ([37dc420](https://github.com/johnlindquist/worktree-cli/commit/37dc420cf1539c68a32926e97c2f35762f5392b0)) + +# 1.0.0 (2025-03-20) + + +### Bug Fixes + +* add write permissions for semantic-release ([d98cae6](https://github.com/johnlindquist/worktree-cli/commit/d98cae6472d06f9cb39f40c9df564143fdf577ef)) +* switch to pnpm ([b95819e](https://github.com/johnlindquist/worktree-cli/commit/b95819e3abd9a44b5b06b0036bedfa5fe3d7c825)) +* update Node.js version to 18 ([ab54632](https://github.com/johnlindquist/worktree-cli/commit/ab54632df1b7094fa6896470fa5f17efcce796f3)) +* update Node.js version to 20.8.1 ([b9d2190](https://github.com/johnlindquist/worktree-cli/commit/b9d2190b5c3b55ce1376ed6c244701a57a8b3d8d)) +* use npm install instead of npm ci ([988aac9](https://github.com/johnlindquist/worktree-cli/commit/988aac9a25d57da7d8d1923029211182e8a7e6a0)) + + +### Features + +* add semantic-release for automated versioning ([11cddea](https://github.com/johnlindquist/worktree-cli/commit/11cddea6295a76beeec42371d429cf1d899b269a)) diff --git a/TESTING.md b/TESTING.md index dd5b444..e993cc1 100644 --- a/TESTING.md +++ b/TESTING.md @@ -8,4 +8,13 @@ - The CI workflow will not make any commits or version bumps - Version updates should be handled manually outside of CI -- Make sure you have set up the `NPM_TOKEN` secret in your GitHub repository settings \ No newline at end of file +- Make sure you have set up the `NPM_TOKEN` secret in your GitHub repository settings + +## New Worktree Sibling Directory Test + +1. In a test repository, run: + ```bash + cursor-worktree new editor + ``` +2. Verify that a new sibling directory named `editor` is created. +3. Confirm that the worktree is added to the Git repository and that the Cursor editor opens the new directory. \ No newline at end of file diff --git a/package.json b/package.json index 533bb3f..7d71c8a 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "cursor-worktree", - "version": "0.0.0-development", + "version": "1.1.0", "description": "A CLI tool for managing Git worktrees with a focus on opening them in the Cursor editor.", "author": "Your Name", "license": "MIT", @@ -11,7 +11,8 @@ "scripts": { "build": "tsc", "start": "node dist/index.js", - "dev": "tsc -w" + "dev": "tsc -w", + "semantic-release": "semantic-release" }, "dependencies": { "chalk": "^5.2.0", @@ -20,6 +21,24 @@ }, "devDependencies": { "@types/node": "^18.0.0", - "typescript": "^5.0.2" + "typescript": "^5.0.2", + "@semantic-release/changelog": "^6.0.3", + "@semantic-release/git": "^10.0.1", + "semantic-release": "^23.0.2" + }, + "release": { + "branches": [ + "main" + ], + "plugins": [ + "@semantic-release/commit-analyzer", + "@semantic-release/release-notes-generator", + "@semantic-release/changelog", + "@semantic-release/npm", + "@semantic-release/git" + ] + }, + "publishConfig": { + "access": "public" } } diff --git a/src/commands/new.ts b/src/commands/new.ts index 46f483c..c4e9c59 100644 --- a/src/commands/new.ts +++ b/src/commands/new.ts @@ -1,24 +1,31 @@ import { execa } from "execa"; import chalk from "chalk"; import { stat } from "node:fs/promises"; -import { resolve } from "node:path"; +import { resolve, join, dirname, basename } from "node:path"; export async function newWorktreeHandler( branchName: string = "main", - options: { path?: string; checkout?: boolean } + options: { path?: string; checkout?: boolean; install?: string; editor?: string } ) { try { // 1. Validate we're in a git repo await execa("git", ["rev-parse", "--is-inside-work-tree"]); // 2. Build final path for the new worktree - const folderName = options.path ?? `./${branchName}-worktree`; + let folderName: string; + if (options.path) { + folderName = options.path; + } else { + const currentDir = process.cwd(); + const parentDir = dirname(currentDir); + const currentDirName = basename(currentDir); + // Create a sibling directory: current directory name concatenated with branchName + folderName = join(parentDir, `${currentDirName}${branchName}`); + } const resolvedPath = resolve(folderName); // 3. (Optional) checkout new local branch if it doesn't exist yet - // This step is only run if user passes `--checkout` if (options.checkout) { - // Check if branch already exists const { stdout } = await execa("git", ["branch", "--list", branchName]); if (!stdout) { console.log(chalk.yellow(`Branch "${branchName}" doesn't exist locally. Creating...`)); @@ -27,7 +34,6 @@ export async function newWorktreeHandler( console.log(chalk.green(`Branch "${branchName}" found locally.`)); } } else { - // Ensure the branch is present, or you might want to skip this check console.log(chalk.gray(`Using branch "${branchName}". Make sure it exists (local or remote).`)); } @@ -35,12 +41,18 @@ export async function newWorktreeHandler( console.log(chalk.blue(`Creating new worktree for branch "${branchName}" at: ${resolvedPath}`)); await execa("git", ["worktree", "add", resolvedPath, branchName]); - // 5. Open in Cursor editor - // (Assuming "cursor " is how you open a folder in Cursor) - console.log(chalk.blue(`Opening ${resolvedPath} in Cursor...`)); - await execa("cursor", [resolvedPath], { stdio: "inherit" }); + // 5. (Optional) Install dependencies if --install flag is provided + if (options.install) { + console.log(chalk.blue(`Installing dependencies using ${options.install} in ${resolvedPath}...`)); + await execa(options.install, ["install"], { cwd: resolvedPath, stdio: "inherit" }); + } + + // 6. Open in the specified editor (or default to "cursor") + const editorCommand = options.editor || "cursor"; + console.log(chalk.blue(`Opening ${resolvedPath} in ${editorCommand}...`)); + await execa(editorCommand, [resolvedPath], { stdio: "inherit" }); - console.log(chalk.green(`Worktree created and opened in Cursor successfully!`)); + console.log(chalk.green(`Worktree created, dependencies installed (if specified), and opened in ${editorCommand} successfully!`)); } catch (error) { if (error instanceof Error) { console.error(chalk.red("Failed to create new worktree:"), error.message); diff --git a/src/index.ts b/src/index.ts index 13dd2cb..aee336a 100644 --- a/src/index.ts +++ b/src/index.ts @@ -18,7 +18,9 @@ program .argument("[branchName]", "Name of the branch to base this worktree on") .option("-p, --path ", "Relative path/folder name for new worktree") .option("-c, --checkout", "Create new branch if it doesn't exist and checkout automatically", false) - .description("Create a new worktree for the specified branch and open it in Cursor.") + .option("-i, --install ", "Package manager to use for installing dependencies (npm, pnpm, bun, etc.)") + .option("-e, --editor ", "Editor to use for opening the worktree (e.g., code, webstorm, windsurf, etc.)") + .description("Create a new worktree for the specified branch, install dependencies if specified, and open in editor.") .action(newWorktreeHandler); program