Skip to content

Update project files - #14

Open
khulnasoft-bot wants to merge 4 commits into
mainfrom
v0/khulnasoft-1c9603f3-2
Open

Update project files#14
khulnasoft-bot wants to merge 4 commits into
mainfrom
v0/khulnasoft-1c9603f3-2

Conversation

@khulnasoft-bot

@khulnasoft-bot khulnasoft-bot commented Jul 31, 2026

Copy link
Copy Markdown
Contributor

Generated by v0

v0 Session

Summary by Sourcery

Add first-class Vercel serverless deployment support and tighten environment-driven configuration for logging, database, auth, and plugins.

New Features:

  • Introduce a Vercel-specific Express entrypoint and API handler wired via vercel.json and an api/index.ts config stub.
  • Add a build script that bundles the server into a single serverless function file for Vercel using esbuild.
  • Provide a shared helper to resolve PostgreSQL connection URLs from various Vercel and Postgres environment conventions.
  • Expose database client configuration options (connection pool size and prepared statements) for server usage.
  • Add a custom SVG Taskcore icon component and use it across the UI instead of the lucide-react Taskcore icon.

Bug Fixes:

  • Guard server version resolution with an environment override and a safe fallback when package.json cannot be loaded.
  • Avoid file-system logging and worker transports in serverless runtimes by defaulting to stdout-based logging.
  • Allow disabling plugins via an environment flag so plugin-related schedulers and loaders do not run when unsupported.

Enhancements:

  • Refine server logging configuration to support serverless runtimes while retaining pretty logging and file logging for long-lived servers.
  • Align database URL resolution in server and tooling to use the shared helper for consistent Postgres configuration.
  • Update the Hermes adapter registry to conform to the ServerAdapterModule listSkills and syncSkills types.
  • Augment Express Request types with an actor property to formalize request identity handling.

Build:

  • Add a vercel:build npm script that builds the workspace, UI, and Vercel serverless function bundle in one step.

Documentation:

  • Add a Vercel deployment guide documenting architecture, required environment, limitations, and deployment steps.
  • Reference the new Vercel deployment documentation from the deployment modes overview.

v0 added 4 commits July 31, 2026 18:11
- Add missing server/src/types/express.d.ts (Request.actor augmentation)
- Cast hermes listSkills/syncSkills at the adapter-utils type boundary
- Replace nonexistent lucide Taskcore icon with local TaskcoreIcon component
- Un-ignore server/src/types/express.d.ts so clones can build
- add serverless entry (server/src/vercel.ts) with Vercel runtime defaults and config guards
- bundle server into a single ESM function via scripts/build-vercel-function.mjs
- support Vercel Postgres/RDS env conventions (POSTGRES_URL, PGHOST/...)
- stdout-only logging and disable plugins/background jobs in serverless runtime
- allow overriding DB pool options (max, prepare) for bounded serverless connections
@khulnasoft-bot khulnasoft-bot added the v0 label Jul 31, 2026 — with Vercel
@vercel

vercel Bot commented Jul 31, 2026

Copy link
Copy Markdown
Contributor

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
taskcore Error Error v0 Jul 31, 2026 9:30pm

Request Review

@coderabbitai

coderabbitai Bot commented Jul 31, 2026

Copy link
Copy Markdown

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 54c90127-8128-472b-8c30-bd8400644666

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review

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.

@sourcery-ai

sourcery-ai Bot commented Jul 31, 2026

Copy link
Copy Markdown

Reviewer's Guide

Adds first-class Vercel serverless deployment support, including a dedicated Express handler, build script, Postgres URL resolution helper, and deployment docs, while tightening server behavior in serverless environments and standardizing the Taskcore icon usage in the UI.

Sequence diagram for Vercel serverless request handling

sequenceDiagram
  actor User
  participant Vercel
  participant api_index as api_index_handler
  participant vercel as taskcoreVercelHandler
  participant bootFn as boot
  participant configFn as loadConfig
  participant pgEnv as resolvePostgresUrlFromEnv
  participant dbFn as createDb
  participant appFn as createAppForServerless

  User->>Vercel: HTTP request
  Vercel->>api_index: invoke default export
  api_index->>vercel: taskcoreVercelHandler(req, res)
  vercel->>bootFn: boot() [on first request]
  bootFn->>configFn: loadConfig()
  configFn-->>bootFn: Config
  bootFn->>pgEnv: resolvePostgresUrlFromEnv()
  pgEnv-->>bootFn: databaseUrl
  bootFn->>dbFn: createDb(databaseUrl, { max, prepare })
  dbFn-->>bootFn: Db
  bootFn->>appFn: createAppForServerless(Config, Db)
  appFn-->>bootFn: ExpressApp
  bootFn-->>vercel: ExpressApp
  vercel->>appFn: ExpressApp(req, res)
  appFn-->>User: HTTP response
Loading

File-Level Changes

Change Details Files
Adapt logging and database client behavior for serverless runtimes and Vercel-specific constraints.
  • Introduce a runtime check for serverless environments and bypass pino worker transports, logging only to stdout when on Vercel/Now.
  • Remove eager log directory creation and use pino-pretty with stdout-only destination in serverless mode, keeping file logging only for non-serverless deployments.
  • Extend the database client factory to accept max connection and prepare options so the Vercel handler can tune pool size and prepared statement behavior.
  • Allow resolving the server version from an environment variable with a safe package.json fallback to support bundled serverless builds.
server/src/middleware/logger.ts
packages/db/src/client.ts
server/src/version.ts
Gate plugin-related startup behavior and dev watcher wiring behind a runtime flag so serverless deployments can disable plugins cleanly.
  • Add TASKCORE_PLUGINS_ENABLED environment flag and compute a pluginsEnabled boolean when creating the Express app.
  • Start job coordinator, scheduler, and tool dispatcher only when plugins are enabled, including guarded initialization logging on failure.
  • Instantiate the plugin dev watcher only when plugins are enabled and UI is in vite-dev mode, and only perform plugin loading and watcher registration when plugins are enabled.
server/src/app.ts
Introduce a shared helper for resolving Postgres URLs from multiple environment conventions and use it across config and runtime-config.
  • Implement resolvePostgresUrlFromEnv to prefer DATABASE_URL, then Vercel POSTGRES_URL/POSTGRES_URL_NON_POOLING, then PG* variables with optional sslmode handling.
  • Export the helper from the shared package index for reuse by server and db runtime configuration code.
  • Update server configuration loading and runtime database target resolution to call the helper instead of reading DATABASE_URL directly.
packages/shared/src/vercel-postgres.ts
packages/shared/src/index.ts
server/src/config.ts
packages/db/src/runtime-config.ts
Add a Vercel-specific Express entrypoint and API function configuration for serverless deployment, including default envs and auth/db guards.
  • Create server/src/vercel.ts that applies Vercel defaults, validates deployment mode and exposure, ensures an external Postgres URL, and boots an Express app tailored for serverless use.
  • Configure the Vercel-specific app to disable UI serving, initialize better-auth only for authenticated mode with trusted origins, and wire storage and feedback services.
  • Tune the Postgres client pool size and prepared statement behavior via environment variables (TASKCORE_PG_MAX_CONNECTIONS and TASKCORE_PG_PREPARE) and use the extended db client options.
  • Export a default handler that lazily boots the app on first request and reuses the instance across subsequent invocations via a cached promise.
server/src/vercel.ts
Add an esbuild-based build script and Vercel project configuration to produce a single serverless function bundle and static UI output.
  • Introduce scripts/build-vercel-function.mjs to bundle server/src/vercel.ts into api/index.js using esbuild, externalizing node_modules while bundling workspace packages.
  • Define an esbuild plugin that automatically treats any resolved dependency under node_modules as external to keep the bundle ESM-clean for Vercel.
  • Inject build-time defines for NODE_ENV and TASKCORE_SERVER_VERSION using the server package.json version, and add a banner to the generated bundle.
  • Add api/index.ts that declares Vercel function config (maxDuration) and re-exports the bundled Express handler, and wire a vercel:build script into the root package.json.
  • Add vercel.json (contents implied by docs) to configure build, output directory, and function behavior for the deployment target.
scripts/build-vercel-function.mjs
api/index.ts
package.json
vercel.json
Document the Vercel deployment model, env requirements, limitations, and repository files involved in serverless support.
  • Add doc/VERCEL.md describing the architecture (API function, static UI, external Postgres), required environment variables, defaults applied in Vercel, and deployment steps.
  • Reference the Vercel deployment guide from the deployment modes documentation for discoverability.
doc/VERCEL.md
doc/DEPLOYMENT-MODES.md
Standardize the Taskcore icon as a custom svg component instead of relying on the lucide-react Taskcore icon across UI components.
  • Create a reusable TaskcoreIcon React component rendering the Taskcore logo via inline SVG and accepting a className for styling.
  • Replace lucide-react Taskcore imports with the new TaskcoreIcon in core UI components such as NewIssueDialog, CommentThread, CompanyRail, IssueChatThread, CompanySkills page, and IssueDetail page.
  • Update usages to import TaskcoreIcon from the appropriate local component path while preserving layout and styling semantics.
ui/src/components/TaskcoreIcon.tsx
ui/src/components/NewIssueDialog.tsx
ui/src/components/CommentThread.tsx
ui/src/components/CompanyRail.tsx
ui/src/components/IssueChatThread.tsx
ui/src/pages/CompanySkills.tsx
ui/src/pages/IssueDetail.tsx
Adjust Hermes adapter registry typings to align listSkills and syncSkills with the ServerAdapterModule interface without changing runtime behavior.
  • Cast hermesListSkills and hermesSyncSkills to the explicit ServerAdapterModule listSkills/syncSkills types via unknown to satisfy TypeScript without altering the underlying implementations.
server/src/adapters/registry.ts
Augment Express Request typings for actor metadata used by auth middleware and permission checks.
  • Add a global Express namespace declaration that extends Request with an actor field describing the request actor type, source, and related identifiers (userId, agentId, companyId, etc.).
  • Define RequestActor and RequestActorSource types documenting the possible actor origins and fields, and export an empty object to ensure the module is treated as a module for type augmentation.
server/src/types/express.d.ts

Tips and commands

Interacting with Sourcery

  • Trigger a new review: Comment @sourcery-ai review on the pull request.
  • Continue discussions: Reply directly to Sourcery's review comments.
  • Generate a GitHub issue from a review comment: Ask Sourcery to create an
    issue from a review comment by replying to it. You can also reply to a
    review comment with @sourcery-ai issue to create an issue from it.
  • Generate a pull request title: Write @sourcery-ai anywhere in the pull
    request title to generate a title at any time. You can also comment
    @sourcery-ai title on the pull request to (re-)generate the title at any time.
  • Generate a pull request summary: Write @sourcery-ai summary anywhere in
    the pull request body to generate a PR summary at any time exactly where you
    want it. You can also comment @sourcery-ai summary on the pull request to
    (re-)generate the summary at any time.
  • Generate reviewer's guide: Comment @sourcery-ai guide on the pull
    request to (re-)generate the reviewer's guide at any time.
  • Resolve all Sourcery comments: Comment @sourcery-ai resolve on the
    pull request to resolve all Sourcery comments. Useful if you've already
    addressed all the comments and don't want to see them anymore.
  • Dismiss all Sourcery reviews: Comment @sourcery-ai dismiss on the pull
    request to dismiss all existing Sourcery reviews. Especially useful if you
    want to start fresh with a new review - don't forget to comment
    @sourcery-ai review to trigger a new review!

Customizing Your Experience

Access your dashboard to:

  • Enable or disable review features such as the Sourcery-generated pull request
    summary, the reviewer's guide, and others.
  • Change the review language.
  • Add, remove or edit custom review instructions.
  • Adjust other review settings.

Getting Help

@sourcery-ai sourcery-ai 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.

Hey - I've found 3 issues, and left some high level feedback:

  • The Hermes adapter registry currently forces hermesListSkills/hermesSyncSkills through as unknown as casts; consider updating the Hermes implementations or the ServerAdapterModule types so they align without unsafe casting.
  • Serverless/Vercel runtime detection is implemented in multiple places (isServerlessRuntime in logger.ts, isVercelRuntime in vercel.ts) with similar env checks; it may be worth centralizing this into a shared helper to avoid drift in the conditions over time.
  • In server/src/vercel.ts, the prepareDisabled flag and TASKCORE_PG_PREPARE semantics are inverted (setting the env to true disables prepared statements); consider renaming the env/variable or flipping the boolean logic to make the behavior more intuitive.
Prompt for AI Agents
Please address the comments from this code review:

## Overall Comments
- The Hermes adapter registry currently forces `hermesListSkills`/`hermesSyncSkills` through `as unknown as` casts; consider updating the Hermes implementations or the `ServerAdapterModule` types so they align without unsafe casting.
- Serverless/Vercel runtime detection is implemented in multiple places (`isServerlessRuntime` in `logger.ts`, `isVercelRuntime` in `vercel.ts`) with similar env checks; it may be worth centralizing this into a shared helper to avoid drift in the conditions over time.
- In `server/src/vercel.ts`, the `prepareDisabled` flag and `TASKCORE_PG_PREPARE` semantics are inverted (setting the env to `true` disables prepared statements); consider renaming the env/variable or flipping the boolean logic to make the behavior more intuitive.

## Individual Comments

### Comment 1
<location path="server/src/middleware/logger.ts" line_range="8-9" />
<code_context>
 import { resolveDefaultLogsDir, resolveHomeAwarePath } from "../home-paths.js";
 import { shouldSilenceHttpSuccessLog } from "./http-log-policy.js";

+function isServerlessRuntime(): boolean {
+  return process.env.VERCEL === "1" || process.env.NOW === "1";
+}
+
</code_context>
<issue_to_address>
**suggestion:** Serverless runtime detection is duplicated and could be centralized.

We now have two helpers for the same Vercel runtime check: `isServerlessRuntime()` here and `isVercelRuntime()` in `server/src/vercel.ts`. Please consolidate this into a single shared utility so runtime detection logic stays consistent across logger configuration and serverless boot code.

Suggested implementation:

```typescript
import path from "node:path";
import pino from "pino";
import { pinoHttp } from "pino-http";
import { readConfigFile } from "../config-file.js";
import { resolveDefaultLogsDir, resolveHomeAwarePath } from "../home-paths.js";
import { shouldSilenceHttpSuccessLog } from "./http-log-policy.js";
import { isVercelRuntime } from "../vercel.js";

function resolveServerLogDir(): string {
  const envOverride = process.env.TASKCORE_LOG_DIR?.trim();
  if (envOverride) return resolveHomeAwarePath(envOverride);
}

const logDir = resolveServerLogDir();

```

1. Replace any usages of `isServerlessRuntime()` in `server/src/middleware/logger.ts` with `isVercelRuntime()` so the shared utility is used consistently.
2. If `isServerlessRuntime` was intended to be exported and used elsewhere, either:
   - Update those call sites to import and use `isVercelRuntime` directly from `server/src/vercel.ts`, or
   - Re-export `isVercelRuntime` under the `isServerlessRuntime` name from a shared module, while keeping the implementation centralized in `vercel.ts`.
</issue_to_address>

### Comment 2
<location path="server/src/vercel.ts" line_range="132-133" />
<code_context>
+  assertVercelConfig(config);
+
+  const maxConnections = Math.max(1, Number(process.env.TASKCORE_PG_MAX_CONNECTIONS) || 10);
+  const prepareDisabled = process.env.TASKCORE_PG_PREPARE !== undefined
+    ? process.env.TASKCORE_PG_PREPARE === "true"
+    : isVercelRuntime();
+  const db = createDb(config.databaseUrl, {
</code_context>
<issue_to_address>
**issue (bug_risk):** `TASKCORE_PG_PREPARE` semantics appear inverted relative to the variable name.

`prepareDisabled` is set to `true` when `TASKCORE_PG_PREPARE === "true"`, and then `{ prepare: false }` is passed to `createDb`. So setting `TASKCORE_PG_PREPARE="true"` actually disables prepared statements. To avoid confusing or misconfiguring deployments, either invert the logic so `"true"` enables prepared statements, or rename the env var (e.g. `TASKCORE_PG_PREPARE_DISABLED`) to match the current behavior.
</issue_to_address>

### Comment 3
<location path="server/src/adapters/registry.ts" line_range="188-189" />
<code_context>
   sessionCodec: hermesSessionCodec,
-  listSkills: hermesListSkills,
-  syncSkills: hermesSyncSkills,
+  listSkills: hermesListSkills as unknown as ServerAdapterModule["listSkills"],
+  syncSkills: hermesSyncSkills as unknown as ServerAdapterModule["syncSkills"],
   models: hermesModels,
   supportsLocalAgentJwt: true,
</code_context>
<issue_to_address>
**suggestion (bug_risk):** Double `unknown` cast hides type mismatches between Hermes skill APIs and `ServerAdapterModule`.

The `unknown``ServerAdapterModule` casts bypass TypeScript’s structural checks, so any mismatch between the Hermes helpers and the expected signatures will only fail at runtime. Instead, update the Hermes helper types (or `ServerAdapterModule` if Hermes is canonical) so they are directly compatible without unsafe casts.

Suggested implementation:

```typescript
  sessionCodec: hermesSessionCodec,
  listSkills: hermesListSkills,
  syncSkills: hermesSyncSkills,
  models: hermesModels,

```

To fully implement the suggestion (and surface any real type mismatches instead of hiding them), you should also:
1. Ensure the object this snippet belongs to is explicitly typed as `ServerAdapterModule`, e.g. `const hermesAdapter: ServerAdapterModule = { ... }`. This will make TypeScript check that `hermesListSkills` and `hermesSyncSkills` match the required signatures.
2. Update the type signatures of `hermesListSkills` and `hermesSyncSkills` in their respective modules so that they are structurally compatible with `ServerAdapterModule["listSkills"]` and `ServerAdapterModule["syncSkills"]` (parameters, return types, and async/Promise shape).
3. If Hermes is the canonical API, adjust the `ServerAdapterModule` interface instead so its `listSkills` and `syncSkills` definitions match the Hermes helpers, then let this registry file rely on standard type inference without casts.
</issue_to_address>

Sourcery is free for open source - if you like our reviews please consider sharing them ✨
Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.

Comment on lines +8 to +9
function isServerlessRuntime(): boolean {
return process.env.VERCEL === "1" || process.env.NOW === "1";

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

suggestion: Serverless runtime detection is duplicated and could be centralized.

We now have two helpers for the same Vercel runtime check: isServerlessRuntime() here and isVercelRuntime() in server/src/vercel.ts. Please consolidate this into a single shared utility so runtime detection logic stays consistent across logger configuration and serverless boot code.

Suggested implementation:

import path from "node:path";
import pino from "pino";
import { pinoHttp } from "pino-http";
import { readConfigFile } from "../config-file.js";
import { resolveDefaultLogsDir, resolveHomeAwarePath } from "../home-paths.js";
import { shouldSilenceHttpSuccessLog } from "./http-log-policy.js";
import { isVercelRuntime } from "../vercel.js";

function resolveServerLogDir(): string {
  const envOverride = process.env.TASKCORE_LOG_DIR?.trim();
  if (envOverride) return resolveHomeAwarePath(envOverride);
}

const logDir = resolveServerLogDir();
  1. Replace any usages of isServerlessRuntime() in server/src/middleware/logger.ts with isVercelRuntime() so the shared utility is used consistently.
  2. If isServerlessRuntime was intended to be exported and used elsewhere, either:
    • Update those call sites to import and use isVercelRuntime directly from server/src/vercel.ts, or
    • Re-export isVercelRuntime under the isServerlessRuntime name from a shared module, while keeping the implementation centralized in vercel.ts.

Comment thread server/src/vercel.ts
Comment on lines +132 to +133
const prepareDisabled = process.env.TASKCORE_PG_PREPARE !== undefined
? process.env.TASKCORE_PG_PREPARE === "true"

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

issue (bug_risk): TASKCORE_PG_PREPARE semantics appear inverted relative to the variable name.

prepareDisabled is set to true when TASKCORE_PG_PREPARE === "true", and then { prepare: false } is passed to createDb. So setting TASKCORE_PG_PREPARE="true" actually disables prepared statements. To avoid confusing or misconfiguring deployments, either invert the logic so "true" enables prepared statements, or rename the env var (e.g. TASKCORE_PG_PREPARE_DISABLED) to match the current behavior.

Comment on lines +188 to +189
listSkills: hermesListSkills as unknown as ServerAdapterModule["listSkills"],
syncSkills: hermesSyncSkills as unknown as ServerAdapterModule["syncSkills"],

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

suggestion (bug_risk): Double unknown cast hides type mismatches between Hermes skill APIs and ServerAdapterModule.

The unknownServerAdapterModule casts bypass TypeScript’s structural checks, so any mismatch between the Hermes helpers and the expected signatures will only fail at runtime. Instead, update the Hermes helper types (or ServerAdapterModule if Hermes is canonical) so they are directly compatible without unsafe casts.

Suggested implementation:

  sessionCodec: hermesSessionCodec,
  listSkills: hermesListSkills,
  syncSkills: hermesSyncSkills,
  models: hermesModels,

To fully implement the suggestion (and surface any real type mismatches instead of hiding them), you should also:

  1. Ensure the object this snippet belongs to is explicitly typed as ServerAdapterModule, e.g. const hermesAdapter: ServerAdapterModule = { ... }. This will make TypeScript check that hermesListSkills and hermesSyncSkills match the required signatures.
  2. Update the type signatures of hermesListSkills and hermesSyncSkills in their respective modules so that they are structurally compatible with ServerAdapterModule["listSkills"] and ServerAdapterModule["syncSkills"] (parameters, return types, and async/Promise shape).
  3. If Hermes is the canonical API, adjust the ServerAdapterModule interface instead so its listSkills and syncSkills definitions match the Hermes helpers, then let this registry file rely on standard type inference without casts.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants