Skip to content

fix(create-nextly-app): make the plugin template scaffold work end to end - #308

Open
aqib-rx wants to merge 23 commits into
mainfrom
fix/plugin-template-scaffold
Open

fix(create-nextly-app): make the plugin template scaffold work end to end#308
aqib-rx wants to merge 23 commits into
mainfrom
fix/plugin-template-scaffold

Conversation

@aqib-rx

@aqib-rx aqib-rx commented Jul 23, 2026

Copy link
Copy Markdown
Collaborator

Summary

Selecting the Plugin template in create-nextly-app failed at every stage: the --template plugin flag was rejected outright, the interactive flow crashed with "App Router not detected" after the full dependency install, and even a hand-recovered scaffold failed its own test suite and could not boot its embedded dev playground. This PR fixes every reproduced defect across the CLI flow, the scaffolder, and the template content, plus the template-distribution gap that allowed them to ship unnoticed, and addresses all review findings from the first round.

The result, verified end to end against the real npm registry: create-nextly-app my-plugin --template plugin -y → install completes → the scaffold's own test / build / check-types pass → pnpm dev boots the playground → /admin returns 200, auto-logged-in as the seeded dev user, with the plugin's Examples collection live in the admin — zero manual steps.

What the Plugin template is

A scaffold for a publishable npm package (not an app): the plugin library in src/ (a definePlugin() factory contributing a collection, a permission, an admin menu entry, and a settings page), plus an embedded dev/ folder holding a minimal Nextly app on SQLite that registers the plugin so authors can exercise it in a real admin with hot-reload. Only dist/ ships (files: ["dist"]); dev/ is never published. It wires tsup for building, vitest with the createTestNextly in-memory harness from @nextlyhq/plugin-sdk/testing, and the nextly-plugin npm keyword for discoverability.

Fixes (original defects)

  1. --template plugin rejectedcli.ts hardcoded validTypes = ["blank", "blog"] while the interactive prompt offered Plugin. Validation (and the "template not found" error in utils/template.ts) now derives from the template registry via getAvailableTemplateNames(), so the flag path, the prompt, --help, and error messages can no longer drift apart.

  2. "App Router not detected" crash after install — after scaffolding, the CLI ran detectProject() on the new directory, which requires a Next.js App Router layout. A plugin scaffold has library code at src/ and its Next app at dev/src/app, so detection aborted — after minutes of dependency installation. Plugin scaffolds now detect only the package manager (the sole field downstream consumes for fresh scaffolds) and skip the app-shaped checks. Additionally, selecting the Plugin template inside an existing Next.js project now fails fast with a clear message: the fresh-scaffold path is skipped there, so proceeding would have installed app dependencies and generated app config without ever copying the plugin source.

  3. pnpm dev aborted demanding DATABASE_URL — the template ships dev/.env.example but nothing created dev/.env (the CLI intentionally skips app-style env generation for plugins). Without it the dialect defaulted to postgresql and the instrumentation hook killed the server. The scaffold now materializes dev/.env from the committed example (overwrite: false preserves a user's own file when scaffolding over an existing directory).

  4. /admin 500 "No QueryClient set" — the playground's admin page mounted RootLayout bare; the admin's data hooks resolve their QueryClient from QueryProvider. Now wrapped in QueryProvider + ErrorBoundary, matching the base app template.

  5. Generated test suite failed out of the boxplugin.test.ts passed collections: plugin.contributes?.collections into createTestNextly (the harness already applies plugin schema contributions itself, so the collection registered twice → slug-collision "Schema configuration is invalid" at boot) and used the removed positional CRUD style (create("examples", {...}), findById). Rewritten to the current Direct API (create({ collection, data }), findByID({ collection, id })), validated against the published packages.

  6. Auto-login promise was falseadmin.devAutoLogin only issues a session for a user that already exists; nothing seeded one, so the first /admin visit dead-ended on the /admin/setup wizard. The playground's instrumentation hook now seeds the matching dev user via the public nextly/database/seeders primitives (idempotent; dev-only). Note: the seed uses getService("adapter") because getNextly().adapter is undefined in the published packages.

  7. Template/package version skew — the CLI build already bundles the plugin template into the published package, but the runtime unconditionally downloaded templates from GitHub main, so the bundled copy was dead code and a GitHub-main template could drift ahead of the npm packages the scaffold installs (exactly the API-drift class behind fix 5). Plugin (and blank) scaffolds now use the bundled copy by default; see the review-round shouldUseBundledTemplate() refactor below for the override rules.

  8. "latest" leaking into peerDependencies — surfaced during E2E verification: when a registry version lookup fails (offline, transient npm error) or under --use-yalc, the plugin package.json generator fell back to the "latest" dist-tag. pnpm 11 rejects that in peerDependencies (ERR_PNPM_INVALID_PEER_DEPENDENCY_SPECIFICATION) and then refuses to run any script in the scaffold, including pnpm dev. Peers now fall back to an open semver range; regular/dev dependencies keep the dist-tag, where it is valid.

Review-round fixes

  • Super-admin seeding race (Greptile P1) — createRegister() fires the runtime's permission seeding in the background (post-init tasks are not awaited), and the runtime's new-permission assignment silently no-ops while the super-admin role does not exist. The boot-time seed could therefore leave the role with an incomplete permission set — 403s precisely on the plugin's own collection. The seed now runs a second pass after the role exists; that pass re-lists all permissions and tops up any created in between. The runtime's assignment call runs after all of its inserts, so either it sees the role and assigns everything itself, or every insert it made is already visible to the second pass — the role converges to the complete set in every interleaving. Verified on a cold first boot by querying the SQLite database: all 32 assignable permissions (including all 5 of the plugin's examples permissions) are on the role. The only unassigned rows are the deliberately hidden legacy permissions resource (buildHiddenPermissionConditions excludes it from every assignable list) — identical to what the /admin/setup wizard produces.
  • --branch honored for bundled templates (CodeRabbit) — bundled-template selection now lives in a tested shouldUseBundledTemplate() helper: blank and plugin scaffold from the CLI-bundled copy by default, while --local-template, --use-yalc, or a non-main --branch force live resolution. Previously an explicit --branch on the blank template was silently ignored. Covered by a unit-test matrix; functionally verified that --template blank --branch <x> now resolves the requested branch (clean 404 message for a nonexistent one) and the default remains offline.
  • Credential seeding locked to next dev (CodeRabbit) — the playground seed guard tightened from NODE_ENV !== "production" to NODE_ENV === "development", so test runners (NODE_ENV=test) never seed credentials; matches the README's dev-only wording. Pinned by a scaffold assertion.
  • @nextlyhq/plugin-sdk yalc-linked for plugin scaffolds (Codex) — --use-yalc plugin scaffolds previously linked nextly/admin/ui/adapters from the yalc store but installed the published plugin-sdk from npm, producing a mismatched local-dev scaffold. The SDK is now part of the yalc set for plugin scaffolds.
  • @nextlyhq/admin-css added to the changeset (Codex) — lockstep completeness; the package is published and was missing from the bump list.
  • Comment/doc polish (CodeRabbit nitpicks) — --help's template list derives from the registry; comments added for the registry-backed error and the generated test's Direct API usage.

Type of change

  • Bug fix (non-breaking change that fixes an issue)

Every behavioral change branches on projectType === "plugin" (previously a guaranteed crash, so there is no working behavior to break) — with two deliberate, argued exceptions: honoring an explicit non-main --branch for the blank template (previously silently ignored, which contradicted the flag's documented purpose), and failing fast when the Plugin template is selected inside an existing Next.js project (previously produced a broken hybrid install).

Related issues

None filed — the failure was reported directly (Plugin template selection fails during create-nextly-app setup).

Changeset

  • I added a changeset (.changeset/plugin-template-scaffold-fixes.md)
  • I selected the correct semver bump (patch — all published packages, lockstep, alpha)

Test plan

  • pnpm lint (clean, --max-warnings 0)
  • pnpm check-types (clean)
  • pnpm exec vitest run in packages/create-nextly-app — 10 files, 116 tests, all passing (baseline was 113; +3 for the shouldUseBundledTemplate matrix)
  • pnpm build (bundled templates re-copied)
  • Manually verified end to end against the real npm registry:
    • create-nextly-app <name> --template plugin -y → scaffold + full install complete
    • Scaffold's own gates: pnpm test (1 passed), pnpm run build (tsup ESM + DTS), pnpm run check-types (clean)
    • pnpm dev/admin returns 200; /admin/api/auth/session returns the seeded dev@nextly.local user with zero manual steps (no setup wizard)
    • Cold-boot database audit: 32/32 assignable permissions on the super-admin role, including all 5 examples permissions
    • --template blank --branch <nonexistent> attempts live resolution and reports a clear 404; default blank scaffold remains offline/bundled

New regression assertions in scaffold-plugin.test.ts pin the template content: dev/.env materialization, QueryProvider/ErrorBoundary wrapping, current-API test shape, two-pass seed, NODE_ENV === "development" guard, and no "latest" peers under the offline fallback (that test runs with the registry stubbed offline, exactly where the dist-tag used to leak in).

Checklist

  • My commits follow the Conventional Commits spec (enforced by commitlint)
  • I targeted the main branch
  • I updated relevant documentation (template README: dev credentials/auto-login; dev/.env.example header; CLI next-steps output)

Notes for reviewers

  • Sequencing quirk worth knowing: the dev-user seed intentionally calls seedSuperAdmin twice — the second pass is what makes the boot race-free against the runtime's background permission seeding (detailed argument in the inline comment in templates/plugin/dev/instrumentation.ts). Please don't "simplify" it to a single call.
  • The 4 permanently unassigned permissions-resource rows in any Nextly database are by design (hidden legacy surface), not a gap in this PR — the setup wizard yields the same 32/36.
  • Known pre-existing, out of scope: the npm latest dist-tag (alpha.37) currently lags alpha (alpha.39) — a release-process question, not addressed here.
  • Template files under templates/ show unresolved-import diagnostics inside the monorepo IDE — expected, since template dependencies only exist after scaffolding; the scaffolded project type-checks clean.

Summary by CodeRabbit

  • New Features
    • Enhanced template registry validation and automatic bundled-template selection for offline scaffolding, including safer override handling.
    • Plugin scaffolds now generate dev/.env from dev/.env.example and provide dev-only auto-login for the admin.
  • Bug Fixes
    • Prevent plugin scaffolds from installing into existing Next.js projects.
    • Improved plugin dependency/version resolution to avoid invalid dist-tag peer dependency specs.
    • Refined yalc plugin install ordering and workspace overrides.
    • Fixed bundled .gitignore rename/restore behavior during packing and scaffolding.
  • Documentation
    • Expanded plugin README and updated dev/.env.example guidance.
  • Tests
    • Strengthened plugin scaffold, template-channel, and bundled-template behavior coverage.

@github-actions github-actions Bot added type: docs Documentation only scope: cli create-nextly-app labels Jul 23, 2026
@coderabbitai

coderabbitai Bot commented Jul 23, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@aqib-rx, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 47 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 317c2a50-387a-4370-a5e7-bb3397ae45b2

📥 Commits

Reviewing files that changed from the base of the PR and between a369327 and 0ec3970.

📒 Files selected for processing (4)
  • packages/create-nextly-app/src/__tests__/scaffold-plugin.test.ts
  • packages/create-nextly-app/src/__tests__/template-channel.test.ts
  • packages/create-nextly-app/src/utils/template.ts
  • packages/create-nextly-app/tsup.config.ts
📝 Walkthrough

Walkthrough

The CLI discovers templates dynamically and supports bundled plugin scaffolding. Plugin creation now enforces fresh-project constraints, prepares environment files, generates semver-safe dependencies, seeds development admin access, wires the admin page, and validates generated output.

Changes

Plugin scaffolding

Layer / File(s) Summary
Dynamic template selection
packages/create-nextly-app/src/cli.ts, packages/create-nextly-app/src/lib/templates.ts, packages/create-nextly-app/src/utils/template.ts, packages/create-nextly-app/src/__tests__/templates.test.ts
Template names, validation, missing-template errors, and bundled-template resolution now use the template registry and source overrides.
Bundled plugin project scaffolding
packages/create-nextly-app/src/create-nextly.ts, packages/create-nextly-app/src/installers/dependencies.ts, packages/create-nextly-app/src/utils/template.ts, packages/create-nextly-app/tsup.config.ts
Plugin installs require fresh projects, bundled templates bypass unnecessary resolution, yalc links the plugin SDK, package ranges avoid dist-tags, and packed gitignore files are restored during scaffolding.
Development playground runtime
templates/plugin/dev/instrumentation.ts, templates/plugin/dev/src/app/admin/[[...params]]/page.tsx, templates/plugin/dev/.env.example, templates/plugin/README.md
Development startup seeds permissions and a super admin; the admin page adds query and error-boundary wrappers; documentation describes dev-only auto-login.
Generated template validation
packages/create-nextly-app/src/__tests__/scaffold-plugin.test.ts, packages/create-nextly-app/src/__tests__/template-channel.test.ts, templates/plugin/src/plugin.test.ts
Tests validate dependency channels, generated playground content, gitignore restoration, and updated plugin test-harness APIs.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Sequence Diagram(s)

sequenceDiagram
  participant CLI
  participant createNextly
  participant PluginTemplate
  participant DevInstrumentation
  participant NextlyServices
  participant AdminPage
  CLI->>createNextly: validate and scaffold plugin project
  createNextly->>PluginTemplate: copy bundled template
  PluginTemplate-->>createNextly: create dev/.env and restore .gitignore
  DevInstrumentation->>NextlyServices: seed permissions and super admin
  AdminPage->>AdminPage: render ErrorBoundary and QueryProvider around RootLayout
Loading

Suggested labels: scope: plugin

Suggested reviewers: mobeenabdullah

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title is concise and accurately summarizes the main change: fixing the plugin template scaffold end to end.
Description check ✅ Passed The description follows the repository template closely and includes all required sections with substantive details.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch fix/plugin-template-scaffold

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@pkg-pr-new

pkg-pr-new Bot commented Jul 23, 2026

Copy link
Copy Markdown

Open in StackBlitz

@nextlyhq/adapter-drizzle

npm i https://pkg.pr.new/@nextlyhq/adapter-drizzle@0ec3970

@nextlyhq/adapter-mysql

npm i https://pkg.pr.new/@nextlyhq/adapter-mysql@0ec3970

@nextlyhq/adapter-postgres

npm i https://pkg.pr.new/@nextlyhq/adapter-postgres@0ec3970

@nextlyhq/adapter-sqlite

npm i https://pkg.pr.new/@nextlyhq/adapter-sqlite@0ec3970

@nextlyhq/admin

npm i https://pkg.pr.new/@nextlyhq/admin@0ec3970

@nextlyhq/admin-css

npm i https://pkg.pr.new/@nextlyhq/admin-css@0ec3970

@nextlyhq/blocks-engine

npm i https://pkg.pr.new/@nextlyhq/blocks-engine@0ec3970

create-nextly-app

npm i https://pkg.pr.new/create-nextly-app@0ec3970

nextly

npm i https://pkg.pr.new/nextly@0ec3970

@nextlyhq/plugin-form-builder

npm i https://pkg.pr.new/@nextlyhq/plugin-form-builder@0ec3970

@nextlyhq/plugin-page-builder

npm i https://pkg.pr.new/@nextlyhq/plugin-page-builder@0ec3970

@nextlyhq/plugin-sdk

npm i https://pkg.pr.new/@nextlyhq/plugin-sdk@0ec3970

@nextlyhq/plugin-seo

npm i https://pkg.pr.new/@nextlyhq/plugin-seo@0ec3970

@nextlyhq/storage-s3

npm i https://pkg.pr.new/@nextlyhq/storage-s3@0ec3970

@nextlyhq/storage-uploadthing

npm i https://pkg.pr.new/@nextlyhq/storage-uploadthing@0ec3970

@nextlyhq/storage-vercel-blob

npm i https://pkg.pr.new/@nextlyhq/storage-vercel-blob@0ec3970

@nextlyhq/ui

npm i https://pkg.pr.new/@nextlyhq/ui@0ec3970

commit: 0ec3970

@greptile-apps

greptile-apps Bot commented Jul 23, 2026

Copy link
Copy Markdown

Greptile Summary

The PR completes the plugin-template scaffolding flow and addresses the previously reported permission-seeding race.

  • Registers the plugin template consistently across CLI validation, help text, template resolution, and project detection.
  • Updates generated plugin dependencies, environment setup, admin providers, tests, and development-user seeding.
  • Uses bundled templates by default while preserving explicit live-source overrides.

Confidence Score: 5/5

The PR appears safe to merge.

No blocking failure remains in the fix for the previously reported Super Admin permission-seeding race.

Important Files Changed

Filename Overview
templates/plugin/dev/instrumentation.ts Adds development-only user and permission seeding with a second reconciliation pass that safely covers the previously reported initialization race.
packages/create-nextly-app/src/create-nextly.ts Adds plugin-specific project handling and selects bundled versus live templates according to explicit source overrides.
packages/create-nextly-app/src/utils/template.ts Generates valid plugin peer ranges and materializes the embedded playground environment during scaffolding.
packages/create-nextly-app/src/lib/templates.ts Centralizes bundled-template selection rules for blank and plugin scaffolds.
templates/plugin/src/plugin.test.ts Updates the generated plugin test to the current harness lifecycle and Direct API signatures.

Reviews (4): Last reviewed commit: "Merge remote-tracking branch 'origin/mai..." | Re-trigger Greptile

Comment thread templates/plugin/dev/instrumentation.ts Outdated

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🧹 Nitpick comments (2)
packages/create-nextly-app/src/utils/template.ts (1)

670-670: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Document the registry-backed error output.

Add a short comment explaining that the registry keeps this message current as templates are added.

As per coding guidelines, “Every code change must include a comment explaining what the code does and why.”

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/create-nextly-app/src/utils/template.ts` at line 670, Add a concise
comment next to the registry-backed “Template not found” error in the template
lookup logic, explaining that getAvailableTemplateNames() keeps the listed
templates current as new templates are added.

Source: Coding guidelines

packages/create-nextly-app/src/cli.ts (1)

37-38: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Keep --help synchronized with template validation.

Line 37 hardcodes template names, while Lines 103-105 use the registry. Newly registered templates will be accepted but omitted from CLI help.

Proposed fix
+  // Keep CLI help aligned with registry-backed template validation.
-  .option("-t, --template <template>", "Project template (blank, blog, plugin)")
+  .option(
+    "-t, --template <template>",
+    `Project template (${getAvailableTemplateNames().join(", ")})`
+  )
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/create-nextly-app/src/cli.ts` around lines 37 - 38, Update the
Commander option definition for --template to derive its listed template names
from the same registry used by the validation logic around lines 103-105, rather
than hardcoding them. Ensure newly registered templates automatically appear in
--help while preserving the existing option description and validation behavior.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/create-nextly-app/src/create-nextly.ts`:
- Around line 358-374: Update the bundled-template selection condition near
usesBundledPluginTemplate to include the blank project type only when
options.branch is main (or unset), so a non-main --branch always reaches
resolveTemplateSource(). Add a regression case covering --template blank with a
non-main branch and verify it resolves the requested branch rather than using
the bundled scaffold.

In `@templates/plugin/dev/instrumentation.ts`:
- Around line 16-28: Restrict the seeding guard in
templates/plugin/dev/instrumentation.ts (lines 16-28) to NODE_ENV ===
"development" or the established explicit local-playground flag, rather than
every non-production environment; keep seedPermissions and seedSuperAdmin
unchanged. In templates/plugin/README.md (lines 14-16), retain the existing
dev-only credential and auto-login documentation, with no direct content change
required unless needed to match the enforced guard.

In `@templates/plugin/src/plugin.test.ts`:
- Around line 22-31: Add a concise nearby comment around the create and findByID
calls explaining that the Direct API uses object-shaped arguments and that the
generated item ID is converted to a string for the lookup. Keep the test
behavior and API calls unchanged.

---

Nitpick comments:
In `@packages/create-nextly-app/src/cli.ts`:
- Around line 37-38: Update the Commander option definition for --template to
derive its listed template names from the same registry used by the validation
logic around lines 103-105, rather than hardcoding them. Ensure newly registered
templates automatically appear in --help while preserving the existing option
description and validation behavior.

In `@packages/create-nextly-app/src/utils/template.ts`:
- Line 670: Add a concise comment next to the registry-backed “Template not
found” error in the template lookup logic, explaining that
getAvailableTemplateNames() keeps the listed templates current as new templates
are added.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: a44cd578-2453-4d05-a5f2-ac6c7ca50688

📥 Commits

Reviewing files that changed from the base of the PR and between 8b01eb2 and e376185.

⛔ Files ignored due to path filters (1)
  • .changeset/plugin-template-scaffold-fixes.md is excluded by !.changeset/**
📒 Files selected for processing (9)
  • packages/create-nextly-app/src/__tests__/scaffold-plugin.test.ts
  • packages/create-nextly-app/src/cli.ts
  • packages/create-nextly-app/src/create-nextly.ts
  • packages/create-nextly-app/src/utils/template.ts
  • templates/plugin/README.md
  • templates/plugin/dev/.env.example
  • templates/plugin/dev/instrumentation.ts
  • templates/plugin/dev/src/app/admin/[[...params]]/page.tsx
  • templates/plugin/src/plugin.test.ts

Comment thread packages/create-nextly-app/src/create-nextly.ts Outdated
Comment thread templates/plugin/dev/instrumentation.ts Outdated
Comment thread templates/plugin/src/plugin.test.ts

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: e376185dba

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment thread .changeset/plugin-template-scaffold-fixes.md
Comment thread packages/create-nextly-app/src/create-nextly.ts

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 5869983d1d

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment thread packages/create-nextly-app/src/lib/templates.ts
Comment thread .changeset/plugin-template-scaffold-fixes.md

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: ebc7d2c585

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment thread packages/create-nextly-app/src/utils/template.ts Outdated
Comment thread packages/create-nextly-app/src/installers/dependencies.ts Outdated
…hannel drift

Bundled templates now carry .gitignore under the publish-safe name
gitignore: npm's packer strips dotted .gitignore files from tarballs, so
published-CLI scaffolds silently lost their ignore rules — including for
the materialized dev/.env. The build renames on copy and the scaffolder
renames back.

Plugin scaffolds resolve the Nextly family from the alpha train (the
template ships inside the CLI, so its generated test and dev playground
exercise current plugin-sdk/admin APIs the lagging latest tag may lack),
with peer ranges still falling back to valid semver.

Under --use-yalc the generator omits Nextly-family devDeps and the
installer yalc-adds before the first install, so the local-package flow
never fetches published Nextly packages it is about to replace.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Nitpick comments (1)
packages/create-nextly-app/tsup.config.ts (1)

23-32: 🚀 Performance & Scalability | 🔵 Trivial | ⚡ Quick win

Mirror the node_modules/.git skip from restoreBundledGitignores.

restoreBundledGitignores (packages/create-nextly-app/src/utils/template.ts) explicitly skips node_modules and .git when recursing to rename gitignore. This packing-time counterpart doesn't, so if a bundled template directory happens to contain a local node_modules (e.g., from testing the dev/ playground before building the CLI), the walk needlessly recurses into it.

♻️ Proposed fix
 function renameGitignoresForPacking(dir: string): void {
   for (const entry of readdirSync(dir, { withFileTypes: true })) {
     const full = path.join(dir, entry.name);
     if (entry.isDirectory()) {
+      if (entry.name === "node_modules" || entry.name === ".git") continue;
       renameGitignoresForPacking(full);
     } else if (entry.name === ".gitignore") {
       renameSync(full, path.join(dir, "gitignore"));
     }
   }
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/create-nextly-app/tsup.config.ts` around lines 23 - 32, Update
renameGitignoresForPacking to skip entries named node_modules or .git before
recursing, matching the existing restoreBundledGitignores behavior; continue
renaming .gitignore files and traversing other directories unchanged.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/create-nextly-app/src/__tests__/scaffold-plugin.test.ts`:
- Around line 81-91: Update the peerDependencies validation in
scaffold-plugin.test.ts to parse each complete spec as a valid semver range
rather than checking only its first character. Ensure invalid values such as
^latest, >=alpha, and 1not-a-version fail while legitimate peer range
expressions remain accepted.

---

Nitpick comments:
In `@packages/create-nextly-app/tsup.config.ts`:
- Around line 23-32: Update renameGitignoresForPacking to skip entries named
node_modules or .git before recursing, matching the existing
restoreBundledGitignores behavior; continue renaming .gitignore files and
traversing other directories unchanged.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 4e6fc761-e088-4f69-bc95-fc79f3254e1e

📥 Commits

Reviewing files that changed from the base of the PR and between 5869983 and 1cd8634.

⛔ Files ignored due to path filters (1)
  • .changeset/plugin-template-scaffold-fixes.md is excluded by !.changeset/**
📒 Files selected for processing (5)
  • packages/create-nextly-app/src/__tests__/scaffold-plugin.test.ts
  • packages/create-nextly-app/src/__tests__/template-channel.test.ts
  • packages/create-nextly-app/src/installers/dependencies.ts
  • packages/create-nextly-app/src/utils/template.ts
  • packages/create-nextly-app/tsup.config.ts

Comment thread packages/create-nextly-app/src/__tests__/scaffold-plugin.test.ts Outdated
… to the local store

Yalc rewrites workspace:* inter-package ranges to *, and semver * never
matches prereleases — so pnpm resolved the linked packages' nested copies
of each other from the registry's last stable release (0.0.1) and the
mixed versions crashed the scaffold's test harness at runtime
(mapKeysToSqlColumns missing from the ancient adapter). The generated
pnpm-workspace.yaml now carries an overrides map pinning every resolution
of the yalc set to file:.yalc copies, and the installer shares the same
package list so the two can never drift.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 1cd8634cd1

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment thread packages/create-nextly-app/src/create-nextly.ts Outdated
aqib-rx added 2 commits July 28, 2026 14:40
….js app

The plugin template always produces a standalone package, but a Next.js
project at cwd routed the run into the install-into-this-project flow —
which ignores the directory argument — so the guard cancelled even for
an explicit target like 'create-nextly-app my-plugin -t plugin' run from
inside an app repo. Plugin runs now always take the fresh-scaffold path
(making that guard unreachable, so it is removed); non-empty targets are
negotiated by the existing directory-conflict prompt, and non-plugin
behavior in existing projects is unchanged.

Also validates generated peer specs with an anchored full-range pattern
instead of a first-character check, which waved through hybrids like
'^latest'.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
packages/create-nextly-app/src/utils/template.ts (2)

206-230: 🔒 Security & Privacy | 🟠 Major | ⚡ Quick win

Preserve an existing .gitignore during restoration.

The overlay path can choose “ignore” and keep existing files, but restoreBundledGitignores unconditionally renames gitignore to .gitignore; fs.rename replaces the destination contents, which can replace user-defined ignore rules and make secrets or generated files committable. Keep/merge the existing destination when present and only rename when .gitignore is absent.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/create-nextly-app/src/utils/template.ts` around lines 206 - 230,
Update restoreBundledGitignores so each gitignore restoration checks whether
.gitignore already exists before renaming. Preserve the existing destination and
avoid overwriting its contents; only rename gitignore when .gitignore is absent,
while retaining the current recursive traversal and exclusions.

493-501: 🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick win

Validate the resolved dependency range instead of trusting the ^ prefix.

resolveNextlyVersions() accepts the raw latest value and wraps it as "^${version}", but a malformed value like ^not-a-version would still pass the current startsWith("^") guard and be written into generated {{nextlyRange}}. Reuse or add a small semver-range validator before returning the caret value, and keep the same validation surface for invalid/careted, exact/version-only, and prerelease inputs.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/create-nextly-app/src/utils/template.ts` around lines 493 - 501,
Update resolvePluginNextlyRange to validate the resolved v as a valid semver
range rather than accepting any value beginning with "^". Reuse an existing
validator or add a small one that consistently handles invalid/caret, exact or
version-only, and prerelease inputs; return ">=0.0.0" for invalid ranges while
preserving valid caret ranges and the useYalc behavior.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@packages/create-nextly-app/src/utils/template.ts`:
- Around line 206-230: Update restoreBundledGitignores so each gitignore
restoration checks whether .gitignore already exists before renaming. Preserve
the existing destination and avoid overwriting its contents; only rename
gitignore when .gitignore is absent, while retaining the current recursive
traversal and exclusions.
- Around line 493-501: Update resolvePluginNextlyRange to validate the resolved
v as a valid semver range rather than accepting any value beginning with "^".
Reuse an existing validator or add a small one that consistently handles
invalid/caret, exact or version-only, and prerelease inputs; return ">=0.0.0"
for invalid ranges while preserving valid caret ranges and the useYalc behavior.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: cbcf2f8a-9667-4b1a-ae4a-e7be4ee283ef

📥 Commits

Reviewing files that changed from the base of the PR and between 1cd8634 and a369327.

📒 Files selected for processing (4)
  • packages/create-nextly-app/src/__tests__/scaffold-plugin.test.ts
  • packages/create-nextly-app/src/create-nextly.ts
  • packages/create-nextly-app/src/installers/dependencies.ts
  • packages/create-nextly-app/src/utils/template.ts
🚧 Files skipped from review as they are similar to previous changes (2)
  • packages/create-nextly-app/src/installers/dependencies.ts
  • packages/create-nextly-app/src/tests/scaffold-plugin.test.ts

…ry versions

Restoring a bundled gitignore now merges into an existing .gitignore
(overlay scaffolds can carry user rules at the destination; a rename
replaced them, silently un-ignoring whatever they covered) — the
template's rules are appended once, so user rules and the required
dev/.env exclusion both hold.

Registry dist-tag payloads are untrusted: fetchLatestVersion now wraps
only complete semver versions (a malformed tag became an invalid
"^not-a-version" install spec in every generated package.json), and the
plugin compat range validates the full caret range before trusting it.
The packing-time gitignore walk also skips node_modules and .git.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

scope: cli create-nextly-app type: docs Documentation only

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants