Skip to content

Feat/environments - #37

Merged
SteakFisher merged 4 commits into
mainfrom
feat/environments
May 14, 2026
Merged

Feat/environments#37
SteakFisher merged 4 commits into
mainfrom
feat/environments

Conversation

@SteakFisher

@SteakFisher SteakFisher commented May 14, 2026

Copy link
Copy Markdown
Member

Summary by CodeRabbit

  • New Features

    • Separate test and production payment modes with distinct API credentials and mode-aware checkout flow.
    • Session-based checkout redirect (/checkout/{id}) that forwards users to the provider URL.
  • Bug Fixes

    • Improved checkout redirect and webhook error handling with clear 400/404 responses and stricter auth-mode validation.
  • Chores

    • Environment config updated to use distinct live/test payment API keys and preserved webhook signing secret.
  • Other

    • Billing/usage pricing now respects the selected test or production mode.

Review Change Stack

@coderabbitai

coderabbitai Bot commented May 14, 2026

Copy link
Copy Markdown

Caution

Review failed

The pull request is closed.

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 4f6cfb42-4f77-4576-8438-b42a6618354b

📥 Commits

Reviewing files that changed from the base of the PR and between 114b52e and 0204f71.

📒 Files selected for processing (6)
  • .env.example
  • src/factory/EventStorageAdapterFactory.ts
  • src/routes/gRPC/payment/createCheckoutLink.ts
  • src/routes/gRPC/payment/paymentProvider.ts
  • src/routes/http/checkoutRedirect.ts
  • src/utils/eventHelpers.ts

📝 Walkthrough

Walkthrough

This PR threads explicit "production" | "test" mode through payment provider clients, session creation, pricing and event storage (ClickHouse/Postgres), updates DB schemas to persist mode and checkout URLs, and adds a proxied checkout redirect route.

Changes

Mode-aware payment and storage layer

Layer / File(s) Summary
Environment config and storage contracts
.env.example, src/interface/storage/Storage.ts
DODO_PAYMENTS_API_KEY split into DODO_PAYMENTS_LIVE_API_KEY and DODO_PAYMENTS_TEST_API_KEY. StorageAdapter.add and price now require apiKeyId and mode: "production" | "test".
Payment provider client with mode-specific instances
src/routes/gRPC/payment/paymentProvider.ts
Introduce mode-aware cached DodoPayments instances and getDodoClient(mode?); createProviderCheckout accepts mode. returnUrl uses REDIRECT_URL.
Checkout link creation with mode threading and proxy URL
src/routes/gRPC/payment/createCheckoutLink.ts
Thread auth.mode into price calculation and provider checkout, persist session via handleAddSession(..., apiKeyId, mode, checkoutUrl), and return proxied URL ${APP_URL}/checkout/${sessionId}. Authorization denies dashboard keys and requires auth.mode.
HTTP redirect handler and route registration
src/routes/http/checkoutRedirect.ts, src/servers/fastifyServer.ts
New handleCheckoutRedirect validates sessionId, resolves stored checkout URL via getCheckoutUrl, returns 404 JSON if missing, otherwise issues HTTP 302. Route GET /checkout/:sessionId registered.
Database schema and session helpers
src/storage/db/postgres/schema.ts, src/storage/db/postgres/helpers/sessions.ts
Add checkoutUrl to sessions table; remove default on events.mode; handleAddSession persists apiKeyId, mode, and optional checkoutUrl. New SessionRow, getSessionByCheckoutId, and getCheckoutUrl helpers added.
Postgres adapter & handlers with mode
src/storage/adapter/postgres/postgres.ts, src/storage/adapter/postgres/handlers/*
PostgresAdapter.add/price now require apiKeyId and mode; EventInsertValues adds required mode; Postgres add/price handlers accept/persist mode and price queries filter by mode. Removed handleAddSession barrel re-export.
Common pricing orchestration
src/storage/adapter/common/priceRequestPayment.ts
handlePriceRequestPayment now accepts mode and forwards it into adapter.price calls for SDK and AI pricing.
ClickHouse adapter & handlers with mode
src/storage/adapter/clickhouse/*
Add mode String to ClickHouse DDL for event tables; ClickHouse adapter add/price require mode and forward it to handlers; ClickHouse handlers persist/filter by mode.
Webhook handler refactor with session helper
src/routes/http/createdCheckout.ts
Use getSessionByCheckoutId for session lookup, return 404 when missing, initialize Postgres after lookup, and call adapter.add(serializedPayment, session.apiKeyId, session.mode) when persisting payments.
Adapter factory routing
src/factory/EventStorageAdapterFactory.ts
Factory now returns PostgresAdapter for SDK_CALL, AI_TOKEN_USAGE, and PAYMENT event types.
Event storage helper type correction
src/utils/eventHelpers.ts
storeEvent requires auth.mode and calls adapter.add(event.serialize(), auth.apiKeyId, auth.mode) without any casts; throws AuthError.permissionDenied when mode missing.

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

  • ScrawnDotDev/Scrawn#35: Overlaps PAYMENT storage/pricing changes and ClickHouse payment handling that this PR further threads with mode.
  • ScrawnDotDev/Scrawn#34: Related auth/mode threading and checkout/event handling changes touched by this PR.

Poem

🐰 I split the keys—live and test, hooray,
Sessions store URLs to guide the way,
Modes travel through pricing and store,
Redirects hop quickly to the checkout door,
A tiny rabbit cheers: payments now play!

🚥 Pre-merge checks | ✅ 3 | ❌ 2

❌ Failed checks (1 warning, 1 inconclusive)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Title check ❓ Inconclusive The title 'Feat/environments' is vague and generic, using a convention-based prefix without conveying what specific environmental feature was implemented or changed. Replace with a more descriptive title such as 'Support separate API keys for test and production environments' or 'Add environment mode support for payment and storage layers'.
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

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

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/environments

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

ESLint skipped: no ESLint configuration detected in root package.json. To enable, add eslint to devDependencies.


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

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 10

Caution

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

⚠️ Outside diff range comments (2)
src/storage/adapter/postgres/handlers/addEventUtils.ts (1)

60-66: ⚠️ Potential issue | 🔴 Critical | ⚡ Quick win

mode can be dropped before insert despite a required DB column

Line 65 makes mode optional, and Line 81 conditionally omits it. Since eventsTable.mode is required, this path can fail inserts at runtime.

Suggested fix
 export type EventInsertValues = {
   reported_timestamp: string;
   ingested_timestamp: string;
   userId: string;
   api_keyId: string | undefined;
-  mode?: "production" | "test";
+  mode: "production" | "test";
 };
@@
       .values({
         reported_timestamp: values.reported_timestamp,
         ingested_timestamp: values.ingested_timestamp,
         userId: values.userId,
         api_keyId: values.api_keyId,
-        ...(values.mode ? { mode: values.mode } : {}),
+        mode: values.mode,
       })

Also applies to: 76-82

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

In `@src/storage/adapter/postgres/handlers/addEventUtils.ts` around lines 60 - 66,
EventInsertValues declares mode as optional and the insert logic conditionally
omits it, but eventsTable.mode is a required DB column so this can cause runtime
insert failures; make mode required in EventInsertValues (remove the ?), and
update the insert construction (the code that references eventsTable.mode / the
conditional omit) to always include mode—either pass through the provided value
or apply a sensible default (e.g., "production") before building the insert so
every insert includes eventsTable.mode.
src/routes/gRPC/payment/createCheckoutLink.ts (1)

67-82: ⚠️ Potential issue | 🔴 Critical | 🏗️ Heavy lift

Make provider checkout creation and session persistence recoverable.

createProviderCheckout happens before handleAddSession. If the DB write fails after the provider call succeeds, this RPC returns an error but leaves a live checkout session with no stored redirect record. A retry can then mint duplicate payment sessions. Add a compensating cancel/update path or persist a pending session before calling the provider.

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

In `@src/routes/gRPC/payment/createCheckoutLink.ts` around lines 67 - 82, The
current flow calls createCheckoutSession (provider creation) before
handleAddSession (DB persistence), which can leave a live provider session if
the DB write fails; make this recoverable by either persisting a pending session
record first or adding a compensating cancel/update after a failed DB write.
Concretely: create a pending session entry in the DB (e.g., status="pending")
for validatedData.userId before calling createCheckoutSession, then call
createCheckoutSession, and on success update that pending record with sessionId
and checkoutUrl via handleAddSession (or a dedicated update method);
alternatively, if you keep provider-first, catch DB errors and call the provider
cancel function (or update via createProviderCheckout cancellation API) to clean
up the remote session and surface a clear error. Ensure changes reference
createCheckoutSession and handleAddSession (or the provider cancel API) so
retries do not create duplicate live sessions.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/routes/gRPC/payment/createCheckoutLink.ts`:
- Around line 85-88: Validate process.env.APP_URL before using it to build the
proxy link: in the createCheckoutLink handler check that APP_URL is present and
a valid URL (parse it with new URL(APP_URL) in a try/catch), construct the
checkout URL using new URL(`/checkout/${sessionResult.id}`,
parsedAppUrl).toString() instead of string concatenation, and handle/throw a
clear error or log and return a gRPC error if APP_URL is missing or malformed;
then set that validated URL on CreateCheckoutLinkResponse via
response.setCheckoutlink(...).
- Line 53: The code currently uses a non-null assertion on auth.mode (const mode
= auth.mode!) which bypasses type checks; instead check auth.mode explicitly and
fail fast if it's null by throwing or returning a domain error before calling
calculatePrice() or createCheckoutSession(); replace the non-null assertion with
an early guard that validates auth.mode is "production" | "test" and then pass
that validated mode to calculatePrice() and createCheckoutSession().

In `@src/routes/gRPC/payment/paymentProvider.ts`:
- Line 20: The webhookKey property is reading
process.env.DODO_PAYMENTS_WEBHOOK_SIGNING_SECRET which doesn't match the
documented .env.example variable; update the usages in paymentProvider.ts (the
webhookKey assignments at the occurrences around the webhookKey lines) to read
process.env.DODO_PAYMENTS_WEBHOOK_SECRET instead of
DODO_PAYMENTS_WEBHOOK_SIGNING_SECRET so the env value from .env.example is
picked up (update both occurrences).

In `@src/routes/http/checkoutRedirect.ts`:
- Around line 4-10: In handleCheckoutRedirect, validate request.params.sessionId
with a Zod schema before calling getCheckoutUrl: create a Zod schema for the
params (including sessionId), parse request.params and catch ZodError, then
convert that ZodError into the appropriate domain/HTTP error (e.g., bad request)
and reply accordingly instead of proceeding to call getCheckoutUrl; ensure the
Zod validation and error conversion happen at the top of handleCheckoutRedirect
so getCheckoutUrl only runs with a validated sessionId.

In `@src/storage/adapter/clickhouse/ClickHouseAdapter.ts`:
- Line 28: The add(serialized: SerializedEvent, apiKeyId?: string, mode?:
"production" | "test") method currently accepts an optional mode which allows
callers to omit environment scoping; change the signature to require mode
(remove the optional ?), validate that mode is present at the start of add and
throw/reject if missing, and propagate the non-optional mode to any internal
handlers or DB calls; apply the same required-mode change and pre-DB validation
to the other write/pricing entry points in this adapter so no write or pricing
path can be invoked without an explicit "production" | "test" mode.

In `@src/storage/adapter/clickhouse/handlers/priceRequestAiTokenUsage.ts`:
- Around line 48-49: The query currently omits the mode predicate when mode is
falsy so test and production data can mix; change the code to resolve a
defaultMode = mode || "production" (or similar) and always build the predicate
using that resolvedMode (e.g., const modeFilter = " AND mode = {mode:String}"),
then pass resolvedMode into the query parameters where the current mode would be
used (update any occurrences that build the query or parameters around
modeFilter and the places noted at lines 51-55 and 57-59 so they use
resolvedMode instead of possibly undefined mode).

In `@src/storage/adapter/clickhouse/handlers/priceRequestSdkCall.ts`:
- Around line 46-47: The optional mode filter currently allows requests without
mode which can mix production/test billing; change the logic in
priceRequestSdkCall so mode defaults to "production" and always append the
filter expression (use the existing modeFilter variable and the query
construction that references it) instead of conditionally omitting it; update
all related occurrences where modeFilter is built/used (including the blocks
around the existing modeFilter declaration and the other uses at the sections
corresponding to the other occurrences) to pass or bind the default "production"
value and keep the SQL fragment "AND mode = {mode:String}" in every query.

In `@src/storage/adapter/clickhouse/schema.ts`:
- Line 9: Existing tables will not get the new mode column because CREATE TABLE
IF NOT EXISTS does not alter schemas; before each of the three CREATE TABLE
statements in src/storage/adapter/clickhouse/schema.ts, add an ALTER TABLE for
that table to add the mode column if missing (use ADD COLUMN IF NOT EXISTS with
a sensible default such as 'production') so pre-existing tables gain the mode
String column prior to any inserts/queries that reference it.

In `@src/storage/adapter/postgres/handlers/addAiTokenUsage.ts`:
- Around line 26-30: The batch insert path in handleAddAiTokenUsage may omit the
required eventsTable.mode when mode param is undefined; update the batch insert
to always supply a valid mode for each row by populating eventsTable.mode with
the provided mode param or a safe default (e.g., 'production') before calling
the insert, or validate/throw if mode must be explicit; change the conditional
exclusion logic so the insert payload always includes eventsTable.mode (e.g.,
eventsTable.mode: mode ?? 'production') to prevent DB constraint errors.

In `@src/storage/db/postgres/helpers/sessions.ts`:
- Line 13: The session model currently treats checkoutUrl as optional and
inserts it without validation; update the code that constructs and inserts
sessions to require and validate checkoutUrl (e.g., non-empty string and valid
URL format using a URL constructor or regex) before any DB operation, and wrap
the insert in a Drizzle ORM transaction (use db.transaction or the project's
transaction helper around sessions.insert/insertSession) so the validation runs
inside the transactional flow; additionally catch DB unique-constraint errors
(Postgres code 23505) around the insert and handle them explicitly (translate to
a clear conflict error or retry logic) instead of letting raw DB errors bubble
up.

---

Outside diff comments:
In `@src/routes/gRPC/payment/createCheckoutLink.ts`:
- Around line 67-82: The current flow calls createCheckoutSession (provider
creation) before handleAddSession (DB persistence), which can leave a live
provider session if the DB write fails; make this recoverable by either
persisting a pending session record first or adding a compensating cancel/update
after a failed DB write. Concretely: create a pending session entry in the DB
(e.g., status="pending") for validatedData.userId before calling
createCheckoutSession, then call createCheckoutSession, and on success update
that pending record with sessionId and checkoutUrl via handleAddSession (or a
dedicated update method); alternatively, if you keep provider-first, catch DB
errors and call the provider cancel function (or update via
createProviderCheckout cancellation API) to clean up the remote session and
surface a clear error. Ensure changes reference createCheckoutSession and
handleAddSession (or the provider cancel API) so retries do not create duplicate
live sessions.

In `@src/storage/adapter/postgres/handlers/addEventUtils.ts`:
- Around line 60-66: EventInsertValues declares mode as optional and the insert
logic conditionally omits it, but eventsTable.mode is a required DB column so
this can cause runtime insert failures; make mode required in EventInsertValues
(remove the ?), and update the insert construction (the code that references
eventsTable.mode / the conditional omit) to always include mode—either pass
through the provided value or apply a sensible default (e.g., "production")
before building the insert so every insert includes eventsTable.mode.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

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

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: f4100d0c-c88a-4dc1-bf34-5a03b049e279

📥 Commits

Reviewing files that changed from the base of the PR and between 31a4887 and cf7e5a2.

📒 Files selected for processing (27)
  • .env.example
  • src/interface/storage/Storage.ts
  • src/routes/gRPC/payment/createCheckoutLink.ts
  • src/routes/gRPC/payment/paymentProvider.ts
  • src/routes/http/checkoutRedirect.ts
  • src/routes/http/createdCheckout.ts
  • src/servers/fastifyServer.ts
  • src/storage/adapter/clickhouse/ClickHouseAdapter.ts
  • src/storage/adapter/clickhouse/handlers/addAiTokenUsage.ts
  • src/storage/adapter/clickhouse/handlers/addPayment.ts
  • src/storage/adapter/clickhouse/handlers/addSdkCall.ts
  • src/storage/adapter/clickhouse/handlers/priceRequestAiTokenUsage.ts
  • src/storage/adapter/clickhouse/handlers/priceRequestSdkCall.ts
  • src/storage/adapter/clickhouse/schema.ts
  • src/storage/adapter/common/priceRequestPayment.ts
  • src/storage/adapter/postgres/handlers/addAiTokenUsage.ts
  • src/storage/adapter/postgres/handlers/addEventUtils.ts
  • src/storage/adapter/postgres/handlers/addPayment.ts
  • src/storage/adapter/postgres/handlers/addSdkCall.ts
  • src/storage/adapter/postgres/handlers/index.ts
  • src/storage/adapter/postgres/handlers/priceRequest.ts
  • src/storage/adapter/postgres/handlers/priceRequestAiTokenUsage.ts
  • src/storage/adapter/postgres/handlers/priceRequestSdkCall.ts
  • src/storage/adapter/postgres/postgres.ts
  • src/storage/db/postgres/helpers/sessions.ts
  • src/storage/db/postgres/schema.ts
  • src/utils/eventHelpers.ts
💤 Files with no reviewable changes (1)
  • src/storage/adapter/postgres/handlers/index.ts

Comment thread src/routes/gRPC/payment/createCheckoutLink.ts Outdated
Comment thread src/routes/gRPC/payment/createCheckoutLink.ts
Comment thread src/routes/gRPC/payment/paymentProvider.ts
Comment thread src/routes/http/checkoutRedirect.ts
Comment thread src/storage/adapter/clickhouse/ClickHouseAdapter.ts Outdated
Comment thread src/storage/adapter/clickhouse/handlers/priceRequestAiTokenUsage.ts Outdated
Comment thread src/storage/adapter/clickhouse/handlers/priceRequestSdkCall.ts Outdated
Comment thread src/storage/adapter/clickhouse/schema.ts
Comment thread src/storage/adapter/postgres/handlers/addAiTokenUsage.ts
Comment thread src/storage/db/postgres/helpers/sessions.ts

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Caution

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

⚠️ Outside diff range comments (1)
src/utils/eventHelpers.ts (1)

31-39: ⚠️ Potential issue | 🔴 Critical | ⚡ Quick win

Non-null assertion masks a real type mismatch — dashboard roles can have auth.mode = null.

The auth.mode! assertion bypasses type safety for a legitimate case. The getModeForRole() function returns null when the API key role is "dashboard", making auth.mode nullable. However, adapter.add() requires mode: "production" | "test" (non-nullable). Passing null violates the storage contract. As per coding guidelines, validate all inputs before DB operations.

🛡️ Proposed fix with runtime validation
 export async function storeEvent(
   event: Event,
   auth: AuthContext
 ): Promise<void> {
   const adapter = await StorageAdapterFactory.getEventStorageAdapter(
     event.type
   );
+  if (!auth.mode) {
+    throw new Error("auth.mode is required for event storage");
+  }
   await adapter.add(event.serialize(), auth.apiKeyId, auth.mode);
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/utils/eventHelpers.ts` around lines 31 - 39, storeEvent currently uses a
non-null assertion on auth.mode which can be null for dashboard roles; update
storeEvent to validate auth.mode (from getModeForRole) before calling
StorageAdapterFactory.getEventStorageAdapter/add: if auth.mode is null either
throw a clear error or map dashboard role to an explicit allowed mode (or refuse
the operation), and pass the validated non-null "production" | "test" value into
adapter.add; reference the storeEvent function,
StorageAdapterFactory.getEventStorageAdapter, and adapter.add when making the
change.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@src/utils/eventHelpers.ts`:
- Around line 31-39: storeEvent currently uses a non-null assertion on auth.mode
which can be null for dashboard roles; update storeEvent to validate auth.mode
(from getModeForRole) before calling
StorageAdapterFactory.getEventStorageAdapter/add: if auth.mode is null either
throw a clear error or map dashboard role to an explicit allowed mode (or refuse
the operation), and pass the validated non-null "production" | "test" value into
adapter.add; reference the storeEvent function,
StorageAdapterFactory.getEventStorageAdapter, and adapter.add when making the
change.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 79b503fc-38be-493a-aa27-6cbac97bb5cb

📥 Commits

Reviewing files that changed from the base of the PR and between cf7e5a2 and 114b52e.

📒 Files selected for processing (21)
  • src/interface/storage/Storage.ts
  • src/routes/gRPC/payment/createCheckoutLink.ts
  • src/routes/http/createdCheckout.ts
  • src/storage/adapter/clickhouse/ClickHouseAdapter.ts
  • src/storage/adapter/clickhouse/handlers/addAiTokenUsage.ts
  • src/storage/adapter/clickhouse/handlers/addPayment.ts
  • src/storage/adapter/clickhouse/handlers/addSdkCall.ts
  • src/storage/adapter/clickhouse/handlers/priceRequestAiTokenUsage.ts
  • src/storage/adapter/clickhouse/handlers/priceRequestSdkCall.ts
  • src/storage/adapter/common/priceRequestPayment.ts
  • src/storage/adapter/postgres/handlers/addAiTokenUsage.ts
  • src/storage/adapter/postgres/handlers/addEventUtils.ts
  • src/storage/adapter/postgres/handlers/addPayment.ts
  • src/storage/adapter/postgres/handlers/addSdkCall.ts
  • src/storage/adapter/postgres/handlers/priceRequest.ts
  • src/storage/adapter/postgres/handlers/priceRequestAiTokenUsage.ts
  • src/storage/adapter/postgres/handlers/priceRequestSdkCall.ts
  • src/storage/adapter/postgres/postgres.ts
  • src/storage/db/postgres/helpers/sessions.ts
  • src/storage/db/postgres/schema.ts
  • src/utils/eventHelpers.ts
🚧 Files skipped from review as they are similar to previous changes (5)
  • src/storage/adapter/postgres/handlers/addSdkCall.ts
  • src/storage/adapter/common/priceRequestPayment.ts
  • src/storage/db/postgres/schema.ts
  • src/routes/gRPC/payment/createCheckoutLink.ts
  • src/storage/db/postgres/helpers/sessions.ts

@SteakFisher
SteakFisher merged commit 2a5b32a into main May 14, 2026
2 of 3 checks passed
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