-
Notifications
You must be signed in to change notification settings - Fork 5
1658 change membership renewal #1665
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull request overview
This PR transitions the membership renewal system from a calendar year-based model to a rolling 12-month model where memberships expire one year from the purchase date. The change aligns with a constitutional amendment mentioned in the updated email template, which becomes effective from 2026.
Key changes:
- Adds
membership_expirytimestamp field to the User schema and generates corresponding database migration - Updates payment and admin flows to set membership expiry dates when users become members
- Modifies user-facing text to reflect "one year from now" instead of "31st Dec {year}"
- Adjusts cron job schedules for membership renewal reminders (from 15:59 to 03:00 UTC)
- Adds new path alias
@/*to tsconfig.json and updates imports across multiple files - Improves error handling in payment components with user-friendly toast notifications
Reviewed changes
Copilot reviewed 29 out of 32 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| src/server/db/schema.ts | Adds membership_expiry timestamp field to User table |
| src/server/db/migrations/0005_daffy_victor_mancha.sql | Migration script to add membership_expiry column |
| src/server/db/migrations/meta/_journal.json | Migration journal entry for the new migration |
| src/server/db/migrations/meta/0005_snapshot.json | Complete schema snapshot including the new membership_expiry field |
| src/server/api/routers/payments/pay.ts | Sets membership_expiry to one year from payment date when user pays |
| src/server/api/routers/admin/users/update-role.ts | Sets membership_expiry when admin assigns "member" role |
| src/app/dashboard/admin/@users/table.tsx | Displays membership expiry date in admin user table with visual indicator for expired memberships |
| src/components/email-template.tsx | Updates renewal reminder email with hardcoded 2025 year and constitutional amendment notice |
| src/app/profile/[id]/profile.tsx | Changes membership description from calendar-year to rolling year |
| src/app/create-account/page.tsx | Updates payment description text for new membership model |
| src/app/create-account/payment.tsx | Updates payment description text for new membership model |
| src/app/create-account/loading.tsx | Updates loading page payment description text |
| src/components/payment/online/index.tsx | Improves error handling with toast notifications and better type checking |
| src/components/payment/online/saved-cards.tsx | Fixes TypeScript type assertion for TokenResult |
| src/components/payment/online/card.tsx | Improves error checking with type guard for result.errors |
| src/components/payment/online/google-pay.tsx | Improves error checking with type guard for result.errors |
| src/components/payment/online/apple-pay.tsx | Improves error checking with type guard for result.errors |
| src/server/api/routers/users/update.ts | Removes completed TODO comment |
| vercel.json | Changes cron schedule timing from 15:59 to 03:00 UTC |
| tsconfig.json | Adds @/* path alias pointing to project root, removes baseUrl |
| src/app/projects/[id]/page.tsx | Updates import to use new @/ alias |
| src/app/projects/(default)/page.tsx | Updates import to use new @/ alias |
| src/app/hack-for-homes/sponsors.tsx | Updates import to use new @/ alias |
| src/app/hack-for-homes/participants/page.tsx | Updates import to use new @/ alias |
| src/app/hack-for-homes/agenda/page.tsx | Updates import to use new @/ alias |
| src/app/events/page.tsx | Updates import to use new @/ alias |
| src/app/about/sponsors.tsx | Updates import to use new @/ alias |
| src/app/about/committee.tsx | Updates import to use new @/ alias |
| src/app/about/clients.tsx | Updates import to use new @/ alias |
| declarations.d.ts | Adds module declaration for CSS files |
| README.md | Adds database migration commands documentation |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| await ctx.db.update(User).set({ role: "member" }).where(eq(User.id, currentUser.id)) | ||
|
|
||
| await ctx.db | ||
| .update(User) | ||
| .set({ membership_expiry: new Date(Date.now() + 365 * 24 * 60 * 60 * 1000) }) |
Copilot
AI
Dec 30, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The two database update operations for the same user should be combined into a single update statement. This is more efficient and reduces the number of database round trips. Consider merging both updates into one:
await ctx.db.update(User).set({ role: "member", membership_expiry: new Date(Date.now() + 365 * 24 * 60 * 60 * 1000) }).where(eq(User.id, currentUser.id))
| await ctx.db.update(User).set({ role: "member" }).where(eq(User.id, currentUser.id)) | |
| await ctx.db | |
| .update(User) | |
| .set({ membership_expiry: new Date(Date.now() + 365 * 24 * 60 * 60 * 1000) }) | |
| await ctx.db | |
| .update(User) | |
| .set({ | |
| role: "member", | |
| membership_expiry: new Date(Date.now() + 365 * 24 * 60 * 60 * 1000), | |
| }) |
| <Text style={text}>Hi {Firstname},</Text> | ||
| <Text style={text}> | ||
| {`Your membership of Coders for Causes ends on 31st Dec ${year}. To keep your membership active, please renew it by clicking the button below.`} | ||
| {`Your membership of Coders for Causes ends on 31st Dec 2025. To keep your membership active, please renew it by clicking the button below.`} |
Copilot
AI
Dec 30, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The hardcoded year "2025" in the email template will become outdated after December 31, 2025. Since this is a reminder email that will be sent annually, the year should be dynamic. Consider using a prop or computing it dynamically based on the user's membership expiry date to ensure the email remains accurate in future years.
|
|
||
| await ctx.db | ||
| .update(User) | ||
| .set({ membership_expiry: new Date(Date.now() + 365 * 24 * 60 * 60 * 1000) }) |
Copilot
AI
Dec 30, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The membership expiry calculation using 365 * 24 * 60 * 60 * 1000 does not account for leap years, which will result in a membership expiring approximately one day earlier than expected every four years. Consider using a more accurate date calculation method such as using the date-fns library's addYears() function or accounting for the actual calendar year.
| if (input.role === "member") { | ||
| await ctx.db | ||
| .update(User) | ||
| .set({ membership_expiry: new Date(Date.now() + 365 * 24 * 60 * 60 * 1000) }) |
Copilot
AI
Dec 30, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The membership expiry calculation using 365 * 24 * 60 * 60 * 1000 does not account for leap years, which will result in a membership expiring approximately one day earlier than expected every four years. Consider using a more accurate date calculation method such as using the date-fns library's addYears() function or accounting for the actual calendar year.
src/app/create-account/payment.tsx
Outdated
| Become a paying member of Coders for Causes for just $5 a year (ends on 31st Dec{" "} | ||
| {new Date().getFullYear()} | ||
| ). There are many benefits to becoming a member which include: | ||
| Become a paying member of Coders for Causes for just $5 a year (ends one year from now ). There are many |
Copilot
AI
Dec 30, 2025
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The extra space before the closing parenthesis in "ends one year from now )" should be removed for consistency and proper formatting.
| Become a paying member of Coders for Causes for just $5 a year (ends one year from now ). There are many | |
| Become a paying member of Coders for Causes for just $5 a year (ends one year from now). There are many |
Change Summary
[Briefly summarise the changes that you made. Just high-level stuff]
Change Form
Fill this up (NA if not available). If a certain criteria is not met, can you please give a reason.
Other Information
[Is there anything in particular in the review that I should be aware of?]