@openpolicy/sdk 0.0.19 → 0.0.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +10 -0
- package/dist/index.d.ts +0 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +0 -3
- package/dist/index.js.map +1 -1
- package/package.json +9 -4
- package/skills/annotate-data-collection/SKILL.md +240 -0
- package/skills/annotate-third-parties/SKILL.md +237 -0
- package/skills/annotate-third-parties/references/known-packages.md +37 -0
- package/skills/define-config/SKILL.md +286 -0
- package/skills/define-config/references/privacy-config.md +153 -0
- package/skills/define-config/references/terms-config.md +130 -0
- package/skills/getting-started/SKILL.md +251 -0
- package/skills/migrate/SKILL.md +360 -0
package/README.md
CHANGED
|
@@ -88,6 +88,16 @@ The SDK exports types and helper functions for _defining_ policies. To compile t
|
|
|
88
88
|
|
|
89
89
|
Full field reference and guides: [openpolicy.sh/docs](https://openpolicy.sh/docs)
|
|
90
90
|
|
|
91
|
+
## AI Agents
|
|
92
|
+
|
|
93
|
+
If you use an AI coding agent (Claude Code, Cursor, Copilot, etc.), run:
|
|
94
|
+
|
|
95
|
+
```sh
|
|
96
|
+
npx @tanstack/intent@latest install
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
This installs skill files that give your agent accurate, up-to-date guidance for OpenPolicy APIs.
|
|
100
|
+
|
|
91
101
|
## Links
|
|
92
102
|
|
|
93
103
|
- [GitHub](https://github.com/jamiedavenport/openpolicy)
|
package/dist/index.d.ts
CHANGED
|
@@ -334,9 +334,6 @@ declare const Providers: {
|
|
|
334
334
|
};
|
|
335
335
|
//#endregion
|
|
336
336
|
//#region src/third-parties.d.ts
|
|
337
|
-
/**
|
|
338
|
-
* TODO
|
|
339
|
-
*/
|
|
340
337
|
declare function thirdParty(_name: string, _purpose: string, _policyUrl: string): void;
|
|
341
338
|
//#endregion
|
|
342
339
|
//#region src/index.d.ts
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","names":["OutputFormat","CompileOptions","formats","Jurisdiction","UserRight","LegalBasis","CompanyConfig","name","legalName","address","contact","PrivacyPolicyConfig","Record","effectiveDate","company","dataCollected","legalBasis","retention","cookies","essential","analytics","marketing","thirdParties","purpose","policyUrl","userRights","jurisdictions","children","underAge","noticeUrl","DisputeResolutionMethod","TermsOfServiceConfig","acceptance","methods","eligibility","minimumAge","jurisdictionRestrictions","accounts","registrationRequired","userResponsibleForCredentials","companyCanTerminate","prohibitedUses","userContent","usersOwnContent","licenseGrantedToCompany","licenseDescription","companyCanRemoveContent","intellectualProperty","companyOwnsService","usersMayNotCopy","payments","hasPaidFeatures","refundPolicy","priceChangesNotice","availability","noUptimeGuarantee","maintenanceWindows","termination","userCanTerminate","effectOfTermination","disclaimers","serviceProvidedAsIs","noWarranties","limitationOfLiability","excludesIndirectDamages","liabilityCap","indemnification","userIndemnifiesCompany","scope","thirdPartyServices","disputeResolution","method","venue","classActionWaiver","governingLaw","jurisdiction","changesPolicy","noticeMethod","noticePeriodDays","privacyPolicyUrl","CookiePolicyCookies","key","CookiePolicyConfig","trackingTechnologies","consentMechanism","hasBanner","hasPreferencePanel","canWithdraw","PolicyInput","type","OpenPolicyConfig","Omit","privacy","terms","cookie","isOpenPolicyConfig","value","ValidationIssue","level","message","CookieConsent","CookieConsentStatus","acceptAll","config","rejectAll","NodeContext","reason","TextNode","context","BoldNode","ItalicNode","LinkNode","href","InlineNode","HeadingNode","ParagraphNode","ListItemNode","ListNode","ordered","items","ContentNode","DocumentSection","id","content","PolicyType","Document","policyType","sections","Node","heading","levelOrContext","text","bold","italic","link","p","li","ul","ol","section","compile","input","validatePrivacyPolicy","validateCookiePolicy","validateTermsOfService","expandOpenPolicyConfig"],"sources":["../../core/dist/index.d.ts","../src/collecting.ts","../src/compliance.ts","../src/data.ts","../src/providers.ts","../src/third-parties.ts","../src/index.ts"],"mappings":"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
|
|
1
|
+
{"version":3,"file":"index.d.ts","names":["OutputFormat","CompileOptions","formats","Jurisdiction","UserRight","LegalBasis","CompanyConfig","name","legalName","address","contact","PrivacyPolicyConfig","Record","effectiveDate","company","dataCollected","legalBasis","retention","cookies","essential","analytics","marketing","thirdParties","purpose","policyUrl","userRights","jurisdictions","children","underAge","noticeUrl","DisputeResolutionMethod","TermsOfServiceConfig","acceptance","methods","eligibility","minimumAge","jurisdictionRestrictions","accounts","registrationRequired","userResponsibleForCredentials","companyCanTerminate","prohibitedUses","userContent","usersOwnContent","licenseGrantedToCompany","licenseDescription","companyCanRemoveContent","intellectualProperty","companyOwnsService","usersMayNotCopy","payments","hasPaidFeatures","refundPolicy","priceChangesNotice","availability","noUptimeGuarantee","maintenanceWindows","termination","userCanTerminate","effectOfTermination","disclaimers","serviceProvidedAsIs","noWarranties","limitationOfLiability","excludesIndirectDamages","liabilityCap","indemnification","userIndemnifiesCompany","scope","thirdPartyServices","disputeResolution","method","venue","classActionWaiver","governingLaw","jurisdiction","changesPolicy","noticeMethod","noticePeriodDays","privacyPolicyUrl","CookiePolicyCookies","key","CookiePolicyConfig","trackingTechnologies","consentMechanism","hasBanner","hasPreferencePanel","canWithdraw","PolicyInput","type","OpenPolicyConfig","Omit","privacy","terms","cookie","isOpenPolicyConfig","value","ValidationIssue","level","message","CookieConsent","CookieConsentStatus","acceptAll","config","rejectAll","NodeContext","reason","TextNode","context","BoldNode","ItalicNode","LinkNode","href","InlineNode","HeadingNode","ParagraphNode","ListItemNode","ListNode","ordered","items","ContentNode","DocumentSection","id","content","PolicyType","Document","policyType","sections","Node","heading","levelOrContext","text","bold","italic","link","p","li","ul","ol","section","compile","input","validatePrivacyPolicy","validateCookiePolicy","validateTermsOfService","expandOpenPolicyConfig"],"sources":["../../core/dist/index.d.ts","../src/collecting.ts","../src/compliance.ts","../src/data.ts","../src/providers.ts","../src/third-parties.ts","../src/index.ts"],"mappings":"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"}
|
package/dist/index.js
CHANGED
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":[],"sources":["../src/collecting.ts","../src/compliance.ts","../src/data.ts","../src/providers.ts","../src/third-parties.ts","../src/index.ts"],"sourcesContent":["/**\n * Declares data collected at the point of storage. Returns `value` unchanged\n * at runtime — the Vite plugin / CLI static analyser (OP-152) will scan calls\n * to `collecting()` at build time and merge the declarations into the\n * compiled privacy policy.\n *\n * The third argument is a plain object literal whose **keys** are field names\n * matching your stored value (for convenient access without a typed callback)\n * and whose **values** are the human-readable labels used in the compiled\n * policy. Only the string values are used by the analyser; the object is\n * never evaluated at runtime. This shape lets you:\n * - keep `value` matching your ORM/table schema exactly,\n * - describe fields with friendly labels for the policy,\n * - omit fields from the policy by leaving them out of the label record\n * (e.g. `hashedPassword`).\n *\n * The category argument and the string values of the label record must be\n * string literals — dynamic values are silently skipped by the analyser.\n *\n * @example\n * ```ts\n * import { collecting } from \"@openpolicy/sdk\";\n *\n * export async function createUser(name: string, email: string) {\n * return db.insert(users).values(\n * collecting(\n * \"Account Information\",\n * { name, email }, // real ORM columns — returned unchanged\n * { name: \"Name\", email: \"Email address\" },\n * ),\n * );\n * }\n * ```\n */\nexport function collecting<T>(\n\t_category: string,\n\tvalue: T,\n\t_label: Partial<Record<keyof T, string>>,\n): T {\n\treturn value;\n}\n","import type { Jurisdiction, LegalBasis, UserRight } from \"@openpolicy/core\";\n\nexport const Compliance = {\n\tGDPR: {\n\t\tjurisdictions: [\"eu\"] as Jurisdiction[],\n\t\tlegalBasis: [\"legitimate_interests\"] as LegalBasis[],\n\t\tuserRights: [\n\t\t\t\"access\",\n\t\t\t\"rectification\",\n\t\t\t\"erasure\",\n\t\t\t\"portability\",\n\t\t\t\"restriction\",\n\t\t\t\"objection\",\n\t\t] as UserRight[],\n\t},\n\tCCPA: {\n\t\tjurisdictions: [\"ca\"] as Jurisdiction[],\n\t\tuserRights: [\n\t\t\t\"access\",\n\t\t\t\"erasure\",\n\t\t\t\"opt_out_sale\",\n\t\t\t\"non_discrimination\",\n\t\t] as UserRight[],\n\t},\n} as const;\n","import type { LegalBasis, UserRight } from \"@openpolicy/core\";\n\nexport const DataCategories = {\n\tAccountInfo: { \"Account Information\": [\"Name\", \"Email address\"] },\n\tSessionData: {\n\t\t\"Session Data\": [\"IP address\", \"User agent\", \"Browser type\"],\n\t},\n\tPaymentInfo: {\n\t\t\"Payment Information\": [\n\t\t\t\"Card last 4 digits\",\n\t\t\t\"Billing name\",\n\t\t\t\"Billing address\",\n\t\t],\n\t},\n\tUsageData: {\n\t\t\"Usage Data\": [\"Pages visited\", \"Features used\", \"Time spent\"],\n\t},\n\tDeviceInfo: {\n\t\t\"Device Information\": [\n\t\t\t\"Device type\",\n\t\t\t\"Operating system\",\n\t\t\t\"Browser version\",\n\t\t],\n\t},\n\tLocationData: { \"Location Data\": [\"Country\", \"City\", \"Timezone\"] },\n\tCommunications: {\n\t\tCommunications: [\"Email content\", \"Support tickets\"],\n\t},\n} as const;\n\nexport const Retention = {\n\tUntilAccountDeletion: \"Until account deletion\",\n\tUntilSessionExpiry: \"Until session expiry\",\n\tThirtyDays: \"30 days\",\n\tNinetyDays: \"90 days\",\n\tOneYear: \"1 year\",\n\tThreeYears: \"3 years\",\n\tAsRequiredByLaw: \"As required by applicable law\",\n} as const;\n\nexport const Rights = {\n\tAccess: \"access\",\n\tRectification: \"rectification\",\n\tErasure: \"erasure\",\n\tPortability: \"portability\",\n\tRestriction: \"restriction\",\n\tObjection: \"objection\",\n\tOptOutSale: \"opt_out_sale\",\n\tNonDiscrimination: \"non_discrimination\",\n} as const satisfies Record<string, UserRight>;\n\nexport const LegalBases = {\n\tConsent: \"consent\",\n\tContract: \"contract\",\n\tLegalObligation: \"legal_obligation\",\n\tVitalInterests: \"vital_interests\",\n\tPublicTask: \"public_task\",\n\tLegitimateInterests: \"legitimate_interests\",\n} as const satisfies Record<string, LegalBasis>;\n","type Provider = { name: string; purpose: string; policyUrl?: string };\n\nexport const Providers = {\n\t// Payments\n\tStripe: {\n\t\tname: \"Stripe\",\n\t\tpurpose: \"Payment processing\",\n\t\tpolicyUrl: \"https://stripe.com/privacy\",\n\t},\n\tPaddle: {\n\t\tname: \"Paddle\",\n\t\tpurpose: \"Payment processing and subscription management\",\n\t\tpolicyUrl: \"https://www.paddle.com/legal/privacy\",\n\t},\n\tLemonSqueezy: {\n\t\tname: \"Lemon Squeezy\",\n\t\tpurpose: \"Payment processing and subscription management\",\n\t\tpolicyUrl: \"https://www.lemonsqueezy.com/privacy\",\n\t},\n\tPayPal: {\n\t\tname: \"PayPal\",\n\t\tpurpose: \"Payment processing\",\n\t\tpolicyUrl: \"https://www.paypal.com/webapps/mpp/ua/privacy-full\",\n\t},\n\n\t// Analytics\n\tGoogleAnalytics: {\n\t\tname: \"Google Analytics\",\n\t\tpurpose: \"Usage analytics\",\n\t\tpolicyUrl: \"https://policies.google.com/privacy\",\n\t},\n\tPostHog: {\n\t\tname: \"PostHog\",\n\t\tpurpose: \"Product analytics and session recording\",\n\t\tpolicyUrl: \"https://posthog.com/privacy\",\n\t},\n\tPlausible: {\n\t\tname: \"Plausible Analytics\",\n\t\tpurpose: \"Privacy-friendly usage analytics\",\n\t\tpolicyUrl: \"https://plausible.io/privacy\",\n\t},\n\tMixpanel: {\n\t\tname: \"Mixpanel\",\n\t\tpurpose: \"Product analytics and event tracking\",\n\t\tpolicyUrl: \"https://mixpanel.com/legal/privacy-policy\",\n\t},\n\n\t// Infrastructure\n\tVercel: {\n\t\tname: \"Vercel\",\n\t\tpurpose: \"Hosting and deployment infrastructure\",\n\t\tpolicyUrl: \"https://vercel.com/legal/privacy-policy\",\n\t},\n\tCloudflare: {\n\t\tname: \"Cloudflare\",\n\t\tpurpose: \"CDN, DNS, and security services\",\n\t\tpolicyUrl: \"https://www.cloudflare.com/privacypolicy/\",\n\t},\n\tAWS: {\n\t\tname: \"Amazon Web Services\",\n\t\tpurpose: \"Cloud infrastructure and hosting\",\n\t\tpolicyUrl: \"https://aws.amazon.com/privacy/\",\n\t},\n\n\t// Auth\n\tAuth0: {\n\t\tname: \"Auth0\",\n\t\tpurpose: \"Authentication and identity management\",\n\t\tpolicyUrl: \"https://auth0.com/privacy\",\n\t},\n\tClerk: {\n\t\tname: \"Clerk\",\n\t\tpurpose: \"Authentication and user management\",\n\t\tpolicyUrl: \"https://clerk.com/privacy\",\n\t},\n\n\t// Email\n\tResend: {\n\t\tname: \"Resend\",\n\t\tpurpose: \"Transactional email delivery\",\n\t\tpolicyUrl: \"https://resend.com/legal/privacy-policy\",\n\t},\n\tPostmark: {\n\t\tname: \"Postmark\",\n\t\tpurpose: \"Transactional email delivery\",\n\t\tpolicyUrl: \"https://wildbit.com/privacy-policy\",\n\t},\n\tSendGrid: {\n\t\tname: \"SendGrid\",\n\t\tpurpose: \"Transactional email delivery\",\n\t\tpolicyUrl: \"https://www.twilio.com/en-us/legal/privacy\",\n\t},\n\tLoops: {\n\t\tname: \"Loops\",\n\t\tpurpose: \"Email marketing and automation\",\n\t\tpolicyUrl: \"https://loops.so/privacy\",\n\t},\n\n\t// Monitoring\n\tSentry: {\n\t\tname: \"Sentry\",\n\t\tpurpose: \"Error monitoring and performance tracking\",\n\t\tpolicyUrl: \"https://sentry.io/privacy/\",\n\t},\n\tDatadog: {\n\t\tname: \"Datadog\",\n\t\tpurpose: \"Infrastructure monitoring and observability\",\n\t\tpolicyUrl: \"https://www.datadoghq.com/legal/privacy/\",\n\t},\n} satisfies Record<string, Provider>;\n","/**\n * TODO\n */\nexport function thirdParty(\n\t_name: string,\n\t_purpose: string,\n\t_policyUrl: string,\n): void {\n\treturn;\n}\n","import type { OpenPolicyConfig } from \"@openpolicy/core\";\n\nexport type {\n\tCookiePolicyConfig,\n\tLegalBasis,\n\tOpenPolicyConfig,\n\tPrivacyPolicyConfig,\n\tTermsOfServiceConfig,\n\tUserRight,\n} from \"@openpolicy/core\";\n\nexport { dataCollected, thirdParties } from \"./auto-collected\";\nexport { collecting } from \"./collecting\";\nexport { Compliance } from \"./compliance\";\nexport { DataCategories, LegalBases, Retention, Rights } from \"./data\";\nexport { Providers } from \"./providers\";\nexport { thirdParty } from \"./third-parties\";\n\nexport function defineConfig(config: OpenPolicyConfig): OpenPolicyConfig {\n\treturn config;\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAkCA,SAAgB,WACf,WACA,OACA,QACI;AACJ,QAAO;;;;ACrCR,MAAa,aAAa;CACzB,MAAM;EACL,eAAe,CAAC,KAAK;EACrB,YAAY,CAAC,uBAAuB;EACpC,YAAY;GACX;GACA;GACA;GACA;GACA;GACA;GACA;EACD;CACD,MAAM;EACL,eAAe,CAAC,KAAK;EACrB,YAAY;GACX;GACA;GACA;GACA;GACA;EACD;CACD;;;ACtBD,MAAa,iBAAiB;CAC7B,aAAa,EAAE,uBAAuB,CAAC,QAAQ,gBAAgB,EAAE;CACjE,aAAa,EACZ,gBAAgB;EAAC;EAAc;EAAc;EAAe,EAC5D;CACD,aAAa,EACZ,uBAAuB;EACtB;EACA;EACA;EACA,EACD;CACD,WAAW,EACV,cAAc;EAAC;EAAiB;EAAiB;EAAa,EAC9D;CACD,YAAY,EACX,sBAAsB;EACrB;EACA;EACA;EACA,EACD;CACD,cAAc,EAAE,iBAAiB;EAAC;EAAW;EAAQ;EAAW,EAAE;CAClE,gBAAgB,EACf,gBAAgB,CAAC,iBAAiB,kBAAkB,EACpD;CACD;AAED,MAAa,YAAY;CACxB,sBAAsB;CACtB,oBAAoB;CACpB,YAAY;CACZ,YAAY;CACZ,SAAS;CACT,YAAY;CACZ,iBAAiB;CACjB;AAED,MAAa,SAAS;CACrB,QAAQ;CACR,eAAe;CACf,SAAS;CACT,aAAa;CACb,aAAa;CACb,WAAW;CACX,YAAY;CACZ,mBAAmB;CACnB;AAED,MAAa,aAAa;CACzB,SAAS;CACT,UAAU;CACV,iBAAiB;CACjB,gBAAgB;CAChB,YAAY;CACZ,qBAAqB;CACrB;;;ACxDD,MAAa,YAAY;CAExB,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,cAAc;EACb,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,iBAAiB;EAChB,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,SAAS;EACR,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,WAAW;EACV,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,UAAU;EACT,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,YAAY;EACX,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,KAAK;EACJ,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,OAAO;EACN,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,OAAO;EACN,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,UAAU;EACT,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,UAAU;EACT,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,OAAO;EACN,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,SAAS;EACR,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD;;;;;;AC1GD,SAAgB,WACf,OACA,UACA,YACO;;;ACWR,SAAgB,aAAa,QAA4C;AACxE,QAAO"}
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../src/collecting.ts","../src/compliance.ts","../src/data.ts","../src/providers.ts","../src/third-parties.ts","../src/index.ts"],"sourcesContent":["/**\n * Declares data collected at the point of storage. Returns `value` unchanged\n * at runtime — the Vite plugin / CLI static analyser (OP-152) will scan calls\n * to `collecting()` at build time and merge the declarations into the\n * compiled privacy policy.\n *\n * The third argument is a plain object literal whose **keys** are field names\n * matching your stored value (for convenient access without a typed callback)\n * and whose **values** are the human-readable labels used in the compiled\n * policy. Only the string values are used by the analyser; the object is\n * never evaluated at runtime. This shape lets you:\n * - keep `value` matching your ORM/table schema exactly,\n * - describe fields with friendly labels for the policy,\n * - omit fields from the policy by leaving them out of the label record\n * (e.g. `hashedPassword`).\n *\n * The category argument and the string values of the label record must be\n * string literals — dynamic values are silently skipped by the analyser.\n *\n * @example\n * ```ts\n * import { collecting } from \"@openpolicy/sdk\";\n *\n * export async function createUser(name: string, email: string) {\n * return db.insert(users).values(\n * collecting(\n * \"Account Information\",\n * { name, email }, // real ORM columns — returned unchanged\n * { name: \"Name\", email: \"Email address\" },\n * ),\n * );\n * }\n * ```\n */\nexport function collecting<T>(\n\t_category: string,\n\tvalue: T,\n\t_label: Partial<Record<keyof T, string>>,\n): T {\n\treturn value;\n}\n","import type { Jurisdiction, LegalBasis, UserRight } from \"@openpolicy/core\";\n\nexport const Compliance = {\n\tGDPR: {\n\t\tjurisdictions: [\"eu\"] as Jurisdiction[],\n\t\tlegalBasis: [\"legitimate_interests\"] as LegalBasis[],\n\t\tuserRights: [\n\t\t\t\"access\",\n\t\t\t\"rectification\",\n\t\t\t\"erasure\",\n\t\t\t\"portability\",\n\t\t\t\"restriction\",\n\t\t\t\"objection\",\n\t\t] as UserRight[],\n\t},\n\tCCPA: {\n\t\tjurisdictions: [\"ca\"] as Jurisdiction[],\n\t\tuserRights: [\n\t\t\t\"access\",\n\t\t\t\"erasure\",\n\t\t\t\"opt_out_sale\",\n\t\t\t\"non_discrimination\",\n\t\t] as UserRight[],\n\t},\n} as const;\n","import type { LegalBasis, UserRight } from \"@openpolicy/core\";\n\nexport const DataCategories = {\n\tAccountInfo: { \"Account Information\": [\"Name\", \"Email address\"] },\n\tSessionData: {\n\t\t\"Session Data\": [\"IP address\", \"User agent\", \"Browser type\"],\n\t},\n\tPaymentInfo: {\n\t\t\"Payment Information\": [\n\t\t\t\"Card last 4 digits\",\n\t\t\t\"Billing name\",\n\t\t\t\"Billing address\",\n\t\t],\n\t},\n\tUsageData: {\n\t\t\"Usage Data\": [\"Pages visited\", \"Features used\", \"Time spent\"],\n\t},\n\tDeviceInfo: {\n\t\t\"Device Information\": [\n\t\t\t\"Device type\",\n\t\t\t\"Operating system\",\n\t\t\t\"Browser version\",\n\t\t],\n\t},\n\tLocationData: { \"Location Data\": [\"Country\", \"City\", \"Timezone\"] },\n\tCommunications: {\n\t\tCommunications: [\"Email content\", \"Support tickets\"],\n\t},\n} as const;\n\nexport const Retention = {\n\tUntilAccountDeletion: \"Until account deletion\",\n\tUntilSessionExpiry: \"Until session expiry\",\n\tThirtyDays: \"30 days\",\n\tNinetyDays: \"90 days\",\n\tOneYear: \"1 year\",\n\tThreeYears: \"3 years\",\n\tAsRequiredByLaw: \"As required by applicable law\",\n} as const;\n\nexport const Rights = {\n\tAccess: \"access\",\n\tRectification: \"rectification\",\n\tErasure: \"erasure\",\n\tPortability: \"portability\",\n\tRestriction: \"restriction\",\n\tObjection: \"objection\",\n\tOptOutSale: \"opt_out_sale\",\n\tNonDiscrimination: \"non_discrimination\",\n} as const satisfies Record<string, UserRight>;\n\nexport const LegalBases = {\n\tConsent: \"consent\",\n\tContract: \"contract\",\n\tLegalObligation: \"legal_obligation\",\n\tVitalInterests: \"vital_interests\",\n\tPublicTask: \"public_task\",\n\tLegitimateInterests: \"legitimate_interests\",\n} as const satisfies Record<string, LegalBasis>;\n","type Provider = { name: string; purpose: string; policyUrl?: string };\n\nexport const Providers = {\n\t// Payments\n\tStripe: {\n\t\tname: \"Stripe\",\n\t\tpurpose: \"Payment processing\",\n\t\tpolicyUrl: \"https://stripe.com/privacy\",\n\t},\n\tPaddle: {\n\t\tname: \"Paddle\",\n\t\tpurpose: \"Payment processing and subscription management\",\n\t\tpolicyUrl: \"https://www.paddle.com/legal/privacy\",\n\t},\n\tLemonSqueezy: {\n\t\tname: \"Lemon Squeezy\",\n\t\tpurpose: \"Payment processing and subscription management\",\n\t\tpolicyUrl: \"https://www.lemonsqueezy.com/privacy\",\n\t},\n\tPayPal: {\n\t\tname: \"PayPal\",\n\t\tpurpose: \"Payment processing\",\n\t\tpolicyUrl: \"https://www.paypal.com/webapps/mpp/ua/privacy-full\",\n\t},\n\n\t// Analytics\n\tGoogleAnalytics: {\n\t\tname: \"Google Analytics\",\n\t\tpurpose: \"Usage analytics\",\n\t\tpolicyUrl: \"https://policies.google.com/privacy\",\n\t},\n\tPostHog: {\n\t\tname: \"PostHog\",\n\t\tpurpose: \"Product analytics and session recording\",\n\t\tpolicyUrl: \"https://posthog.com/privacy\",\n\t},\n\tPlausible: {\n\t\tname: \"Plausible Analytics\",\n\t\tpurpose: \"Privacy-friendly usage analytics\",\n\t\tpolicyUrl: \"https://plausible.io/privacy\",\n\t},\n\tMixpanel: {\n\t\tname: \"Mixpanel\",\n\t\tpurpose: \"Product analytics and event tracking\",\n\t\tpolicyUrl: \"https://mixpanel.com/legal/privacy-policy\",\n\t},\n\n\t// Infrastructure\n\tVercel: {\n\t\tname: \"Vercel\",\n\t\tpurpose: \"Hosting and deployment infrastructure\",\n\t\tpolicyUrl: \"https://vercel.com/legal/privacy-policy\",\n\t},\n\tCloudflare: {\n\t\tname: \"Cloudflare\",\n\t\tpurpose: \"CDN, DNS, and security services\",\n\t\tpolicyUrl: \"https://www.cloudflare.com/privacypolicy/\",\n\t},\n\tAWS: {\n\t\tname: \"Amazon Web Services\",\n\t\tpurpose: \"Cloud infrastructure and hosting\",\n\t\tpolicyUrl: \"https://aws.amazon.com/privacy/\",\n\t},\n\n\t// Auth\n\tAuth0: {\n\t\tname: \"Auth0\",\n\t\tpurpose: \"Authentication and identity management\",\n\t\tpolicyUrl: \"https://auth0.com/privacy\",\n\t},\n\tClerk: {\n\t\tname: \"Clerk\",\n\t\tpurpose: \"Authentication and user management\",\n\t\tpolicyUrl: \"https://clerk.com/privacy\",\n\t},\n\n\t// Email\n\tResend: {\n\t\tname: \"Resend\",\n\t\tpurpose: \"Transactional email delivery\",\n\t\tpolicyUrl: \"https://resend.com/legal/privacy-policy\",\n\t},\n\tPostmark: {\n\t\tname: \"Postmark\",\n\t\tpurpose: \"Transactional email delivery\",\n\t\tpolicyUrl: \"https://wildbit.com/privacy-policy\",\n\t},\n\tSendGrid: {\n\t\tname: \"SendGrid\",\n\t\tpurpose: \"Transactional email delivery\",\n\t\tpolicyUrl: \"https://www.twilio.com/en-us/legal/privacy\",\n\t},\n\tLoops: {\n\t\tname: \"Loops\",\n\t\tpurpose: \"Email marketing and automation\",\n\t\tpolicyUrl: \"https://loops.so/privacy\",\n\t},\n\n\t// Monitoring\n\tSentry: {\n\t\tname: \"Sentry\",\n\t\tpurpose: \"Error monitoring and performance tracking\",\n\t\tpolicyUrl: \"https://sentry.io/privacy/\",\n\t},\n\tDatadog: {\n\t\tname: \"Datadog\",\n\t\tpurpose: \"Infrastructure monitoring and observability\",\n\t\tpolicyUrl: \"https://www.datadoghq.com/legal/privacy/\",\n\t},\n} satisfies Record<string, Provider>;\n","export function thirdParty(\n\t_name: string,\n\t_purpose: string,\n\t_policyUrl: string,\n): void {\n\treturn;\n}\n","import type { OpenPolicyConfig } from \"@openpolicy/core\";\n\nexport type {\n\tCookiePolicyConfig,\n\tLegalBasis,\n\tOpenPolicyConfig,\n\tPrivacyPolicyConfig,\n\tTermsOfServiceConfig,\n\tUserRight,\n} from \"@openpolicy/core\";\n\nexport { dataCollected, thirdParties } from \"./auto-collected\";\nexport { collecting } from \"./collecting\";\nexport { Compliance } from \"./compliance\";\nexport { DataCategories, LegalBases, Retention, Rights } from \"./data\";\nexport { Providers } from \"./providers\";\nexport { thirdParty } from \"./third-parties\";\n\nexport function defineConfig(config: OpenPolicyConfig): OpenPolicyConfig {\n\treturn config;\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAkCA,SAAgB,WACf,WACA,OACA,QACI;AACJ,QAAO;;;;ACrCR,MAAa,aAAa;CACzB,MAAM;EACL,eAAe,CAAC,KAAK;EACrB,YAAY,CAAC,uBAAuB;EACpC,YAAY;GACX;GACA;GACA;GACA;GACA;GACA;GACA;EACD;CACD,MAAM;EACL,eAAe,CAAC,KAAK;EACrB,YAAY;GACX;GACA;GACA;GACA;GACA;EACD;CACD;;;ACtBD,MAAa,iBAAiB;CAC7B,aAAa,EAAE,uBAAuB,CAAC,QAAQ,gBAAgB,EAAE;CACjE,aAAa,EACZ,gBAAgB;EAAC;EAAc;EAAc;EAAe,EAC5D;CACD,aAAa,EACZ,uBAAuB;EACtB;EACA;EACA;EACA,EACD;CACD,WAAW,EACV,cAAc;EAAC;EAAiB;EAAiB;EAAa,EAC9D;CACD,YAAY,EACX,sBAAsB;EACrB;EACA;EACA;EACA,EACD;CACD,cAAc,EAAE,iBAAiB;EAAC;EAAW;EAAQ;EAAW,EAAE;CAClE,gBAAgB,EACf,gBAAgB,CAAC,iBAAiB,kBAAkB,EACpD;CACD;AAED,MAAa,YAAY;CACxB,sBAAsB;CACtB,oBAAoB;CACpB,YAAY;CACZ,YAAY;CACZ,SAAS;CACT,YAAY;CACZ,iBAAiB;CACjB;AAED,MAAa,SAAS;CACrB,QAAQ;CACR,eAAe;CACf,SAAS;CACT,aAAa;CACb,aAAa;CACb,WAAW;CACX,YAAY;CACZ,mBAAmB;CACnB;AAED,MAAa,aAAa;CACzB,SAAS;CACT,UAAU;CACV,iBAAiB;CACjB,gBAAgB;CAChB,YAAY;CACZ,qBAAqB;CACrB;;;ACxDD,MAAa,YAAY;CAExB,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,cAAc;EACb,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,iBAAiB;EAChB,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,SAAS;EACR,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,WAAW;EACV,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,UAAU;EACT,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,YAAY;EACX,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,KAAK;EACJ,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,OAAO;EACN,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,OAAO;EACN,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,UAAU;EACT,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,UAAU;EACT,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,OAAO;EACN,MAAM;EACN,SAAS;EACT,WAAW;EACX;CAGD,QAAQ;EACP,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD,SAAS;EACR,MAAM;EACN,SAAS;EACT,WAAW;EACX;CACD;;;AC7GD,SAAgB,WACf,OACA,UACA,YACO;;;ACcR,SAAgB,aAAa,QAA4C;AACxE,QAAO"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@openpolicy/sdk",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.20",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Public API for defining privacy policies with OpenPolicy",
|
|
6
6
|
"license": "GPL-3.0-only",
|
|
@@ -11,7 +11,8 @@
|
|
|
11
11
|
},
|
|
12
12
|
"files": [
|
|
13
13
|
"dist",
|
|
14
|
-
"README.md"
|
|
14
|
+
"README.md",
|
|
15
|
+
"skills"
|
|
15
16
|
],
|
|
16
17
|
"exports": {
|
|
17
18
|
".": {
|
|
@@ -28,6 +29,10 @@
|
|
|
28
29
|
"dependencies": {},
|
|
29
30
|
"devDependencies": {
|
|
30
31
|
"@openpolicy/core": "workspace:*",
|
|
31
|
-
"@openpolicy/tooling": "workspace:*"
|
|
32
|
-
|
|
32
|
+
"@openpolicy/tooling": "workspace:*",
|
|
33
|
+
"@tanstack/intent": "^0.0.29"
|
|
34
|
+
},
|
|
35
|
+
"keywords": [
|
|
36
|
+
"tanstack-intent"
|
|
37
|
+
]
|
|
33
38
|
}
|
|
@@ -0,0 +1,240 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: annotate-data-collection
|
|
3
|
+
description: >
|
|
4
|
+
Mark data collection points in source code with collecting(category, value,
|
|
5
|
+
labels) so the autoCollect() Vite plugin can populate privacy.dataCollected
|
|
6
|
+
automatically at build time via static AST analysis. All arguments must be
|
|
7
|
+
string literals. Spread the dataCollected sentinel from @openpolicy/sdk into
|
|
8
|
+
the config for plugin output to take effect.
|
|
9
|
+
type: core
|
|
10
|
+
library: openpolicy
|
|
11
|
+
library_version: "0.0.19"
|
|
12
|
+
requires:
|
|
13
|
+
- openpolicy/vite-setup
|
|
14
|
+
sources:
|
|
15
|
+
- jamiedavenport/openpolicy:packages/sdk/src/auto-collected.ts
|
|
16
|
+
- jamiedavenport/openpolicy:packages/vite-auto-collect/src/analyse.ts
|
|
17
|
+
---
|
|
18
|
+
|
|
19
|
+
This skill builds on openpolicy/vite-setup. Read it first.
|
|
20
|
+
|
|
21
|
+
## How it works
|
|
22
|
+
|
|
23
|
+
`collecting(category, value, labels)` is a **pass-through at runtime** — it returns `value` unchanged. Its purpose is to serve as a static marker. During a Vite build, `autoCollect()` scans your source files using oxc-parser, finds every `collecting()` call, and merges the extracted category/label data into the `dataCollected` virtual module exported from `@openpolicy/sdk`.
|
|
24
|
+
|
|
25
|
+
The scanned data only reaches your policy config if you import the `dataCollected` sentinel and spread it into `privacy.dataCollected`. Without the spread, all collected annotations are silently discarded.
|
|
26
|
+
|
|
27
|
+
**Critical constraint: every argument that the plugin reads must be a string literal.** The AST scanner does not evaluate expressions. Variables, template literals, and computed values are silently skipped with no warning.
|
|
28
|
+
|
|
29
|
+
## Setup
|
|
30
|
+
|
|
31
|
+
Install and wire `autoCollect()` first (see openpolicy/vite-setup). Then follow these three steps:
|
|
32
|
+
|
|
33
|
+
**Step 1 — Annotate a data collection point in your app code:**
|
|
34
|
+
|
|
35
|
+
```ts
|
|
36
|
+
// src/users/create.ts
|
|
37
|
+
import { collecting } from "@openpolicy/sdk";
|
|
38
|
+
|
|
39
|
+
export async function createUser(name: string, email: string) {
|
|
40
|
+
return db.insert(users).values(
|
|
41
|
+
collecting(
|
|
42
|
+
"Account Information", // category — must be a string literal
|
|
43
|
+
{ name, email }, // value — returned unchanged at runtime
|
|
44
|
+
{ name: "Name", email: "Email address" }, // labels — values must be string literals
|
|
45
|
+
),
|
|
46
|
+
);
|
|
47
|
+
}
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
**Step 2 — Spread the sentinel into your config:**
|
|
51
|
+
|
|
52
|
+
```ts
|
|
53
|
+
// openpolicy.ts
|
|
54
|
+
import { defineConfig, dataCollected } from "@openpolicy/sdk";
|
|
55
|
+
|
|
56
|
+
export default defineConfig({
|
|
57
|
+
company: {
|
|
58
|
+
name: "Acme",
|
|
59
|
+
legalName: "Acme, Inc.",
|
|
60
|
+
address: "123 Main St, San Francisco, CA 94105",
|
|
61
|
+
contact: "privacy@acme.com",
|
|
62
|
+
},
|
|
63
|
+
privacy: {
|
|
64
|
+
effectiveDate: "2026-01-01",
|
|
65
|
+
dataCollected: {
|
|
66
|
+
...dataCollected, // populated by autoCollect() at build time
|
|
67
|
+
// add manually-tracked categories here if needed
|
|
68
|
+
},
|
|
69
|
+
},
|
|
70
|
+
});
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
**Step 3 — Verify the plugin is active in vite.config.ts:**
|
|
74
|
+
|
|
75
|
+
```ts
|
|
76
|
+
// vite.config.ts
|
|
77
|
+
import { defineConfig } from "vite";
|
|
78
|
+
import { autoCollect } from "@openpolicy/vite-auto-collect";
|
|
79
|
+
|
|
80
|
+
export default defineConfig({
|
|
81
|
+
plugins: [autoCollect()],
|
|
82
|
+
});
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
At build time, `autoCollect()` scans `src/` for `collecting()` calls and injects the result into the `dataCollected` sentinel before your config module is evaluated.
|
|
86
|
+
|
|
87
|
+
## Core Patterns
|
|
88
|
+
|
|
89
|
+
### 1. Basic annotation
|
|
90
|
+
|
|
91
|
+
Wrap the value you are storing at any data collection point. The third argument maps your field names to human-readable policy labels. Fields you omit from the label record are not included in the policy.
|
|
92
|
+
|
|
93
|
+
```ts
|
|
94
|
+
import { collecting } from "@openpolicy/sdk";
|
|
95
|
+
|
|
96
|
+
// Database insert
|
|
97
|
+
const row = collecting(
|
|
98
|
+
"Contact Information",
|
|
99
|
+
{ email, phone },
|
|
100
|
+
{ email: "Email address", phone: "Phone number" },
|
|
101
|
+
);
|
|
102
|
+
await db.insert(contacts).values(row);
|
|
103
|
+
|
|
104
|
+
// Form submission
|
|
105
|
+
const payload = collecting(
|
|
106
|
+
"Support Request",
|
|
107
|
+
{ subject, body, userId },
|
|
108
|
+
{ subject: "Subject line", body: "Message content" },
|
|
109
|
+
// userId omitted — not included in the policy
|
|
110
|
+
);
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
### 2. Using DataCategories presets
|
|
114
|
+
|
|
115
|
+
`DataCategories` provides preset category names and label arrays aligned with common GDPR/CCPA categories. Use these to keep your annotations consistent with the generated policy text.
|
|
116
|
+
|
|
117
|
+
```ts
|
|
118
|
+
import { collecting, DataCategories } from "@openpolicy/sdk";
|
|
119
|
+
|
|
120
|
+
// DataCategories.AccountInfo = { "Account Information": ["Name", "Email address"] }
|
|
121
|
+
// Use the category string from the preset key
|
|
122
|
+
const user = collecting(
|
|
123
|
+
"Account Information",
|
|
124
|
+
{ name, email },
|
|
125
|
+
{ name: "Name", email: "Email address" },
|
|
126
|
+
);
|
|
127
|
+
|
|
128
|
+
// DataCategories.SessionData = { "Session Data": ["IP address", "User agent", "Browser type"] }
|
|
129
|
+
const session = collecting(
|
|
130
|
+
"Session Data",
|
|
131
|
+
{ ip, userAgent },
|
|
132
|
+
{ ip: "IP address", userAgent: "User agent" },
|
|
133
|
+
);
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
Available presets: `AccountInfo`, `SessionData`, `PaymentInfo`, `UsageData`, `DeviceInfo`, `LocationData`, `Communications`.
|
|
137
|
+
|
|
138
|
+
Note: `DataCategories` values are objects for spreading into `dataCollected` manually; the string keys are the category names to use in `collecting()` calls.
|
|
139
|
+
|
|
140
|
+
### 3. Spreading the sentinel into config
|
|
141
|
+
|
|
142
|
+
The sentinel must be spread with `...dataCollected` — not assigned directly. You can add manually-tracked categories alongside the auto-collected ones.
|
|
143
|
+
|
|
144
|
+
```ts
|
|
145
|
+
import { defineConfig, dataCollected } from "@openpolicy/sdk";
|
|
146
|
+
|
|
147
|
+
export default defineConfig({
|
|
148
|
+
company: { /* ... */ },
|
|
149
|
+
privacy: {
|
|
150
|
+
effectiveDate: "2026-01-01",
|
|
151
|
+
dataCollected: {
|
|
152
|
+
...dataCollected, // auto-collected at build time
|
|
153
|
+
"Analytics": ["Page views", "Click events"], // manually declared
|
|
154
|
+
},
|
|
155
|
+
jurisdictions: ["eu", "us"],
|
|
156
|
+
legalBasis: "legitimate_interests",
|
|
157
|
+
userRights: ["access", "erasure", "portability"],
|
|
158
|
+
},
|
|
159
|
+
});
|
|
160
|
+
```
|
|
161
|
+
|
|
162
|
+
## Common Mistakes
|
|
163
|
+
|
|
164
|
+
### MISTAKE 1 (HIGH) — Dynamic values in `collecting()` arguments
|
|
165
|
+
|
|
166
|
+
The plugin uses static AST analysis and only recognises string literal nodes. Any non-literal — a variable, template literal, or computed expression — causes the entire call to be silently skipped. No warning is emitted.
|
|
167
|
+
|
|
168
|
+
```ts
|
|
169
|
+
// WRONG: variable in category position — silently skipped
|
|
170
|
+
const category = "Account Information";
|
|
171
|
+
collecting(category, { name, email }, { name: "Name", email: "Email address" });
|
|
172
|
+
|
|
173
|
+
// WRONG: template literal — silently skipped
|
|
174
|
+
collecting(`${"Account"} Information`, { name, email }, { name: "Name", email: "Email address" });
|
|
175
|
+
|
|
176
|
+
// WRONG: dynamic label value — silently skipped
|
|
177
|
+
const label = "Email address";
|
|
178
|
+
collecting("Account Information", { name, email }, { name: "Name", email: label });
|
|
179
|
+
```
|
|
180
|
+
|
|
181
|
+
```ts
|
|
182
|
+
// CORRECT: every argument the plugin reads is a string literal
|
|
183
|
+
collecting(
|
|
184
|
+
"Account Information",
|
|
185
|
+
{ name, email },
|
|
186
|
+
{ name: "Name", email: "Email address" },
|
|
187
|
+
);
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
The `value` argument (second position) is never read by the scanner and can be any expression.
|
|
191
|
+
|
|
192
|
+
### MISTAKE 2 (HIGH) — Not spreading `dataCollected` into the config
|
|
193
|
+
|
|
194
|
+
Even with `collecting()` calls throughout your codebase and `autoCollect()` wired up in Vite, the plugin output has no effect unless you import `dataCollected` from `@openpolicy/sdk` and spread it into `privacy.dataCollected`. Without the spread the sentinel is an empty object `{}` and the policy compiles with no auto-collected data.
|
|
195
|
+
|
|
196
|
+
```ts
|
|
197
|
+
// WRONG: sentinel not imported or spread
|
|
198
|
+
export default defineConfig({
|
|
199
|
+
privacy: {
|
|
200
|
+
dataCollected: {
|
|
201
|
+
"Account Information": ["Email"], // only manually-declared items appear
|
|
202
|
+
},
|
|
203
|
+
},
|
|
204
|
+
});
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
```ts
|
|
208
|
+
// CORRECT: sentinel imported and spread
|
|
209
|
+
import { defineConfig, dataCollected } from "@openpolicy/sdk";
|
|
210
|
+
|
|
211
|
+
export default defineConfig({
|
|
212
|
+
privacy: {
|
|
213
|
+
dataCollected: {
|
|
214
|
+
...dataCollected, // auto-collected entries merged here
|
|
215
|
+
"Account Information": ["Email"], // any manual additions
|
|
216
|
+
},
|
|
217
|
+
},
|
|
218
|
+
});
|
|
219
|
+
```
|
|
220
|
+
|
|
221
|
+
### MISTAKE 3 (MEDIUM) — Calling `collecting()` with fewer than 3 arguments
|
|
222
|
+
|
|
223
|
+
The plugin requires all three positional arguments: `category`, `value`, and `labels`. Calls with fewer than 3 arguments are silently skipped by the scanner. There is no runtime error because `collecting()` is a pass-through — it still returns `value` — but the call is never recorded in the policy.
|
|
224
|
+
|
|
225
|
+
```ts
|
|
226
|
+
// WRONG: missing labels argument — silently skipped by plugin
|
|
227
|
+
collecting("Account Information", { name, email });
|
|
228
|
+
|
|
229
|
+
// WRONG: only one argument — silently skipped
|
|
230
|
+
collecting("Account Information");
|
|
231
|
+
```
|
|
232
|
+
|
|
233
|
+
```ts
|
|
234
|
+
// CORRECT: all three arguments present
|
|
235
|
+
collecting(
|
|
236
|
+
"Account Information",
|
|
237
|
+
{ name, email },
|
|
238
|
+
{ name: "Name", email: "Email address" },
|
|
239
|
+
);
|
|
240
|
+
```
|
|
@@ -0,0 +1,237 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: annotate-third-parties
|
|
3
|
+
description: >
|
|
4
|
+
Mark third-party service dependencies in source code using thirdParty() so
|
|
5
|
+
the autoCollect() Vite plugin can populate the thirdParties sentinel for the
|
|
6
|
+
privacy policy config. Covers manual annotation, usePackageJson auto-detection
|
|
7
|
+
from the KNOWN_PACKAGES registry, combining both approaches, and the Providers
|
|
8
|
+
preset as a static alternative.
|
|
9
|
+
type: core
|
|
10
|
+
library: openpolicy
|
|
11
|
+
library_version: "0.0.19"
|
|
12
|
+
requires:
|
|
13
|
+
- openpolicy/vite-setup
|
|
14
|
+
sources:
|
|
15
|
+
- jamiedavenport/openpolicy:packages/sdk/src/third-parties.ts
|
|
16
|
+
- jamiedavenport/openpolicy:packages/vite-auto-collect/src/known-packages.ts
|
|
17
|
+
---
|
|
18
|
+
|
|
19
|
+
This skill builds on openpolicy/vite-setup. Read it first.
|
|
20
|
+
|
|
21
|
+
## How It Works
|
|
22
|
+
|
|
23
|
+
`thirdParty()` is a **runtime no-op**. It is a build-time marker — `autoCollect()` scans source files statically via `oxc-parser` and extracts the three string literal arguments. The plugin then populates the `thirdParties` sentinel exported from `@openpolicy/sdk`. Without the plugin, `thirdParty()` calls have no effect whatsoever.
|
|
24
|
+
|
|
25
|
+
The populated sentinel must be spread into `privacy.thirdParties` in the config file. Without the spread, the plugin output is discarded and the policy renders with no third parties listed.
|
|
26
|
+
|
|
27
|
+
## Setup
|
|
28
|
+
|
|
29
|
+
Three moving parts must all be in place:
|
|
30
|
+
|
|
31
|
+
**1. `vite.config.ts` — enable the plugin**
|
|
32
|
+
|
|
33
|
+
```ts
|
|
34
|
+
import { defineConfig } from "vite";
|
|
35
|
+
import { autoCollect } from "@openpolicy/vite-auto-collect";
|
|
36
|
+
|
|
37
|
+
export default defineConfig({
|
|
38
|
+
plugins: [
|
|
39
|
+
autoCollect({
|
|
40
|
+
thirdParties: { usePackageJson: true }, // optional — see below
|
|
41
|
+
}),
|
|
42
|
+
],
|
|
43
|
+
});
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
**2. Source file — annotate next to the usage**
|
|
47
|
+
|
|
48
|
+
```ts
|
|
49
|
+
import { thirdParty } from "@openpolicy/sdk";
|
|
50
|
+
|
|
51
|
+
// Place next to where you initialise or use the third-party SDK
|
|
52
|
+
thirdParty("Stripe", "Payment processing", "https://stripe.com/privacy");
|
|
53
|
+
|
|
54
|
+
// ... rest of your Stripe integration
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
**3. `openpolicy.ts` — spread the sentinel into config**
|
|
58
|
+
|
|
59
|
+
```ts
|
|
60
|
+
import { defineConfig, thirdParties } from "@openpolicy/sdk";
|
|
61
|
+
|
|
62
|
+
export default defineConfig({
|
|
63
|
+
company: {
|
|
64
|
+
name: "Acme",
|
|
65
|
+
legalName: "Acme, Inc.",
|
|
66
|
+
address: "123 Main St, San Francisco, CA 94105",
|
|
67
|
+
contact: "privacy@acme.com",
|
|
68
|
+
},
|
|
69
|
+
privacy: {
|
|
70
|
+
effectiveDate: "2026-01-01",
|
|
71
|
+
thirdParties: [...thirdParties],
|
|
72
|
+
},
|
|
73
|
+
});
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
## Core Patterns
|
|
77
|
+
|
|
78
|
+
### 1. Manual thirdParty() annotation
|
|
79
|
+
|
|
80
|
+
Call `thirdParty(name, purpose, policyUrl)` with three string literals next to wherever you initialise the third-party integration. All three arguments must be string literals — dynamic values are silently skipped by the static analyser.
|
|
81
|
+
|
|
82
|
+
```ts
|
|
83
|
+
import { thirdParty } from "@openpolicy/sdk";
|
|
84
|
+
|
|
85
|
+
// Correct: all string literals
|
|
86
|
+
thirdParty("Intercom", "Customer messaging", "https://www.intercom.com/legal/privacy");
|
|
87
|
+
|
|
88
|
+
// Wrong: variable — silently skipped at build time
|
|
89
|
+
const name = "Intercom";
|
|
90
|
+
thirdParty(name, "Customer messaging", "https://www.intercom.com/legal/privacy");
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
Deduplication is by `name` — the first occurrence wins when files are walked in sorted alphabetical order. Calling `thirdParty()` with the same name from multiple files is safe.
|
|
94
|
+
|
|
95
|
+
### 2. usePackageJson auto-detection
|
|
96
|
+
|
|
97
|
+
`autoCollect({ thirdParties: { usePackageJson: true } })` reads `package.json` at build time and cross-references every entry in `dependencies` and `devDependencies` against the built-in KNOWN_PACKAGES registry. Matched packages are merged into `thirdParties` automatically, with deduplication by service name.
|
|
98
|
+
|
|
99
|
+
This is the fastest way to cover common services (Stripe, Sentry, PostHog, Vercel, etc.) without any source annotations.
|
|
100
|
+
|
|
101
|
+
```ts
|
|
102
|
+
// vite.config.ts
|
|
103
|
+
autoCollect({ thirdParties: { usePackageJson: true } })
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
See [references/known-packages.md](references/known-packages.md) for the full list of ~30 auto-detected packages.
|
|
107
|
+
|
|
108
|
+
### 3. Combining both approaches
|
|
109
|
+
|
|
110
|
+
`thirdParty()` annotations and `usePackageJson` are merged at build time. The plugin deduplicates by service name — `thirdParty()` entries from source files are added first (sorted file order), then package.json detections fill in any remaining services not already seen.
|
|
111
|
+
|
|
112
|
+
Use this combination when:
|
|
113
|
+
- Most services are covered by the KNOWN_PACKAGES registry (`usePackageJson: true`)
|
|
114
|
+
- A few services are not in the registry and need explicit `thirdParty()` calls
|
|
115
|
+
|
|
116
|
+
```ts
|
|
117
|
+
// vite.config.ts
|
|
118
|
+
autoCollect({ thirdParties: { usePackageJson: true } })
|
|
119
|
+
|
|
120
|
+
// src/lib/custom-analytics.ts
|
|
121
|
+
import { thirdParty } from "@openpolicy/sdk";
|
|
122
|
+
thirdParty("Fathom Analytics", "Privacy-friendly web analytics", "https://usefathom.com/privacy");
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
```ts
|
|
126
|
+
// openpolicy.ts — one spread covers both sources
|
|
127
|
+
import { defineConfig, thirdParties } from "@openpolicy/sdk";
|
|
128
|
+
|
|
129
|
+
export default defineConfig({
|
|
130
|
+
privacy: {
|
|
131
|
+
thirdParties: [...thirdParties],
|
|
132
|
+
},
|
|
133
|
+
});
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
### 4. Providers presets as a static alternative
|
|
137
|
+
|
|
138
|
+
`Providers` from `@openpolicy/sdk` is a collection of pre-filled third-party objects for common services. Use this when you want to declare third parties statically in `openpolicy.ts` without any source annotations or plugin scanning.
|
|
139
|
+
|
|
140
|
+
```ts
|
|
141
|
+
import { defineConfig, Providers } from "@openpolicy/sdk";
|
|
142
|
+
|
|
143
|
+
export default defineConfig({
|
|
144
|
+
privacy: {
|
|
145
|
+
thirdParties: [
|
|
146
|
+
Providers.Stripe,
|
|
147
|
+
Providers.Sentry,
|
|
148
|
+
Providers.Vercel,
|
|
149
|
+
{ name: "Custom Service", purpose: "Internal logging", policyUrl: "https://example.com/privacy" },
|
|
150
|
+
],
|
|
151
|
+
},
|
|
152
|
+
});
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
Available presets: `Stripe`, `Paddle`, `LemonSqueezy`, `PayPal`, `GoogleAnalytics`, `PostHog`, `Plausible`, `Mixpanel`, `Vercel`, `Cloudflare`, `AWS`, `Auth0`, `Clerk`, `Resend`, `Postmark`, `SendGrid`, `Loops`, `Sentry`, `Datadog`.
|
|
156
|
+
|
|
157
|
+
Note: when using `Providers` statically, you can still spread `thirdParties` alongside it to capture any additional auto-collected services:
|
|
158
|
+
|
|
159
|
+
```ts
|
|
160
|
+
privacy: {
|
|
161
|
+
thirdParties: [...thirdParties, Providers.Cloudflare],
|
|
162
|
+
}
|
|
163
|
+
```
|
|
164
|
+
|
|
165
|
+
## Common Mistakes
|
|
166
|
+
|
|
167
|
+
### HIGH — Using thirdParty() without the autoCollect() plugin and expecting a runtime effect
|
|
168
|
+
|
|
169
|
+
`thirdParty()` is defined as a no-op function that immediately returns `undefined`. It has no runtime behaviour. The only way it produces output in the policy is when `autoCollect()` is present in `vite.config.ts` and scans the file at build time.
|
|
170
|
+
|
|
171
|
+
```ts
|
|
172
|
+
// WRONG: calling thirdParty() and expecting it to affect the policy at runtime
|
|
173
|
+
import { thirdParty } from "@openpolicy/sdk";
|
|
174
|
+
thirdParty("Stripe", "Payment processing", "https://stripe.com/privacy");
|
|
175
|
+
// Without autoCollect() in vite.config.ts, this does nothing
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
```ts
|
|
179
|
+
// Correct: autoCollect() in vite.config.ts is the required prerequisite
|
|
180
|
+
// vite.config.ts
|
|
181
|
+
import { autoCollect } from "@openpolicy/vite-auto-collect";
|
|
182
|
+
export default defineConfig({ plugins: [autoCollect()] });
|
|
183
|
+
|
|
184
|
+
// src/lib/stripe.ts — scanned at build time by the plugin
|
|
185
|
+
import { thirdParty } from "@openpolicy/sdk";
|
|
186
|
+
thirdParty("Stripe", "Payment processing", "https://stripe.com/privacy");
|
|
187
|
+
```
|
|
188
|
+
|
|
189
|
+
### HIGH — Not spreading thirdParties sentinel into privacy.thirdParties
|
|
190
|
+
|
|
191
|
+
Even when `autoCollect()` scans the source and populates the sentinel, the populated value is discarded unless it is imported and spread into `privacy.thirdParties` in the config. The privacy policy then renders with an empty third-party section, which may be legally invalid.
|
|
192
|
+
|
|
193
|
+
```ts
|
|
194
|
+
// WRONG: thirdParties not imported or spread
|
|
195
|
+
export default defineConfig({
|
|
196
|
+
privacy: {
|
|
197
|
+
thirdParties: [], // static empty array, discards plugin output
|
|
198
|
+
},
|
|
199
|
+
});
|
|
200
|
+
```
|
|
201
|
+
|
|
202
|
+
```ts
|
|
203
|
+
// Correct
|
|
204
|
+
import { defineConfig, thirdParties } from "@openpolicy/sdk";
|
|
205
|
+
|
|
206
|
+
export default defineConfig({
|
|
207
|
+
privacy: {
|
|
208
|
+
thirdParties: [...thirdParties],
|
|
209
|
+
// or combine with static entries:
|
|
210
|
+
// thirdParties: [...thirdParties, Providers.Cloudflare],
|
|
211
|
+
},
|
|
212
|
+
});
|
|
213
|
+
```
|
|
214
|
+
|
|
215
|
+
### MEDIUM — Not enabling usePackageJson when known packages are used
|
|
216
|
+
|
|
217
|
+
The KNOWN_PACKAGES registry covers ~30 common npm packages. Without `usePackageJson: true`, packages like `@sentry/browser`, `posthog-js`, or `@stripe/stripe-js` are not auto-detected and must each be annotated manually with `thirdParty()`. Enabling the option costs nothing and eliminates this annotation burden for any covered package.
|
|
218
|
+
|
|
219
|
+
```ts
|
|
220
|
+
// WRONG: usePackageJson not enabled — known packages not auto-detected
|
|
221
|
+
autoCollect()
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
```ts
|
|
225
|
+
// Correct
|
|
226
|
+
autoCollect({ thirdParties: { usePackageJson: true } })
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
## References
|
|
230
|
+
|
|
231
|
+
- [Known packages registry](references/known-packages.md) — full table of npm packages auto-detected by `usePackageJson: true`
|
|
232
|
+
- `packages/sdk/src/third-parties.ts` — thirdParty() implementation (runtime no-op)
|
|
233
|
+
- `packages/sdk/src/providers.ts` — Providers preset objects
|
|
234
|
+
- `packages/sdk/src/auto-collected.ts` — thirdParties sentinel definition
|
|
235
|
+
- `packages/vite-auto-collect/src/index.ts` — autoCollect() plugin, AutoCollectOptions type
|
|
236
|
+
- `packages/vite-auto-collect/src/analyse.ts` — static AST extraction logic
|
|
237
|
+
- `packages/vite-auto-collect/src/known-packages.ts` — KNOWN_PACKAGES registry source
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
# Known Packages Registry
|
|
2
|
+
|
|
3
|
+
These npm package names are auto-detected when `usePackageJson: true` is set in `autoCollect()`. The plugin reads `dependencies` and `devDependencies` from the project root `package.json` and matches entries against this registry. Multiple package names can map to the same service — deduplication is by service name, first match wins.
|
|
4
|
+
|
|
5
|
+
| npm package | Service name | Purpose |
|
|
6
|
+
|---|---|---|
|
|
7
|
+
| `stripe` | Stripe | Payment processing |
|
|
8
|
+
| `@stripe/stripe-js` | Stripe | Payment processing |
|
|
9
|
+
| `braintree` | Braintree | Payment processing |
|
|
10
|
+
| `@braintree/browser-drop-in` | Braintree | Payment processing |
|
|
11
|
+
| `@sentry/browser` | Sentry | Error tracking |
|
|
12
|
+
| `@sentry/node` | Sentry | Error tracking |
|
|
13
|
+
| `@sentry/nextjs` | Sentry | Error tracking |
|
|
14
|
+
| `@sentry/react` | Sentry | Error tracking |
|
|
15
|
+
| `@sentry/vue` | Sentry | Error tracking |
|
|
16
|
+
| `@datadog/browser-rum` | Datadog | Monitoring |
|
|
17
|
+
| `dd-trace` | Datadog | Monitoring |
|
|
18
|
+
| `posthog-js` | PostHog | Product analytics |
|
|
19
|
+
| `posthog-node` | PostHog | Product analytics |
|
|
20
|
+
| `mixpanel-browser` | Mixpanel | Product analytics |
|
|
21
|
+
| `@segment/analytics-next` | Segment | Customer data platform |
|
|
22
|
+
| `@amplitude/analytics-browser` | Amplitude | Product analytics |
|
|
23
|
+
| `amplitude-js` | Amplitude | Product analytics |
|
|
24
|
+
| `@vercel/analytics` | Vercel Analytics | Web analytics |
|
|
25
|
+
| `plausible-tracker` | Plausible | Web analytics |
|
|
26
|
+
| `logrocket` | LogRocket | Session recording |
|
|
27
|
+
| `@hotjar/browser` | Hotjar | Session recording |
|
|
28
|
+
| `resend` | Resend | Transactional email |
|
|
29
|
+
| `@sendgrid/mail` | SendGrid | Transactional email |
|
|
30
|
+
| `intercom-client` | Intercom | Customer messaging |
|
|
31
|
+
| `@intercom/messenger-js-sdk` | Intercom | Customer messaging |
|
|
32
|
+
|
|
33
|
+
## Services not in the registry
|
|
34
|
+
|
|
35
|
+
For services not listed here, use `thirdParty()` source annotations or the `Providers` preset constants from `@openpolicy/sdk`. See the main skill file for examples.
|
|
36
|
+
|
|
37
|
+
The registry source is at `packages/vite-auto-collect/src/known-packages.ts`.
|