Skip to content

Main - #115

Merged
Thejas775 merged 14 commits into
developmentfrom
main
Jul 14, 2026
Merged

Main#115
Thejas775 merged 14 commits into
developmentfrom
main

Conversation

@Thejas775

@Thejas775 Thejas775 commented Jul 13, 2026

Copy link
Copy Markdown
Collaborator

Description

Type of Change

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • Documentation update
  • Refactoring (no functional changes)
  • Build/CI changes

Related Issues

Fixes #

Checklist

  • My code follows the code style of this project
  • I have run ./gradlew spotlessApply to format my code
  • I have run ./gradlew detekt and fixed any issues
  • I have added tests that prove my fix is effective or that my feature works
  • All new and existing tests passed
  • I have updated the documentation accordingly
  • I have added/updated KDoc comments for public APIs

Testing

  • Unit tests pass on JVM
  • Unit tests pass on Android
  • Unit tests pass on iOS
  • Manual testing performed

Screenshots (if applicable)

Additional Notes

Summary by CodeRabbit

  • New Features
    • Lifetime entitlements are now granted for successfully completed Stripe one-time (payment-mode) checkouts.
    • Async payment checkouts now receive entitlements once payment is confirmed.
  • Bug Fixes
    • Payment checkout flows no longer miss entitlement issuance.
    • Billing and premium subscription lookup failures during device transfer/revocation are now recorded for easier troubleshooting.
  • Tests
    • Added deterministic test coverage for billing initialization, authentication, OTP verification/ownership checks, logout resets, and device transfer behavior.

therajanmaurya and others added 10 commits June 19, 2026 10:43
release: promote development → main (2026-06-19T05:13:28Z)
Promote development → main (bom1 region)
release: promote development → main (2026-06-20T14:07:32Z)
release: promote development → main (2026-06-23T14:29:25Z)
release: promote development → main (2026-06-23T15:03:03Z)
release: promote development → main (2026-06-23T15:41:26Z)
release: promote development → main (2026-06-23T16:36:19Z)
…bservability, Next.js security

- stripe-webhook: grant entitlement on mode=payment + async_payment_succeeded
  (one-time/lifetime purchases were silently dropped); reuses subscription-handler
  upsert path (email/current_period_end), ~100yr period for lifetime.
- PayCraftBillingManager: replace 3 silent catches with PayCraftLogger.onError
  (transferToDevice, revokeCurrentDevice, applyPremiumResult); add 11 unit tests
  covering premium/cache application, logout reset, OAuth error, OTP decisioning,
  transfer abort guard.
- dashboard: bump Next.js 14.2.15 -> 14.2.35 (resolves the 2025-12-11 critical CVE).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…e-existing UI files)

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
fix(paycraft): production hardening — lifetime entitlement + billing observability + Next.js security
@cloudflare-workers-and-pages

cloudflare-workers-and-pages Bot commented Jul 13, 2026

Copy link
Copy Markdown

Deploying with  Cloudflare Workers  Cloudflare Workers

The latest updates on your project. Learn more about integrating Git with Workers.

Status Name Latest Commit Updated (UTC)
❌ Deployment failed
View logs
paycraft-docs 68af408 Jul 14 2026, 11:43 AM

@vercel

vercel Bot commented Jul 13, 2026

Copy link
Copy Markdown

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

Project Deployment Actions Updated (UTC)
pay-craft Ready Ready Preview, Comment Jul 14, 2026 11:43am

@coderabbitai

coderabbitai Bot commented Jul 13, 2026

Copy link
Copy Markdown

Review Change Stack

Important

Review skipped

Review was skipped due to path filters

⛔ Files ignored due to path filters (1)
  • dashboard/pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml

CodeRabbit blocks several paths by default. You can override this behavior by explicitly including those paths in the path filters. For example, including **/dist/** will override the default block on the dist directory, by removing the pattern from both the lists.

⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 024a1c30-a35a-4890-ab3f-6c0875917cd9

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
📝 Walkthrough

Walkthrough

PayCraftBillingManager now logs selected failures and gains deterministic state and RPC tests. Stripe webhooks now grant lifetime entitlements for settled payment-mode checkouts, including asynchronous payments. UI imports and the dashboard Next.js version are updated.

Changes

Billing manager behavior

Layer / File(s) Summary
Billing error observability
cmp-paycraft/src/commonMain/kotlin/com/mobilebytelabs/paycraft/core/PayCraftBillingManager.kt
Transfer, revocation, and premium subscription lookup failures now emit error logs while preserving existing fallback behavior.
Billing state and RPC tests
cmp-paycraft/src/commonTest/kotlin/com/mobilebytelabs/paycraft/core/PayCraftBillingManagerTest.kt
Faked service and store dependencies support tests for initialization, logout, authentication, OTP, ownership, and device transfer behavior.

Stripe payment entitlements

Layer / File(s) Summary
Settled payment checkout handling
supabase/functions/stripe-webhook/index.ts
Paid payment-mode checkout sessions now create lifetime entitlements using payment and plan metadata.
Async payment settlement handling
supabase/functions/stripe-webhook/index.ts
Asynchronously succeeded payment-mode sessions now create the same lifetime entitlement payload.

Maintenance updates

Layer / File(s) Summary
Import and dependency maintenance
cmp-paycraft/src/commonMain/kotlin/com/mobilebytelabs/paycraft/ui/PayCraftBanner.kt, cmp-paycraft/src/commonMain/kotlin/com/mobilebytelabs/paycraft/ui/PayCraftPaywall.kt, dashboard/package.json
UI imports are relocated, and the dashboard next dependency is updated to version 14.2.35.

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

Sequence Diagram(s)

sequenceDiagram
  participant Stripe
  participant stripe_webhook
  participant handleSubscriptionEvent
  Stripe->>stripe_webhook: checkout.session.completed or checkout.session.async_payment_succeeded
  stripe_webhook->>stripe_webhook: Check payment mode and settlement
  stripe_webhook->>handleSubscriptionEvent: Create lifetime entitlement
Loading

Possibly related PRs

  • MobileByteLabs/PayCraft#60: Modifies the same Stripe webhook checkout handling with webhook secret detection and mode-aware processing.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 inconclusive)

Check name Status Explanation Resolution
Title check ❓ Inconclusive The title is too generic and does not describe the billing, webhook, testing, or dependency changes in this pull request. Use a short descriptive title that names the main change, such as Stripe entitlement handling, billing fixes, or Next.js upgrade.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch main

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.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (1)
supabase/functions/stripe-webhook/index.ts (1)

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

Duplicate lifetime-entitlement construction between the two handlers.

Lines 236-260 (completed handler) and 284-305 (async handler) build the exact same lifetimePeriodEnd, oneTimeId, and handleSubscriptionEvent payload. Extracting a shared helper (e.g. grantLifetimeEntitlement(session, tenantId, eventType, email)) removes the duplication and prevents the two paths from silently drifting apart on future edits.

Also applies to: 265-308

🤖 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 `@supabase/functions/stripe-webhook/index.ts` around lines 205 - 261, Extract
the duplicated lifetime-entitlement construction from the completed and async
payment handlers into a shared helper, such as grantLifetimeEntitlement,
accepting the session, tenantId, eventType, and email. Move the
lifetimePeriodEnd calculation, oneTimeId selection, and handleSubscriptionEvent
payload into that helper, then call it from both branches while preserving the
existing payment-settlement guard and behavior.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@supabase/functions/stripe-webhook/index.ts`:
- Around line 229-234: The payment-status guard in the checkout session handling
must treat "no_payment_required" as settled. Update the condition around
session.payment_status to block only "unpaid" (while preserving the existing
wait-and-break behavior), allowing "paid" and "no_payment_required" sessions to
continue to entitlement processing.

---

Nitpick comments:
In `@supabase/functions/stripe-webhook/index.ts`:
- Around line 205-261: Extract the duplicated lifetime-entitlement construction
from the completed and async payment handlers into a shared helper, such as
grantLifetimeEntitlement, accepting the session, tenantId, eventType, and email.
Move the lifetimePeriodEnd calculation, oneTimeId selection, and
handleSubscriptionEvent payload into that helper, then call it from both
branches while preserving the existing payment-settlement guard and behavior.
🪄 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

Run ID: 924e6f37-65b1-429d-a711-b9bd02c62981

📥 Commits

Reviewing files that changed from the base of the PR and between 7442ff1 and 9373224.

⛔ Files ignored due to path filters (1)
  • dashboard/package-lock.json is excluded by !**/package-lock.json
📒 Files selected for processing (6)
  • cmp-paycraft/src/commonMain/kotlin/com/mobilebytelabs/paycraft/core/PayCraftBillingManager.kt
  • cmp-paycraft/src/commonMain/kotlin/com/mobilebytelabs/paycraft/ui/PayCraftBanner.kt
  • cmp-paycraft/src/commonMain/kotlin/com/mobilebytelabs/paycraft/ui/PayCraftPaywall.kt
  • cmp-paycraft/src/commonTest/kotlin/com/mobilebytelabs/paycraft/core/PayCraftBillingManagerTest.kt
  • dashboard/package.json
  • supabase/functions/stripe-webhook/index.ts

Comment thread supabase/functions/stripe-webhook/index.ts Outdated
…checkout)

CodeRabbit (PR #115): a fully-discounted payment-mode checkout completes with
payment_status='no_payment_required'. The prior guard skipped entitlement for
anything != 'paid' and waited for async_payment_succeeded, which never fires for
such sessions → the user never got lifetime access. Now grant on both 'paid' and
'no_payment_required'; only genuinely 'unpaid' async sessions await settlement.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ayment-required

fix(stripe-webhook): grant lifetime entitlement on no_payment_required (100%-off checkout)
Thejas775 and others added 2 commits July 14, 2026 17:01
…l deploy)

#114 bumped next 14.2.15→14.2.35 in package.json via npm, so pnpm-lock.yaml stayed
at 14.2.15. Vercel builds with 'pnpm install --frozen-lockfile' → ERR_PNPM_OUTDATED_LOCKFILE
(lockfile 14.2.15 ≠ manifest 14.2.35) → production build failed. Regenerated the lock
with pnpm 10 so frozen-install matches.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
fix(dashboard): sync pnpm-lock.yaml with next@14.2.35 — unblocks Vercel deploy
@Thejas775
Thejas775 merged commit a63ec55 into development Jul 14, 2026
18 of 21 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.

2 participants