Term Policy Document
Overview
The Term Policy module manages legal agreements and user consent within the application. It provides a complete workflow for creating, versioning, managing, and enforcing user acceptance of legal policies such as terms of service, privacy policies, marketing consents, and cookie policies.
Related Documents
- Database Documentation - Migration, seeding, and schema details
- Authorization Documentation - RBAC for admin operations
- Authentication Documentation - User authentication requirements
- Presign Documentation - How to upload the contents
Table of Contents
- Overview
- Related Documents
- Policy Types
- Policy Status
- Flow
- User Endpoints
- Admin Endpoints
- TermPolicyAcceptanceProtected
- Migration & Seeding
- Contribution
Policy Types
Four policy types are available via EnumTermPolicyType:
| Type | Description |
|---|---|
termsOfService | Terms of Service agreement |
privacy | Privacy Policy |
marketing | Marketing consent |
cookies | Cookie Policy |
Each type can have multiple versions. Users must accept the latest published version to access protected endpoints.
Policy Status
Term policies follow a two-stage status:
Draft Status
- Policy created by admin
- Content files stored in private S3 bucket
- Can be edited, updated, or deleted
- Not visible to users
- Path:
{uploadContentPath}/{type}/{version}/{language}.hbs
Published Status
- Policy published by admin
- Content files moved to public S3 bucket
- Cannot be edited or deleted
- Visible to all users
- Invalidates all existing user acceptances for that policy type
- All active users must re-accept the new version
- Path:
{contentPublicPath}/{type}/{version}/{language}.hbs
Important: When a new version is published, all users termPolicy[type] flags are set to false, requiring them to accept the new version before accessing protected endpoints.
Flow
Admin Flow Diagram
User Flow Diagram
User Endpoints
Users interact with term policies through acceptance and viewing their acceptance history.
List Published Policies
Users can view all published policies available for acceptance:
GET /term-policy/listReturns policies with cursor pagination, optionally filtered by type.
Accept Policy
To accept a specific policy type:
POST /user/term-policy/accept
{
"type": "termsOfService"
}View Acceptance History
Users can view their acceptance history:
GET /user/term-policy/list/acceptedReturns all policies the user has accepted with timestamps and policy details.
Admin Endpoints
Admins manage the complete lifecycle of term policies from creation to publishing.
Generate Presign URL
Generate presigned URL for uploading content to S3:
POST /term-policy/generate/content/presignCreate Policy
Create new policy with initial content:
POST /term-policy/createAdd Content
Add new language variant to draft policy:
PUT /term-policy/update/:termPolicyId/content/addUpdate Content
Replace existing language content in draft policy:
PUT /term-policy/update/:termPolicyId/content/updateRemove Content
Remove specific language variant from draft policy:
DELETE /term-policy/update/:termPolicyId/content/removeGet Content
Get presigned URL to download policy content:
POST /term-policy/get/:termPolicyId/content/:languagePublish Policy
Publish policy and invalidate all user acceptances:
PATCH /term-policy/publish/:termPolicyIdCritical: Publishing sets termPolicy[type] to false for all users, requiring re-acceptance. Once published, policy cannot be edited or deleted.
List Policies
List all policies with optional filters:
GET /term-policy/list?type=termsOfService&status=draftDelete Policy
Delete draft policy and remove S3 content:
DELETE /term-policy/delete/:termPolicyIdOnly draft policies can be deleted.
TermPolicyAcceptanceProtected
The @TermPolicyAcceptanceProtected() decorator protects endpoints by requiring users to accept specific policies before accessing them.
Important: This decorator requires both @UserProtected() and @AuthJwtAccessProtected() to be applied. Without these decorators, the endpoint will return a 403 Forbidden error.
Decorator order (from top to bottom):
@TermPolicyAcceptanceProtected()
@UserProtected()
@AuthJwtAccessProtected()Basic Usage
@Controller('user')
export class UserController {
// Requires termsOfService acceptance
@TermPolicyAcceptanceProtected(EnumTermPolicyType.termsOfService)
@UserProtected()
@AuthJwtAccessProtected()
@Get('/profile')
async getProfile() {
return { message: 'Profile data' };
}
// Requires both termsOfService and privacy acceptance
@TermPolicyAcceptanceProtected(
EnumTermPolicyType.termsOfService,
EnumTermPolicyType.privacy
)
@UserProtected()
@AuthJwtAccessProtected()
@Get('/settings')
async getSettings() {
return { message: 'Settings data' };
}
// Requires marketing consent
@TermPolicyAcceptanceProtected(EnumTermPolicyType.marketing)
@UserProtected()
@AuthJwtAccessProtected()
@Get('/newsletter')
async getNewsletter() {
return { message: 'Newsletter content' };
}
// Default: requires termsOfService and privacy
@TermPolicyAcceptanceProtected()
@UserProtected()
@AuthJwtAccessProtected()
@Get('/dashboard')
async getDashboard() {
return { message: 'Dashboard data' };
}
}How It Works
Important Notes
@TermPolicyAcceptanceProtected()requires@UserProtected()and@AuthJwtAccessProtected()to be applied- Decorator order from top to bottom:
@TermPolicyAcceptanceProtected()→@UserProtected()→@AuthJwtAccessProtected() - For more details about
@AuthJwtAccessProtected(), see Authentication Documentation - For more details about
@UserProtected(), see Authorization Documentation - Without the required decorators, the endpoint will throw a 403 Forbidden error
- If no term policies are specified, it defaults to requiring
termsOfServiceandprivacyacceptance - All specified term policies must be accepted by the user for access to be granted
- Incorrect decorator ordering will result in runtime errors
Migration & Seeding
Template migration seed available at:
src/migration/seeds/migration.template-term-policy.seed.tsThis seed file provides:
- Sample term policies for all types
- Multi-language content examples
- Published policy setup
For detailed migration and seeding instructions, see Database Documentation.
Contribution
Special thanks to [Gzerox][ref-contributor-gzerox] for contributing to the Term Policy module implementation.