Skip to content

feat(web): root docs locale and portless dev flow#192

Merged
yacosta738 merged 2 commits into
mainfrom
docs/default-lang-without-slag
Mar 11, 2026
Merged

feat(web): root docs locale and portless dev flow#192
yacosta738 merged 2 commits into
mainfrom
docs/default-lang-without-slag

Conversation

@yacosta738
Copy link
Copy Markdown
Contributor

This pull request introduces "portless" local development URLs and tooling across the web client apps (docs, chat, dashboard, and marketing). The main goal is to simplify local development by using named subdomains (e.g., http://chat.localhost:1355) instead of separate ports, while still supporting legacy port-based workflows via an environment variable. Documentation and configuration files have been updated accordingly, and the portless dependency has been added to relevant packages.

Key changes:

Portless Development Environment Integration:

  • Updated all web app package scripts (docs, chat, dashboard) to use portless run for development and preview commands, enabling named local URLs instead of port numbers. Legacy port-based development is still supported via PORTLESS=0. (clients/web/apps/docs/package.json, clients/web/apps/chat/package.json, clients/web/apps/dashboard/package.json) [1] [2] [3] [4] [5] [6] [7]
  • Added portless as a devDependency in all relevant package.json files. [1] [2] [3]

Documentation Updates:

  • Updated all README files to document the new portless URLs, how to run in legacy mode, and the new development workflow. (clients/web/README.md, clients/web/apps/docs/README.md, clients/web/apps/chat/README.md, clients/web/apps/dashboard/README.md) [1] [2] [3] [4] [5]
  • Clarified usage of portless for one-off usage with pnpm dlx or npx.

Configuration and Locale Improvements:

  • Modified astro.config.mjs to support PORTLESS_URL and improved port resolution logic for the docs site. [1] [2]
  • Changed the default locale from "en" to "root" in the docs app, and updated locale definitions accordingly. [1] [2]

Documentation Path Fixes:

  • Fixed outdated or broken documentation links to remove /en/ from paths, reflecting the new locale structure and correct documentation locations. (clients/agent-runtime/CONTRIBUTING.md, clients/agent-runtime/firmware/corvus-esp32-ui/README.md) [1] [2]

These changes streamline local development, improve documentation clarity, and update configuration to support the new portless workflow.

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Mar 11, 2026

📝 Walkthrough

Summary by CodeRabbit

  • New Features

    • Portless development mode added, providing unified localhost:1355 URLs for apps.
  • Bug Fixes

    • Fixed incorrect documentation links.
  • Documentation

    • Updated development setup with portless URLs and PORTLESS=0 override.
    • Reorganized docs locale labeling and adjusted intro assets and redirect behavior.
  • Chores

    • Improved installer to detect/preserve existing install method.
    • Bumped pnpm and added portless as a dev dependency; updated dev/preview scripts.

Walkthrough

Integrates "portless" into multiple web apps (dev/start/preview scripts and workspace), updates port/URL resolution and docs locale defaults, fixes a few documentation links and image paths, and enhances the marketing app installer to detect and preserve existing install methods.

Changes

Cohort / File(s) Summary
Documentation link & asset fixes
clients/agent-runtime/CONTRIBUTING.md, clients/agent-runtime/firmware/corvus-esp32-ui/README.md, clients/web/apps/docs/src/content/docs/intro/introduction.mdx
Corrected relative links to CI map and hardware docs; fixed an image asset path.
Portless integration — package scripts & deps
clients/web/apps/chat/package.json, clients/web/apps/dashboard/package.json, clients/web/apps/docs/package.json, clients/web/apps/marketing/package.json, clients/web/pnpm-workspace.yaml, clients/web/package.json
Replaced direct vite/astro ports with portless run --name <app> wrappers and added portless to devDependencies; added portless to workspace catalog; adjusted root scripts and added dev:docs.
App README updates (portless usage & legacy port fallbacks)
clients/web/README.md, clients/web/apps/chat/README.md, clients/web/apps/dashboard/README.md, clients/web/apps/docs/README.md, clients/web/apps/marketing/README.md
Documented portless dev URLs (e.g., *.localhost:1355), added PORTLESS=0 fallback instructions and legacy port notes.
Astro/Vite config: port & URL resolution
clients/web/apps/docs/astro.config.mjs, clients/web/apps/marketing/astro.config.mjs
Added portlessUrl fallback; changed port resolution to prefer PORT/env.PORT when finite then fall back to URL-parsed port; updated server/preview port usage.
Locale & docs structure changes
clients/web/apps/docs/astro.config.mjs, clients/web/apps/docs/src/content/docs/guides/structure.md, clients/web/apps/docs/src/content/docs/es/guides/structure.md, clients/web/apps/docs/src/pages/en/[...slug].astro, clients/web/apps/docs/src/pages/index.astro
Switched default locale identifier from en to root, swapped doc listings for English/Spanish, removed previous homepage redirect, and added slug-based redirect page for legacy paths.
Marketing installer enhancements
clients/web/apps/marketing/public/install
Added EXISTING_INSTALL_METHOD detection and logic to preserve prior non-binary install methods; improved yarn handling for Yarn 2+, adjusted install and post-install flows and health checks.
Marketing app base URL usage
clients/web/apps/marketing/src/pages/index.astro
Added portlessUrl helper and changed base URL selection to prefer MARKETING_URL or the portless fallback in non-production.

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~50 minutes

Possibly related PRs

Suggested reviewers

  • yuniel-acosta
🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title follows Conventional Commit style with 'feat' prefix and clearly describes the main changes: introducing portless development and root locale for docs.
Description check ✅ Passed The description provides comprehensive coverage of all changes including portless integration, documentation updates, configuration adjustments, and locale changes with clear sections and rationale.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch docs/default-lang-without-slag

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 and usage tips.

@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented Mar 11, 2026

✅ Contributor Report

User: @yacosta738
Status: Passed (12/13 metrics passed)

Metric Description Value Threshold Status
PR Merge Rate PRs merged vs closed 89% >= 30%
Repo Quality Repos with ≥100 stars 0 >= 0
Positive Reactions Positive reactions received 9 >= 1
Negative Reactions Negative reactions received 0 <= 5
Account Age GitHub account age 3056 days >= 30 days
Activity Consistency Regular activity over time 108% >= 0%
Issue Engagement Issues with community engagement 0 >= 0
Code Reviews Code reviews given to others 398 >= 0
Merger Diversity Unique maintainers who merged PRs 2 >= 0
Repo History Merge Rate Merge rate in this repo 91% >= 0%
Repo History Min PRs Previous PRs in this repo 145 >= 0
Profile Completeness Profile richness (bio, followers) 90 >= 0
Suspicious Patterns Spam-like activity detection 1 N/A

Contributor Report evaluates based on public GitHub activity. Analysis period: 2025-03-11 to 2026-03-11

@sentry
Copy link
Copy Markdown

sentry Bot commented Mar 11, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 9

Caution

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

⚠️ Outside diff range comments (1)
clients/web/README.md (1)

80-84: ⚠️ Potential issue | 🟡 Minor

Add the missing pnpm dev:docs command.

This section now lists app-specific dev commands for marketing/chat/dashboard, but omits docs even though clients/web/package.json still exposes dev:docs. That leaves the README out of sync with the actual workspace contract.

Suggested doc fix
 # Development
 pnpm dev
+pnpm dev:docs
 pnpm dev:marketing
 pnpm dev:chat
 pnpm dev:dashboard

As per coding guidelines, "**/*.{md,mdx}: Verify technical accuracy and that docs stay aligned with code changes."

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/README.md` around lines 80 - 84, The Development list in
clients/web/README.md omits the pnpm dev:docs command; add "pnpm dev:docs" to
the dev commands block so it matches the scripts exposed in
clients/web/package.json (ensure the entry exactly matches the script name
dev:docs), keeping formatting consistent with the existing lines.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@clients/web/apps/chat/package.json`:
- Around line 11-13: Add an explicit default port to Vite’s configuration so
legacy PORTLESS=0 falls back to 4323: update vite.config.ts (the export default
defineConfig(...) object) to include server: { port: 4323 } so Vite uses port
4323 when no --port flag is provided; ensure the property is a numeric value and
placed at the top-level of the exported config object so existing scripts
(dev/build/preview) keep their behavior while preserving the README contract.

In `@clients/web/apps/docs/README.md`:
- Around line 20-21: Update the docs line that shows the legacy startup command
so it also documents the fallback server URL; specifically, modify the README
entry for "PORTLESS=0 pnpm run dev" to state that the legacy server will be
available at http://localhost:4321 (or the configured port), ensuring the
command text "PORTLESS=0 pnpm run dev" and the URL are included together so
readers know where to access the running app.

In `@clients/web/apps/docs/src/content/docs/es/guides/structure.md`:
- Around line 48-51: The Spanish locale section currently references top-level
paths `docs/` and `docs/es/` that no longer exist; update the ES entries so they
mirror the English entries using the project's docs content root (i.e., use the
same relative paths for `index.mdx` and `guides/` under the project's docs
content directory rather than `docs/`/`docs/es/`) so the Spanish guide points to
the correct in-repo locations and stays aligned with the English version.

In `@clients/web/apps/docs/src/pages/en/`[...slug].astro:
- Around line 2-6: Astro.redirect(...) is being invoked but its response is not
returned, so requests under /en/* continue to render; update the handler to
return the redirect response by returning the result of Astro.redirect(...) (use
the existing symbols: Astro.redirect, slug, baseUrl) so the redirect is actually
sent to the client.

In `@clients/web/apps/marketing/astro.config.mjs`:
- Around line 20-24: The port parsing currently uses Number.parseInt on
portCandidate which accepts partial strings and out-of-range values; update the
logic around portCandidate/parsedPort/resolvedPort to first ensure portCandidate
is purely digits (e.g., match /^\d+$/) then parse to an integer and validate
it's between 0 and 65535 (inclusive); if the digit check or range check fails,
fall back to getPortFromUrl(marketingUrl, PORTS.MARKETING); keep references to
portCandidate, parsedPort, resolvedPort, getPortFromUrl, and PORTS.MARKETING so
reviewers can find and verify the change.

In `@clients/web/apps/marketing/public/install`:
- Around line 52-73: The detection currently labels executables with a Node
shebang as generic "package" (EXISTING_INSTALL_METHOD) but then fails to
identify the actual package manager when the path lacks pm keywords, causing a
non-interactive fallthrough to "binary"; fix by resolving the symlink target of
EXISTING_CMD_PATH (e.g., with readlink -f) and, if it points into a
node_modules/.bin or into an install tree, walk parent directories to detect
package manager metadata (presence of pnpm-lock.yaml, yarn.lock,
package-lock.json or a package.json with a yarn usage hint) and set
EXISTING_INSTALL_METHOD to the specific pm (pnpm/yarn/bun/npm) before using the
case match; also replace any use of transient yarn dlx for persistent installs
by preferring a persistent yarn global install path or detecting Yarn v2+
(berry) via .yarn/releases or .yarnrc.yml and treat it as a non-global package
manager rather than as creating a persistent binary.
- Around line 801-809: The current branch uses "yarn dlx" for Yarn 2+ which does
not persist the CLI; update the install logic so when yarn_major >= 2 you fail
fast with a clear error (stderr) and exit non-zero, telling users to install via
npm/pnpm/bun (or run "yarn set version classic" if you want to support legacy
global installs), and reference the CLI by name via "$CLI_PACKAGE" in the
message; this prevents post_install_steps() from silently passing when has_cmd
corvus will later fail.

In `@clients/web/apps/marketing/src/pages/index.astro`:
- Around line 16-20: Links in the CTAs still include the retired "/en" locale
segment causing 404s; update all places that build docs links (look for the
docsBaseUrl usage inside installMethods, quickLinks, faqGroups, and the hero
panel) to remove the hardcoded "/en" segment so links are `${docsBaseUrl}/...`
(or construct via a helper that uses root locale), ensuring you update every
occurrence and tests/fixtures that expect the old path.

In `@clients/web/package.json`:
- Around line 15-16: The root "dev" script in package.json currently runs "pnpm
--parallel -r run dev" which fails when workspaces like packages/locales and
packages/ui lack a dev script; update the "dev" script (the "dev" entry in
package.json) to either add --if-present (e.g., pnpm --parallel -r --if-present
run dev) so pnpm skips packages without a dev script, or restrict the command to
the intended apps using a workspace filter (e.g., pnpm --parallel -r --filter
`@corvus/apps` run dev) so only app packages are targeted.

---

Outside diff comments:
In `@clients/web/README.md`:
- Around line 80-84: The Development list in clients/web/README.md omits the
pnpm dev:docs command; add "pnpm dev:docs" to the dev commands block so it
matches the scripts exposed in clients/web/package.json (ensure the entry
exactly matches the script name dev:docs), keeping formatting consistent with
the existing lines.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 71555406-94dc-4609-8be6-2e5e51dd6ca6

📥 Commits

Reviewing files that changed from the base of the PR and between 05588a5 and 71ba310.

⛔ Files ignored due to path filters (1)
  • clients/web/pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (40)
  • clients/agent-runtime/CONTRIBUTING.md
  • clients/agent-runtime/firmware/corvus-esp32-ui/README.md
  • clients/web/README.md
  • clients/web/apps/chat/README.md
  • clients/web/apps/chat/package.json
  • clients/web/apps/dashboard/README.md
  • clients/web/apps/dashboard/package.json
  • clients/web/apps/docs/README.md
  • clients/web/apps/docs/astro.config.mjs
  • clients/web/apps/docs/package.json
  • clients/web/apps/docs/src/content/docs/404.mdx
  • clients/web/apps/docs/src/content/docs/clients/agent-runtime/architecture.md
  • clients/web/apps/docs/src/content/docs/clients/agent-runtime/ci-map.md
  • clients/web/apps/docs/src/content/docs/clients/agent-runtime/index.mdx
  • clients/web/apps/docs/src/content/docs/clients/agent-runtime/pr-workflow.md
  • clients/web/apps/docs/src/content/docs/es/guides/structure.md
  • clients/web/apps/docs/src/content/docs/guides/architecture.md
  • clients/web/apps/docs/src/content/docs/guides/architecture/overview.md
  • clients/web/apps/docs/src/content/docs/guides/cli-reference.md
  • clients/web/apps/docs/src/content/docs/guides/configuration.md
  • clients/web/apps/docs/src/content/docs/guides/customization.md
  • clients/web/apps/docs/src/content/docs/guides/development.md
  • clients/web/apps/docs/src/content/docs/guides/features.md
  • clients/web/apps/docs/src/content/docs/guides/getting-started.md
  • clients/web/apps/docs/src/content/docs/guides/gpg-setup.md
  • clients/web/apps/docs/src/content/docs/guides/hardware-peripherals-design.md
  • clients/web/apps/docs/src/content/docs/guides/release.md
  • clients/web/apps/docs/src/content/docs/guides/structure.md
  • clients/web/apps/docs/src/content/docs/guides/surrealdb.md
  • clients/web/apps/docs/src/content/docs/index.mdx
  • clients/web/apps/docs/src/content/docs/intro/introduction.mdx
  • clients/web/apps/docs/src/pages/en/[...slug].astro
  • clients/web/apps/docs/src/pages/index.astro
  • clients/web/apps/marketing/README.md
  • clients/web/apps/marketing/astro.config.mjs
  • clients/web/apps/marketing/package.json
  • clients/web/apps/marketing/public/install
  • clients/web/apps/marketing/src/pages/index.astro
  • clients/web/package.json
  • clients/web/pnpm-workspace.yaml
💤 Files with no reviewable changes (1)
  • clients/web/apps/docs/src/pages/index.astro
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: pr-checks
  • GitHub Check: sonar
  • GitHub Check: Cloudflare Pages
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{md,mdx}

⚙️ CodeRabbit configuration file

**/*.{md,mdx}: Verify technical accuracy and that docs stay aligned with code changes.
For user-facing docs, check EN/ES parity or explicitly note pending translation gaps.

Files:

  • clients/web/apps/chat/README.md
  • clients/web/apps/dashboard/README.md
  • clients/web/apps/docs/src/content/docs/guides/structure.md
  • clients/web/apps/docs/src/content/docs/intro/introduction.mdx
  • clients/agent-runtime/CONTRIBUTING.md
  • clients/agent-runtime/firmware/corvus-esp32-ui/README.md
  • clients/web/README.md
  • clients/web/apps/docs/README.md
  • clients/web/apps/marketing/README.md
  • clients/web/apps/docs/src/content/docs/es/guides/structure.md
**/*

⚙️ CodeRabbit configuration file

**/*: Security first, performance second.
Validate input boundaries, auth/authz implications, and secret management.
Look for behavioral regressions, missing tests, and contract breaks across modules.

Files:

  • clients/web/apps/chat/README.md
  • clients/web/apps/dashboard/README.md
  • clients/web/apps/docs/src/content/docs/guides/structure.md
  • clients/web/apps/chat/package.json
  • clients/web/apps/docs/src/content/docs/intro/introduction.mdx
  • clients/agent-runtime/CONTRIBUTING.md
  • clients/agent-runtime/firmware/corvus-esp32-ui/README.md
  • clients/web/README.md
  • clients/web/apps/docs/README.md
  • clients/web/apps/marketing/src/pages/index.astro
  • clients/web/apps/docs/src/pages/en/[...slug].astro
  • clients/web/package.json
  • clients/web/apps/marketing/public/install
  • clients/web/apps/marketing/README.md
  • clients/web/apps/dashboard/package.json
  • clients/web/apps/docs/package.json
  • clients/web/apps/docs/astro.config.mjs
  • clients/web/apps/marketing/astro.config.mjs
  • clients/web/pnpm-workspace.yaml
  • clients/web/apps/docs/src/content/docs/es/guides/structure.md
  • clients/web/apps/marketing/package.json
🧠 Learnings (10)
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/src/main.rs : Preserve CLI contract unless change is intentional and documented; prefer explicit errors over silent fallback for unsupported critical paths

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T07:28:38.934Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: AGENTS.md:0-0
Timestamp: 2026-02-17T07:28:38.934Z
Learning: Applies to .agents/AGENTS.md : Document agent configurations and capabilities in AGENTS.md

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/src/{security,gateway,tools}/**/*.rs : Treat `src/security/`, `src/gateway/`, `src/tools/` as high-risk surfaces and never broaden filesystem/network execution scope without explicit policy checks

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/src/{security,gateway,tools,config}/**/*.rs : Do not silently weaken security policy or access constraints; keep default behavior secure-by-default with deny-by-default where applicable

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T07:28:38.934Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: AGENTS.md:0-0
Timestamp: 2026-02-17T07:28:38.934Z
Learning: Applies to .agents/AGENTS.md : Maintain comprehensive agent metadata including name, description, purpose, and capabilities

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/.github/**/*.{yml,yaml} : For workflow/template-only changes, ensure YAML/template syntax validity

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/**/*.rs : Run `cargo fmt --all -- --check`, `cargo clippy --all-targets -- -D warnings`, and `cargo test` for code validation, or document which checks were skipped and why

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T07:28:38.934Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: AGENTS.md:0-0
Timestamp: 2026-02-17T07:28:38.934Z
Learning: Applies to .agents/AGENTS.md : Include version information and compatibility details for agents

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Include threat/risk notes and rollback strategy for security, runtime, and gateway changes; add or update tests for boundary checks and failure modes

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
📚 Learning: 2026-02-17T12:31:17.076Z
Learnt from: CR
Repo: dallay/corvus PR: 0
File: clients/agent-runtime/AGENTS.md:0-0
Timestamp: 2026-02-17T12:31:17.076Z
Learning: Applies to clients/agent-runtime/src/**/*.rs : Avoid unnecessary allocations, clones, and blocking operations to maintain performance and efficiency

Applied to files:

  • clients/agent-runtime/CONTRIBUTING.md
🪛 LanguageTool
clients/web/apps/marketing/README.md

[grammar] ~32-~32: Cambia la palabra o signo.
Context: ...p://marketing.localhost:1355(portless) - Prod default:https://profiletailors.co...

(QB_NEW_ES_OTHER_ERROR_IDS_REPLACEMENT_SPACE)


[grammar] ~33-~33: Cambia la palabra o signo.
Context: ...alhost:1355(portless) - Prod default:https://profiletailors.com` - El puerto de dev/preview se toma de `P...

(QB_NEW_ES_OTHER_ERROR_IDS_REPLACEMENT_SPACE)

clients/web/apps/docs/src/content/docs/es/guides/structure.md

[grammar] ~49-~49: Elimina la puntuación
Context: ...en inglés (locale raíz). - index.mdx: Página de inicio. - guides/: Guías ...

(QB_NEW_ES_OTHER_ERROR_IDS_UNNECESSARY_PUNCTUATION)

🔇 Additional comments (9)
clients/agent-runtime/firmware/corvus-esp32-ui/README.md (1)

106-106: Link target matches the new docs locale layout.

This path update looks correct and stays aligned with the docs app’s root-locale structure. As per coding guidelines, "Verify technical accuracy and that docs stay aligned with code changes."

clients/web/pnpm-workspace.yaml (1)

21-21: Approve — portless@0.6.0 is properly wired into the workspace catalog.

Alphabetically ordered and correctly referenced as "catalog:" across all four consuming apps (chat, dashboard, docs, marketing). Since portless is dev-only, no production security surface is introduced.

clients/agent-runtime/CONTRIBUTING.md (1)

50-51: Documentation links are correct. Both pr-workflow.md and ci-map.md exist at the specified paths. No issues.

clients/web/apps/dashboard/package.json (2)

11-13: LGTM - portless integration follows established pattern.

The dev/preview scripts wrap Vite with portless run --name dashboard, consistent with other apps in this PR. The --name dashboard flag enables the http://dashboard.localhost:1355 URL documented in the README.


41-41: Dependency addition looks good.

Portless is correctly added as a devDependency using catalog:, which resolves to version 0.6.0 per the workspace catalog. Dev-only scope is appropriate since this is tooling for local development.

clients/web/apps/dashboard/README.md (1)

19-21: The README port documentation is accurate and consistent with the codebase.

The parent README (clients/web/README.md) explicitly documents that the dashboard's legacy dev port (when PORTLESS=0) is 4324. This port is confirmed across the test configuration and follows the established pattern for all web apps in the monorepo. No changes needed.

			> Likely an incorrect or invalid review comment.
clients/web/apps/chat/README.md (1)

23-25: LGTM!

Documentation is accurate and consistent with the parent README (clients/web/README.md:26-40) which confirms the same portless URL and legacy port mapping.

clients/web/apps/chat/package.json (1)

40-40: LGTM!

The catalog: reference correctly resolves to portless: 0.6.0 as defined in clients/web/pnpm-workspace.yaml. Consistent with other apps in the monorepo adopting the same pattern.

clients/web/apps/docs/astro.config.mjs (1)

28-32: This scenario doesn't occur under portless's contract.

According to portless run source code, PORT is always injected as an environment variable alongside PORTLESS_URL—even when a fixed app port is forced. The fallback to getPortFromUrl(docsUrl, PORTS.DOCS) will not execute in the portless flow, so the code is safe as-is.

			> Likely an incorrect or invalid review comment.

Comment on lines +11 to +13
"dev": "portless run --name chat vite --config vite.config.ts",
"build": "vue-tsc -b && vite build --config vite.config.ts",
"preview": "vite preview --config vite.config.ts --port 4323",
"preview": "portless run --name chat vite preview --config vite.config.ts",
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Check if vite.config.ts specifies port 4323 for fallback behavior
fd -t f 'vite.config.ts' clients/web/apps/chat --exec cat {}

Repository: dallay/corvus

Length of output: 674


🏁 Script executed:

fd -t f -i 'readme*' clients/web/apps/chat

Repository: dallay/corvus

Length of output: 88


🏁 Script executed:

git ls-files clients/web/apps/chat | grep -i readme

Repository: dallay/corvus

Length of output: 88


🌐 Web query:

portless PORTLESS=0 environment variable fallback behavior vite

💡 Result:

portless has a built-in “escape hatch” env var:

  • If PORTLESS=0 (or PORTLESS=skip), portless bypasses the proxy entirely and just runs your command normally (no named .localhost URL, no proxy auto-start, and no portless port/host injection). [1]
  • Normally, portless assigns your app a random port (4000–4999) and sets PORT/HOST; because Vite ignores PORT, portless instead auto-injects --port and --host when it is enabled. [1]
  • With PORTLESS=0, that injection doesn’t happen, so Vite falls back to its normal behavior (default dev port, and if that port is taken it will try the next available port). [2]

Example

PORTLESS=0 pnpm dev   # runs plain `vite` (or whatever your dev script runs), no proxy

Sources: portless configuration docs [1]; Vite server option docs (port fallback) [2].


🏁 Script executed:

cat -n clients/web/apps/chat/README.md

Repository: dallay/corvus

Length of output: 956


Fix port fallback for PORTLESS=0 legacy mode.

The --port 4323 flag was removed from the vite commands, and vite.config.ts does not specify server.port. When PORTLESS=0 is set, portless bypasses entirely and Vite falls back to port 5173 instead of the documented 4323.

Add server: { port: 4323 } to vite.config.ts to preserve the README contract: "Use PORTLESS=0 pnpm dev:chat to run on http://localhost:4323".

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/chat/package.json` around lines 11 - 13, Add an explicit
default port to Vite’s configuration so legacy PORTLESS=0 falls back to 4323:
update vite.config.ts (the export default defineConfig(...) object) to include
server: { port: 4323 } so Vite uses port 4323 when no --port flag is provided;
ensure the property is a numeric value and placed at the top-level of the
exported config object so existing scripts (dev/build/preview) keep their
behavior while preserving the README contract.

Comment on lines +20 to +21
# Run without portless (legacy localhost port)
PORTLESS=0 pnpm run dev
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Document the legacy URL as well.

PORTLESS=0 pnpm run dev is useful, but this section never says that the fallback server is then on http://localhost:4321. Without the URL, the legacy workflow is only half documented.

Suggested doc fix
 # Run without portless (legacy localhost port)
+# http://localhost:4321
 PORTLESS=0 pnpm run dev

As per coding guidelines, "**/*.{md,mdx}: Verify technical accuracy and that docs stay aligned with code changes. For user-facing docs, check EN/ES parity or explicitly note pending translation gaps."

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
# Run without portless (legacy localhost port)
PORTLESS=0 pnpm run dev
# Run without portless (legacy localhost port)
# http://localhost:4321
PORTLESS=0 pnpm run dev
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/docs/README.md` around lines 20 - 21, Update the docs line
that shows the legacy startup command so it also documents the fallback server
URL; specifically, modify the README entry for "PORTLESS=0 pnpm run dev" to
state that the legacy server will be available at http://localhost:4321 (or the
configured port), ensuring the command text "PORTLESS=0 pnpm run dev" and the
URL are included together so readers know where to access the running app.

Comment on lines +48 to +51
- **`docs/`**: Documentación en inglés (locale raíz).
- `index.mdx`: Página de inicio.
- `guides/`: Guías detalladas del proyecto.
- **`docs/en/`**: Documentación en inglés (si aplica).
- **`docs/es/`**: Documentación en español.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Fix the Spanish locale paths.

These entries still point to docs/ and docs/es/, but the actual paths after this locale swap are under clients/web/apps/docs/src/content/docs/. Right now the ES page diverges from the English guide and sends readers to directories that do not exist at the repo root.

Suggested doc fix
-- **`docs/`**: Documentación en inglés (locale raíz).
+- **`clients/web/apps/docs/src/content/docs/`**: Documentación en inglés (locale raíz).
   - `index.mdx`: Página de inicio.
   - `guides/`: Guías detalladas del proyecto.
-- **`docs/es/`**: Documentación en español.
+- **`clients/web/apps/docs/src/content/docs/es/`**: Documentación en español.

As per coding guidelines, "**/*.{md,mdx}: Verify technical accuracy and that docs stay aligned with code changes. For user-facing docs, check EN/ES parity or explicitly note pending translation gaps."

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- **`docs/`**: Documentación en inglés (locale raíz).
- `index.mdx`: Página de inicio.
- `guides/`: Guías detalladas del proyecto.
- **`docs/en/`**: Documentación en inglés (si aplica).
- **`docs/es/`**: Documentación en español.
- **`clients/web/apps/docs/src/content/docs/`**: Documentación en inglés (locale raíz).
- `index.mdx`: Página de inicio.
- `guides/`: Guías detalladas del proyecto.
- **`clients/web/apps/docs/src/content/docs/es/`**: Documentación en español.
🧰 Tools
🪛 LanguageTool

[grammar] ~49-~49: Elimina la puntuación
Context: ...en inglés (locale raíz). - index.mdx: Página de inicio. - guides/: Guías ...

(QB_NEW_ES_OTHER_ERROR_IDS_UNNECESSARY_PUNCTUATION)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/docs/src/content/docs/es/guides/structure.md` around lines
48 - 51, The Spanish locale section currently references top-level paths `docs/`
and `docs/es/` that no longer exist; update the ES entries so they mirror the
English entries using the project's docs content root (i.e., use the same
relative paths for `index.mdx` and `guides/` under the project's docs content
directory rather than `docs/`/`docs/es/`) so the Spanish guide points to the
correct in-repo locations and stays aligned with the English version.

Comment on lines +2 to +6
const { slug } = Astro.params;
const baseUrl = import.meta.env.BASE_URL.endsWith("/")
? import.meta.env.BASE_URL.slice(0, -1)
: import.meta.env.BASE_URL;
Astro.redirect(`${baseUrl}${slug ? `/${slug}` : "/"}`);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🌐 Web query:

In Astro v5, does page frontmatter need return Astro.redirect(...) for the redirect response to be sent?

💡 Result:

Yes. In Astro v5, a page must return Astro.redirect(...) from its frontmatter for the redirect response to be sent; just calling Astro.redirect(...) without returning it will not trigger the redirect. [1]

(And Astro.redirect() returns a Response, which is one of the only valid things you can return from a page.) [2]

Sources: [1] Astro API reference (redirect()), [2] Astro error docs (“Only Response can be returned”)


Return the redirect response.

This calls Astro.redirect(...) but never returns it, leaving legacy /en/* requests to render as pages instead of triggering redirects.

Minimal fix
-Astro.redirect(`${baseUrl}${slug ? `/${slug}` : "/"}`);
+return Astro.redirect(`${baseUrl}${slug ? `/${slug}` : "/"}`);
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/docs/src/pages/en/`[...slug].astro around lines 2 - 6,
Astro.redirect(...) is being invoked but its response is not returned, so
requests under /en/* continue to render; update the handler to return the
redirect response by returning the result of Astro.redirect(...) (use the
existing symbols: Astro.redirect, slug, baseUrl) so the redirect is actually
sent to the client.

Comment on lines +20 to +24
const portCandidate = process.env.PORT ?? env.PORT;
const parsedPort = Number.parseInt(portCandidate ?? "", 10);
const resolvedPort = Number.isFinite(parsedPort)
? parsedPort
: getPortFromUrl(marketingUrl, PORTS.MARKETING);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

🧩 Analysis chain

🏁 Script executed:

# First, examine the actual file
cat -n clients/web/apps/marketing/astro.config.mjs | head -40

Repository: dallay/corvus

Length of output: 1530


🏁 Script executed:

# Test Number.parseInt() behavior with the claimed problematic values
node <<'EOF'
console.log("Testing Number.parseInt() behavior:");
console.log("parseInt('123abc', 10):", Number.parseInt("123abc", 10));
console.log("parseInt('0', 10):", Number.parseInt("0", 10));
console.log("parseInt('70000', 10):", Number.parseInt("70000", 10));
console.log("parseInt('', 10):", Number.parseInt("", 10));
console.log("parseInt('abc', 10):", Number.parseInt("abc", 10));
console.log("");
console.log("isFinite() checks:");
console.log("isFinite(123):", Number.isFinite(123));
console.log("isFinite(NaN):", Number.isFinite(NaN));
console.log("isFinite(0):", Number.isFinite(0));
console.log("isFinite(70000):", Number.isFinite(70000));
console.log("");
console.log("isInteger() checks:");
console.log("isInteger(123):", Number.isInteger(123));
console.log("isInteger(0):", Number.isInteger(0));
console.log("isInteger(NaN):", Number.isInteger(NaN));
console.log("");
console.log("Port range validation [1..65535]:");
console.log("Valid port 80:", 80 >= 1 && 80 <= 65535);
console.log("Valid port 8080:", 8080 >= 1 && 8080 <= 65535);
console.log("Invalid port 0:", 0 >= 1 && 0 <= 65535);
console.log("Invalid port 65536:", 65536 >= 1 && 65536 <= 65535);
console.log("Invalid port 70000:", 70000 >= 1 && 70000 <= 65535);
EOF

Repository: dallay/corvus

Length of output: 552


🏁 Script executed:

# Test the regex pattern from the diff suggestion
node <<'EOF'
const regex = /^(?:0|[1-9]\d{0,4})$/;
const testValues = ["0", "1", "80", "8080", "65535", "65536", "70000", "123abc", "abc", "", "00", "08", "99999"];
console.log("Testing regex /^(?:0|[1-9]\\d{0,4})$/:");
testValues.forEach(val => {
  console.log(`"${val}": ${regex.test(val)}`);
});
EOF

Repository: dallay/corvus

Length of output: 257


Fix port validation—current regex in diff allows invalid ports beyond 65535.

The issue is real: Number.parseInt() accepts partial strings ("123abc"123) and out-of-range values, bypassing fallback logic. However, the suggested regex /^(?:0|[1-9]\d{0,4})$/ still accepts invalid ports like 65536, 70000, and 99999 because [1-9]\d{0,4} allows up to 5 digits.

Use a strict range check instead:

Corrected diff
 const portCandidate = process.env.PORT ?? env.PORT;
-const parsedPort = Number.parseInt(portCandidate ?? "", 10);
-const resolvedPort = Number.isFinite(parsedPort)
+const parsedPort = Number.parseInt(portCandidate ?? "", 10);
+const resolvedPort =
+  Number.isInteger(parsedPort) && parsedPort >= 1 && parsedPort <= 65535
   ? parsedPort
   : getPortFromUrl(marketingUrl, PORTS.MARKETING);
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/marketing/astro.config.mjs` around lines 20 - 24, The port
parsing currently uses Number.parseInt on portCandidate which accepts partial
strings and out-of-range values; update the logic around
portCandidate/parsedPort/resolvedPort to first ensure portCandidate is purely
digits (e.g., match /^\d+$/) then parse to an integer and validate it's between
0 and 65535 (inclusive); if the digit check or range check fails, fall back to
getPortFromUrl(marketingUrl, PORTS.MARKETING); keep references to portCandidate,
parsedPort, resolvedPort, getPortFromUrl, and PORTS.MARKETING so reviewers can
find and verify the change.

Comment on lines +52 to +73
if [ -L "$EXISTING_CMD_PATH" ] || printf "%s" "$EXISTING_CMD_PATH" | grep -q "/node_modules/.bin/"; then
EXISTING_INSTALL_METHOD="package"
else
local first_line=""
first_line="$(head -n 1 "$EXISTING_CMD_PATH" 2>/dev/null || true)"
if printf "%s" "$first_line" | grep -qi "node"; then
EXISTING_INSTALL_METHOD="package"
fi
fi

if [ "$EXISTING_INSTALL_METHOD" = "package" ]; then
case "$EXISTING_CMD_PATH" in
*pnpm*) EXISTING_INSTALL_METHOD="pnpm" ;;
*yarn*) EXISTING_INSTALL_METHOD="yarn" ;;
*bun*) EXISTING_INSTALL_METHOD="bun" ;;
*npm*) EXISTING_INSTALL_METHOD="npm" ;;
esac
fi

if [ -z "$EXISTING_INSTALL_METHOD" ]; then
EXISTING_INSTALL_METHOD="binary"
fi
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

cd clients/web/apps/marketing/public && wc -l install

Repository: dallay/corvus

Length of output: 69


🏁 Script executed:

cd clients/web/apps/marketing/public && head -n 100 install | tail -n 60

Repository: dallay/corvus

Length of output: 1656


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '52,73p' install

Repository: dallay/corvus

Length of output: 830


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '800,820p' install

Repository: dallay/corvus

Length of output: 619


🏁 Script executed:

cd clients/web/apps/marketing/public && grep -n "select_install_method" install

Repository: dallay/corvus

Length of output: 114


🏁 Script executed:

cd clients/web/apps/marketing/public && rg -n "INSTALL_METHOD" -A 2 -B 2 install | head -100

Repository: dallay/corvus

Length of output: 3149


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '821,875p' install

Repository: dallay/corvus

Length of output: 1707


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '857,870p' install

Repository: dallay/corvus

Length of output: 470


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '1,30p' install

Repository: dallay/corvus

Length of output: 890


🏁 Script executed:

cat > /tmp/verify_detection.sh << 'EOF'
#!/bin/bash

# Simulate npm global install at /usr/local/bin/corvus with Node shebang
EXISTING_CMD_PATH="/usr/local/bin/corvus"
EXISTING_INSTALL_METHOD=""

# Simulate the detection logic from lines 52-73
if [ -L "$EXISTING_CMD_PATH" ] || printf "%s" "$EXISTING_CMD_PATH" | grep -q "/node_modules/.bin/"; then
  EXISTING_INSTALL_METHOD="package"
  echo "Step 1: Symlink or node_modules check → package"
else
  echo "Step 1: Not symlink/node_modules, checking shebang..."
  # Simulate a Node shebang file (we'll just assume it passes)
  EXISTING_INSTALL_METHOD="package"
  echo "Step 2: Shebang check → package"
fi

if [ "$EXISTING_INSTALL_METHOD" = "package" ]; then
  case "$EXISTING_CMD_PATH" in
    *pnpm*) EXISTING_INSTALL_METHOD="pnpm" ;;
    *yarn*) EXISTING_INSTALL_METHOD="yarn" ;;
    *bun*) EXISTING_INSTALL_METHOD="bun" ;;
    *npm*) EXISTING_INSTALL_METHOD="npm" ;;
  esac
  echo "Step 3: Pattern matching on '$EXISTING_CMD_PATH' → EXISTING_INSTALL_METHOD='$EXISTING_INSTALL_METHOD'"
fi

if [ -z "$EXISTING_INSTALL_METHOD" ]; then
  EXISTING_INSTALL_METHOD="binary"
  echo "Step 4: Empty fallback → binary"
else
  echo "Step 4: Not empty, stays as '$EXISTING_INSTALL_METHOD'"
fi

echo ""
echo "Final EXISTING_INSTALL_METHOD: '$EXISTING_INSTALL_METHOD'"
echo ""

# Now simulate non-interactive mode decision (lines 857-870)
ALREADY_INSTALLED="1"
INSTALL_METHOD=""
echo "In non-interactive mode:"
if [ "$ALREADY_INSTALLED" = "1" ] && [ -n "$EXISTING_INSTALL_METHOD" ] && [ "$EXISTING_INSTALL_METHOD" != "binary" ]; then
  case "$EXISTING_INSTALL_METHOD" in
    pnpm|npm|yarn|bun)
      INSTALL_METHOD="$EXISTING_INSTALL_METHOD"
      echo "  Matched specific PM → INSTALL_METHOD='$INSTALL_METHOD'"
      ;;
    *)
      INSTALL_METHOD="binary"
      echo "  Fallthrough (*) case → INSTALL_METHOD='binary'"
      ;;
  esac
else
  INSTALL_METHOD="binary"
  echo "  Default → INSTALL_METHOD='binary'"
fi

echo ""
echo "RESULT: Will attempt BINARY install despite existing '$EXISTING_INSTALL_METHOD' install"
EOF
chmod +x /tmp/verify_detection.sh
/tmp/verify_detection.sh

Repository: dallay/corvus

Length of output: 457


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '789,820p' install

Repository: dallay/corvus

Length of output: 907


🏁 Script executed:

cat > /tmp/verify_yarn_issue.sh << 'EOF'
#!/bin/bash

# The issue: yarn dlx is a one-time executor, not a persistent install
echo "Yarn 2+ handling analysis:"
echo ""
echo "Line 808-809 does:"
echo "  yarn dlx `@dallay/corvus`"
echo ""
echo "Problem: yarn dlx runs the package in a temp environment, doesn't install globally."
echo "The install script then tries to set EXISTING_INSTALL_METHOD=yarn for future runs."
echo "But 'yarn dlx' doesn't create a persistent binary at a fixed path."
echo ""
echo "Expected behavior: Use 'yarn global add' or equivalent persistent install."
echo "Actual behavior: Uses transient execution which won't be detected on next run."
EOF
cat /tmp/verify_yarn_issue.sh

Repository: dallay/corvus

Length of output: 680


🏁 Script executed:

cd clients/web/apps/marketing/public && grep -n "is_interactive" install

Repository: dallay/corvus

Length of output: 177


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '1000,1012p' install

Repository: dallay/corvus

Length of output: 278


🏁 Script executed:

cd clients/web/apps/marketing/public && sed -n '110,130p' install

Repository: dallay/corvus

Length of output: 362


🏁 Script executed:

cat > /tmp/verify_yarn_dlx.sh << 'EOF'
#!/bin/bash
echo "Yarn dlx behavior analysis:"
echo ""
echo "yarn dlx is documented as: run a package in a temporary environment"
echo "It does NOT create a persistent binary in a fixed location."
echo "On subsequent runs, 'command -v corvus' will NOT find it if it was only via dlx."
echo ""
echo "Contrast with yarn global add:"
echo "  - Creates persistent entry in yarn global bin directory"
echo "  - 'command -v corvus' will find it"
echo "  - Detection logic can identify it"
EOF
cat /tmp/verify_yarn_dlx.sh

Repository: dallay/corvus

Length of output: 539


Avoid generic "package" classification in detection—it falls back to binary install in non-interactive mode.

When an existing npm/yarn install is at a generic path like /usr/local/bin/corvus, the detection logic (lines 52–73) classifies it as "package" via shebang check. The pattern matching then fails to narrow it to a specific package manager (the path lacks pnpm/yarn/bun/npm keywords). In non-interactive mode, the fallthrough case (line 864) converts this generic "package" classification to "binary", triggering an unwanted binary install alongside the existing package-manager install. Resolve the symlink target, check package manager metadata, or detect the specific PM before falling back to binary.

Additionally, the Yarn 2+ branch (line 808) uses yarn dlx, which is a transient executor—not a persistent global install. This won't create a detectable binary for future runs and breaks the installer's expectation of persistent installation.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/marketing/public/install` around lines 52 - 73, The
detection currently labels executables with a Node shebang as generic "package"
(EXISTING_INSTALL_METHOD) but then fails to identify the actual package manager
when the path lacks pm keywords, causing a non-interactive fallthrough to
"binary"; fix by resolving the symlink target of EXISTING_CMD_PATH (e.g., with
readlink -f) and, if it points into a node_modules/.bin or into an install tree,
walk parent directories to detect package manager metadata (presence of
pnpm-lock.yaml, yarn.lock, package-lock.json or a package.json with a yarn usage
hint) and set EXISTING_INSTALL_METHOD to the specific pm (pnpm/yarn/bun/npm)
before using the case match; also replace any use of transient yarn dlx for
persistent installs by preferring a persistent yarn global install path or
detecting Yarn v2+ (berry) via .yarn/releases or .yarnrc.yml and treat it as a
non-global package manager rather than as creating a persistent binary.

Comment on lines +801 to +809
local yarn_version=""
local yarn_major=""
yarn_version="$(yarn --version 2>/dev/null || true)"
yarn_major="${yarn_version%%.*}"
if [ -n "$yarn_version" ] && [ "$yarn_major" -ge 2 ] 2>/dev/null; then
yarn dlx "$CLI_PACKAGE"
else
yarn global add "$CLI_PACKAGE"
fi
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

# First, examine the full context of the install script
head -50 clients/web/apps/marketing/public/install

Repository: dallay/corvus

Length of output: 1287


🏁 Script executed:

# Check the size and then read around the flagged lines to understand context
wc -l clients/web/apps/marketing/public/install

Repository: dallay/corvus

Length of output: 103


🏁 Script executed:

# Look at the context around lines 801-809
sed -n '750,850p' clients/web/apps/marketing/public/install | cat -n

Repository: dallay/corvus

Length of output: 3774


🏁 Script executed:

# Search for $CLI_PACKAGE definition in the script
grep -n "CLI_PACKAGE" clients/web/apps/marketing/public/install | head -20

Repository: dallay/corvus

Length of output: 306


🏁 Script executed:

# Check where install_via_package_manager is called and what happens after
grep -n "install_via_package_manager\|verify_install\|command -v corvus" clients/web/apps/marketing/public/install | head -20

Repository: dallay/corvus

Length of output: 267


🏁 Script executed:

# Look for post-installation validation or checks
sed -n '900,1012p' clients/web/apps/marketing/public/install | cat -n

Repository: dallay/corvus

Length of output: 4107


🌐 Web query:

yarn dlx behavior Yarn 2+ temporary environment persistent installation

💡 Result:

  • yarn dlx always runs in a temporary environment: it installs the requested package(s) just for the execution and then runs the binary from your current working directory, without recording anything in your project (no package.json / lockfile changes, and Yarn doesn’t track the installed name/version). [1]
  • What can persist is the download cache/store: even though the dlx “environment” is ephemeral, Yarn stores downloaded packages in its cache (and, depending on linker/mode, uses a global content-addressable store shared across projects), so subsequent dlx runs may reuse already-downloaded artifacts. [2][3]
  • If you want a persistent installation, use yarn add (dependencies/devDependencies) rather than dlx. [1]

Sources:
[1] Yarn CLI docs: yarn dlx (temporary env; not recommended as yarn add) (yarnpkg.com)
[2] Yarn “Install modes” (global store shared across projects, e.g. $HOME/.yarn/berry/index) (yarnpkg.com)
[3] Yarn .yarnrc.yml settings (cacheFolder: where downloaded packages are stored; shareable across projects) (yarnpkg.com)

Citations:


yarn dlx does not create a persistent global install for Yarn 2+.

yarn dlx executes a package in a temporary environment only—it doesn't leave @dallay/corvus on PATH or available in future sessions. The script later checks for the command with has_cmd corvus in post_install_steps(), which will fail silently and print a warning ("corvus command not found in PATH yet") rather than hard-failing. This masks a broken installation path and misleads users into thinking the CLI was installed successfully.

Either reject Yarn 2+ users with a clear error message directing them to npm, pnpm, or bun, or implement yarn add --global for Yarn 2+ as a proper persistent install.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/marketing/public/install` around lines 801 - 809, The
current branch uses "yarn dlx" for Yarn 2+ which does not persist the CLI;
update the install logic so when yarn_major >= 2 you fail fast with a clear
error (stderr) and exit non-zero, telling users to install via npm/pnpm/bun (or
run "yarn set version classic" if you want to support legacy global installs),
and reference the CLI by name via "$CLI_PACKAGE" in the message; this prevents
post_install_steps() from silently passing when has_cmd corvus will later fail.

Comment on lines +16 to +20
const portlessUrl = isProdLike
? ""
: resolvePublicUrl(process.env.PORTLESS_URL ?? env.PORTLESS_URL, "");
const marketingBaseUrl = resolvePublicUrl(
env.MARKETING_URL,
env.MARKETING_URL ?? (portlessUrl || undefined),
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Drop the retired /en docs prefix in the CTAs below.

This page still builds docs links like ${docsBaseUrl}/en/... in installMethods, quickLinks, faqGroups, and the hero panel. With the docs default locale moved to root, those links now point at the old route tree and will 404 unless deprecated aliases are kept around. As per coding guidelines, **/*: Security first, performance second. Validate input boundaries, auth/authz implications, and secret management. Look for behavioral regressions, missing tests, and contract breaks across modules.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/marketing/src/pages/index.astro` around lines 16 - 20, Links
in the CTAs still include the retired "/en" locale segment causing 404s; update
all places that build docs links (look for the docsBaseUrl usage inside
installMethods, quickLinks, faqGroups, and the hero panel) to remove the
hardcoded "/en" segment so links are `${docsBaseUrl}/...` (or construct via a
helper that uses root locale), ensuring you update every occurrence and
tests/fixtures that expect the old path.

Comment thread clients/web/package.json
Comment on lines +15 to +16
"dev": "pnpm --parallel -r run dev",
"dev:docs": "pnpm --filter @corvus/docs run dev",
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
python - <<'PY'
import json, glob

paths = sorted(
    glob.glob("clients/web/apps/*/package.json") +
    glob.glob("clients/web/packages/*/package.json")
)

missing = []
for path in paths:
    with open(path, "r", encoding="utf-8") as fh:
        pkg = json.load(fh)
    if "dev" not in pkg.get("scripts", {}):
        missing.append(path)

for path in missing:
    print(path)
PY

Repository: dallay/corvus

Length of output: 135


Add --if-present to the recursive dev script or restrict to apps only.

pnpm --parallel -r run dev now runs dev across every workspace package. However, clients/web/packages/locales and clients/web/packages/ui lack a dev script, causing the root dev flow to fail before app servers start.

Fix
-    "dev": "pnpm --parallel -r run dev",
+    "dev": "pnpm --parallel -r --if-present run dev",

Either use --if-present (skips missing scripts) or narrow the filter to just --filter @corvus/apps`` if packages shouldn't implement dev.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
"dev": "pnpm --parallel -r run dev",
"dev:docs": "pnpm --filter @corvus/docs run dev",
"dev": "pnpm --parallel -r --if-present run dev",
"dev:docs": "pnpm --filter `@corvus/docs` run dev",
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/package.json` around lines 15 - 16, The root "dev" script in
package.json currently runs "pnpm --parallel -r run dev" which fails when
workspaces like packages/locales and packages/ui lack a dev script; update the
"dev" script (the "dev" entry in package.json) to either add --if-present (e.g.,
pnpm --parallel -r --if-present run dev) so pnpm skips packages without a dev
script, or restrict the command to the intended apps using a workspace filter
(e.g., pnpm --parallel -r --filter `@corvus/apps` run dev) so only app packages
are targeted.

@cloudflare-workers-and-pages
Copy link
Copy Markdown

cloudflare-workers-and-pages Bot commented Mar 11, 2026

Deploying corvus with  Cloudflare Pages  Cloudflare Pages

Latest commit: 7ee7cb3
Status: ✅  Deploy successful!
Preview URL: https://30c87850.corvus-42x.pages.dev
Branch Preview URL: https://docs-default-lang-without-sl.corvus-42x.pages.dev

View logs

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

♻️ Duplicate comments (2)
clients/web/package.json (1)

15-15: ⚠️ Potential issue | 🟠 Major

Scope the root dev script to app workspaces.

pnpm --parallel -r run dev now fans out across every workspace under clients/web, but this PR only wires portless dev entrypoints for the app packages. That broadens the root dev contract and can still fail as soon as a non-app workspace lacks scripts.dev. Filter this to ./apps/* instead of running recursively across the whole workspace.

Suggested change
-    "dev": "pnpm --parallel -r run dev",
+    "dev": "pnpm --parallel -r --filter ./apps/* run dev",

As per coding guidelines, "Look for behavioral regressions, missing tests, and contract breaks across modules."

#!/bin/bash
python - <<'PY'
import json
from pathlib import Path

paths = sorted(
    list(Path("clients/web/apps").rglob("package.json")) +
    list(Path("clients/web/packages").rglob("package.json"))
)

for path in paths:
    pkg = json.loads(path.read_text())
    scripts = pkg.get("scripts", {})
    dev = scripts.get("dev")
    print(f"{path}: {dev if dev is not None else 'MISSING scripts.dev'}")
PY
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/package.json` at line 15, The root "dev" script in
clients/web/package.json currently uses a recursive workspace run that fans out
to every workspace; change it to only target the app workspaces under ./apps/*
so it doesn't try to run dev in non-app packages. Update the "dev" script entry
(the "dev" property in clients/web/package.json) to scope the pnpm parallel run
to the apps folder (./apps/*) rather than using the recursive -r behavior,
ensuring only app workspaces are invoked.
clients/web/apps/chat/package.json (1)

11-13: ⚠️ Potential issue | 🟠 Major

Keep the legacy 4323 fallback intact.

Line 11 and Line 13 remove the only explicit 4323 pin, while clients/web/packages/shared/env.mjs:149-154 and clients/web/build.gradle.kts:61-71 still hardcode chat on 4323. With PORTLESS=0, that regresses to Vite's default dev/preview ports unless vite.config.ts now sets both server.port and preview.port. Preserve the old port in config, or keep the old --port 4323 flags behind the escape hatch.

As per coding guidelines, "Look for behavioral regressions, missing tests, and contract breaks across modules."

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/chat/package.json` around lines 11 - 13, The dev/preview
scripts removed the explicit --port 4323 fallback which breaks other modules
that still assume chat runs on 4323 (see clients/web/packages/shared/env.mjs and
clients/web/build.gradle.kts); restore the legacy behavior by either adding back
the --port 4323 flag to the "dev" and "preview" scripts in package.json or
ensure vite.config.ts explicitly sets both server.port and preview.port to 4323
so the escape hatch (PORTLESS=0) retains the old port; update the "dev" script
(symbol: "dev") and "preview" script (symbol: "preview") accordingly to preserve
compatibility.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@clients/web/apps/dashboard/package.json`:
- Around line 11-13: Playwright is launching the dev server with a fixed --port
but the dev script "dev": "portless run --name dashboard vite" lets Portless
pick a dynamic port and ignores downstream --port flags; update the Playwright
webServer launch command (the entry that currently invokes the "dev" script) to
call portless with either an explicit passthrough or app-port so Vite sees the
port—e.g. change the command to use "portless run --name dashboard -- vite
--host 127.0.0.1 --port 4324" or "portless run --name dashboard --app-port 4324
vite --host 127.0.0.1" (alternatively, make Vite respect PORT env and let
Portless inject it). Ensure the change targets the Playwright webServer launch
configuration referenced in playwright.config.ts.

---

Duplicate comments:
In `@clients/web/apps/chat/package.json`:
- Around line 11-13: The dev/preview scripts removed the explicit --port 4323
fallback which breaks other modules that still assume chat runs on 4323 (see
clients/web/packages/shared/env.mjs and clients/web/build.gradle.kts); restore
the legacy behavior by either adding back the --port 4323 flag to the "dev" and
"preview" scripts in package.json or ensure vite.config.ts explicitly sets both
server.port and preview.port to 4323 so the escape hatch (PORTLESS=0) retains
the old port; update the "dev" script (symbol: "dev") and "preview" script
(symbol: "preview") accordingly to preserve compatibility.

In `@clients/web/package.json`:
- Line 15: The root "dev" script in clients/web/package.json currently uses a
recursive workspace run that fans out to every workspace; change it to only
target the app workspaces under ./apps/* so it doesn't try to run dev in non-app
packages. Update the "dev" script entry (the "dev" property in
clients/web/package.json) to scope the pnpm parallel run to the apps folder
(./apps/*) rather than using the recursive -r behavior, ensuring only app
workspaces are invoked.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: aa147de5-5742-423f-8368-f60143fcc202

📥 Commits

Reviewing files that changed from the base of the PR and between 71ba310 and 7ee7cb3.

⛔ Files ignored due to path filters (1)
  • clients/web/pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (6)
  • clients/web/apps/chat/package.json
  • clients/web/apps/dashboard/package.json
  • clients/web/apps/docs/src/content/docs/guides/architecture/overview.md
  • clients/web/apps/docs/src/content/docs/guides/release.md
  • clients/web/package.json
  • clients/web/pnpm-workspace.yaml
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Cloudflare Pages
🧰 Additional context used
📓 Path-based instructions (1)
**/*

⚙️ CodeRabbit configuration file

**/*: Security first, performance second.
Validate input boundaries, auth/authz implications, and secret management.
Look for behavioral regressions, missing tests, and contract breaks across modules.

Files:

  • clients/web/pnpm-workspace.yaml
  • clients/web/apps/chat/package.json
  • clients/web/apps/dashboard/package.json
  • clients/web/package.json
🔇 Additional comments (1)
clients/web/pnpm-workspace.yaml (1)

21-21: No known vulnerabilities found for portless@0.6.0.

Package exists, is actively maintained, and has zero reported security advisories. Safe to add.

Comment on lines +11 to +13
"dev": "portless run --name dashboard vite",
"build": "vue-tsc -b && vite build",
"preview": "vite preview --port 4324",
"preview": "portless run --name dashboard vite preview",
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

fd -t f "vite.config" clients/web/apps/dashboard/

Repository: dallay/corvus

Length of output: 140


🏁 Script executed:

cat -n clients/web/apps/dashboard/playwright.config.ts

Repository: dallay/corvus

Length of output: 684


🏁 Script executed:

cat -n clients/web/apps/dashboard/vite.config.ts

Repository: dallay/corvus

Length of output: 686


🏁 Script executed:

fd -t f "build.gradle.kts" | head -5

Repository: dallay/corvus

Length of output: 232


🏁 Script executed:

rg -A 5 "portless" clients/web/apps/dashboard/package.json

Repository: dallay/corvus

Length of output: 792


🏁 Script executed:

rg -i "portless" clients/web/ --type-list

Repository: dallay/corvus

Length of output: 446


🏁 Script executed:

fd -t f "portless.config\|portless\." clients/web/

Repository: dallay/corvus

Length of output: 39


🌐 Web query:

portless node port forwarding vite --port flag

💡 Result:

  • Vite supports --port (and --host) on the CLI:

    • vite --port 5173 --host 0.0.0.0
    • or via npm scripts: npm run dev -- --port 5173 --host 0.0.0.0 [1]
  • Portless + Vite: Portless is designed to run your dev server on an assigned port and proxy it to a stable name (e.g. http://myapp.localhost:1355). For frameworks that ignore PORT (including Vite), Portless auto-injects the right --port and --host flags. So this is usually enough:

    • portless myapp npm run dev [2]
  • If you need to pass flags through Portless to Vite, use -- to stop Portless flag parsing and pass the rest to the child command:

    • portless myapp -- npm run dev -- --port 5173 --host 0.0.0.0 [2]
  • If you want Portless to use a fixed internal app port (instead of an auto-assigned one):

    • portless myapp --app-port 5173 npm run dev [2]
  • If you hit a proxy “Bad Gateway” with Vite, ensure Vite is listening on the injected port and on all interfaces (example config shown here): set server.port from process.env.PORT and server.host to 0.0.0.0. [3]

Sources: Vite CLI options [1]; Portless flags/behavior (including Vite auto-injection and -- passthrough) [2]; Vite-specific Portless config notes [3].


🏁 Script executed:

# Check if portless is documented in any README or config files
rg -l "portless" clients/web/ | head -10

Repository: dallay/corvus

Length of output: 417


Fix the Playwright webServer command to work with portless.

Line 11 now routes pnpm dev through portless, but playwright.config.ts line 11 still passes --port 4324 to that script. Portless auto-assigns a dynamic port and ignores downstream --port flags unless passed after -- or configured with --app-port. Playwright will then wait on http://127.0.0.1:4324 while Vite runs on a different port, causing test:e2e to hang or fail.

Either update the Playwright command to:

  • portless run --name dashboard -- vite --host 127.0.0.1 --port 4324, or
  • portless run --name dashboard --app-port 4324 vite --host 127.0.0.1

Or configure Vite to respect PORT env var and let Portless inject it dynamically.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@clients/web/apps/dashboard/package.json` around lines 11 - 13, Playwright is
launching the dev server with a fixed --port but the dev script "dev": "portless
run --name dashboard vite" lets Portless pick a dynamic port and ignores
downstream --port flags; update the Playwright webServer launch command (the
entry that currently invokes the "dev" script) to call portless with either an
explicit passthrough or app-port so Vite sees the port—e.g. change the command
to use "portless run --name dashboard -- vite --host 127.0.0.1 --port 4324" or
"portless run --name dashboard --app-port 4324 vite --host 127.0.0.1"
(alternatively, make Vite respect PORT env and let Portless inject it). Ensure
the change targets the Playwright webServer launch configuration referenced in
playwright.config.ts.

@sonarqubecloud
Copy link
Copy Markdown

@yacosta738 yacosta738 merged commit 0bba656 into main Mar 11, 2026
20 checks passed
@yacosta738 yacosta738 deleted the docs/default-lang-without-slag branch March 11, 2026 08:27
@yacosta738 yacosta738 mentioned this pull request Mar 16, 2026
This was referenced Apr 29, 2026
@dallay-bot dallay-bot Bot mentioned this pull request May 3, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant