@frontfriend/sdk 1.2.3 → 1.2.4

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.
@@ -1 +1 @@
1
- var j=(n,e)=>()=>(e||n((e={exports:{}}).exports,e),e.exports);var S=j((q,F)=>{F.exports={name:"@frontfriend/sdk",version:"1.2.3"}});var C=j(($,b)=>{var{name:w}=S();b.exports={PACKAGE_NAME:w}});var{PACKAGE_NAME:m}=C(),u=require("fs"),E=require("http"),O=require("https"),i=require("path"),g=["contracts","tokens","components"],T=["app/globals.css","src/app/globals.css","styles/globals.css","src/styles/globals.css","src/styles.css","src/index.css","src/style.css"],k={next:["next.config.js","next.config.mjs","next.config.ts"],vite:["vite.config.ts","vite.config.js","vite.config.mts","vite.config.mjs"]},x=["primereact","@mui/material","antd","@chakra-ui/react","@mantine/core","@fluentui/react"],I=["style-dictionary","@tokens-studio/sd-transforms","@vanilla-extract/css","styled-components","@emotion/react"];function A(n){try{return JSON.parse(u.readFileSync(n,"utf8"))}catch{return{}}}function h(n){if(n===void 0)return null;if(!Array.isArray(n)){let t=new Error("`adopt` in frontfriend.config.js must be an array.");throw t.code="FRONTFRIEND_CONFIG_VALIDATION",t}let e=n.filter(t=>!g.includes(t));if(e.length>0){let t=new Error(`Unknown Frontfriend adoption level: ${e.join(", ")}.`);throw t.code="FRONTFRIEND_CONFIG_VALIDATION",t}let o=n.includes("components")?2:n.includes("tokens")?1:0;return g.slice(0,o+1)}function _(n){for(let[e,o]of Object.entries(k)){let t=o.find(s=>u.existsSync(i.join(n,s)));if(!t)continue;let r=u.readFileSync(i.join(n,t),"utf8");return{buildTool:e,present:r.includes(`${m}/${e}`)}}return{buildTool:null,present:!1}}function v(n){let e=[i.join(n,"components","ui"),i.join(n,"src","components","ui"),i.join(n,"app","components","ui")].filter(r=>u.existsSync(r)),o=new Set;function t(r){for(let s of u.readdirSync(r,{withFileTypes:!0})){let c=i.join(r,s.name);if(s.isDirectory())t(c);else if(/\.(js|jsx|ts|tsx|vue)$/.test(s.name)){if(!u.readFileSync(c,"utf8").includes(m))continue;let a=i.basename(s.name,i.extname(s.name));o.add(a.toLowerCase()==="index"?i.basename(r):a.toLowerCase())}}}return e.forEach(t),[...o].sort()}function P(n){let e=A(i.join(n,"package.json")),o={...e.dependencies||{},...e.devDependencies||{}},t=o.tailwindcss||null,s=[A(i.join(n,"components.json"))?.tailwind?.css,...T].filter(Boolean).find(a=>u.existsSync(i.join(n,a))),c=s?u.readFileSync(i.join(n,s),"utf8"):"",l=I.filter(a=>o[a]);return!l.length&&/:root[\s\S]*--(?:color|spacing|font|radius)-[\w-]+\s*:/.test(c)&&!c.includes(`${m}/theme.css`)&&l.push("css-custom-properties"),{nativeTokens:{present:c.includes("/* Frontfriend managed native tokens: start */"),file:s||null},tailwind:{present:!!t,version:t,major:t&&Number((String(t).match(/\d+/)||[])[0])||null},componentsJson:u.existsSync(i.join(n,"components.json")),themeImport:{present:c.includes(`${m}/theme.css`)||/@import\s+["'][^"']*node_modules\/\.cache\/frontfriend\/theme\.css["']/.test(c),file:s||null},plugin:_(n),frontfriendComponents:v(n),foreignComponentLibraries:x.filter(a=>o[a]),foreignTokenSystems:l}}function D(n,e){let o=h(n)||g,t=o.includes("tokens"),r=o.includes("components"),s=[];return t&&!e.themeImport.present&&!e.nativeTokens?.present&&s.push("Config adopts tokens, but the Frontfriend theme import was not observed."),!t&&e.themeImport.present&&s.push("Frontfriend tokens are present in CSS but are not adopted in config."),r&&!e.componentsJson&&s.push("Config adopts components, but components.json was not observed."),!r&&e.frontfriendComponents.length>0&&s.push("Frontfriend components are installed but are not adopted in config."),s}function L({apiUrl:n,token:e,ffId:o,name:t,adopt:r,observed:s,framework:c,primitive:l}){if(!n||!e||!o||!t||!c||l===void 0)return Promise.resolve({reported:!1,unavailable:!0});let a=new URL("/api/apps/sync",n),y=JSON.stringify({ffId:o,name:t,adopt:h(r),observed:s,runtime:"sdk",framework:c,primitive:l}),N=a.protocol==="https:"?O:E;return new Promise(d=>{let f=N.request(a,{method:"POST",headers:{authorization:`Bearer ${e}`,"content-type":"application/json","content-length":Buffer.byteLength(y)}},p=>{p.resume(),p.on("end",()=>{p.statusCode>=200&&p.statusCode<300?d({reported:!0,unavailable:!1}):d({reported:!1,unavailable:!0})})});f.on("error",()=>d({reported:!1,unavailable:!0})),f.setTimeout(1500,()=>{f.destroy(),d({reported:!1,unavailable:!0})}),f.end(y)})}module.exports={ADOPTION_LEVELS:g,normalizeAdopt:h,probeAdoption:P,adoptionWarnings:D,reportAdoption:L};
1
+ var j=(n,e)=>()=>(e||n((e={exports:{}}).exports,e),e.exports);var S=j((q,F)=>{F.exports={name:"@frontfriend/sdk",version:"1.2.4"}});var C=j(($,b)=>{var{name:w}=S();b.exports={PACKAGE_NAME:w}});var{PACKAGE_NAME:m}=C(),u=require("fs"),E=require("http"),O=require("https"),i=require("path"),g=["contracts","tokens","components"],T=["app/globals.css","src/app/globals.css","styles/globals.css","src/styles/globals.css","src/styles.css","src/index.css","src/style.css"],k={next:["next.config.js","next.config.mjs","next.config.ts"],vite:["vite.config.ts","vite.config.js","vite.config.mts","vite.config.mjs"]},x=["primereact","@mui/material","antd","@chakra-ui/react","@mantine/core","@fluentui/react"],I=["style-dictionary","@tokens-studio/sd-transforms","@vanilla-extract/css","styled-components","@emotion/react"];function A(n){try{return JSON.parse(u.readFileSync(n,"utf8"))}catch{return{}}}function h(n){if(n===void 0)return null;if(!Array.isArray(n)){let t=new Error("`adopt` in frontfriend.config.js must be an array.");throw t.code="FRONTFRIEND_CONFIG_VALIDATION",t}let e=n.filter(t=>!g.includes(t));if(e.length>0){let t=new Error(`Unknown Frontfriend adoption level: ${e.join(", ")}.`);throw t.code="FRONTFRIEND_CONFIG_VALIDATION",t}let o=n.includes("components")?2:n.includes("tokens")?1:0;return g.slice(0,o+1)}function _(n){for(let[e,o]of Object.entries(k)){let t=o.find(s=>u.existsSync(i.join(n,s)));if(!t)continue;let r=u.readFileSync(i.join(n,t),"utf8");return{buildTool:e,present:r.includes(`${m}/${e}`)}}return{buildTool:null,present:!1}}function v(n){let e=[i.join(n,"components","ui"),i.join(n,"src","components","ui"),i.join(n,"app","components","ui")].filter(r=>u.existsSync(r)),o=new Set;function t(r){for(let s of u.readdirSync(r,{withFileTypes:!0})){let c=i.join(r,s.name);if(s.isDirectory())t(c);else if(/\.(js|jsx|ts|tsx|vue)$/.test(s.name)){if(!u.readFileSync(c,"utf8").includes(m))continue;let a=i.basename(s.name,i.extname(s.name));o.add(a.toLowerCase()==="index"?i.basename(r):a.toLowerCase())}}}return e.forEach(t),[...o].sort()}function P(n){let e=A(i.join(n,"package.json")),o={...e.dependencies||{},...e.devDependencies||{}},t=o.tailwindcss||null,s=[A(i.join(n,"components.json"))?.tailwind?.css,...T].filter(Boolean).find(a=>u.existsSync(i.join(n,a))),c=s?u.readFileSync(i.join(n,s),"utf8"):"",l=I.filter(a=>o[a]);return!l.length&&/:root[\s\S]*--(?:color|spacing|font|radius)-[\w-]+\s*:/.test(c)&&!c.includes(`${m}/theme.css`)&&l.push("css-custom-properties"),{nativeTokens:{present:c.includes("/* Frontfriend managed native tokens: start */"),file:s||null},tailwind:{present:!!t,version:t,major:t&&Number((String(t).match(/\d+/)||[])[0])||null},componentsJson:u.existsSync(i.join(n,"components.json")),themeImport:{present:c.includes(`${m}/theme.css`)||/@import\s+["'][^"']*node_modules\/\.cache\/frontfriend\/theme\.css["']/.test(c),file:s||null},plugin:_(n),frontfriendComponents:v(n),foreignComponentLibraries:x.filter(a=>o[a]),foreignTokenSystems:l}}function D(n,e){let o=h(n)||g,t=o.includes("tokens"),r=o.includes("components"),s=[];return t&&!e.themeImport.present&&!e.nativeTokens?.present&&s.push("Config adopts tokens, but the Frontfriend theme import was not observed."),!t&&e.themeImport.present&&s.push("Frontfriend tokens are present in CSS but are not adopted in config."),r&&!e.componentsJson&&s.push("Config adopts components, but components.json was not observed."),!r&&e.frontfriendComponents.length>0&&s.push("Frontfriend components are installed but are not adopted in config."),s}function L({apiUrl:n,token:e,ffId:o,name:t,adopt:r,observed:s,framework:c,primitive:l}){if(!n||!e||!o||!t||!c||l===void 0)return Promise.resolve({reported:!1,unavailable:!0});let a=new URL("/api/apps/sync",n),y=JSON.stringify({ffId:o,name:t,adopt:h(r),observed:s,runtime:"sdk",framework:c,primitive:l}),N=a.protocol==="https:"?O:E;return new Promise(d=>{let f=N.request(a,{method:"POST",headers:{authorization:`Bearer ${e}`,"content-type":"application/json","content-length":Buffer.byteLength(y)}},p=>{p.resume(),p.on("end",()=>{p.statusCode>=200&&p.statusCode<300?d({reported:!0,unavailable:!1}):d({reported:!1,unavailable:!0})})});f.on("error",()=>d({reported:!1,unavailable:!0})),f.setTimeout(1500,()=>{f.destroy(),d({reported:!1,unavailable:!0})}),f.end(y)})}module.exports={ADOPTION_LEVELS:g,normalizeAdopt:h,probeAdoption:P,adoptionWarnings:D,reportAdoption:L};
@@ -1,6 +1,6 @@
1
- var _=Object.create;var m=Object.defineProperty;var M=Object.getOwnPropertyDescriptor;var L=Object.getOwnPropertyNames;var $=Object.getPrototypeOf,N=Object.prototype.hasOwnProperty;var V=(t,e)=>()=>(e||t((e={exports:{}}).exports,e),e.exports),F=(t,e)=>{for(var r in e)m(t,r,{get:e[r],enumerable:!0})},v=(t,e,r,s)=>{if(e&&typeof e=="object"||typeof e=="function")for(let n of L(e))!N.call(t,n)&&n!==r&&m(t,n,{get:()=>e[n],enumerable:!(s=M(e,n))||s.enumerable});return t};var H=(t,e,r)=>(r=t!=null?_($(t)):{},v(e||!t||!t.__esModule?m(r,"default",{value:t,enumerable:!0}):r,t)),J=t=>v(m({},"__esModule",{value:!0}),t);var O=V((ae,P)=>{var u=require("fs"),l=require("path"),{createHash:T}=require("crypto"),G=".frontfriend/design",q=".frontfriend/.gitignore";function W(){return["# Managed by `frontfriend design sync`.","# audit/ holds regenerable capture artifacts (screenshots, probes) \u2014 never commit.","# design/ is the committed read-only contract mirror \u2014 keep it tracked.","audit/","# design-working/ is an explicit, disposable working preview.","design-working/",""].join(`
2
- `)}function f(t){return typeof t!="string"||t.length===0||t.startsWith("/")||t.includes("\\")?!1:t.split("/").every(e=>e!==""&&e!=="."&&e!=="..")}function b(t){let e=t.body.endsWith(`
3
- `)?t.body.slice(0,-1):t.body;return["<!-- frontfriend design mirror \u2014 DO NOT EDIT (overwritten by `frontfriend design sync`)",`slug: ${t.slug}`,`maturity: ${t.maturity}`,`implemented: ${t.implemented}`,`implementation: ${t.implementation||"unknown"}`,`version: ${t.version}`,"-->","",e,""].join(`
4
- `)}function A(t){return[`# Frontfriend design mirror \u2014 ${t.name}`,"","This directory is a READ-ONLY mirror of the Design System design contracts",`(Design System "${t.name}", ff-id \`${t.ff_id}\`) managed on the Frontfriend platform.`,"","Every file here is overwritten by `frontfriend design sync`. Do not edit by","hand: local changes are discarded on the next sync, and files whose contract","was removed upstream are deleted. Edit contracts on the platform instead.",""].join(`
5
- `)}function E({design_system:t,contracts:e}){let r=[...e].filter(n=>f(n.slug)).sort((n,a)=>n.kind.localeCompare(a.kind)||n.slug.localeCompare(a.slug)),s={"README.md":A(t)};for(let n of r)s[n.slug]=b(n);return s}function I(t,e){let r={};for(let[n,a]of Object.entries(t))e[n]!==a&&(r[n]=a);let s=Object.keys(e).filter(n=>!(n in t)).sort();return{writes:r,deletes:s}}var R=t=>T("sha256").update(t).digest("hex");function X(t){return Object.fromEntries(Object.entries(t).filter(([e])=>e!=="README.md"&&f(e)).map(([e,r])=>[e,R(r)]))}function K(t,e){let r=()=>{throw new Error("Invalid or incomplete mirror response. No local files were changed; retry sync.")};(!t||typeof t.design_system?.ff_id!="string"||typeof t.design_system?.name!="string"||!Array.isArray(t.contracts))&&r();let s=new Map;for(let o of t.contracts)(!o||!f(o.slug)||o.slug==="README.md"||typeof o.body!="string"||typeof o.kind!="string"||typeof o.maturity!="string"||typeof o.implemented!="boolean"||!Number.isSafeInteger(o.version)||o.version<1||s.has(o.slug))&&r(),s.set(o.slug,b(o));if(t.protocol===void 0)return t.manifest!==void 0&&r(),I(E(t),e);(t.protocol!==1||!Array.isArray(t.manifest))&&r();let n={"README.md":A(t.design_system)},a=new Set;for(let o of t.manifest){(!o||!f(o.slug)||o.slug==="README.md"||!/^[a-f0-9]{64}$/.test(o.hash)||a.has(o.slug))&&r(),a.add(o.slug);let i=s.get(o.slug)??e[o.slug];(typeof i!="string"||R(i)!==o.hash)&&r(),Object.defineProperty(n,o.slug,{value:i,enumerable:!0})}return[...s.keys()].some(o=>!a.has(o))&&r(),I(n,e)}function Q(t){let e={};if(!u.existsSync(t))return e;let r=s=>{for(let n of u.readdirSync(s,{withFileTypes:!0})){let a=l.join(s,n.name);if(n.isDirectory())r(a);else if(n.isFile()){let o=l.relative(t,a).split(l.sep).join("/");e[o]=u.readFileSync(a,"utf8")}}};return r(t),e}function Y(t,e){for(let[r,s]of Object.entries(e.writes)){let n=l.join(t,...r.split("/"));u.mkdirSync(l.dirname(n),{recursive:!0}),u.writeFileSync(n,s)}for(let r of e.deletes){let s=l.join(t,...r.split("/"));u.rmSync(s,{force:!0});let n=l.dirname(s),a=l.resolve(t);for(;l.resolve(n)!==a&&u.existsSync(n)&&u.readdirSync(n).length===0;)u.rmdirSync(n),n=l.dirname(n)}}function B(t,e,r){if(!e||t.contract_selection!==1||t.selection?.design_snapshot_id!==e.snapshotId||t.selection?.digest!==e.snapshotDigest||t.app?.id!==e.appId||t.design_system?.ff_id!==r)throw new Error("Contract mirror does not match the selected App snapshot.");let s=[...e.sharedContracts,...e.contracts],n=t.manifest??t.contracts,a=new Map(s.map(o=>[o.slug,o]));if(!Array.isArray(n)||!Array.isArray(t.contracts)||n.length!==s.length||new Set(n.map(o=>o.slug)).size!==s.length||n.some(o=>!a.has(o.slug)))throw new Error("Contract mirror inventory does not match the snapshot.");for(let o of t.contracts){let i=a.get(o.slug);if(!i||o.revision_id!==i.revisionId||o.digest!==i.digest||o.version!==i.version||o.kind!==i.kind)throw new Error("Contract body identity does not match its snapshot pin.");let p={appId:e.contracts.some(d=>d.slug===i.slug)?e.appId:null,body:o.body,designSystemId:e.designSystemId,kind:o.kind,maturity:o.maturity,slug:o.slug,title:o.title};if(T("sha256").update(JSON.stringify(p)).digest("hex")!==i.digest)throw new Error("Contract content does not match its immutable digest.")}return s}P.exports={validatePinnedMirror:B,MIRROR_DIR:G,FRONTFRIEND_GITIGNORE_PATH:q,renderFrontfriendGitignore:W,isSafeSlug:f,renderContractFile:b,renderMirrorReadme:A,buildMirrorTree:E,planMirrorSync:I,hashMirrorFile:R,knownMirrorHashes:X,planMirrorResponse:K,readMirrorTree:Q,applyMirrorPlan:Y}});var ne={};F(ne,{adoptionDigest:()=>x,normalizeLock:()=>j,parseApplicationLock:()=>ee,serializeApplicationLock:()=>te,sortedObject:()=>C});module.exports=J(ne);var z=Object.freeze([Object.freeze({framework:"react",primitive:"radix"}),Object.freeze({framework:"react",primitive:"base"}),Object.freeze({framework:"react",primitive:"aria"}),Object.freeze({framework:"vue",primitive:"reka"})]),U=new Set(z.map(t=>`${t.framework}/${t.primitive}`)),w=class extends Error{constructor(e,r,s={}){super(r),this.name="ProjectTargetError",this.code=e,Object.assign(this,s)}};function h(t,e="Project target"){let r=t,s=typeof r?.framework=="string"?r.framework.trim().toLowerCase():"",n=typeof r?.primitive=="string"?r.primitive.trim().toLowerCase():"",a=`${s}/${n}`;if(!s||!n||!U.has(a))throw new w("INVALID_PROJECT_TARGET",`${e} must be exactly one of react/radix, react/base, react/aria, or vue/reka; received ${a}.`,{framework:s||null,primitive:n||null});return{framework:s,primitive:n}}var c=class extends Error{constructor(r,s=[]){super(r);this.code="ADOPTION_CONFLICT";this.name="AdoptionConflictError",this.conflicts=s}};var S=H(require("node:crypto"));function k(t){return S.default.createHash("sha256").update(Buffer.from(t)).digest("hex")}var{isSafeSlug:Z}=O();function C(t){return Object.fromEntries(Object.entries(t).sort(([e],[r])=>e.localeCompare(r)).map(([e,r])=>[e,r&&typeof r=="object"&&!Array.isArray(r)?{...r,...Array.isArray(r.files)?{files:[...r.files].sort((s,n)=>s.path.localeCompare(n.path))}:{}}:r]))}function y(t){return Array.isArray(t)?t.map(y):t&&typeof t=="object"?Object.fromEntries(Object.keys(t).filter(e=>e!=="adoptionDigest").sort().map(e=>[e,y(t[e])])):t}function x(t){return k(JSON.stringify(y(t)))}function j(t){let e=t;if(!e||![1,2,3].includes(Number(e.schemaVersion))||typeof e.components!="object"||e.components===null)throw new c("Unsupported or malformed frontfriend.lock.json.");let r=Object.fromEntries(Object.entries(e.components).map(([i,p])=>{let g=p;if(!g||!["canonical","private"].includes(String(g.source))||typeof g.versionId!="string"||typeof g.semver!="string")throw new c(`Unsupported source kind for ${i}.`);return[i,g]})),s={releaseId:e.releaseId==null?null:String(e.releaseId),tokenVersionId:String(e.tokenVersionId),projectTarget:e.schemaVersion===3&&e.projectTarget===null&&Object.keys(r).length===0?null:h(e.projectTarget,"Application lock target"),components:r};for(let i of Object.values(r)){if(!i.projectTarget)continue;let p=h(i.projectTarget,"Component adoption target");if(!s.projectTarget||p.framework!==s.projectTarget.framework||p.primitive!==s.projectTarget.primitive)throw new c("Component adoption belongs to another Project target.")}if(e.schemaVersion===1)return{...s,projectTarget:h(e.projectTarget,"Application lock target"),schemaVersion:1,components:r};if(typeof e.designSystemId!="string"||!e.designSystemId||typeof e.ffId!="string"||!e.ffId||typeof e.adoptionDigest!="string"||!e.adoptionDigest||typeof e.tokenSourceReleaseId!="string"||!e.tokenSourceReleaseId||!Array.isArray(e.sourceReleaseIds))throw new c("Malformed v2 Frontfriend adoption snapshot.");let n={...s,schemaVersion:e.schemaVersion===3?3:2,...e.schemaVersion===3?{design:e.design}:{},designSystemId:e.designSystemId,ffId:e.ffId,...e.baseLibrary!==void 0?{baseLibrary:e.baseLibrary}:{},...e.baseProvenance!==void 0?{baseProvenance:e.baseProvenance}:{},...e.replacements!==void 0?{replacements:e.replacements}:{},adoptionDigest:e.adoptionDigest,tokenSourceReleaseId:e.tokenSourceReleaseId,sourceReleaseIds:[...new Set(e.sourceReleaseIds.map(String))].sort(),components:r};if(n.baseLibrary!==void 0&&!["frontfriend","shadcn"].includes(n.baseLibrary))throw new c("Unsupported base library in Application lock.");if(n.schemaVersion===3){let i=n.design;if(!i||i.designSystemId!==n.designSystemId||!i.appId||!i.snapshotId||!i.sharedSourceReleaseId||!Array.isArray(i.contracts)||!Array.isArray(i.sharedContracts))throw new c("Malformed Application design adoption.");let p=[...i.sharedContracts,...i.contracts];if(new Set(p.map(d=>d.slug)).size!==p.length||p.some(d=>d.designSystemId!==n.designSystemId||!d.revisionId||!d.contractId||!Z(d.slug)||!d.slug.endsWith(".md")||!Number.isInteger(d.version)||d.version<1||!/^[a-f0-9]{64}$/.test(d.digest)))throw new c("Invalid contract revision pins in the Application lock.");if(i.sharedContracts.some(d=>!["guidelines","design-context","guideline-chapter","layout","pattern"].includes(d.kind))||i.contracts.some(d=>!["app-context","page"].includes(d.kind)))throw new c("Contract pins have invalid shared or App ownership.");if(k(JSON.stringify(y({schemaVersion:1,appId:i.appId,sharedSourceReleaseId:i.sharedSourceReleaseId,contracts:[...i.contracts].sort((d,D)=>d.slug.localeCompare(D.slug))})))!==i.snapshotDigest)throw new c("Application design snapshot digest does not match its manifest.")}else if(e.design!==void 0)throw new c("Contract pins require a schema version 3 Application lock.");let a=Object.values(n.components).map(i=>{if(typeof i.sourceReleaseId!="string"||!i.sourceReleaseId)throw new c("Every v2 component adoption must identify its immutable source Release.");return i.sourceReleaseId}),o=[...new Set([n.tokenSourceReleaseId,...a,...n.design?[n.design.sharedSourceReleaseId]:[]])].sort();if(JSON.stringify(o)!==JSON.stringify(n.sourceReleaseIds))throw new c("The adoption source Releases do not match the token and component provenance.");if(n.releaseId&&(o.length!==1||o[0]!==n.releaseId))throw new c("A lock may reference a Release only when its complete closure matches that Release.");if(x(n)!==n.adoptionDigest)throw new c("The adoption snapshot digest does not match its manifest.");return n}function ee(t){try{return j(typeof t=="string"?JSON.parse(t):t)}catch(e){throw e instanceof c?e:new c(`Invalid frontfriend.lock.json: ${e instanceof Error?e.message:String(e)}`)}}function te(t){let e=j(t);return`${JSON.stringify({...e,components:C(e.components)},null,2)}
6
- `}0&&(module.exports={adoptionDigest,normalizeLock,parseApplicationLock,serializeApplicationLock,sortedObject});
1
+ var V=Object.create;var h=Object.defineProperty;var F=Object.getOwnPropertyDescriptor;var H=Object.getOwnPropertyNames;var J=Object.getPrototypeOf,z=Object.prototype.hasOwnProperty;var U=(e,t)=>()=>(t||e((t={exports:{}}).exports,t),t.exports),G=(e,t)=>{for(var n in t)h(e,n,{get:t[n],enumerable:!0})},E=(e,t,n,s)=>{if(t&&typeof t=="object"||typeof t=="function")for(let r of H(t))!z.call(e,r)&&r!==n&&h(e,r,{get:()=>t[r],enumerable:!(s=F(t,r))||s.enumerable});return e};var q=(e,t,n)=>(n=e!=null?V(J(e)):{},E(t||!e||!e.__esModule?h(n,"default",{value:e,enumerable:!0}):n,e)),W=e=>E(h({},"__esModule",{value:!0}),e);var C=U((fe,P)=>{var g=require("fs"),l=require("path"),{createHash:D}=require("crypto"),Q=".frontfriend/design",Y=".frontfriend/.gitignore";function B(){return["# Managed by `frontfriend design sync`.","# audit/ holds regenerable capture artifacts (screenshots, probes) \u2014 never commit.","# design/ is the committed read-only contract mirror \u2014 keep it tracked.","audit/","# design-working/ is an explicit, disposable working preview.","design-working/",""].join(`
2
+ `)}function f(e){return typeof e!="string"||e.length===0||e.startsWith("/")||e.includes("\\")?!1:e.split("/").every(t=>t!==""&&t!=="."&&t!=="..")}function b(e){let t=e.body.endsWith(`
3
+ `)?e.body.slice(0,-1):e.body;return["<!-- frontfriend design mirror \u2014 DO NOT EDIT (overwritten by `frontfriend design sync`)",`slug: ${e.slug}`,`maturity: ${e.maturity}`,`implemented: ${e.implemented}`,`implementation: ${e.implementation||"unknown"}`,`version: ${e.version}`,"-->","",t,""].join(`
4
+ `)}function R(e){return[`# Frontfriend design mirror \u2014 ${e.name}`,"","This directory is a READ-ONLY mirror of the Design System design contracts",`(Design System "${e.name}", ff-id \`${e.ff_id}\`) managed on the Frontfriend platform.`,"","Every file here is overwritten by `frontfriend design sync`. Do not edit by","hand: local changes are discarded on the next sync, and files whose contract","was removed upstream are deleted. Edit contracts on the platform instead.",""].join(`
5
+ `)}function O({design_system:e,contracts:t}){let n=[...t].filter(r=>f(r.slug)).sort((r,a)=>r.kind.localeCompare(a.kind)||r.slug.localeCompare(a.slug)),s={"README.md":R(e)};for(let r of n)s[r.slug]=b(r);return s}function I(e,t){let n={};for(let[r,a]of Object.entries(e))t[r]!==a&&(n[r]=a);let s=Object.keys(t).filter(r=>!(r in e)).sort();return{writes:n,deletes:s}}var j=e=>D("sha256").update(e).digest("hex");function Z(e){return Object.fromEntries(Object.entries(e).filter(([t])=>t!=="README.md"&&f(t)).map(([t,n])=>[t,j(n)]))}function ee(e,t){let n=()=>{throw new Error("Invalid or incomplete mirror response. No local files were changed; retry sync.")};(!e||typeof e.design_system?.ff_id!="string"||typeof e.design_system?.name!="string"||!Array.isArray(e.contracts))&&n();let s=new Map;for(let o of e.contracts)(!o||!f(o.slug)||o.slug==="README.md"||typeof o.body!="string"||typeof o.kind!="string"||typeof o.maturity!="string"||typeof o.implemented!="boolean"||!Number.isSafeInteger(o.version)||o.version<1||s.has(o.slug))&&n(),s.set(o.slug,b(o));if(e.protocol===void 0)return e.manifest!==void 0&&n(),I(O(e),t);(e.protocol!==1||!Array.isArray(e.manifest))&&n();let r={"README.md":R(e.design_system)},a=new Set;for(let o of e.manifest){(!o||!f(o.slug)||o.slug==="README.md"||!/^[a-f0-9]{64}$/.test(o.hash)||a.has(o.slug))&&n(),a.add(o.slug);let i=s.get(o.slug)??t[o.slug];(typeof i!="string"||j(i)!==o.hash)&&n(),Object.defineProperty(r,o.slug,{value:i,enumerable:!0})}return[...s.keys()].some(o=>!a.has(o))&&n(),I(r,t)}function te(e){let t={};if(!g.existsSync(e))return t;let n=s=>{for(let r of g.readdirSync(s,{withFileTypes:!0})){let a=l.join(s,r.name);if(r.isDirectory())n(a);else if(r.isFile()){let o=l.relative(e,a).split(l.sep).join("/");t[o]=g.readFileSync(a,"utf8")}}};return n(e),t}function ne(e,t){for(let[n,s]of Object.entries(t.writes)){let r=l.join(e,...n.split("/"));g.mkdirSync(l.dirname(r),{recursive:!0}),g.writeFileSync(r,s)}for(let n of t.deletes){let s=l.join(e,...n.split("/"));g.rmSync(s,{force:!0});let r=l.dirname(s),a=l.resolve(e);for(;l.resolve(r)!==a&&g.existsSync(r)&&g.readdirSync(r).length===0;)g.rmdirSync(r),r=l.dirname(r)}}function re(e,t,n){if(!t||e.contract_selection!==1||e.selection?.design_snapshot_id!==t.snapshotId||e.selection?.digest!==t.snapshotDigest||e.app?.id!==t.appId||e.design_system?.ff_id!==n)throw new Error("Contract mirror does not match the selected App snapshot.");let s=[...t.sharedContracts,...t.contracts],r=e.manifest??e.contracts,a=new Map(s.map(o=>[o.slug,o]));if(!Array.isArray(r)||!Array.isArray(e.contracts)||r.length!==s.length||new Set(r.map(o=>o.slug)).size!==s.length||r.some(o=>!a.has(o.slug)))throw new Error("Contract mirror inventory does not match the snapshot.");for(let o of e.contracts){let i=a.get(o.slug);if(!i||o.revision_id!==i.revisionId||o.digest!==i.digest||o.version!==i.version||o.kind!==i.kind)throw new Error("Contract body identity does not match its snapshot pin.");let p={appId:t.contracts.some(d=>d.slug===i.slug)?t.appId:null,body:o.body,designSystemId:t.designSystemId,kind:o.kind,maturity:o.maturity,slug:o.slug,title:o.title};if(D("sha256").update(JSON.stringify(p)).digest("hex")!==i.digest)throw new Error("Contract content does not match its immutable digest.")}return s}P.exports={validatePinnedMirror:re,MIRROR_DIR:Q,FRONTFRIEND_GITIGNORE_PATH:Y,renderFrontfriendGitignore:B,isSafeSlug:f,renderContractFile:b,renderMirrorReadme:R,buildMirrorTree:O,planMirrorSync:I,hashMirrorFile:j,knownMirrorHashes:Z,planMirrorResponse:ee,readMirrorTree:te,applyMirrorPlan:ne}});var de={};G(de,{adoptionDigest:()=>k,canonicalApplicationLock:()=>M,canonicalDesignAdoption:()=>_,hasValidAdoptionDigest:()=>$,normalizeLock:()=>v,parseApplicationLock:()=>ae,sameAdoption:()=>ie,serializeApplicationLock:()=>ce,sortContractPins:()=>S,sortedObject:()=>L});module.exports=W(de);var X=Object.freeze([Object.freeze({framework:"react",primitive:"radix"}),Object.freeze({framework:"react",primitive:"base"}),Object.freeze({framework:"react",primitive:"aria"}),Object.freeze({framework:"vue",primitive:"reka"})]),K=new Set(X.map(e=>`${e.framework}/${e.primitive}`)),A=class extends Error{constructor(t,n,s={}){super(n),this.name="ProjectTargetError",this.code=t,Object.assign(this,s)}};function y(e,t="Project target"){let n=e,s=typeof n?.framework=="string"?n.framework.trim().toLowerCase():"",r=typeof n?.primitive=="string"?n.primitive.trim().toLowerCase():"",a=`${s}/${r}`;if(!s||!r||!K.has(a))throw new A("INVALID_PROJECT_TARGET",`${t} must be exactly one of react/radix, react/base, react/aria, or vue/reka; received ${a}.`,{framework:s||null,primitive:r||null});return{framework:s,primitive:r}}var c=class extends Error{constructor(n,s=[]){super(n);this.code="ADOPTION_CONFLICT";this.name="AdoptionConflictError",this.conflicts=s}};var x=q(require("node:crypto"));function w(e){return x.default.createHash("sha256").update(Buffer.from(e)).digest("hex")}var{isSafeSlug:oe}=C();function L(e){return Object.fromEntries(Object.entries(e).sort(([t],[n])=>t.localeCompare(n)).map(([t,n])=>[t,n&&typeof n=="object"&&!Array.isArray(n)?{...n,...Array.isArray(n.files)?{files:[...n.files].sort((s,r)=>s.path.localeCompare(r.path))}:{}}:n]))}function m(e){return Array.isArray(e)?e.map(m):e&&typeof e=="object"?Object.fromEntries(Object.keys(e).filter(t=>t!=="adoptionDigest").sort().map(t=>[t,m(e[t])])):e}var T=(e,t)=>e<t?-1:e>t?1:0;function S(e){return[...e].sort((t,n)=>T(t.slug,n.slug)||T(t.kind,n.kind))}function _(e){return{...e,contracts:S(e.contracts),sharedContracts:S(e.sharedContracts)}}function M(e){return{...e,...e.design?{design:_(e.design)}:{},...Array.isArray(e.sourceReleaseIds)?{sourceReleaseIds:[...new Set(e.sourceReleaseIds)].sort(T)}:{},...e.components?{components:Object.fromEntries(Object.entries(e.components).map(([t,n])=>[t,Array.isArray(n?.files)?{...n,files:[...n.files].sort((s,r)=>s.path.localeCompare(r.path))}:n]))}:{}}}function k(e){return w(JSON.stringify(m(M(e))))}function se(e){return w(JSON.stringify(m(e)))}function $(e){return typeof e.adoptionDigest=="string"&&(k(e)===e.adoptionDigest||se(e)===e.adoptionDigest)}function ie(e,t){return k(e)===k(t)}function v(e){let t=e;if(!t||![1,2,3].includes(Number(t.schemaVersion))||typeof t.components!="object"||t.components===null)throw new c("Unsupported or malformed frontfriend.lock.json.");let n=Object.fromEntries(Object.entries(t.components).map(([i,p])=>{let u=p;if(!u||!["canonical","private"].includes(String(u.source))||typeof u.versionId!="string"||typeof u.semver!="string")throw new c(`Unsupported source kind for ${i}.`);return[i,u]})),s={releaseId:t.releaseId==null?null:String(t.releaseId),tokenVersionId:String(t.tokenVersionId),projectTarget:t.schemaVersion===3&&t.projectTarget===null&&Object.keys(n).length===0?null:y(t.projectTarget,"Application lock target"),components:n};for(let i of Object.values(n)){if(!i.projectTarget)continue;let p=y(i.projectTarget,"Component adoption target");if(!s.projectTarget||p.framework!==s.projectTarget.framework||p.primitive!==s.projectTarget.primitive)throw new c("Component adoption belongs to another Project target.")}if(t.schemaVersion===1)return{...s,projectTarget:y(t.projectTarget,"Application lock target"),schemaVersion:1,components:n};if(typeof t.designSystemId!="string"||!t.designSystemId||typeof t.ffId!="string"||!t.ffId||typeof t.adoptionDigest!="string"||!t.adoptionDigest||typeof t.tokenSourceReleaseId!="string"||!t.tokenSourceReleaseId||!Array.isArray(t.sourceReleaseIds))throw new c("Malformed v2 Frontfriend adoption snapshot.");let r={...s,schemaVersion:t.schemaVersion===3?3:2,...t.schemaVersion===3?{design:t.design}:{},designSystemId:t.designSystemId,ffId:t.ffId,...t.baseLibrary!==void 0?{baseLibrary:t.baseLibrary}:{},...t.baseProvenance!==void 0?{baseProvenance:t.baseProvenance}:{},...t.replacements!==void 0?{replacements:t.replacements}:{},adoptionDigest:t.adoptionDigest,tokenSourceReleaseId:t.tokenSourceReleaseId,sourceReleaseIds:[...new Set(t.sourceReleaseIds.map(String))].sort(),components:n};if(r.baseLibrary!==void 0&&!["frontfriend","shadcn"].includes(r.baseLibrary))throw new c("Unsupported base library in Application lock.");if(r.schemaVersion===3){let i=r.design;if(!i||i.designSystemId!==r.designSystemId||!i.appId||!i.snapshotId||!i.sharedSourceReleaseId||!Array.isArray(i.contracts)||!Array.isArray(i.sharedContracts))throw new c("Malformed Application design adoption.");let p=[...i.sharedContracts,...i.contracts];if(new Set(p.map(d=>d.slug)).size!==p.length||p.some(d=>d.designSystemId!==r.designSystemId||!d.revisionId||!d.contractId||!oe(d.slug)||!d.slug.endsWith(".md")||!Number.isInteger(d.version)||d.version<1||!/^[a-f0-9]{64}$/.test(d.digest)))throw new c("Invalid contract revision pins in the Application lock.");if(i.sharedContracts.some(d=>!["guidelines","design-context","guideline-chapter","layout","pattern"].includes(d.kind))||i.contracts.some(d=>!["app-context","page"].includes(d.kind)))throw new c("Contract pins have invalid shared or App ownership.");if(w(JSON.stringify(m({schemaVersion:1,appId:i.appId,sharedSourceReleaseId:i.sharedSourceReleaseId,contracts:[...i.contracts].sort((d,N)=>d.slug.localeCompare(N.slug))})))!==i.snapshotDigest)throw new c("Application design snapshot digest does not match its manifest.")}else if(t.design!==void 0)throw new c("Contract pins require a schema version 3 Application lock.");let a=Object.values(r.components).map(i=>{if(typeof i.sourceReleaseId!="string"||!i.sourceReleaseId)throw new c("Every v2 component adoption must identify its immutable source Release.");return i.sourceReleaseId}),o=[...new Set([r.tokenSourceReleaseId,...a,...r.design?[r.design.sharedSourceReleaseId]:[]])].sort();if(JSON.stringify(o)!==JSON.stringify(r.sourceReleaseIds))throw new c("The adoption source Releases do not match the token and component provenance.");if(r.releaseId&&(o.length!==1||o[0]!==r.releaseId))throw new c("A lock may reference a Release only when its complete closure matches that Release.");if(!$(r))throw new c("The adoption snapshot digest does not match its manifest.");return r}function ae(e){try{return v(typeof e=="string"?JSON.parse(e):e)}catch(t){throw t instanceof c?t:new c(`Invalid frontfriend.lock.json: ${t instanceof Error?t.message:String(t)}`)}}function ce(e){let t=v(e);return`${JSON.stringify({...t,components:L(t.components)},null,2)}
6
+ `}0&&(module.exports={adoptionDigest,canonicalApplicationLock,canonicalDesignAdoption,hasValidAdoptionDigest,normalizeLock,parseApplicationLock,sameAdoption,serializeApplicationLock,sortContractPins,sortedObject});