@ciandt-flow/flow-ai-obs 0.5.0-beta.211 → 0.5.2-beta.220
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/dist/cli.js +23 -23
- package/dist/index.js +11 -11
- package/dist/setup.js +2 -2
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
'use strict';var kn=require('https'),w=require('fs'),ue=require('os'),pt=require('path'),child_process=require('child_process'),Mn=require('http'),util=require('util'),crypto=require('crypto');function _interopNamespace(e){if(e&&e.__esModule)return e;var n=Object.create(null);if(e){Object.keys(e).forEach(function(k){if(k!=='default'){var d=Object.getOwnPropertyDescriptor(e,k);Object.defineProperty(n,k,d.get?d:{enumerable:true,get:function(){return e[k]}});}})}n.default=e;return Object.freeze(n)}var kn__namespace=/*#__PURE__*/_interopNamespace(kn);var w__namespace=/*#__PURE__*/_interopNamespace(w);var ue__namespace=/*#__PURE__*/_interopNamespace(ue);var pt__namespace=/*#__PURE__*/_interopNamespace(pt);var Mn__namespace=/*#__PURE__*/_interopNamespace(Mn);var oe=Object.defineProperty;var hn=Object.getOwnPropertyDescriptor;var Sn=Object.getOwnPropertyNames;var En=Object.prototype.hasOwnProperty;var Dt=(t=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(t,{get:(e,r)=>(typeof require<"u"?require:e)[r]}):t)(function(t){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+t+'" is not supported')});var p=(t,e)=>()=>(t&&(e=t(t=0)),e);var wn=(t,e)=>()=>(e||t((e={exports:{}}).exports,e),e.exports),U=(t,e)=>{for(var r in e)oe(t,r,{get:e[r],enumerable:true});},Tn=(t,e,r,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let s of Sn(e))!En.call(t,s)&&s!==r&&oe(t,s,{get:()=>e[s],enumerable:!(n=hn(e,s))||n.enumerable});return t};var N=t=>Tn(oe({},"__esModule",{value:true}),t);var Bt=wn((eo,yn)=>{yn.exports={name:"@ciandt-flow/flow-ai-obs",version:"0.5.
|
|
2
|
+
'use strict';var kn=require('https'),w=require('fs'),ue=require('os'),pt=require('path'),child_process=require('child_process'),Mn=require('http'),util=require('util'),crypto=require('crypto');function _interopNamespace(e){if(e&&e.__esModule)return e;var n=Object.create(null);if(e){Object.keys(e).forEach(function(k){if(k!=='default'){var d=Object.getOwnPropertyDescriptor(e,k);Object.defineProperty(n,k,d.get?d:{enumerable:true,get:function(){return e[k]}});}})}n.default=e;return Object.freeze(n)}var kn__namespace=/*#__PURE__*/_interopNamespace(kn);var w__namespace=/*#__PURE__*/_interopNamespace(w);var ue__namespace=/*#__PURE__*/_interopNamespace(ue);var pt__namespace=/*#__PURE__*/_interopNamespace(pt);var Mn__namespace=/*#__PURE__*/_interopNamespace(Mn);var oe=Object.defineProperty;var hn=Object.getOwnPropertyDescriptor;var Sn=Object.getOwnPropertyNames;var En=Object.prototype.hasOwnProperty;var Dt=(t=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(t,{get:(e,r)=>(typeof require<"u"?require:e)[r]}):t)(function(t){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+t+'" is not supported')});var p=(t,e)=>()=>(t&&(e=t(t=0)),e);var wn=(t,e)=>()=>(e||t((e={exports:{}}).exports,e),e.exports),U=(t,e)=>{for(var r in e)oe(t,r,{get:e[r],enumerable:true});},Tn=(t,e,r,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let s of Sn(e))!En.call(t,s)&&s!==r&&oe(t,s,{get:()=>e[s],enumerable:!(n=hn(e,s))||n.enumerable});return t};var N=t=>Tn(oe({},"__esModule",{value:true}),t);var Bt=wn((eo,yn)=>{yn.exports={name:"@ciandt-flow/flow-ai-obs",version:"0.5.2-beta.220",description:"Claude Code hooks for Langfuse OTLP tracing \u2014 cross-platform",main:"dist/index.js",bin:{"flow-ai-obs":"dist/cli.js","flow-ai-obs-setup":"dist/setup.js"},scripts:{build:"tsup",test:"jest",typecheck:"tsc --noEmit",lint:"eslint src bin scripts",format:'prettier --write "src/**/*.ts" "bin/**/*.ts" "scripts/**/*.ts"',"format:check":'prettier --check "src/**/*.ts" "bin/**/*.ts" "scripts/**/*.ts"',"security-scan":"trufflehog filesystem src/ --fail --no-update --exclude-paths .trufflehogignore",postinstall:`node -e "require('fs').existsSync('dist/setup.js') && require('child_process').execFileSync(process.execPath, ['dist/setup.js'], {stdio:'inherit'})"`,prepublishOnly:"npm run security-scan && npm run build","release:npm":"changeset publish",changeset:"changeset","version-packages":"changeset version","install:hooks":"node dist/cli.js install","auth:login":"node dist/cli.js auth login","auth:logout":"node dist/cli.js auth logout","auth:status":"node dist/cli.js auth status",smoke:"bash scripts/smoke-test.sh","smoke:debug":"bash scripts/smoke-test.sh --debug","smoke:send":"bash scripts/smoke-test.sh --send --allow-http --debug"},files:["dist/","README.md","LICENSE.md"],keywords:["claude-code","langfuse","observability","otlp","hooks","flow","ciandt"],author:"CI&T Flow Team",license:"SEE LICENSE IN LICENSE.md",private:false,dependencies:{keytar:"7.9.0"},devDependencies:{"@changesets/changelog-github":"^0.6.0","@changesets/cli":"^2.30.0","@types/jest":"^30.0.0","@types/node":"^25.8.0",jest:"^30.4.2","ts-jest":"^29.4.9",tsup:"^8.5.1","eslint-config-prettier":"^10.1.5",prettier:"^3.5.3",typescript:"^6.0.3","typescript-eslint":"^8.33.0"},engines:{node:">=18.0.0"},publishConfig:{registry:"https://registry.npmjs.org",access:"public"},repository:{type:"git",url:"git+https://github.com/CI-T-HyperX/flow-codeassistant-observability.git"}};});var ie={};U(ie,{bold:()=>H,cyan:()=>B,dim:()=>E,green:()=>P,red:()=>D,yellow:()=>L});function it(t,e){return _n?r=>`\x1B[${t}m${r}\x1B[${e}m`:r=>r}var _n,P,D,L,B,H,E,at=p(()=>{_n=!process.env.NO_COLOR&&process.stdout.isTTY;P=it("32","39"),D=it("31","39"),L=it("33","39"),B=it("36","39"),H=it("1","22"),E=it("2","22");});var Ht={};U(Ht,{checkForUpdate:()=>Rn,isNewer:()=>ce});function ct(){return ae||(ae=Bt()),ae}function ce(t,e){let r=o=>{let i=String(o).replace(/^v/,"").match(/^(\d+)\.(\d+)\.(\d+)/);return i?[+i[1],+i[2],+i[3]]:null},n=r(t),s=r(e);return !n||!s?false:s[0]!==n[0]?s[0]>n[0]:s[1]!==n[1]?s[1]>n[1]:s[2]>n[2]}function vn(){try{let t=JSON.parse(w__namespace.default.readFileSync(Ve,"utf8"));return typeof t.latestVersion!="string"||Date.now()-t.checkedAt>=bn?null:t}catch{return null}}function Nn(t,e){try{w__namespace.default.writeFileSync(Ve,JSON.stringify({latestVersion:t,updatePriority:e??null,checkedAt:Date.now()}),{mode:384});}catch{}}function Pn(t){let e=ct().name,r=kn__namespace.default.get(`https://registry.npmjs.org/${encodeURIComponent(e)}/latest`,{timeout:In},n=>{if(n.statusCode!==200)return n.resume(),t(new Error(`HTTP ${n.statusCode}`));let s="";n.setEncoding("utf8"),n.on("data",o=>{s+=o;}),n.on("end",()=>{try{let o=JSON.parse(s);if(typeof o.version!="string")throw new Error("no version field");t(null,{version:o.version,updatePriority:typeof o.updatePriority=="string"?o.updatePriority:null});}catch(o){t(o);}});});r.on("error",t),r.on("timeout",()=>{r.destroy(new Error("timeout"));});}function Be(t){let e=ct().name,n=` Update available: ${ct().version} \u2192 ${t}`,s=` Run: npm install -g ${e}`,o=Math.max(n.length,s.length)+2,i="\u2500".repeat(o);process.stderr.write(`
|
|
3
3
|
\u256D${i}\u256E
|
|
4
4
|
\u2502${n.padEnd(o)}\u2502
|
|
5
5
|
\u2502${s.padEnd(o)}\u2502
|
|
@@ -8,26 +8,26 @@
|
|
|
8
8
|
`);}function He(t){let e=ct().name;process.stderr.write(`
|
|
9
9
|
[${e}] Critical update detected \u2014 auto-updating to ${t}...
|
|
10
10
|
|
|
11
|
-
`),child_process.spawn("npm",["install","-g",`${e}@${t}`],{detached:true,stdio:"ignore",windowsHide:true}).unref();}function Rn(){try{let t=vn();if(t){ce(ct().version,t.latestVersion)&&(t.updatePriority==="auto"?He(t.latestVersion):Be(t.latestVersion));return}setImmediate(()=>{Pn((e,r)=>{e||!r||(Nn(r.version,r.updatePriority),ce(ct().version,r.version)&&(r.updatePriority==="auto"?He(r.version):Be(r.version)));});});}catch{}}var ae,Ve,bn,In,jt=p(()=>{Ve=pt__namespace.default.join(ue__namespace.default.tmpdir(),"flow-obs-update-cache.json"),bn=1440*60*1e3,In=3e3;});var
|
|
11
|
+
`),child_process.spawn("npm",["install","-g",`${e}@${t}`],{detached:true,stdio:"ignore",windowsHide:true}).unref();}function Rn(){try{let t=vn();if(t){ce(ct().version,t.latestVersion)&&(t.updatePriority==="auto"?He(t.latestVersion):Be(t.latestVersion));return}setImmediate(()=>{Pn((e,r)=>{e||!r||(Nn(r.version,r.updatePriority),ce(ct().version,r.version)&&(r.updatePriority==="auto"?He(r.version):Be(r.version)));});});}catch{}}var ae,Ve,bn,In,jt=p(()=>{Ve=pt__namespace.default.join(ue__namespace.default.tmpdir(),"flow-obs-update-cache.json"),bn=1440*60*1e3,In=3e3;});var V,z,Vt,Yt,Gt,le,Lt,lt,f,Wt,ut,Ye,R,Ge,F,T=p(()=>{V=process.env.FLOW_BASE_URL||"https://flow.ciandt.com",z={AUTH_ENGINE:process.env.FLOW_AUTH_ENGINE_URL||`${V}/auth-engine-api/v2/api-key/token`,GATEWAY_TRACES:process.env.FLOW_GATEWAY_TRACES_URL||`${V}/flow-langfuse-gateway/v1/traces`,GATEWAY_HEALTH:process.env.FLOW_GATEWAY_HEALTH_URL||`${V}/flow-langfuse-gateway/v1/health`,OTEL_ENDPOINT:process.env.FLOW_OTEL_ENDPOINT_URL||`${V}/otel`},Vt={SERVICE:"flow-plugins-cli",ACCOUNT_CREDS:"credentials",ACCOUNT_TOKEN:"token-cache"},Yt="FLOW-nodejs",Gt="config.json",le={SCOPE_NAME:"flow-ai-obs",SCOPE_VERSION:"0.1.0"},Lt={ANTHROPIC_BASE_URL:process.env.FLOW_LLM_PROXY_URL??`${V}/flow-llm-proxy/`,ANTHROPIC_MODEL:process.env.FLOW_LLM_PROXY_MODEL??"anthropic.claude-4-6-sonnet",ANTHROPIC_SMALL_FAST_MODEL:process.env.FLOW_LLM_PROXY_SMALL_MODEL??"anthropic.claude-4-6-sonnet",CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS:"1"},lt={CLAUDE_CODE_ENABLE_TELEMETRY:"1",OTEL_EXPORTER_OTLP_ENDPOINT:z.OTEL_ENDPOINT,OTEL_EXPORTER_OTLP_PROTOCOL:"http/json",OTEL_METRICS_EXPORTER:"otlp",OTEL_LOGS_EXPORTER:"otlp",OTEL_LOG_TOOL_DETAILS:"1",OTEL_LOG_USER_PROMPTS:"1"},f={FLOW_TELEMETRY:"FLOW_TELEMETRY",FLOW_TELEMETRY_GATEWAY:"FLOW_TELEMETRY_GATEWAY_URL",LANGFUSE_BASE_URL:"LANGFUSE_BASE_URL",LANGFUSE_PUBLIC_KEY:"LANGFUSE_PUBLIC_KEY",LANGFUSE_SECRET_KEY:"LANGFUSE_SECRET_KEY",ANTHROPIC_MODEL:"ANTHROPIC_MODEL",ANTHROPIC_AUTH_TOKEN:"ANTHROPIC_AUTH_TOKEN",FLOW_OBS_DEBUG:"FLOW_TELEMETRY_DEBUG",FLOW_OBS_ALLOW_HTTP:"FLOW_TELEMETRY_ALLOW_HTTP",BUFFER_TTL_DAYS:"FLOW_TELEMETRY_BUFFER_TTL_DAYS",BUFFER_MAX_FILES:"FLOW_TELEMETRY_BUFFER_MAX_FILES"},Wt={KEYCHAIN_ENABLED:false},ut={LOCK_STALE_MS:3e4,CONNECTIVITY_MAX_RETRY:3,CONNECTIVITY_RETRY_MS:2e3},Ye={UserPromptSubmit:5,PreToolUse:3,PostToolUse:10,Stop:15},R={FILE_PREFIX:"flow-obs-buffer-",DEFAULT_TTL_DAYS:4,MIN_TTL_DAYS:1,MAX_TTL_DAYS:30,DEFAULT_MAX_FILES:50,MIN_MAX_FILES:1,MAX_MAX_FILES:500,REPLAY_BATCH_SIZE:10},Ge="flow-ai-obs-debug.log",F={TOOL_INPUT:2e4,TOOL_OUTPUT:2e4,TRACE_OUTPUT:2e4,USER_INSTRUCTION:1e4,TRACE_INPUT:5e4,TOOL_BRIEF:60},{API_URL:process.env.FLOW_METRICS_URL||`${V}/metrics-collector-api/log-event`,BOOSTER:"flow-ai-obs"};});function l(...t){if(process.env[f.FLOW_OBS_DEBUG]!=="1")return;let e=`[${new Date().toISOString()}] ${t.join(" ")}
|
|
12
12
|
`;try{w.writeFileSync($n,e,{flag:"a"});}catch(r){process.stderr.write(`[flow-obs debug ERROR] ${r.message}
|
|
13
|
-
`);}}var $n,$=p(()=>{T();$n=pt.join(ue.tmpdir(),Ge);});function Bn(t){if(!Dn.test(t))throw new Error(`Invalid tenant value: "${t}". Tenant must be lowercase alphanumeric and hyphens (1-64 chars).`)}function Hn(t,e){let r=e.length>400?e.slice(0,400)+"\u2026":e;l("toAuthError",`status=${t} body=${r}`);try{let n=JSON.parse(e);if(typeof n.error=="string"&&(l("toAuthError",`api_error_code=${n.error}`+(n.message?` api_message=${n.message}`:"")),
|
|
14
|
-
`,{encoding:"utf8",mode:384});try{w__namespace.chmodSync(t,384);}catch{}}finally{qe(e);}return {settingsPath:t,preserved:r}}async function Xe(t){let e;try{e=(await
|
|
15
|
-
`,{encoding:"utf8",mode:384});try{w__namespace.chmodSync(e,384);}catch{}}finally{qe(r);}}var Yn,It=p(()=>{T();bt();Yn=ut.LOCK_STALE_MS;});function vt(){let t=ue__namespace.default.homedir();if(process.platform==="darwin")return pt__namespace.default.join(t,"Library","Preferences",Yt,Gt);if(process.platform==="win32"){let r=process.env.APPDATA??pt__namespace.default.join(t,"AppData","Roaming");return pt__namespace.default.join(r,Yt,Gt)}let e=process.env.XDG_CONFIG_HOME??pt__namespace.default.join(t,".config");return pt__namespace.default.join(e,Yt,Gt)}function fe(){try{let t=w__namespace.default.readFileSync(vt(),"utf8");return JSON.parse(t)}catch{return {}}}function ze(t){let e=vt();w__namespace.default.mkdirSync(pt__namespace.default.dirname(e),{recursive:true}),w__namespace.default.writeFileSync(e,JSON.stringify(t,null,2),{encoding:"utf8",mode:384});}var pe,qt,Ze=p(()=>{T();pe={credentials:"credentials","token-cache":"tokenCache"};qt=class{static isAvailable(){return true}static hasExistingData(){try{if(!w__namespace.default.existsSync(vt()))return !1;let e=JSON.parse(w__namespace.default.readFileSync(vt(),"utf8"));return !!(e&&e.credentials)}catch{return false}}async getSecret(e,r){let n=fe(),s=pe[r]??r,o=n[s];return o?typeof o=="string"?o:JSON.stringify(o):null}async setSecret(e,r,n){let s=fe(),o=pe[r]??r;if(r==="token-cache")try{s[o]=JSON.parse(n);}catch{s[o]=n;}else s[o]=n;ze(s);}async deleteSecret(e,r){let n=fe(),s=pe[r]??r;return s in n?(delete n[s],ze(n),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${vt()}`}};});var Qe={};U(Qe,{MacOsKeyVaultProvider:()=>ge});var me,ge,tr=p(()=>{me=util.promisify(child_process.execFile),ge=class{static async isAvailable(){try{return w.accessSync("/usr/bin/security",w.constants.X_OK),!0}catch{return false}}async getSecret(e,r){try{let{stdout:n}=await me("security",["find-generic-password","-w","-a",r,"-s",e]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await me("security",["add-generic-password","-U","-a",r,"-s",e,"-w",n]);}async deleteSecret(e,r){try{return await me("security",["delete-generic-password","-a",r,"-s",e]),!0}catch{return false}}getStoragePath(){return "macOS Keychain"}};});var rr={};U(rr,{LinuxKeyVaultProvider:()=>he});var er,he,nr=p(()=>{er=util.promisify(child_process.execFile),he=class{static async isAvailable(){let e=["/usr/bin/secret-tool","/bin/secret-tool","/usr/local/bin/secret-tool"];for(let r of e)try{return w.accessSync(r,w.constants.X_OK),!0}catch{}return false}async getSecret(e,r){try{let{stdout:n}=await er("secret-tool",["lookup","service",e,"account",r]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await new Promise((s,o)=>{let i=child_process.spawn("secret-tool",["store","--label",e,"service",e,"account",r]);i.on("error",o),i.on("close",a=>{a===0?s():o(new Error(`secret-tool exited with code ${a}`));}),i.stdin.write(n),i.stdin.end();});}async deleteSecret(e,r){try{return await er("secret-tool",["clear","service",e,"account",r]),!0}catch{return false}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var sr={};U(sr,{WindowsKeyVaultProvider:()=>Se});var Se,or=p(()=>{Se=class{static async isAvailable(){try{return await Dt("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return false}}async getSecret(e,r){return Dt("keytar").getPassword(e,r)}async setSecret(e,r,n){await Dt("keytar").setPassword(e,r,n);}async deleteSecret(e,r){return Dt("keytar").deletePassword(e,r)}getStoragePath(){return "Windows Credential Manager"}};});async function ir(){return await rs()??new qt}async function rs(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:t}=await Promise.resolve().then(()=>(tr(),Qe));return await t.isAvailable()?new t:null}case "linux":{let{LinuxKeyVaultProvider:t}=await Promise.resolve().then(()=>(nr(),rr));return await t.isAvailable()?new t:null}case "win32":{let{WindowsKeyVaultProvider:t}=await Promise.resolve().then(()=>(or(),sr));return await t.isAvailable()?new t:null}default:return null}}var ar=p(()=>{Ze();});function mt(){return Ee||(Ee=ir()),Ee}async function _(){let e=await(await mt()).getSecret(ft,we);if(!e)return null;try{return JSON.parse(e)}catch{return null}}async function ye(t){if(!t.clientId||!t.clientSecret||!t.tenant)throw new Error("clientId, clientSecret and tenant are required");await(await mt()).setSecret(ft,we,JSON.stringify(t));}async function cr(){let t=await mt();await t.deleteSecret(ft,we),await t.deleteSecret(ft,Te);}async function Jt(t){await(await mt()).setSecret(ft,Te,JSON.stringify({accessToken:t.accessToken,expiresAt:t.expiresAt}));}async function gt(){let e=await(await mt()).getSecret(ft,Te);if(!e)return null;try{let r=JSON.parse(e);return {accessToken:r.accessToken,expiresAt:r.expiresAt}}catch{return null}}async function ht(){let t=await gt();return t?new Date(t.expiresAt)>new Date:false}async function Q(){let t=await gt();if(!t||!t.accessToken)return null;try{let e=t.accessToken.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8"));return r.email??r.preferred_username??r.upn??r.sub??null}catch{return null}}async function _e(){let t=await mt();if(typeof t.getStoragePath=="function")return t.getStoragePath();let e=process.platform;return e==="darwin"?"macOS Keychain":e==="win32"?"Windows Credential Manager":"Linux Secret Service (libsecret)"}async function lr(){let t=await _();return !!(t&&t.clientId&&t.clientSecret&&t.tenant)}var ft,we,Te,Ee,St=p(()=>{ar();T();ft=Vt.SERVICE,we=Vt.ACCOUNT_CREDS,Te=Vt.ACCOUNT_TOKEN,Ee=null;});function ss(t){return ns.some(e=>e.test(t))}function os(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8"));return r.email||r.preferred_username||r.upn||r.sub||null}catch{return null}}function Y(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8")),{clientId:n,clientSecret:s,tenant:o}=r;return !n||!s||!o?null:{clientId:n,clientSecret:s,tenant:o}}catch{return null}}function dr(t){let e=Buffer.from(JSON.stringify({alg:"none",typ:"JWT"})).toString("base64url"),r=Buffer.from(JSON.stringify({clientId:t.clientId,clientSecret:t.clientSecret,tenant:t.tenant})).toString("base64url");return `${e}.${r}.`}function ur(t){let e;try{e=new URL(t);}catch{throw new Error(`Invalid URL: ${t}`)}let r=process.env[f.FLOW_OBS_ALLOW_HTTP]==="true";if(!r&&e.protocol!=="https:")throw new Error(`URL must use HTTPS: ${t}`);if(e.username||e.password)throw new Error(`URL must not contain embedded credentials: ${t}`);if(!r&&ss(e.hostname))throw new Error(`SSRF: private/loopback host not allowed: ${e.hostname}`);return t}async function pr(){let t=Y(process.env[f.ANTHROPIC_AUTH_TOKEN]);if(t)return {user:await Q().catch(()=>null)??t.clientId,tenant:t.tenant};if(Kt.KEYCHAIN_ENABLED)try{let e=await _();if(!e)return {user:"",tenant:""};let r=await Q()??e.clientId??"",n=e.tenant??"";return {user:r,tenant:n}}catch{return {user:"",tenant:""}}return {user:"",tenant:""}}async function is(t){if(await ht()){let r=await gt();return l("getOrRefreshToken",`using cached token, expires=${r.expiresAt}`),r.accessToken}l("getOrRefreshToken",`token expired \u2014 refreshing via auth-engine (tenant=${t.tenant} clientId=${t.clientId})`);let e=await V(t);try{await Jt(e);}catch(r){l("getOrRefreshToken",`token cache save failed (non-fatal): ${r.message}`);}return l("getOrRefreshToken",`token refreshed, expires=${e.expiresAt}`),e.accessToken}function as(t,e){let r=e&&e.accessToken?e.accessToken:"";return {endpoint:t.replace(/\/$/,"")+"/flow-langfuse-gateway/v1/traces",authHeader:`Bearer ${r}`}}function cs(t,e,r){let n=Buffer.from(`${e}:${r}`).toString("base64");return {endpoint:t.replace(/\/$/,"")+"/api/public/otel/v1/traces",authHeader:`Basic ${n}`}}async function tt(){let t=[],e=process.env[f.ANTHROPIC_MODEL]??"",r=Y(process.env[f.ANTHROPIC_AUTH_TOKEN]);l("resolveCredentials",r?"credentials resolved from ANTHROPIC_AUTH_TOKEN":"ANTHROPIC_AUTH_TOKEN absent or invalid"),!r&&Kt.KEYCHAIN_ENABLED&&(r=await _(),r&&l("resolveCredentials","credentials resolved from keychain (FEATURES.KEYCHAIN_ENABLED=true)"));let n=r?r.tenant:"",s=process.env[f.FLOW_TELEMETRY]==="true",o=process.env[f.LANGFUSE_BASE_URL],i=process.env[f.LANGFUSE_PUBLIC_KEY],a=process.env[f.LANGFUSE_SECRET_KEY];if(s&&o&&i&&a){let m="",k=n;if(r)m=await Q().catch(()=>null)??r.clientId;else if(Kt.KEYCHAIN_ENABLED)try{let O=await _();O&&(m=await Q()??O.clientId,k=O.tenant);}catch{}let y={user:m??"",tenant:k??"",team:"",project:"",model:e};t.push({mode:"direct",...cs(ur(o),i,a),...y}),l("resolveCredentials","direct mode active",`user=${y.user}`,`tenant=${y.tenant}`);}if(!r){if(t.length===0){let m=[];return m.authError=false,m}return t}let c;try{c=await is(r);}catch(m){if(l("resolveCredentials",`token refresh failed: ${m.message}`,`(tenant=${r.tenant} clientId=${r.clientId})`),t.length>0)return t;let k=[];return k.authError=true,k}let S={user:os(c)??r.clientId,tenant:n,team:"",project:"",model:e},A=process.env[f.FLOW_TELEMETRY_GATEWAY]??X;return t.push({mode:"gateway",...as(ur(A),{accessToken:c}),...S}),t}async function fr(){return (await tt()).length>0}var ns,et=p(()=>{St();bt();T();$();ns=[/^localhost\.?$/i,/^127\./,/^10\./,/^172\.(1[6-9]|2\d|3[01])\./,/^192\.168\./,/^169\.254\./,/^0\.0\.0\.0$/,/^::1$/,/^\[::1\]$/,/^\[::ffff:/i,/^\[f[cd]/i,/^\[fe80:/i,/^metadata\.google\.internal\.?$/i,/^metadata\.azure\.internal\.?$/i,/(?:^|\.)localtest\.me\.?$/i,/(?:^|\.)lvh\.me\.?$/i,/(?:^|\.)vcap\.me\.?$/i];});var hr={};U(hr,{runLogin:()=>K,runLogout:()=>fs,runStatus:()=>ms});function G(t){return typeof t=="string"?t.replace(ls,""):t}function Pt(t,e={}){return new Promise((r,n)=>{let{masked:s=false,defaultValue:o=""}=e;process.stdout.write(t+o);let i=o;function a(){try{process.stdin.setRawMode(!1);}catch{}}process.once("uncaughtException",a),process.once("unhandledRejection",a);let c=S=>{if(S===""){u(),n(new Error("SIGINT"));return}if(S==="\r"||S===`
|
|
13
|
+
`);}}var $n,$=p(()=>{T();$n=pt.join(ue.tmpdir(),Ge);});function Bn(t){if(!Dn.test(t))throw new Error(`Invalid tenant value: "${t}". Tenant must be lowercase alphanumeric and hyphens (1-64 chars).`)}function Hn(t,e){let r=e.length>400?e.slice(0,400)+"\u2026":e;l("toAuthError",`status=${t} body=${r}`);try{let n=JSON.parse(e);if(typeof n.error=="string"&&(l("toAuthError",`api_error_code=${n.error}`+(n.message?` api_message=${n.message}`:"")),We[n.error]))return new Error(We[n.error])}catch{}return t===401||t===403||t===500?new Error("Invalid credentials"):t>=400&&t<500?new Error("Authentication request was rejected"):new Error("Authentication service unavailable, please try again later")}function Y(t){return new Promise((e,r)=>{try{Bn(t.tenant);}catch(u){return r(u)}let n=JSON.stringify({clientSecret:t.clientSecret}),s=new URL(z.AUTH_ENGINE),o=s.protocol==="https:",i={hostname:s.hostname,port:s.port||(o?443:80),path:s.pathname+s.search,method:"POST",headers:{"Content-Type":"application/json","Content-Length":Buffer.byteLength(n),FlowTenant:t.tenant}};l("getToken",`requesting token tenant=${t.tenant} host=${i.hostname} path=${i.path}`);let c=(o?kn__namespace.default:Mn__namespace.default).request(i,u=>{let S=[];u.on("data",A=>S.push(A)),u.on("end",()=>{let A=S.join("");if((u.statusCode??0)>=400)return r(Hn(u.statusCode??0,A));let m;try{m=JSON.parse(A);}catch{return r(new Error("Invalid response from auth engine"))}let k=m.expires_at??new Date(Date.now()+(m.expires_in??3600)*1e3).toISOString();e({accessToken:m.access_token??"",expiresAt:k});});});c.on("error",u=>r(new Error(`Network error: ${u.message}`))),c.write(n),c.end();})}var Dn,We,bt=p(()=>{T();$();Dn=/^[a-z0-9][a-z0-9-]{0,62}[a-z0-9]$|^[a-z0-9]$/;We={INVALID_CLIENT_SECRET:"Invalid Client Secret \u2014 check the value and try again",INVALID_CLIENT_ID:"Invalid Client ID \u2014 check the value and try again",INVALID_TENANT:"Invalid Tenant \u2014 check the value and try again",TENANT_NOT_FOUND:"Tenant not found \u2014 verify the tenant identifier"};});function dt(){return process.platform==="win32"?pt__namespace.join(process.env.APPDATA||pt__namespace.join(ue__namespace.homedir(),"AppData","Roaming"),"Claude","settings.json"):pt__namespace.join(ue__namespace.homedir(),".claude","settings.json")}function Ke(t){try{let e=w__namespace.statSync(t);Date.now()-e.mtimeMs>Yn&&w__namespace.unlinkSync(t);}catch{}try{w__namespace.writeFileSync(t,String(process.pid),{flag:"wx"});}catch(e){throw e.code==="EEXIST"?new Error("Another install is already in progress. If this is stale, remove: "+t):e}}function qe(t){try{w__namespace.unlinkSync(t);}catch{}}function Gn(t,e){let n=(Array.isArray(t)?t:[]).map(s=>{if(!Array.isArray(s?.hooks))return null;let o=s.hooks.filter(i=>!i.command?.startsWith?.("flow-ai-obs "));return o.length>0?{...s,hooks:o}:null}).filter(s=>s!=null);return [e,...n]}function Je(){let t=dt(),e=t+".lock",r=[];w__namespace.mkdirSync(pt__namespace.dirname(t),{recursive:true}),Ke(e);try{if(w__namespace.existsSync(t)){w__namespace.copyFileSync(t,t+".bkp");try{w__namespace.chmodSync(t+".bkp",384);}catch{}}let n={};try{n=JSON.parse(w__namespace.readFileSync(t,"utf8"));}catch{}let s=n.env&&typeof n.env=="object"?n.env:{};n.env={...lt,...Lt,...s},n.otelHeadersHelper="flow-ai-obs otel-headers",(!n.hooks||typeof n.hooks!="object"||Array.isArray(n.hooks))&&(n.hooks={});let o=(c,u)=>({matcher:"",hooks:[{type:"command",command:`flow-ai-obs ${c}`,timeout:u}]}),i=["UserPromptSubmit","PreToolUse","PostToolUse","Stop"],a=n.hooks;for(let c of i){let u=Gn(a[c],o(c,Ye[c]));u.length>1&&r.push(c),a[c]=u;}w__namespace.writeFileSync(t,JSON.stringify(n,null,2)+`
|
|
14
|
+
`,{encoding:"utf8",mode:384});try{w__namespace.chmodSync(t,384);}catch{}}finally{qe(e);}return {settingsPath:t,preserved:r}}async function Xe(t){let e;try{e=(await Y(t)).accessToken;}catch{return false}return e?new Promise(r=>{de(`Bearer ${e}`,r,1);}):false}function de(t,e,r){let n=new URL(z.GATEWAY_TRACES),s=JSON.stringify({resourceSpans:[],validation_run:true}),o=n.protocol==="https:",i={hostname:n.hostname,port:n.port||(o?443:80),path:n.pathname,method:"POST",headers:{"Content-Type":"application/json",Authorization:t,"Content-Length":Buffer.byteLength(s)}},c=(o?kn__namespace:Mn__namespace).request(i,u=>{u.resume(),u.statusCode===200||u.statusCode===204?e(true):r<ut.CONNECTIVITY_MAX_RETRY?setTimeout(()=>de(t,e,r+1),ut.CONNECTIVITY_RETRY_MS):e(false);});c.on("error",()=>{r<ut.CONNECTIVITY_MAX_RETRY?setTimeout(()=>de(t,e,r+1),ut.CONNECTIVITY_RETRY_MS):e(false);}),c.write(s),c.end();}function Kt(t){let e=dt(),r=e+".lock";w__namespace.mkdirSync(pt__namespace.dirname(e),{recursive:true}),Ke(r);try{let n={};try{n=JSON.parse(w__namespace.readFileSync(e,"utf8"));}catch{}(!n.env||typeof n.env!="object")&&(n.env={}),Object.assign(n.env,t),w__namespace.writeFileSync(e,JSON.stringify(n,null,2)+`
|
|
15
|
+
`,{encoding:"utf8",mode:384});try{w__namespace.chmodSync(e,384);}catch{}}finally{qe(r);}}var Yn,It=p(()=>{T();bt();Yn=ut.LOCK_STALE_MS;});function vt(){let t=ue__namespace.default.homedir();if(process.platform==="darwin")return pt__namespace.default.join(t,"Library","Preferences",Yt,Gt);if(process.platform==="win32"){let r=process.env.APPDATA??pt__namespace.default.join(t,"AppData","Roaming");return pt__namespace.default.join(r,Yt,Gt)}let e=process.env.XDG_CONFIG_HOME??pt__namespace.default.join(t,".config");return pt__namespace.default.join(e,Yt,Gt)}function fe(){try{let t=w__namespace.default.readFileSync(vt(),"utf8");return JSON.parse(t)}catch{return {}}}function ze(t){let e=vt();w__namespace.default.mkdirSync(pt__namespace.default.dirname(e),{recursive:true}),w__namespace.default.writeFileSync(e,JSON.stringify(t,null,2),{encoding:"utf8",mode:384});}var pe,qt,Ze=p(()=>{T();pe={credentials:"credentials","token-cache":"tokenCache"};qt=class{static isAvailable(){return true}static hasExistingData(){try{if(!w__namespace.default.existsSync(vt()))return !1;let e=JSON.parse(w__namespace.default.readFileSync(vt(),"utf8"));return !!(e&&e.credentials)}catch{return false}}async getSecret(e,r){let n=fe(),s=pe[r]??r,o=n[s];return o?typeof o=="string"?o:JSON.stringify(o):null}async setSecret(e,r,n){let s=fe(),o=pe[r]??r;if(r==="token-cache")try{s[o]=JSON.parse(n);}catch{s[o]=n;}else s[o]=n;ze(s);}async deleteSecret(e,r){let n=fe(),s=pe[r]??r;return s in n?(delete n[s],ze(n),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${vt()}`}};});var Qe={};U(Qe,{MacOsKeyVaultProvider:()=>ge});var me,ge,tr=p(()=>{me=util.promisify(child_process.execFile),ge=class{static async isAvailable(){try{return w.accessSync("/usr/bin/security",w.constants.X_OK),!0}catch{return false}}async getSecret(e,r){try{let{stdout:n}=await me("security",["find-generic-password","-w","-a",r,"-s",e]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await me("security",["add-generic-password","-U","-a",r,"-s",e,"-w",n]);}async deleteSecret(e,r){try{return await me("security",["delete-generic-password","-a",r,"-s",e]),!0}catch{return false}}getStoragePath(){return "macOS Keychain"}};});var rr={};U(rr,{LinuxKeyVaultProvider:()=>he});var er,he,nr=p(()=>{er=util.promisify(child_process.execFile),he=class{static async isAvailable(){let e=["/usr/bin/secret-tool","/bin/secret-tool","/usr/local/bin/secret-tool"];for(let r of e)try{return w.accessSync(r,w.constants.X_OK),!0}catch{}return false}async getSecret(e,r){try{let{stdout:n}=await er("secret-tool",["lookup","service",e,"account",r]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await new Promise((s,o)=>{let i=child_process.spawn("secret-tool",["store","--label",e,"service",e,"account",r]);i.on("error",o),i.on("close",a=>{a===0?s():o(new Error(`secret-tool exited with code ${a}`));}),i.stdin.write(n),i.stdin.end();});}async deleteSecret(e,r){try{return await er("secret-tool",["clear","service",e,"account",r]),!0}catch{return false}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var sr={};U(sr,{WindowsKeyVaultProvider:()=>Se});var Se,or=p(()=>{Se=class{static async isAvailable(){try{return await Dt("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return false}}async getSecret(e,r){return Dt("keytar").getPassword(e,r)}async setSecret(e,r,n){await Dt("keytar").setPassword(e,r,n);}async deleteSecret(e,r){return Dt("keytar").deletePassword(e,r)}getStoragePath(){return "Windows Credential Manager"}};});async function ir(){return await rs()??new qt}async function rs(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:t}=await Promise.resolve().then(()=>(tr(),Qe));return await t.isAvailable()?new t:null}case "linux":{let{LinuxKeyVaultProvider:t}=await Promise.resolve().then(()=>(nr(),rr));return await t.isAvailable()?new t:null}case "win32":{let{WindowsKeyVaultProvider:t}=await Promise.resolve().then(()=>(or(),sr));return await t.isAvailable()?new t:null}default:return null}}var ar=p(()=>{Ze();});function mt(){return Ee||(Ee=ir()),Ee}async function _(){let e=await(await mt()).getSecret(ft,we);if(!e)return null;try{return JSON.parse(e)}catch{return null}}async function ye(t){if(!t.clientId||!t.clientSecret||!t.tenant)throw new Error("clientId, clientSecret and tenant are required");await(await mt()).setSecret(ft,we,JSON.stringify(t));}async function cr(){let t=await mt();await t.deleteSecret(ft,we),await t.deleteSecret(ft,Te);}async function Jt(t){await(await mt()).setSecret(ft,Te,JSON.stringify({accessToken:t.accessToken,expiresAt:t.expiresAt}));}async function gt(){let e=await(await mt()).getSecret(ft,Te);if(!e)return null;try{let r=JSON.parse(e);return {accessToken:r.accessToken,expiresAt:r.expiresAt}}catch{return null}}async function ht(){let t=await gt();return t?new Date(t.expiresAt)>new Date:false}async function Q(){let t=await gt();if(!t||!t.accessToken)return null;try{let e=t.accessToken.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8"));return r.email??r.preferred_username??r.upn??r.sub??null}catch{return null}}async function _e(){let t=await mt();if(typeof t.getStoragePath=="function")return t.getStoragePath();let e=process.platform;return e==="darwin"?"macOS Keychain":e==="win32"?"Windows Credential Manager":"Linux Secret Service (libsecret)"}async function lr(){let t=await _();return !!(t&&t.clientId&&t.clientSecret&&t.tenant)}var ft,we,Te,Ee,St=p(()=>{ar();T();ft=Vt.SERVICE,we=Vt.ACCOUNT_CREDS,Te=Vt.ACCOUNT_TOKEN,Ee=null;});function ss(t){return ns.some(e=>e.test(t))}function os(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8"));return r.email||r.preferred_username||r.upn||r.sub||null}catch{return null}}function G(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8")),{clientId:n,clientSecret:s,tenant:o}=r;return !n||!s||!o?null:{clientId:n,clientSecret:s,tenant:o}}catch{return null}}function dr(t){let e=Buffer.from(JSON.stringify({alg:"none",typ:"JWT"})).toString("base64url"),r=Buffer.from(JSON.stringify({clientId:t.clientId,clientSecret:t.clientSecret,tenant:t.tenant})).toString("base64url");return `${e}.${r}.`}function ur(t){let e;try{e=new URL(t);}catch{throw new Error(`Invalid URL: ${t}`)}let r=process.env[f.FLOW_OBS_ALLOW_HTTP]==="true";if(!r&&e.protocol!=="https:")throw new Error(`URL must use HTTPS: ${t}`);if(e.username||e.password)throw new Error(`URL must not contain embedded credentials: ${t}`);if(!r&&ss(e.hostname))throw new Error(`SSRF: private/loopback host not allowed: ${e.hostname}`);return t}async function pr(){let t=G(process.env[f.ANTHROPIC_AUTH_TOKEN]);if(t)return {user:await Q().catch(()=>null)??t.clientId,tenant:t.tenant};if(Wt.KEYCHAIN_ENABLED)try{let e=await _();if(!e)return {user:"",tenant:""};let r=await Q()??e.clientId??"",n=e.tenant??"";return {user:r,tenant:n}}catch{return {user:"",tenant:""}}return {user:"",tenant:""}}async function is(t){if(await ht()){let r=await gt();return l("getOrRefreshToken",`using cached token, expires=${r.expiresAt}`),r.accessToken}l("getOrRefreshToken",`token expired \u2014 refreshing via auth-engine (tenant=${t.tenant} clientId=${t.clientId})`);let e=await Y(t);try{await Jt(e);}catch(r){l("getOrRefreshToken",`token cache save failed (non-fatal): ${r.message}`);}return l("getOrRefreshToken",`token refreshed, expires=${e.expiresAt}`),e.accessToken}function as(t,e){let r=e&&e.accessToken?e.accessToken:"";return {endpoint:t.replace(/\/$/,"")+"/flow-langfuse-gateway/v1/traces",authHeader:`Bearer ${r}`}}function cs(t,e,r){let n=Buffer.from(`${e}:${r}`).toString("base64");return {endpoint:t.replace(/\/$/,"")+"/api/public/otel/v1/traces",authHeader:`Basic ${n}`}}async function tt(){let t=[],e=process.env[f.ANTHROPIC_MODEL]??"",r=G(process.env[f.ANTHROPIC_AUTH_TOKEN]);l("resolveCredentials",r?"credentials resolved from ANTHROPIC_AUTH_TOKEN":"ANTHROPIC_AUTH_TOKEN absent or invalid"),!r&&Wt.KEYCHAIN_ENABLED&&(r=await _(),r&&l("resolveCredentials","credentials resolved from keychain (FEATURES.KEYCHAIN_ENABLED=true)"));let n=r?r.tenant:"",s=process.env[f.FLOW_TELEMETRY]==="true",o=process.env[f.LANGFUSE_BASE_URL],i=process.env[f.LANGFUSE_PUBLIC_KEY],a=process.env[f.LANGFUSE_SECRET_KEY];if(s&&o&&i&&a){let m="",k=n;if(r)m=await Q().catch(()=>null)??r.clientId;else if(Wt.KEYCHAIN_ENABLED)try{let O=await _();O&&(m=await Q()??O.clientId,k=O.tenant);}catch{}let y={user:m??"",tenant:k??"",team:"",project:"",model:e};t.push({mode:"direct",...cs(ur(o),i,a),...y}),l("resolveCredentials","direct mode active",`user=${y.user}`,`tenant=${y.tenant}`);}if(!r){if(t.length===0){let m=[];return m.authError=false,m}return t}let c;try{c=await is(r);}catch(m){if(l("resolveCredentials",`token refresh failed: ${m.message}`,`(tenant=${r.tenant} clientId=${r.clientId})`),t.length>0)return t;let k=[];return k.authError=true,k}let S={user:os(c)??r.clientId,tenant:n,team:"",project:"",model:e},A=process.env[f.FLOW_TELEMETRY_GATEWAY]??V;return t.push({mode:"gateway",...as(ur(A),{accessToken:c}),...S}),t}async function fr(){return (await tt()).length>0}var ns,et=p(()=>{St();bt();T();$();ns=[/^localhost\.?$/i,/^127\./,/^10\./,/^172\.(1[6-9]|2\d|3[01])\./,/^192\.168\./,/^169\.254\./,/^0\.0\.0\.0$/,/^::1$/,/^\[::1\]$/,/^\[::ffff:/i,/^\[f[cd]/i,/^\[fe80:/i,/^metadata\.google\.internal\.?$/i,/^metadata\.azure\.internal\.?$/i,/(?:^|\.)localtest\.me\.?$/i,/(?:^|\.)lvh\.me\.?$/i,/(?:^|\.)vcap\.me\.?$/i];});var hr={};U(hr,{runLogin:()=>K,runLogout:()=>fs,runStatus:()=>ms});function W(t){return typeof t=="string"?t.replace(ls,""):t}function Pt(t,e={}){return new Promise((r,n)=>{let{masked:s=false,defaultValue:o=""}=e;process.stdout.write(t+o);let i=o;function a(){try{process.stdin.setRawMode(!1);}catch{}}process.once("uncaughtException",a),process.once("unhandledRejection",a);let c=S=>{if(S===""){u(),n(new Error("SIGINT"));return}if(S==="\r"||S===`
|
|
16
16
|
`){u(),process.stdout.write(`
|
|
17
|
-
`),r(i);return}if(S==="\x7F"){i.length>0&&(i=i.slice(0,-1),process.stdout.write("\b \b"));return}S.startsWith("\x1B")||(i+=S,process.stdout.write(s?"*".repeat(S.length):S));};function u(){process.stdin.setRawMode(false),process.stdin.removeListener("data",c),process.removeListener("uncaughtException",a),process.removeListener("unhandledRejection",a);}process.stdin.setRawMode(true),process.stdin.resume(),process.stdin.setEncoding("utf8"),process.stdin.on("data",c);})}async function mr(t){try{let e=await _();(!e||e.clientId!==t.clientId||e.clientSecret!==t.clientSecret||e.tenant!==t.tenant)&&await ye(t);}catch{}}async function gr(t){let{accessToken:e,expiresAt:r}=await
|
|
17
|
+
`),r(i);return}if(S==="\x7F"){i.length>0&&(i=i.slice(0,-1),process.stdout.write("\b \b"));return}S.startsWith("\x1B")||(i+=S,process.stdout.write(s?"*".repeat(S.length):S));};function u(){process.stdin.setRawMode(false),process.stdin.removeListener("data",c),process.removeListener("uncaughtException",a),process.removeListener("unhandledRejection",a);}process.stdin.setRawMode(true),process.stdin.resume(),process.stdin.setEncoding("utf8"),process.stdin.on("data",c);})}async function mr(t){try{let e=await _();(!e||e.clientId!==t.clientId||e.clientSecret!==t.clientSecret||e.tenant!==t.tenant)&&await ye(t);}catch{}}async function gr(t){let{accessToken:e,expiresAt:r}=await Y(t);await ye(t),await Jt({accessToken:e,expiresAt:r});try{let n=dr(t);Kt({[f.ANTHROPIC_AUTH_TOKEN]:n});}catch{}}async function us(t){try{return await gr(t),process.stdout.write(P(` \u2713 Setup complete. Tenant: ${W(t.tenant)}
|
|
18
18
|
|
|
19
|
-
`)),0}catch(e){return process.stderr.write(D(` \u2717 Authentication failed: ${
|
|
19
|
+
`)),0}catch(e){return process.stderr.write(D(` \u2717 Authentication failed: ${W(e.message)}
|
|
20
20
|
`)),1}}async function ds(){try{process.stdout.write(`
|
|
21
21
|
`);let t=(await Pt(B(" ? ")+"Client ID: ")).trim(),e=(await Pt(B(" ? ")+"Client Secret: ",{masked:!0})).trim(),r=(await Pt(B(" ? ")+"Tenant: ")).trim();if(!t||!e||!r)return process.stderr.write(D(` \u2717 All fields are required
|
|
22
|
-
`)),1;try{await gr({clientId:t,clientSecret:e,tenant:r});}catch(n){return process.stderr.write(D(` \u2717 Authentication failed: ${
|
|
23
|
-
`)),1}return process.stdout.write(P(` \u2713 Setup complete. Tenant: ${
|
|
22
|
+
`)),1;try{await gr({clientId:t,clientSecret:e,tenant:r});}catch(n){return process.stderr.write(D(` \u2717 Authentication failed: ${W(n.message)}
|
|
23
|
+
`)),1}return process.stdout.write(P(` \u2713 Setup complete. Tenant: ${W(r)}
|
|
24
24
|
`)),process.stdout.write(` Storage: ${await _e()}
|
|
25
25
|
|
|
26
26
|
`),0}catch(t){if(t.message==="SIGINT")throw t;return process.stderr.write(D(` \u2717 Unexpected error: ${t.message}
|
|
27
|
-
`)),1}}async function K(t={}){if(t.clientId&&t.clientSecret&&t.tenant)return us({clientId:t.clientId,clientSecret:t.clientSecret,tenant:t.tenant});let e=
|
|
27
|
+
`)),1}}async function K(t={}){if(t.clientId&&t.clientSecret&&t.tenant)return us({clientId:t.clientId,clientSecret:t.clientSecret,tenant:t.tenant});let e=G(process.env[f.ANTHROPIC_AUTH_TOKEN]);e&&await mr(e);let r=e||await _();if(r){process.stdout.write(`
|
|
28
28
|
`),process.stdout.write(H(` Already authenticated
|
|
29
|
-
`)),process.stdout.write(E(" Tenant: ")+
|
|
30
|
-
`),process.stdout.write(E(" Client ID: ")+
|
|
29
|
+
`)),process.stdout.write(E(" Tenant: ")+W(r.tenant)+`
|
|
30
|
+
`),process.stdout.write(E(" Client ID: ")+W(r.clientId)+`
|
|
31
31
|
`),process.stdout.write(`
|
|
32
32
|
`);let n;try{n=await Pt(B(" ? ")+"Re-authenticate? (y/N): ");}catch(s){if(s.message==="SIGINT")return process.stdout.write(`
|
|
33
33
|
`),130;throw s}if(n.trim().toLowerCase()!=="y")return process.stdout.write(P(` \u2713 Using existing credentials.
|
|
@@ -39,10 +39,10 @@
|
|
|
39
39
|
`),130;throw t}}async function fs(t=false){if(!await lr())return process.stdout.write(L(` \u26A0 You are not authenticated
|
|
40
40
|
`)),0;if(!t){let e=await ps();if(e!==null)return e}try{return await cr(),process.stdout.write(P(` \u2713 Credentials removed successfully
|
|
41
41
|
`)),0}catch{return process.stderr.write(D(` \u2717 Error removing credentials
|
|
42
|
-
`)),1}}async function ms(){let t=
|
|
42
|
+
`)),1}}async function ms(){let t=G(process.env[f.ANTHROPIC_AUTH_TOKEN]);t&&await mr(t);let e=t||await _();if(!e)return process.stdout.write(L(" \u26A0 Not authenticated. Run `flow-ai-obs auth login` to set up.\n")),0;if(!t&&!await ht())return process.stdout.write(L(" \u26A0 Session expired. Run `flow-ai-obs auth login` to re-authenticate.\n")),0;let r=e.clientSecret.length>4?"****...****"+e.clientSecret.slice(-4):"****",n=t?"ANTHROPIC_AUTH_TOKEN (settings.json)":await _e();return process.stdout.write(`
|
|
43
43
|
`+H(` Authenticated
|
|
44
|
-
`)),process.stdout.write(E(" Tenant: ")+
|
|
45
|
-
`),process.stdout.write(E(" Client ID: ")+
|
|
44
|
+
`)),process.stdout.write(E(" Tenant: ")+W(e.tenant)+`
|
|
45
|
+
`),process.stdout.write(E(" Client ID: ")+W(e.clientId)+`
|
|
46
46
|
`),process.stdout.write(E(" Client Secret: ")+r+`
|
|
47
47
|
`),process.stdout.write(E(" Storage: ")+n+`
|
|
48
48
|
|
|
@@ -86,7 +86,7 @@
|
|
|
86
86
|
Setup aborted. Run \`flow-ai-obs auth login\` to retry.
|
|
87
87
|
|
|
88
88
|
`),e;process.stdout.write(`
|
|
89
|
-
`);let r=await Ae();if(r!==0)return r;try{
|
|
89
|
+
`);let r=await Ae();if(r!==0)return r;try{Kt(Lt);}catch(s){process.stderr.write(` \u26A0 Could not write LLM Proxy config: ${s.message}
|
|
90
90
|
`);}process.stdout.write(H(" Flow LLM Proxy configured")+` (model provider)
|
|
91
91
|
`);for(let[s,o]of Object.entries(Lt))process.stdout.write(E(` ${s.padEnd(36)}`)+o+`
|
|
92
92
|
`);process.stdout.write(`
|
|
@@ -102,7 +102,7 @@
|
|
|
102
102
|
|
|
103
103
|
`)),0}var yr=p(()=>{T();at();Rt();Oe();It();St();});var _r={};U(_r,{runOtelHeaders:()=>Ts});async function Ts(){let t;try{t=await _();}catch{return process.stderr.write(`[flow-ai-obs otel-headers] Failed to read credentials
|
|
104
104
|
`),1}if(!t)return process.stderr.write(`[flow-ai-obs otel-headers] Not authenticated \u2014 run: flow-ai-obs auth login
|
|
105
|
-
`),1;let e;try{e=(await
|
|
105
|
+
`),1;let e;try{e=(await Y(t)).accessToken;}catch(r){return process.stderr.write(`[flow-ai-obs otel-headers] Token fetch failed: ${r.message}
|
|
106
106
|
`),1}return e?(process.stdout.write(`{"Authorization": "Bearer ${e}"}
|
|
107
107
|
`),0):(process.stderr.write(`[flow-ai-obs otel-headers] Empty token received
|
|
108
108
|
`),1)}var kr=p(()=>{St();bt();});var Or={};U(Or,{runCheck:()=>ys});function Le(t){return !t||t.length<=8?"****":t.slice(0,4)+"****...****"+t.slice(-4)}function Ct(t){process.stdout.write(` \u2713 ${t}
|
|
@@ -112,13 +112,13 @@
|
|
|
112
112
|
`);}function I(){process.stdout.write(`
|
|
113
113
|
`);}async function ys(){I(),process.stdout.write(` flow-claude-observability \u2014 configuration check
|
|
114
114
|
`),I(),process.stdout.write(` Auth
|
|
115
|
-
`);let t=
|
|
115
|
+
`);let t=G(process.env[f.ANTHROPIC_AUTH_TOKEN]),e=t||await _();if(!e){zt("Not authenticated \u2014 starting setup..."),I();let a=await K();if(a!==0)return a;if(t=G(process.env[f.ANTHROPIC_AUTH_TOKEN]),e=t||await _(),!e)return Zt("Authentication failed"),I(),1;I(),process.stdout.write(` Auth
|
|
116
116
|
`);}if(!t&&!await ht()){zt("Session expired \u2014 re-authenticating..."),I();let a=await K();if(a!==0)return a;I(),process.stdout.write(` Auth
|
|
117
117
|
`);}let r=await Q()||e.clientId;Ct("Authenticated"),b(`Tenant: ${e.tenant}`),b(`User: ${r}`),I(),process.stdout.write(` Native OTEL
|
|
118
118
|
`);let n={};try{let a=w__namespace.readFileSync(dt(),"utf8");n=JSON.parse(a).env||{};}catch{}let s=Object.keys(lt).filter(a=>!n[a]);if(s.length===0?(Ct("All OTEL env vars present in settings.json"),b(`Endpoint: ${n.OTEL_EXPORTER_OTLP_ENDPOINT}`)):(zt(`${s.length} OTEL var(s) missing from settings.json \u2014 native metrics/logs disabled`),s.forEach(a=>Zt(`Missing: ${a}`)),b("Run: flow-ai-obs install (restores missing vars automatically)")),I(),process.stdout.write(` Tracing
|
|
119
119
|
`),process.env[f.FLOW_TELEMETRY]==="true"){Ct("FLOW_TELEMETRY=true (direct mode enabled)");let a=[f.LANGFUSE_BASE_URL,f.LANGFUSE_PUBLIC_KEY,f.LANGFUSE_SECRET_KEY].filter(c=>!process.env[c]);a.length>0&&a.forEach(c=>zt(`Missing: ${c}`));}else b("FLOW_TELEMETRY not set \u2014 direct mode inactive (gateway mode may still be active)");let i=await tt();if(!i||i.length===0)return i&&i.authError?Zt("Token refresh failed \u2014 gateway mode could not activate"):(Zt("No active destinations \u2014 no traces will be sent"),b("For direct mode: set FLOW_TELEMETRY=true + LANGFUSE_BASE_URL + LANGFUSE_PUBLIC_KEY + LANGFUSE_SECRET_KEY"),b("For gateway mode: run flow-claude-observability auth login")),I(),1;for(let a of i)if(a.mode==="gateway"){let c=await gt();Ct("Mode: gateway"),b(`Endpoint: ${a.endpoint}`),b(`Token: ${Le(c?.accessToken)}`);}else a.mode==="direct"&&(Ct("Mode: direct"),b(`Endpoint: ${a.endpoint}`),b(`PK: ${Le(process.env[f.LANGFUSE_PUBLIC_KEY])}`),b(`SK: ${Le(process.env[f.LANGFUSE_SECRET_KEY])}`));return I(),process.stdout.write(` All checks passed \u2014 observability is active.
|
|
120
120
|
`),I(),0}var Lr=p(()=>{St();et();It();T();Rt();});function x(t,e){let r=typeof t=="object"?JSON.stringify(t):String(t??"");return r.length>e?r.slice(0,e)+" \u2026[truncated]":r}function Qt(t,e=100){return String(t??"").split(`
|
|
121
|
-
`)[0].slice(0,e).trim()}function br(){return new Promise(t=>{let e="";process.stdin.setEncoding("utf8"),process.stdin.on("data",r=>{e+=r;}),process.stdin.on("end",()=>{try{t(JSON.parse(e));}catch{t({});}});})}function C(t){process.stdout.write(JSON.stringify(t));}var Et=p(()=>{});function
|
|
121
|
+
`)[0].slice(0,e).trim()}function br(){return new Promise(t=>{let e="";process.stdin.setEncoding("utf8"),process.stdin.on("data",r=>{e+=r;}),process.stdin.on("end",()=>{try{t(JSON.parse(e));}catch{t({});}});})}function C(t){process.stdout.write(JSON.stringify(t));}var Et=p(()=>{});function q(){return String(BigInt(Date.now())*1000000n)}var be,rt,Ut=p(()=>{be=()=>crypto.randomBytes(16).toString("hex"),rt=()=>crypto.randomBytes(8).toString("hex");});function Rs(t,e){let r=pt.resolve(t);if(!r.startsWith(e))throw new Error(`Path traversal detected: ${t}`);return r}function Ie(t){if(!Ns.test(t))throw new Error(`Invalid session ID: ${t}`);return Rs(pt.join(ue.tmpdir(),`flow-obs-${t}.json`),Ps)}function wt(t){let e=Ie(t);if(!w.existsSync(e))return null;try{return JSON.parse(w.readFileSync(e,"utf8"))}catch{return null}}function Tt(t,e){w.writeFileSync(Ie(t),JSON.stringify(e),{encoding:"utf8",mode:384});}function ve(t){try{w.unlinkSync(Ie(t));}catch{}}var Ns,Ps,Ft=p(()=>{Ns=/^[0-9a-f-]{1,64}$/i,Ps=pt.normalize(ue.tmpdir())+pt.sep;});function Rr(t){if(!t||!w.existsSync(t))return null;try{let e=w.readFileSync(t,"utf8").trimEnd().split(`
|
|
122
122
|
`);for(let r=e.length-1;r>=0;r--)try{let n=JSON.parse(e[r]);if(n.type==="user"&&n.uuid)return n.uuid}catch{}}catch{}return null}function Ne(t){if(!t||!w.existsSync(t))return null;try{let e=w.readFileSync(t,"utf8").trimEnd().split(`
|
|
123
123
|
`),r=[],n=0,s=0;for(let o=e.length-1;o>=0;o--)try{let i=JSON.parse(e[o]);if(i.type==="user")break;if(i.type==="assistant"){let c=(i.message?.content??[]).filter(S=>S.type==="text").map(S=>S.text??"").join("");c&&r.unshift(c);let u=i.message?.usage??{};n+=(u.input_tokens??0)+(u.cache_read_input_tokens??0)+(u.cache_creation_input_tokens??0),s+=u.output_tokens??0;}}catch{}return !r.length&&n===0?null:{text:r.join(`
|
|
124
124
|
|
|
@@ -128,11 +128,11 @@
|
|
|
128
128
|
Traces will not be captured until you re-authenticate.
|
|
129
129
|
Run: flow-ai-obs auth login
|
|
130
130
|
|
|
131
|
-
`),l("UserPromptSubmit","auth expired \u2014 warning emitted to stderr"));}catch{}let s=Rr(t.transcript_path)||be(),o=$r(r),i=o?te(o,n):null,a=o?ee(o,n):null;Tt(e,{traceId:be(),spanId:rt(),startNs:
|
|
132
|
-
`,{flag:"a",encoding:"utf8",mode:384}),l("sendTraces:dump",`request appendada em ${Yr}`);}catch(i){l("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function
|
|
131
|
+
`),l("UserPromptSubmit","auth expired \u2014 warning emitted to stderr"));}catch{}let s=Rr(t.transcript_path)||be(),o=$r(r),i=o?te(o,n):null,a=o?ee(o,n):null;Tt(e,{traceId:be(),spanId:rt(),startNs:q(),sessionId:e,prompt:r,cwd:n,traceName:s,transcriptPath:t.transcript_path||"",model:process.env[f.ANTHROPIC_MODEL]||"",toolCalls:[],spans:[],pendingTool:null,slashSkill:o,skillContent:i,skillArtifacts:a}),l("UserPromptSubmit",`sid=${e}`,`traceName=${s}`,`slashSkill=${o}`),C(t);}var Dr=p(()=>{Ut();Ft();Pe();re();Et();$();T();et();});async function Br(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},s=wt(e);s&&(s.pendingTool={name:r,inputStr:x(n,F.TOOL_INPUT),startNs:q()},Tt(e,s)),l("PreToolUse",`sid=${e}`,`tool=${r}`,`stateFound=${!!s}`),C(t);}var Hr=p(()=>{Ut();Ft();Et();$();T();});function d(t,e){return e==null||e===""?null:{key:t,value:{stringValue:String(e)}}}function nt(...t){return t.filter(e=>e!==null)}function jr(t,e){return {resourceSpans:[{resource:{attributes:t},scopeSpans:[{scope:Bs,spans:Array.isArray(e)?e:[e]}]}]}}var Bs,h,Vr=p(()=>{T();Bs={name:le.SCOPE_NAME,version:le.SCOPE_VERSION},h={TRACE_NAME:"langfuse.trace.name",TRACE_INPUT:"langfuse.trace.input",TRACE_OUTPUT:"langfuse.trace.output",TRACE_METADATA:"langfuse.trace.metadata",TRACE_TAGS:"langfuse.trace.tags",USER_ID:"langfuse.user.id",SESSION_ID:"langfuse.session.id",OBS_NAME:"langfuse.observation.name",OBS_INPUT:"langfuse.observation.input",OBS_OUTPUT:"langfuse.observation.output",OBS_LEVEL:"langfuse.observation.level",OBS_TYPE:"langfuse.observation.type",MODEL:"gen_ai.request.model",INPUT_TOKENS:"gen_ai.usage.input_tokens",OUTPUT_TOKENS:"gen_ai.usage.output_tokens"};});function Gr(t,e,r,n,s){if(process.env[f.FLOW_OBS_DEBUG]!=="1")return;let o=JSON.stringify({ts:new Date().toISOString(),request:{method:"POST",url:t,headers:e,body:JSON.parse(r)},response:{status:n,body:s}});try{w.writeFileSync(Yr,o+`
|
|
132
|
+
`,{flag:"a",encoding:"utf8",mode:384}),l("sendTraces:dump",`request appendada em ${Yr}`);}catch(i){l("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function Ws(t){let e=new URL(t),r=new URL(z.GATEWAY_HEALTH);return r.hostname=e.hostname,r.port=e.port,r.protocol=e.protocol,r}function Wr(t,e){return new Promise((r,n)=>{let s=t._isSSL?kn__namespace.default:Mn__namespace.default;t.headers=Object.assign({},t.headers,{Connection:"close"});let o=s.request(t,i=>{let a=[];i.on("data",c=>a.push(c)),i.on("end",()=>r({statusCode:i.statusCode??0,body:a.join("")}));});o.setTimeout(1e4,()=>{o.destroy(new Error("Request timeout"));}),o.on("error",i=>n(new Error(`Network error: ${i.message}`))),e&&o.write(e),o.end();})}async function Kr(t,e){let r;try{r=Ws(t);}catch{return false}let n=r.protocol==="https:";try{let s={};e&&(s.Authorization=String(e).replace(/[\r\n]/g,""));let o=await Wr({hostname:r.hostname,port:r.port||(n?443:80),path:r.pathname,method:"GET",headers:s,_isSSL:n},null);return l("checkHealth",`url=${r.href} status=${o.statusCode}`),o.statusCode>=200&&o.statusCode<300}catch{return false}}async function ne(t,e,r){let n=JSON.stringify(t),s=new URL(e),o=s.protocol==="https:",i=String(r).replace(/[\r\n]/g,""),a={"Content-Type":"application/json",Authorization:i,"Content-Length":Buffer.byteLength(n)};l("sendTraces:request",`POST ${e}`),l("sendTraces:request",`headers=${JSON.stringify({...a,Authorization:i.slice(0,20)+"\u2026"})}`),l("sendTraces:request",`body=${n.slice(0,500)}${n.length>500?"\u2026":""}`);try{let c=await Wr({hostname:s.hostname,port:s.port||(o?443:80),path:s.pathname,method:"POST",headers:a,_isSSL:o},n);return l("sendTraces:response",`status=${c.statusCode}`),Gr(e,a,n,c.statusCode,c.body),c.statusCode}catch(c){return l("sendTraces:error",c.message),Gr(e,a,n,0,c.message),0}}var Yr,qr=p(()=>{T();$();Yr=pt.join(ue.tmpdir(),"flow-obs-requests.ndjson");});function Ks(){let t=parseInt(process.env[f.BUFFER_TTL_DAYS]??"",10);return (Number.isFinite(t)?Math.max(R.MIN_TTL_DAYS,Math.min(R.MAX_TTL_DAYS,t)):R.DEFAULT_TTL_DAYS)*24*60*60*1e3}function qs(){let t=parseInt(process.env[f.BUFFER_MAX_FILES]??"",10);return Number.isFinite(t)?Math.max(R.MIN_MAX_FILES,Math.min(R.MAX_MAX_FILES,t)):R.DEFAULT_MAX_FILES}function Xr(t){if(/[/\\]/.test(t))throw new Error(`Invalid buffer fileId: ${t}`);return pt__namespace.default.join(ue__namespace.default.tmpdir(),`${R.FILE_PREFIX}${t}.json`)}function Ce(){let t=ue__namespace.default.tmpdir(),e;try{e=w__namespace.default.readdirSync(t);}catch{return []}return e.filter(r=>r.startsWith(R.FILE_PREFIX)&&r.endsWith(".json")).map(r=>{let n=pt__namespace.default.join(t,r),s=0;try{s=w__namespace.default.statSync(n).mtimeMs;}catch{}return {full:n,mtime:s}}).sort((r,n)=>r.mtime-n.mtime).map(r=>r.full)}function $t(t){try{let e=qs(),r=Ce();if(r.length>=e){let o=r.slice(0,r.length-e+1);for(let i of o)try{w__namespace.default.unlinkSync(i);}catch{}}let n=`${Date.now()}-${Math.random().toString(36).slice(2,8)}`,s={fileId:n,bufferedAt:Date.now(),payload:t};return w__namespace.default.writeFileSync(Xr(n),JSON.stringify(s),{encoding:"utf8",mode:384}),l("buffer",`saved fileId=${n}`),n}catch(e){return l("buffer",`saveToBuffer failed: ${e.message}`),null}}function zr(t){let e=Ce(),r=t!=null&&t>0?t:e.length,n=[];for(let s of e){if(n.length>=r)break;try{let o=w__namespace.default.readFileSync(s,"utf8"),i=JSON.parse(o);i&&i.fileId&&i.payload&&n.push(i);}catch{l("buffer",`skipping malformed file: ${s}`);}}return n}function Zr(t){try{w__namespace.default.unlinkSync(Xr(t)),l("buffer",`deleted fileId=${t}`);}catch{}}function Qr(){let t=Date.now()-Ks();for(let e of Ce())try{let{mtimeMs:r}=w__namespace.default.statSync(e);r<t&&(w__namespace.default.unlinkSync(e),l("buffer",`evicted stale: ${pt__namespace.default.basename(e)}`));}catch{}}var tn=p(()=>{T();$();});async function Js(t){Qr();let e=zr(R.REPLAY_BATCH_SIZE);e.length&&(l("replayBufferedTraces",`replaying ${e.length} buffered trace(s)`),await Promise.allSettled(e.map(async r=>{try{let n=await ne(r.payload,t.endpoint,t.authHeader);n>=200&&n<300?(Zr(r.fileId),l("replayBufferedTraces",`replayed fileId=${r.fileId} status=${n}`)):l("replayBufferedTraces",`replay failed fileId=${r.fileId} status=${n}`);}catch(n){l("replayBufferedTraces",`replay error fileId=${r.fileId}: ${n.message}`);}})));}async function en(t){let e=await tt();if(!e.length)return e.authError&&(l("postToLangfuse","auth refresh failed \u2014 buffering trace"),$t(t)),0;let r=await Promise.all(e.map(async o=>{if(o.mode!=="gateway")return {creds:o,healthy:true};let i=await Kr(o.endpoint,o.authHeader);return {creds:o,healthy:i}})),n=r.find(o=>o.creds.mode==="gateway"&&o.healthy)?.creds??r.find(o=>o.creds.mode==="direct")?.creds;return n&&await Js(n),(await Promise.all(r.map(async({creds:o,healthy:i})=>{if(o.mode==="gateway"){if(!i)return l("postToLangfuse","gateway health check failed \u2014 buffering trace"),$t(t),0;let c=await ne(t,o.endpoint,o.authHeader);return (c===0||c>=500)&&(l("postToLangfuse",`gateway send failed (status ${c}) \u2014 buffering trace`),$t(t)),c}let a=await ne(t,o.endpoint,o.authHeader);return (a===0||a>=500)&&(l("postToLangfuse",`direct endpoint unavailable (status ${a}) \u2014 buffering trace`),$t(t)),a}))).find(o=>o!==0)??0}var rn=p(()=>{et();$();qr();tn();T();});var Ue=p(()=>{Vr();rn();});function _t(t){if(t==null)return "";let e=typeof t=="string"?t:JSON.stringify(t);return Xs.reduce((r,{re:n,replace:s})=>r.replace(n,s),e)}var v,Xs,Fe=p(()=>{v="[REDACTED]",Xs=[{re:/\b(sk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`sk-${v}`},{re:/\b(pk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`pk-${v}`},{re:/\b(Bearer\s+)[A-Za-z0-9\-._~+/]+=*/gi,replace:(t,e)=>`${e}${v}`},{re:/\b(Basic\s+)[A-Za-z0-9+/]+=*/gi,replace:(t,e)=>`${e}${v}`},{re:/(-----BEGIN [A-Z ]+-----)[^-]*(-----END [A-Z ]+-----)/g,replace:(t,e,r)=>`${e}
|
|
133
133
|
${v}
|
|
134
|
-
${r}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${v}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${v}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${v}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${v}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${v}`},{re:/\b([A-Z0-9_]*(?:SECRET|TOKEN|KEY|PASSWORD|PASSWD|PWD|CREDENTIAL|API)[A-Z0-9_]*\s*=\s*)(['"]?)([^\s'"#\n]+)\2/gi,replace:(t,e,r)=>`${e}${r}${v}${r}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${v}@`}];});async function nn(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},s=t.tool_response||"",o=wt(e);if(!o){C(t);return}let i=
|
|
135
|
-
`)),y=u?.inputTokens??0,O=u?.outputTokens??0,Mt=i.map((g,
|
|
134
|
+
${r}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${v}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${v}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${v}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${v}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${v}`},{re:/\b([A-Z0-9_]*(?:SECRET|TOKEN|KEY|PASSWORD|PASSWD|PWD|CREDENTIAL|API)[A-Z0-9_]*\s*=\s*)(['"]?)([^\s'"#\n]+)\2/gi,replace:(t,e,r)=>`${e}${r}${v}${r}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${v}@`}];});async function nn(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},s=t.tool_response||"",o=wt(e);if(!o){C(t);return}let i=q(),a=o.pendingTool,c=a?.name===r,u=c?a.startNs:String(BigInt(i)-200000000n),S=c?a.inputStr:x(n,F.TOOL_INPUT),A=S,m=null;if(r==="Skill"){let Ot=typeof n=="object"&&n!==null?n.skill||n.name||n.skillName||n.commandName||String(Object.values(n)[0]??""):String(n);m=Ot?String(Ot).trim():null;let ot=m?te(m,o.cwd):null;ot&&(A=ot,o.skillContent||(o.skillContent=ot),o.skillArtifacts||(o.skillArtifacts=ee(m,o.cwd))),m&&!o.slashSkill&&(o.slashSkill=m),l("PostToolUse","Skill tool detected",`skillName=${m}`,`contentFound=${!!ot}`);}let k=_t(x(s,F.TOOL_OUTPUT)),y=/\b(error|exception|failed|failure|traceback|errno)\b/i.test(k.slice(0,500)),O=y?"ERROR":"DEFAULT",Mt=rt(),st=Math.round(Number(BigInt(i)-BigInt(u))/1e6),At={Agent:"AGENT",Task:"AGENT"}[r]??"TOOL",se=r==="Skill"&&m?m:Qt(S,60);o.toolCalls.push({tool:r,brief:se,error:y,durationMs:st});let j=o.spans;j.push({traceId:o.traceId,spanId:Mt,parentSpanId:o.spanId,name:r,kind:3,startTimeUnixNano:u,endTimeUnixNano:i,attributes:nt(d(h.OBS_NAME,r),d(h.OBS_TYPE,At),d(h.OBS_LEVEL,O),d(h.OBS_INPUT,_t(A)),d(h.OBS_OUTPUT,k),d("tool.name",r),d("tool.error",String(y)),r==="Skill"&&m?d("skill.name",m):null,r==="Skill"?d("skill.invocation","slash-command"):null),status:{code:y?2:1}}),o.pendingTool=null,Tt(e,o),l("PostToolUse",`sid=${e}`,`tool=${r}`,`error=${y}`,`durationMs=${st}`,`totalSpans=${j.length}`),C(t);}var sn=p(()=>{Ut();Ft();Ue();Et();re();$();T();Fe();});function an(t,e,r){let n=Object.keys(on).find(i=>(t??"").toLowerCase().includes(i));if(!n)return;let s=on[n],o=(e*s.input+r*s.output)/1e6;return Math.round(o*1e6)/1e6}var on,cn=p(()=>{on={"claude-opus-4-6":{input:15,output:75},"claude-opus-4-5":{input:15,output:75},"claude-sonnet-4-6":{input:3,output:15},"claude-sonnet-4-5":{input:3,output:15},"claude-haiku-4-5":{input:.8,output:4},"claude-4-6-opus":{input:15,output:75},"claude-4-6-sonnet":{input:3,output:15},"claude-4-5-opus":{input:15,output:75},"claude-4-5-sonnet":{input:3,output:15},"claude-4-5-haiku":{input:.8,output:4},"claude-3-5-sonnet-20241022":{input:3,output:15},"claude-3-5-haiku-20241022":{input:.8,output:4},"claude-3-opus-20240229":{input:15,output:75}};});async function ln(t){let e=t.session_id||"unknown",r=t.stop_reason||"end_turn",n=wt(e);if(!n){C(t);return}n.slashSkill&&!/^[a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?$/i.test(n.slashSkill)&&(l("Stop",`sid=${e}`,`slashSkill rejected post-disk: "${n.slashSkill}"`),n.slashSkill=null);let s=q(),o=await pr(),i=n.toolCalls,a=n.spans;if(n.slashSkill&&!i.some(g=>g.tool==="Skill")){let g=rt(),X=n.skillContent?n.skillContent:JSON.stringify({skill:n.slashSkill});i.push({tool:"Skill",brief:n.slashSkill,error:false,durationMs:0,synthetic:true}),a.push({traceId:n.traceId,spanId:g,parentSpanId:n.spanId,name:"Skill",kind:3,startTimeUnixNano:n.startNs,endTimeUnixNano:n.startNs,attributes:nt(d(h.OBS_NAME,"Skill"),d(h.OBS_TYPE,"TOOL"),d(h.OBS_LEVEL,"DEFAULT"),d(h.OBS_INPUT,X),d(h.OBS_OUTPUT,"loaded via slash command"),d("tool.name","Skill"),d("tool.error","false"),d("skill.name",n.slashSkill),d("skill.invocation","slash-command")),status:{code:1}}),l("Stop",`slashSkill=${n.slashSkill}`,"synthetic span injected");}let c=t.transcript_path||n.transcriptPath||"",u=Ne(c);if(c&&(i.some(g=>g.tool==="Skill"&&!g.synthetic)||!!n.slashSkill)&&!u?.text){await new Promise(X=>setTimeout(X,500));let g=Ne(c);g?.text&&(u=g);}l("Stop",`transcriptPath=${c||"(empty)"}`,`assistantOut=${u?`text=${u.text.length}chars`:"null"}`);let A=i.length,m=i.filter(g=>g.error).length,k=_t(u?.text?x(u.text,F.TRACE_OUTPUT):A===0?"No tools used":i.map((g,X)=>`${X+1}. ${g.tool}${g.brief?` \u2192 ${g.brief}`:""}${g.error?" [ERROR]":""}`).join(`
|
|
135
|
+
`)),y=u?.inputTokens??0,O=u?.outputTokens??0,Mt=i.map((g,X)=>`${X+1}. ${g.tool}${g.brief?` \u2192 ${g.brief}`:""}${g.error?" [ERROR]":""} (${g.durationMs}ms)`),st=!!(n.slashSkill||i.some(g=>g.tool==="Skill")),$e=i.some(g=>g.tool==="Agent");if(!st&&!$e){l("Stop",`sid=${e}`,"skipping trace \u2014 no Skill or Agent calls found"),ve(e),C(t);return}let At=st?"skill":"agent",se=Math.round(Number(BigInt(s)-BigInt(n.startNs))/1e6),xe=an(n.model,y,O),j=xr(n);j==="prerequisite_required"&&u?.text&&(j="complete"),j==="prerequisite_required"&&(a.push({traceId:n.traceId,spanId:rt(),parentSpanId:n.spanId,name:"prerequisite-check",kind:3,startTimeUnixNano:n.startNs,endTimeUnixNano:s,attributes:nt(d(h.OBS_NAME,"prerequisite-check"),d(h.OBS_TYPE,"EVENT"),d(h.OBS_LEVEL,"WARNING"),d(h.OBS_OUTPUT,k),d("skill.name",n.slashSkill||void 0),d("execution_status","prerequisite_required")),status:{code:1}}),l("Stop",`sid=${e}`,"prerequisite-check span injected",`skill=${n.slashSkill}`));let Ot=(()=>{if(!(!st||!n.prompt)){if(n.slashSkill){let g=n.prompt.replace(new RegExp(`^\\/${n.slashSkill}\\s*`,"i"),"").trim();return g?x(g,F.USER_INSTRUCTION):void 0}return x(n.prompt,F.USER_INSTRUCTION)||void 0}})(),ot=JSON.stringify({trace_type:At,...j!==null&&{execution_status:j},...n.slashSkill?{skill_name:n.slashSkill}:{},...n.skillArtifacts?.length&&{skill_artifacts:n.skillArtifacts},...Ot!==void 0&&{user_instruction:Ot},latency_ms:se,...y&&{tokens_input:y},...O&&{tokens_output:O},cost_usd:xe,...n.model?{model:n.model}:{},toolCount:A,errorCount:m,stopReason:r,sessionId:n.sessionId,tools:Mt.length?Mt:void 0}),Me=_t(x(n.prompt,F.TRACE_INPUT)),pn=nt(d(h.TRACE_NAME,n.traceName),d(h.TRACE_INPUT,Me),d(h.TRACE_OUTPUT,k),d(h.OBS_INPUT,Me),d(h.OBS_OUTPUT,k),d(h.TRACE_METADATA,ot),d(h.SESSION_ID,n.sessionId),d(h.USER_ID,o.user),d(h.OBS_TYPE,"GENERATION"),d(h.MODEL,n.model),y?d(h.INPUT_TOKENS,y):null,O?d(h.OUTPUT_TOKENS,O):null,d("claude.stop_reason",r),d("claude.tool_count",String(A)),d("claude.error_count",String(m)),d("claude.session_id",n.sessionId),d("flow.trace_type",At),{key:h.TRACE_TAGS,value:{arrayValue:{values:[{stringValue:At}]}}}),fn={traceId:n.traceId,spanId:n.spanId,name:n.traceName,kind:1,startTimeUnixNano:n.startNs,endTimeUnixNano:s,attributes:pn,status:{code:m>0?2:1}},mn=nt(d("service.name",process.env.LANGFUSE_PROJECT_NAME||"claude-code"),d("deployment.environment",process.env.LANGFUSE_ENVIRONMENT||"default")),De=[...a,fn];l("Stop",`sid=${e}`,`totalTools=${A}`,`errorTools=${m}`,`spans=${De.length}`,`inputTokens=${y}`,`outputTokens=${O}`,`traceOutput="${Qt(k,80)}"`);let gn=await en(jr(mn,De));l("Stop",`POST status=${gn}`,`traceId=${n.traceId}`),ve(e),C(t);}var un=p(()=>{Ut();Ft();Ue();et();cn();Pe();Et();$();re();Fe();T();});async function zs(){let t=process.argv[2];if(!await fr()){let r=[];process.stdin.on("data",n=>r.push(n)),process.stdin.on("end",()=>process.stdout.write(r.join("")));return}let e=await br();switch(t){case "UserPromptSubmit":await Mr(e);break;case "PreToolUse":await Br(e);break;case "PostToolUse":await nn(e);break;case "Stop":await ln(e);break;default:process.stderr.write(`[flow-obs] unknown event: ${t}
|
|
136
136
|
`),process.stdout.write(JSON.stringify(e));}}var dn=p(()=>{et();Et();Dr();Hr();sn();un();zs().catch(t=>{process.stderr.write(`[flow-obs] fatal: ${t.message}
|
|
137
137
|
`),process.exit(0);});});var Qs=new Set(["UserPromptSubmit","PreToolUse","PostToolUse","Stop"]),[,,M,xt]=process.argv;function kt(t,e){let r=t.indexOf(e);return r!==-1?t[r+1]:void 0}if(M==="--version"||M==="-v"){let{version:t}=Bt();process.stdout.write(t+`
|
|
138
138
|
`),process.exit(0);}else if(M==="--help"||M==="-h"){let{bold:t,cyan:e,dim:r}=(at(),N(ie)),{version:n}=Bt();process.stdout.write(`
|
package/dist/index.js
CHANGED
|
@@ -1,20 +1,20 @@
|
|
|
1
|
-
'use strict';var child_process=require('child_process'),util=require('util'),
|
|
2
|
-
`;try{
|
|
3
|
-
`);}}var Ke=/^[a-z0-9][a-z0-9-]{0,62}[a-z0-9]$|^[a-z0-9]$/;function je(t){if(!Ke.test(t))throw new Error(`Invalid tenant value: "${t}". Tenant must be lowercase alphanumeric and hyphens (1-64 chars).`)}var
|
|
4
|
-
`)[0].slice(0,e).trim()}function qt(){return new Promise(t=>{let e="";process.stdin.setEncoding("utf8"),process.stdin.on("data",n=>{e+=n;}),process.stdin.on("end",()=>{try{t(JSON.parse(e));}catch{t({});}});})}function O(t){process.stdout.write(JSON.stringify(t));}var ht=()=>crypto.randomBytes(16).toString("hex"),b=()=>crypto.randomBytes(8).toString("hex");function
|
|
5
|
-
`);for(let n=e.length-1;n>=0;n--)try{let r=JSON.parse(e[n]);if(r.type==="user"&&r.uuid)return r.uuid}catch{}}catch{}return null}function Ot(t){if(!t||!
|
|
1
|
+
'use strict';var child_process=require('child_process'),util=require('util'),R=require('fs'),$=require('path'),fe=require('os'),Ve=require('https'),Ge=require('http'),crypto=require('crypto');function _interopDefault(e){return e&&e.__esModule?e:{default:e}}var R__default=/*#__PURE__*/_interopDefault(R);var $__default=/*#__PURE__*/_interopDefault($);var fe__default=/*#__PURE__*/_interopDefault(fe);var Ve__default=/*#__PURE__*/_interopDefault(Ve);var Ge__default=/*#__PURE__*/_interopDefault(Ge);var Ie=Object.defineProperty;var q=(t=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(t,{get:(e,n)=>(typeof require<"u"?require:e)[n]}):t)(function(t){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+t+'" is not supported')});var ct=(t,e)=>()=>(t&&(e=t(t=0)),e);var lt=(t,e)=>{for(var n in e)Ie(t,n,{get:e[n],enumerable:true});};var Ut={};lt(Ut,{MacOsKeyVaultProvider:()=>mt});var ft,mt,vt=ct(()=>{ft=util.promisify(child_process.execFile),mt=class{static async isAvailable(){try{return R.accessSync("/usr/bin/security",R.constants.X_OK),!0}catch{return false}}async getSecret(e,n){try{let{stdout:r}=await ft("security",["find-generic-password","-w","-a",n,"-s",e]);return r.trim()||null}catch{return null}}async setSecret(e,n,r){await ft("security",["add-generic-password","-U","-a",n,"-s",e,"-w",r]);}async deleteSecret(e,n){try{return await ft("security",["delete-generic-password","-a",n,"-s",e]),!0}catch{return false}}getStoragePath(){return "macOS Keychain"}};});var $t={};lt($t,{LinuxKeyVaultProvider:()=>gt});var Ct,gt,Ft=ct(()=>{Ct=util.promisify(child_process.execFile),gt=class{static async isAvailable(){let e=["/usr/bin/secret-tool","/bin/secret-tool","/usr/local/bin/secret-tool"];for(let n of e)try{return R.accessSync(n,R.constants.X_OK),!0}catch{}return false}async getSecret(e,n){try{let{stdout:r}=await Ct("secret-tool",["lookup","service",e,"account",n]);return r.trim()||null}catch{return null}}async setSecret(e,n,r){await new Promise((o,s)=>{let i=child_process.spawn("secret-tool",["store","--label",e,"service",e,"account",n]);i.on("error",s),i.on("close",u=>{u===0?o():s(new Error(`secret-tool exited with code ${u}`));}),i.stdin.write(r),i.stdin.end();});}async deleteSecret(e,n){try{return await Ct("secret-tool",["clear","service",e,"account",n]),!0}catch{return false}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var Bt={};lt(Bt,{WindowsKeyVaultProvider:()=>_t});var _t,Dt=ct(()=>{_t=class{static async isAvailable(){try{return await q("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return false}}async getSecret(e,n){return q("keytar").getPassword(e,n)}async setSecret(e,n,r){await q("keytar").setPassword(e,n,r);}async deleteSecret(e,n){return q("keytar").deletePassword(e,n)}getStoragePath(){return "Windows Credential Manager"}};});var I=process.env.FLOW_BASE_URL||"https://flow.ciandt.com",Y={AUTH_ENGINE:process.env.FLOW_AUTH_ENGINE_URL||`${I}/auth-engine-api/v2/api-key/token`,GATEWAY_TRACES:process.env.FLOW_GATEWAY_TRACES_URL||`${I}/flow-langfuse-gateway/v1/traces`,GATEWAY_HEALTH:process.env.FLOW_GATEWAY_HEALTH_URL||`${I}/flow-langfuse-gateway/v1/health`,OTEL_ENDPOINT:process.env.FLOW_OTEL_ENDPOINT_URL||`${I}/otel`},X={SERVICE:"flow-plugins-cli",ACCOUNT_TOKEN:"token-cache"},z="FLOW-nodejs",Z="config.json",ut={SCOPE_NAME:"flow-ai-obs",SCOPE_VERSION:"0.1.0"};({ANTHROPIC_BASE_URL:process.env.FLOW_LLM_PROXY_URL??`${I}/flow-llm-proxy/`,ANTHROPIC_MODEL:process.env.FLOW_LLM_PROXY_MODEL??"anthropic.claude-4-6-sonnet",ANTHROPIC_SMALL_FAST_MODEL:process.env.FLOW_LLM_PROXY_SMALL_MODEL??"anthropic.claude-4-6-sonnet"});var g={FLOW_TELEMETRY:"FLOW_TELEMETRY",FLOW_TELEMETRY_GATEWAY:"FLOW_TELEMETRY_GATEWAY_URL",LANGFUSE_BASE_URL:"LANGFUSE_BASE_URL",LANGFUSE_PUBLIC_KEY:"LANGFUSE_PUBLIC_KEY",LANGFUSE_SECRET_KEY:"LANGFUSE_SECRET_KEY",ANTHROPIC_MODEL:"ANTHROPIC_MODEL",ANTHROPIC_AUTH_TOKEN:"ANTHROPIC_AUTH_TOKEN",FLOW_OBS_DEBUG:"FLOW_TELEMETRY_DEBUG",FLOW_OBS_ALLOW_HTTP:"FLOW_TELEMETRY_ALLOW_HTTP",BUFFER_TTL_DAYS:"FLOW_TELEMETRY_BUFFER_TTL_DAYS",BUFFER_MAX_FILES:"FLOW_TELEMETRY_BUFFER_MAX_FILES"};var A={FILE_PREFIX:"flow-obs-buffer-",DEFAULT_TTL_DAYS:4,MIN_TTL_DAYS:1,MAX_TTL_DAYS:30,DEFAULT_MAX_FILES:50,MIN_MAX_FILES:1,MAX_MAX_FILES:500,REPLAY_BATCH_SIZE:10},Pt="flow-ai-obs-debug.log",k={TOOL_INPUT:2e4,TOOL_OUTPUT:2e4,TRACE_OUTPUT:2e4,USER_INSTRUCTION:1e4,TRACE_INPUT:5e4};({API_URL:process.env.FLOW_METRICS_URL||`${I}/metrics-collector-api/log-event`});var pt={credentials:"credentials","token-cache":"tokenCache"};function W(){let t=fe__default.default.homedir();if(process.platform==="darwin")return $__default.default.join(t,"Library","Preferences",z,Z);if(process.platform==="win32"){let n=process.env.APPDATA??$__default.default.join(t,"AppData","Roaming");return $__default.default.join(n,z,Z)}let e=process.env.XDG_CONFIG_HOME??$__default.default.join(t,".config");return $__default.default.join(e,z,Z)}function dt(){try{let t=R__default.default.readFileSync(W(),"utf8");return JSON.parse(t)}catch{return {}}}function bt(t){let e=W();R__default.default.mkdirSync($__default.default.dirname(e),{recursive:true}),R__default.default.writeFileSync(e,JSON.stringify(t,null,2),{encoding:"utf8",mode:384});}var tt=class{static isAvailable(){return true}static hasExistingData(){try{if(!R__default.default.existsSync(W()))return !1;let e=JSON.parse(R__default.default.readFileSync(W(),"utf8"));return !!(e&&e.credentials)}catch{return false}}async getSecret(e,n){let r=dt(),o=pt[n]??n,s=r[o];return s?typeof s=="string"?s:JSON.stringify(s):null}async setSecret(e,n,r){let o=dt(),s=pt[n]??n;if(n==="token-cache")try{o[s]=JSON.parse(r);}catch{o[s]=r;}else o[s]=r;bt(o);}async deleteSecret(e,n){let r=dt(),o=pt[n]??n;return o in r?(delete r[o],bt(r),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${W()}`}};async function Mt(){return await De()??new tt}async function De(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:t}=await Promise.resolve().then(()=>(vt(),Ut));return await t.isAvailable()?new t:null}case "linux":{let{LinuxKeyVaultProvider:t}=await Promise.resolve().then(()=>(Ft(),$t));return await t.isAvailable()?new t:null}case "win32":{let{WindowsKeyVaultProvider:t}=await Promise.resolve().then(()=>(Dt(),Bt));return await t.isAvailable()?new t:null}default:return null}}var Et=X.SERVICE,xt=X.ACCOUNT_TOKEN,St=null;function Tt(){return St||(St=Mt()),St}async function Ht(t){await(await Tt()).setSecret(Et,xt,JSON.stringify({accessToken:t.accessToken,expiresAt:t.expiresAt}));}async function nt(){let e=await(await Tt()).getSecret(Et,xt);if(!e)return null;try{let n=JSON.parse(e);return {accessToken:n.accessToken,expiresAt:n.expiresAt}}catch{return null}}async function Yt(){let t=await nt();return t?new Date(t.expiresAt)>new Date:false}async function G(){let t=await nt();if(!t||!t.accessToken)return null;try{let e=t.accessToken.split(".");if(e.length<2)return null;let n=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8"));return n.email??n.preferred_username??n.upn??n.sub??null}catch{return null}}var We=$.join(fe.tmpdir(),Pt);function a(...t){if(process.env[g.FLOW_OBS_DEBUG]!=="1")return;let e=`[${new Date().toISOString()}] ${t.join(" ")}
|
|
2
|
+
`;try{R.writeFileSync(We,e,{flag:"a"});}catch(n){process.stderr.write(`[flow-obs debug ERROR] ${n.message}
|
|
3
|
+
`);}}var Ke=/^[a-z0-9][a-z0-9-]{0,62}[a-z0-9]$|^[a-z0-9]$/;function je(t){if(!Ke.test(t))throw new Error(`Invalid tenant value: "${t}". Tenant must be lowercase alphanumeric and hyphens (1-64 chars).`)}var Wt={INVALID_CLIENT_SECRET:"Invalid Client Secret \u2014 check the value and try again",INVALID_CLIENT_ID:"Invalid Client ID \u2014 check the value and try again",INVALID_TENANT:"Invalid Tenant \u2014 check the value and try again",TENANT_NOT_FOUND:"Tenant not found \u2014 verify the tenant identifier"};function Je(t,e){let n=e.length>400?e.slice(0,400)+"\u2026":e;a("toAuthError",`status=${t} body=${n}`);try{let r=JSON.parse(e);if(typeof r.error=="string"&&(a("toAuthError",`api_error_code=${r.error}`+(r.message?` api_message=${r.message}`:"")),Wt[r.error]))return new Error(Wt[r.error])}catch{}return t===401||t===403||t===500?new Error("Invalid credentials"):t>=400&&t<500?new Error("Authentication request was rejected"):new Error("Authentication service unavailable, please try again later")}function Vt(t){return new Promise((e,n)=>{try{je(t.tenant);}catch(p){return n(p)}let r=JSON.stringify({clientSecret:t.clientSecret}),o=new URL(Y.AUTH_ENGINE),s=o.protocol==="https:",i={hostname:o.hostname,port:o.port||(s?443:80),path:o.pathname+o.search,method:"POST",headers:{"Content-Type":"application/json","Content-Length":Buffer.byteLength(r),FlowTenant:t.tenant}};a("getToken",`requesting token tenant=${t.tenant} host=${i.hostname} path=${i.path}`);let l=(s?Ve__default.default:Ge__default.default).request(i,p=>{let S=[];p.on("data",T=>S.push(T)),p.on("end",()=>{let T=S.join("");if((p.statusCode??0)>=400)return n(Je(p.statusCode??0,T));let d;try{d=JSON.parse(T);}catch{return n(new Error("Invalid response from auth engine"))}let E=d.expires_at??new Date(Date.now()+(d.expires_in??3600)*1e3).toISOString();e({accessToken:d.access_token??"",expiresAt:E});});});l.on("error",p=>n(new Error(`Network error: ${p.message}`))),l.write(r),l.end();})}var qe=[/^localhost\.?$/i,/^127\./,/^10\./,/^172\.(1[6-9]|2\d|3[01])\./,/^192\.168\./,/^169\.254\./,/^0\.0\.0\.0$/,/^::1$/,/^\[::1\]$/,/^\[::ffff:/i,/^\[f[cd]/i,/^\[fe80:/i,/^metadata\.google\.internal\.?$/i,/^metadata\.azure\.internal\.?$/i,/(?:^|\.)localtest\.me\.?$/i,/(?:^|\.)lvh\.me\.?$/i,/(?:^|\.)vcap\.me\.?$/i];function Xe(t){return qe.some(e=>e.test(t))}function ze(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let n=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8"));return n.email||n.preferred_username||n.upn||n.sub||null}catch{return null}}function Kt(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let n=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8")),{clientId:r,clientSecret:o,tenant:s}=n;return !r||!o||!s?null:{clientId:r,clientSecret:o,tenant:s}}catch{return null}}function Gt(t){let e;try{e=new URL(t);}catch{throw new Error(`Invalid URL: ${t}`)}let n=process.env[g.FLOW_OBS_ALLOW_HTTP]==="true";if(!n&&e.protocol!=="https:")throw new Error(`URL must use HTTPS: ${t}`);if(e.username||e.password)throw new Error(`URL must not contain embedded credentials: ${t}`);if(!n&&Xe(e.hostname))throw new Error(`SSRF: private/loopback host not allowed: ${e.hostname}`);return t}async function jt(){let t=Kt(process.env[g.ANTHROPIC_AUTH_TOKEN]);if(t)return {user:await G().catch(()=>null)??t.clientId,tenant:t.tenant};return {user:"",tenant:""}}async function Ze(t){if(await Yt()){let n=await nt();return a("getOrRefreshToken",`using cached token, expires=${n.expiresAt}`),n.accessToken}a("getOrRefreshToken",`token expired \u2014 refreshing via auth-engine (tenant=${t.tenant} clientId=${t.clientId})`);let e=await Vt(t);try{await Ht(e);}catch(n){a("getOrRefreshToken",`token cache save failed (non-fatal): ${n.message}`);}return a("getOrRefreshToken",`token refreshed, expires=${e.expiresAt}`),e.accessToken}function Qe(t,e){let n=e&&e.accessToken?e.accessToken:"";return {endpoint:t.replace(/\/$/,"")+"/flow-langfuse-gateway/v1/traces",authHeader:`Bearer ${n}`}}function tn(t,e,n){let r=Buffer.from(`${e}:${n}`).toString("base64");return {endpoint:t.replace(/\/$/,"")+"/api/public/otel/v1/traces",authHeader:`Basic ${r}`}}async function K(){let t=[],e=process.env[g.ANTHROPIC_MODEL]??"",n=Kt(process.env[g.ANTHROPIC_AUTH_TOKEN]);a("resolveCredentials",n?"credentials resolved from ANTHROPIC_AUTH_TOKEN":"ANTHROPIC_AUTH_TOKEN absent or invalid");let r=n?n.tenant:"",o=process.env[g.FLOW_TELEMETRY]==="true",s=process.env[g.LANGFUSE_BASE_URL],i=process.env[g.LANGFUSE_PUBLIC_KEY],u=process.env[g.LANGFUSE_SECRET_KEY];if(o&&s&&i&&u){let d="",E=r;if(n)d=await G().catch(()=>null)??n.clientId;let _={user:d??"",tenant:E??"",team:"",project:"",model:e};t.push({mode:"direct",...tn(Gt(s),i,u),..._}),a("resolveCredentials","direct mode active",`user=${_.user}`,`tenant=${_.tenant}`);}if(!n){if(t.length===0){let d=[];return d.authError=false,d}return t}let l;try{l=await Ze(n);}catch(d){if(a("resolveCredentials",`token refresh failed: ${d.message}`,`(tenant=${n.tenant} clientId=${n.clientId})`),t.length>0)return t;let E=[];return E.authError=true,E}let S={user:ze(l)??n.clientId,tenant:r,team:"",project:"",model:e},T=process.env[g.FLOW_TELEMETRY_GATEWAY]??I;return t.push({mode:"gateway",...Qe(Gt(T),{accessToken:l}),...S}),t}async function Jt(){return (await K()).length>0}function w(t,e){let n=typeof t=="object"?JSON.stringify(t):String(t??"");return n.length>e?n.slice(0,e)+" \u2026[truncated]":n}function rt(t,e=100){return String(t??"").split(`
|
|
4
|
+
`)[0].slice(0,e).trim()}function qt(){return new Promise(t=>{let e="";process.stdin.setEncoding("utf8"),process.stdin.on("data",n=>{e+=n;}),process.stdin.on("end",()=>{try{t(JSON.parse(e));}catch{t({});}});})}function O(t){process.stdout.write(JSON.stringify(t));}var ht=()=>crypto.randomBytes(16).toString("hex"),b=()=>crypto.randomBytes(8).toString("hex");function N(){return String(BigInt(Date.now())*1000000n)}var un=/^[0-9a-f-]{1,64}$/i,pn=$.normalize(fe.tmpdir())+$.sep;function dn(t,e){let n=$.resolve(t);if(!n.startsWith(e))throw new Error(`Path traversal detected: ${t}`);return n}function yt(t){if(!un.test(t))throw new Error(`Invalid session ID: ${t}`);return dn($.join(fe.tmpdir(),`flow-obs-${t}.json`),pn)}function F(t){let e=yt(t);if(!R.existsSync(e))return null;try{return JSON.parse(R.readFileSync(e,"utf8"))}catch{return null}}function B(t,e){R.writeFileSync(yt(t),JSON.stringify(e),{encoding:"utf8",mode:384});}function At(t){try{R.unlinkSync(yt(t));}catch{}}function te(t){if(!t||!R.existsSync(t))return null;try{let e=R.readFileSync(t,"utf8").trimEnd().split(`
|
|
5
|
+
`);for(let n=e.length-1;n>=0;n--)try{let r=JSON.parse(e[n]);if(r.type==="user"&&r.uuid)return r.uuid}catch{}}catch{}return null}function Ot(t){if(!t||!R.existsSync(t))return null;try{let e=R.readFileSync(t,"utf8").trimEnd().split(`
|
|
6
6
|
`),n=[],r=0,o=0;for(let s=e.length-1;s>=0;s--)try{let i=JSON.parse(e[s]);if(i.type==="user")break;if(i.type==="assistant"){let l=(i.message?.content??[]).filter(S=>S.type==="text").map(S=>S.text??"").join("");l&&n.unshift(l);let p=i.message?.usage??{};r+=(p.input_tokens??0)+(p.cache_read_input_tokens??0)+(p.cache_creation_input_tokens??0),o+=p.output_tokens??0;}}catch{}return !n.length&&r===0?null:{text:n.join(`
|
|
7
7
|
|
|
8
|
-
`),inputTokens:r,outputTokens:o}}catch{}return null}var _n=new Set([".venv","__pycache__",".git","node_modules"]),Sn=new Set([".pyc",".pyo"]),En=new Set(["SKILL.md",".DS_Store",".gitignore"]);function re(t){return t.replace(":","/")}function st(t,e){if(!t)return null;let n=re(t),r=[$.join(fe.homedir(),".claude","skills",n,"SKILL.md"),$.join(e??"",".claude","skills",n,"SKILL.md")];for(let o of r)if(
|
|
9
|
-
`)[0].match(/^\/([a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?)(?:\s.*)?$/i)?.[1]??null}var Tn=new Set(["Read","Write","Edit","MultiEdit","Bash","Glob","Grep","TodoWrite","WebFetch","WebSearch","Agent","Task"]);function oe(t){return !!t.slashSkill||t.toolCalls.some(r=>r.tool==="Skill")?t.toolCalls.some(r=>r.tool==="Skill"&&!r.synthetic||Tn.has(r.tool))?"complete":"prerequisite_required":null}function ot(t,e){if(!t)return null;let n=re(t),r=[$.join(fe.homedir(),".claude","skills",n),$.join(e??"",".claude","skills",n)],o=null;for(let u of r)if(
|
|
8
|
+
`),inputTokens:r,outputTokens:o}}catch{}return null}var _n=new Set([".venv","__pycache__",".git","node_modules"]),Sn=new Set([".pyc",".pyo"]),En=new Set(["SKILL.md",".DS_Store",".gitignore"]);function re(t){return t.replace(":","/")}function st(t,e){if(!t)return null;let n=re(t),r=[$.join(fe.homedir(),".claude","skills",n,"SKILL.md"),$.join(e??"",".claude","skills",n,"SKILL.md")];for(let o of r)if(R.existsSync(o))try{return R.readFileSync(o,"utf8")}catch{}return null}function se(t){return t.split(`
|
|
9
|
+
`)[0].match(/^\/([a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?)(?:\s.*)?$/i)?.[1]??null}var Tn=new Set(["Read","Write","Edit","MultiEdit","Bash","Glob","Grep","TodoWrite","WebFetch","WebSearch","Agent","Task"]);function oe(t){return !!t.slashSkill||t.toolCalls.some(r=>r.tool==="Skill")?t.toolCalls.some(r=>r.tool==="Skill"&&!r.synthetic||Tn.has(r.tool))?"complete":"prerequisite_required":null}function ot(t,e){if(!t)return null;let n=re(t),r=[$.join(fe.homedir(),".claude","skills",n),$.join(e??"",".claude","skills",n)],o=null;for(let u of r)if(R.existsSync($.join(u,"SKILL.md"))){o=u;break}if(!o)return null;let s=[];function i(u,l){for(let p of R.readdirSync(u,{withFileTypes:true})){if(_n.has(p.name)||En.has(p.name)||Sn.has($.extname(p.name)))continue;let S=l?`${l}/${p.name}`:p.name;p.isDirectory()?i($.join(u,p.name),S):s.push(S);}}return i(o,""),s.length>0?s:null}async function ie(t){let e=t.session_id||"unknown",n=t.prompt||"",r=t.cwd||"";try{(await K()).authError===!0&&(process.stderr.write(`
|
|
10
10
|
\u26A0 flow-ai-obs: Your Flow credentials have expired.
|
|
11
11
|
Traces will not be captured until you re-authenticate.
|
|
12
12
|
Run: flow-ai-obs auth login
|
|
13
13
|
|
|
14
|
-
`),a("UserPromptSubmit","auth expired \u2014 warning emitted to stderr"));}catch{}let o=te(t.transcript_path)||ht(),s=se(n),i=s?st(s,r):null,u=s?ot(s,r):null;B(e,{traceId:ht(),spanId:b(),startNs:
|
|
15
|
-
`,{flag:"a",encoding:"utf8",mode:384}),a("sendTraces:dump",`request appendada em ${le}`);}catch(i){a("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function Ln(t){let e=new URL(t),n=new URL(Y.GATEWAY_HEALTH);return n.hostname=e.hostname,n.port=e.port,n.protocol=e.protocol,n}function pe(t,e){return new Promise((n,r)=>{let o=t._isSSL?
|
|
14
|
+
`),a("UserPromptSubmit","auth expired \u2014 warning emitted to stderr"));}catch{}let o=te(t.transcript_path)||ht(),s=se(n),i=s?st(s,r):null,u=s?ot(s,r):null;B(e,{traceId:ht(),spanId:b(),startNs:N(),sessionId:e,prompt:n,cwd:r,traceName:o,transcriptPath:t.transcript_path||"",model:process.env[g.ANTHROPIC_MODEL]||"",toolCalls:[],spans:[],pendingTool:null,slashSkill:s,skillContent:i,skillArtifacts:u}),a("UserPromptSubmit",`sid=${e}`,`traceName=${o}`,`slashSkill=${s}`),O(t);}async function ae(t){let e=t.session_id||"unknown",n=t.tool_name||"unknown",r=t.tool_input||{},o=F(e);o&&(o.pendingTool={name:n,inputStr:w(r,k.TOOL_INPUT),startNs:N()},B(e,o)),a("PreToolUse",`sid=${e}`,`tool=${n}`,`stateFound=${!!o}`),O(t);}var hn={name:ut.SCOPE_NAME,version:ut.SCOPE_VERSION},m={TRACE_NAME:"langfuse.trace.name",TRACE_INPUT:"langfuse.trace.input",TRACE_OUTPUT:"langfuse.trace.output",TRACE_METADATA:"langfuse.trace.metadata",TRACE_TAGS:"langfuse.trace.tags",USER_ID:"langfuse.user.id",SESSION_ID:"langfuse.session.id",OBS_NAME:"langfuse.observation.name",OBS_INPUT:"langfuse.observation.input",OBS_OUTPUT:"langfuse.observation.output",OBS_LEVEL:"langfuse.observation.level",OBS_TYPE:"langfuse.observation.type",MODEL:"gen_ai.request.model",INPUT_TOKENS:"gen_ai.usage.input_tokens",OUTPUT_TOKENS:"gen_ai.usage.output_tokens"};function c(t,e){return e==null||e===""?null:{key:t,value:{stringValue:String(e)}}}function U(...t){return t.filter(e=>e!==null)}function ce(t,e){return {resourceSpans:[{resource:{attributes:t},scopeSpans:[{scope:hn,spans:Array.isArray(e)?e:[e]}]}]}}var le=$.join(fe.tmpdir(),"flow-obs-requests.ndjson");function ue(t,e,n,r,o){if(process.env[g.FLOW_OBS_DEBUG]!=="1")return;let s=JSON.stringify({ts:new Date().toISOString(),request:{method:"POST",url:t,headers:e,body:JSON.parse(n)},response:{status:r,body:o}});try{R.writeFileSync(le,s+`
|
|
15
|
+
`,{flag:"a",encoding:"utf8",mode:384}),a("sendTraces:dump",`request appendada em ${le}`);}catch(i){a("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function Ln(t){let e=new URL(t),n=new URL(Y.GATEWAY_HEALTH);return n.hostname=e.hostname,n.port=e.port,n.protocol=e.protocol,n}function pe(t,e){return new Promise((n,r)=>{let o=t._isSSL?Ve__default.default:Ge__default.default;t.headers=Object.assign({},t.headers,{Connection:"close"});let s=o.request(t,i=>{let u=[];i.on("data",l=>u.push(l)),i.on("end",()=>n({statusCode:i.statusCode??0,body:u.join("")}));});s.setTimeout(1e4,()=>{s.destroy(new Error("Request timeout"));}),s.on("error",i=>r(new Error(`Network error: ${i.message}`))),e&&s.write(e),s.end();})}async function de(t,e){let n;try{n=Ln(t);}catch{return false}let r=n.protocol==="https:";try{let o={};e&&(o.Authorization=String(e).replace(/[\r\n]/g,""));let s=await pe({hostname:n.hostname,port:n.port||(r?443:80),path:n.pathname,method:"GET",headers:o,_isSSL:r},null);return a("checkHealth",`url=${n.href} status=${s.statusCode}`),s.statusCode>=200&&s.statusCode<300}catch{return false}}async function it(t,e,n){let r=JSON.stringify(t),o=new URL(e),s=o.protocol==="https:",i=String(n).replace(/[\r\n]/g,""),u={"Content-Type":"application/json",Authorization:i,"Content-Length":Buffer.byteLength(r)};a("sendTraces:request",`POST ${e}`),a("sendTraces:request",`headers=${JSON.stringify({...u,Authorization:i.slice(0,20)+"\u2026"})}`),a("sendTraces:request",`body=${r.slice(0,500)}${r.length>500?"\u2026":""}`);try{let l=await pe({hostname:o.hostname,port:o.port||(s?443:80),path:o.pathname,method:"POST",headers:u,_isSSL:s},r);return a("sendTraces:response",`status=${l.statusCode}`),ue(e,u,r,l.statusCode,l.body),l.statusCode}catch(l){return a("sendTraces:error",l.message),ue(e,u,r,0,l.message),0}}function In(){let t=parseInt(process.env[g.BUFFER_TTL_DAYS]??"",10);return (Number.isFinite(t)?Math.max(A.MIN_TTL_DAYS,Math.min(A.MAX_TTL_DAYS,t)):A.DEFAULT_TTL_DAYS)*24*60*60*1e3}function Nn(){let t=parseInt(process.env[g.BUFFER_MAX_FILES]??"",10);return Number.isFinite(t)?Math.max(A.MIN_MAX_FILES,Math.min(A.MAX_MAX_FILES,t)):A.DEFAULT_MAX_FILES}function me(t){if(/[/\\]/.test(t))throw new Error(`Invalid buffer fileId: ${t}`);return $__default.default.join(fe__default.default.tmpdir(),`${A.FILE_PREFIX}${t}.json`)}function wt(){let t=fe__default.default.tmpdir(),e;try{e=R__default.default.readdirSync(t);}catch{return []}return e.filter(n=>n.startsWith(A.FILE_PREFIX)&&n.endsWith(".json")).map(n=>{let r=$__default.default.join(t,n),o=0;try{o=R__default.default.statSync(r).mtimeMs;}catch{}return {full:r,mtime:o}}).sort((n,r)=>n.mtime-r.mtime).map(n=>n.full)}function j(t){try{let e=Nn(),n=wt();if(n.length>=e){let s=n.slice(0,n.length-e+1);for(let i of s)try{R__default.default.unlinkSync(i);}catch{}}let r=`${Date.now()}-${Math.random().toString(36).slice(2,8)}`,o={fileId:r,bufferedAt:Date.now(),payload:t};return R__default.default.writeFileSync(me(r),JSON.stringify(o),{encoding:"utf8",mode:384}),a("buffer",`saved fileId=${r}`),r}catch(e){return a("buffer",`saveToBuffer failed: ${e.message}`),null}}function ge(t){let e=wt(),n=t,r=[];for(let o of e){if(r.length>=n)break;try{let s=R__default.default.readFileSync(o,"utf8"),i=JSON.parse(s);i&&i.fileId&&i.payload&&r.push(i);}catch{a("buffer",`skipping malformed file: ${o}`);}}return r}function _e(t){try{R__default.default.unlinkSync(me(t)),a("buffer",`deleted fileId=${t}`);}catch{}}function Se(){let t=Date.now()-In();for(let e of wt())try{let{mtimeMs:n}=R__default.default.statSync(e);n<t&&(R__default.default.unlinkSync(e),a("buffer",`evicted stale: ${$__default.default.basename(e)}`));}catch{}}async function Rn(t){Se();let e=ge(A.REPLAY_BATCH_SIZE);e.length&&(a("replayBufferedTraces",`replaying ${e.length} buffered trace(s)`),await Promise.allSettled(e.map(async n=>{try{let r=await it(n.payload,t.endpoint,t.authHeader);r>=200&&r<300?(_e(n.fileId),a("replayBufferedTraces",`replayed fileId=${n.fileId} status=${r}`)):a("replayBufferedTraces",`replay failed fileId=${n.fileId} status=${r}`);}catch(r){a("replayBufferedTraces",`replay error fileId=${n.fileId}: ${r.message}`);}})));}async function Ee(t){let e=await K();if(!e.length)return e.authError&&(a("postToLangfuse","auth refresh failed \u2014 buffering trace"),j(t)),0;let n=await Promise.all(e.map(async s=>{if(s.mode!=="gateway")return {creds:s,healthy:true};let i=await de(s.endpoint,s.authHeader);return {creds:s,healthy:i}})),r=n.find(s=>s.creds.mode==="gateway"&&s.healthy)?.creds??n.find(s=>s.creds.mode==="direct")?.creds;return r&&await Rn(r),(await Promise.all(n.map(async({creds:s,healthy:i})=>{if(s.mode==="gateway"){if(!i)return a("postToLangfuse","gateway health check failed \u2014 buffering trace"),j(t),0;let l=await it(t,s.endpoint,s.authHeader);return (l===0||l>=500)&&(a("postToLangfuse",`gateway send failed (status ${l}) \u2014 buffering trace`),j(t)),l}let u=await it(t,s.endpoint,s.authHeader);return (u===0||u>=500)&&(a("postToLangfuse",`direct endpoint unavailable (status ${u}) \u2014 buffering trace`),j(t)),u}))).find(s=>s!==0)??0}var y="[REDACTED]",Pn=[{re:/\b(sk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`sk-${y}`},{re:/\b(pk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`pk-${y}`},{re:/\b(Bearer\s+)[A-Za-z0-9\-._~+/]+=*/gi,replace:(t,e)=>`${e}${y}`},{re:/\b(Basic\s+)[A-Za-z0-9+/]+=*/gi,replace:(t,e)=>`${e}${y}`},{re:/(-----BEGIN [A-Z ]+-----)[^-]*(-----END [A-Z ]+-----)/g,replace:(t,e,n)=>`${e}
|
|
16
16
|
${y}
|
|
17
|
-
${n}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${y}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${y}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${y}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${y}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${y}`},{re:/\b([A-Z0-9_]*(?:SECRET|TOKEN|KEY|PASSWORD|PASSWD|PWD|CREDENTIAL|API)[A-Z0-9_]*\s*=\s*)(['"]?)([^\s'"#\n]+)\2/gi,replace:(t,e,n)=>`${e}${n}${y}${n}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${y}@`}];function
|
|
18
|
-
`)),_=p?.inputTokens??0,h=p?.outputTokens??0,J=i.map((f,
|
|
17
|
+
${n}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${y}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${y}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${y}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${y}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${y}`},{re:/\b([A-Z0-9_]*(?:SECRET|TOKEN|KEY|PASSWORD|PASSWD|PWD|CREDENTIAL|API)[A-Z0-9_]*\s*=\s*)(['"]?)([^\s'"#\n]+)\2/gi,replace:(t,e,n)=>`${e}${n}${y}${n}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${y}@`}];function M(t){if(t==null)return "";let e=typeof t=="string"?t:JSON.stringify(t);return Pn.reduce((n,{re:r,replace:o})=>n.replace(r,o),e)}async function Te(t){let e=t.session_id||"unknown",n=t.tool_name||"unknown",r=t.tool_input||{},o=t.tool_response||"",s=F(e);if(!s){O(t);return}let i=N(),u=s.pendingTool,l=u?.name===n,p=l?u.startNs:String(BigInt(i)-200000000n),S=l?u.inputStr:w(r,k.TOOL_INPUT),T=S,d=null;if(n==="Skill"){let H=typeof r=="object"&&r!==null?r.skill||r.name||r.skillName||r.commandName||String(Object.values(r)[0]??""):String(r);d=H?String(H).trim():null;let C=d?st(d,s.cwd):null;C&&(T=C,s.skillContent||(s.skillContent=C),s.skillArtifacts||(s.skillArtifacts=ot(d,s.cwd))),d&&!s.slashSkill&&(s.slashSkill=d),a("PostToolUse","Skill tool detected",`skillName=${d}`,`contentFound=${!!C}`);}let E=M(w(o,k.TOOL_OUTPUT)),_=/\b(error|exception|failed|failure|traceback|errno)\b/i.test(E.slice(0,500)),h=_?"ERROR":"DEFAULT",J=b(),v=Math.round(Number(BigInt(i)-BigInt(p))/1e6),x={Agent:"AGENT",Task:"AGENT"}[n]??"TOOL",at=n==="Skill"&&d?d:rt(S,60);s.toolCalls.push({tool:n,brief:at,error:_,durationMs:v});let L=s.spans;L.push({traceId:s.traceId,spanId:J,parentSpanId:s.spanId,name:n,kind:3,startTimeUnixNano:p,endTimeUnixNano:i,attributes:U(c(m.OBS_NAME,n),c(m.OBS_TYPE,x),c(m.OBS_LEVEL,h),c(m.OBS_INPUT,M(T)),c(m.OBS_OUTPUT,E),c("tool.name",n),c("tool.error",String(_)),n==="Skill"&&d?c("skill.name",d):null,n==="Skill"?c("skill.invocation","slash-command"):null),status:{code:_?2:1}}),s.pendingTool=null,B(e,s),a("PostToolUse",`sid=${e}`,`tool=${n}`,`error=${_}`,`durationMs=${v}`,`totalSpans=${L.length}`),O(t);}var he={"claude-opus-4-6":{input:15,output:75},"claude-opus-4-5":{input:15,output:75},"claude-sonnet-4-6":{input:3,output:15},"claude-sonnet-4-5":{input:3,output:15},"claude-haiku-4-5":{input:.8,output:4},"claude-4-6-opus":{input:15,output:75},"claude-4-6-sonnet":{input:3,output:15},"claude-4-5-opus":{input:15,output:75},"claude-4-5-sonnet":{input:3,output:15},"claude-4-5-haiku":{input:.8,output:4},"claude-3-5-sonnet-20241022":{input:3,output:15},"claude-3-5-haiku-20241022":{input:.8,output:4},"claude-3-opus-20240229":{input:15,output:75}};function ye(t,e,n){let r=Object.keys(he).find(i=>(t??"").toLowerCase().includes(i));if(!r)return;let o=he[r],s=(e*o.input+n*o.output)/1e6;return Math.round(s*1e6)/1e6}async function Ae(t){let e=t.session_id||"unknown",n=t.stop_reason||"end_turn",r=F(e);if(!r){O(t);return}r.slashSkill&&!/^[a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?$/i.test(r.slashSkill)&&(a("Stop",`sid=${e}`,`slashSkill rejected post-disk: "${r.slashSkill}"`),r.slashSkill=null);let o=N(),s=await jt(),i=r.toolCalls,u=r.spans;if(r.slashSkill&&!i.some(f=>f.tool==="Skill")){let f=b(),P=r.skillContent?r.skillContent:JSON.stringify({skill:r.slashSkill});i.push({tool:"Skill",brief:r.slashSkill,error:false,durationMs:0,synthetic:true}),u.push({traceId:r.traceId,spanId:f,parentSpanId:r.spanId,name:"Skill",kind:3,startTimeUnixNano:r.startNs,endTimeUnixNano:r.startNs,attributes:U(c(m.OBS_NAME,"Skill"),c(m.OBS_TYPE,"TOOL"),c(m.OBS_LEVEL,"DEFAULT"),c(m.OBS_INPUT,P),c(m.OBS_OUTPUT,"loaded via slash command"),c("tool.name","Skill"),c("tool.error","false"),c("skill.name",r.slashSkill),c("skill.invocation","slash-command")),status:{code:1}}),a("Stop",`slashSkill=${r.slashSkill}`,"synthetic span injected");}let l=t.transcript_path||r.transcriptPath||"",p=Ot(l);if(l&&(i.some(f=>f.tool==="Skill"&&!f.synthetic)||!!r.slashSkill)&&!p?.text){await new Promise(P=>setTimeout(P,500));let f=Ot(l);f?.text&&(p=f);}a("Stop",`transcriptPath=${l||"(empty)"}`,`assistantOut=${p?`text=${p.text.length}chars`:"null"}`);let T=i.length,d=i.filter(f=>f.error).length,E=M(p?.text?w(p.text,k.TRACE_OUTPUT):T===0?"No tools used":i.map((f,P)=>`${P+1}. ${f.tool}${f.brief?` \u2192 ${f.brief}`:""}${f.error?" [ERROR]":""}`).join(`
|
|
18
|
+
`)),_=p?.inputTokens??0,h=p?.outputTokens??0,J=i.map((f,P)=>`${P+1}. ${f.tool}${f.brief?` \u2192 ${f.brief}`:""}${f.error?" [ERROR]":""} (${f.durationMs}ms)`),v=!!(r.slashSkill||i.some(f=>f.tool==="Skill")),Lt=i.some(f=>f.tool==="Agent");if(!v&&!Lt){a("Stop",`sid=${e}`,"skipping trace \u2014 no Skill or Agent calls found"),At(e),O(t);return}let x=v?"skill":"agent",at=Math.round(Number(BigInt(o)-BigInt(r.startNs))/1e6),It=ye(r.model,_,h),L=oe(r);L==="prerequisite_required"&&p?.text&&(L="complete"),L==="prerequisite_required"&&(u.push({traceId:r.traceId,spanId:b(),parentSpanId:r.spanId,name:"prerequisite-check",kind:3,startTimeUnixNano:r.startNs,endTimeUnixNano:o,attributes:U(c(m.OBS_NAME,"prerequisite-check"),c(m.OBS_TYPE,"EVENT"),c(m.OBS_LEVEL,"WARNING"),c(m.OBS_OUTPUT,E),c("skill.name",r.slashSkill||void 0),c("execution_status","prerequisite_required")),status:{code:1}}),a("Stop",`sid=${e}`,"prerequisite-check span injected",`skill=${r.slashSkill}`));let H=(()=>{if(!(!v||!r.prompt)){if(r.slashSkill){let f=r.prompt.replace(new RegExp(`^\\/${r.slashSkill}\\s*`,"i"),"").trim();return f?w(f,k.USER_INSTRUCTION):void 0}return w(r.prompt,k.USER_INSTRUCTION)||void 0}})(),C=JSON.stringify({trace_type:x,...L!==null&&{execution_status:L},...r.slashSkill?{skill_name:r.slashSkill}:{},...r.skillArtifacts?.length&&{skill_artifacts:r.skillArtifacts},...H!==void 0&&{user_instruction:H},latency_ms:at,..._&&{tokens_input:_},...h&&{tokens_output:h},cost_usd:It,...r.model?{model:r.model}:{},toolCount:T,errorCount:d,stopReason:n,sessionId:r.sessionId,tools:J.length?J:void 0}),Nt=M(w(r.prompt,k.TRACE_INPUT)),Oe=U(c(m.TRACE_NAME,r.traceName),c(m.TRACE_INPUT,Nt),c(m.TRACE_OUTPUT,E),c(m.OBS_INPUT,Nt),c(m.OBS_OUTPUT,E),c(m.TRACE_METADATA,C),c(m.SESSION_ID,r.sessionId),c(m.USER_ID,s.user),c(m.OBS_TYPE,"GENERATION"),c(m.MODEL,r.model),_?c(m.INPUT_TOKENS,_):null,h?c(m.OUTPUT_TOKENS,h):null,c("claude.stop_reason",n),c("claude.tool_count",String(T)),c("claude.error_count",String(d)),c("claude.session_id",r.sessionId),c("flow.trace_type",x),{key:m.TRACE_TAGS,value:{arrayValue:{values:[{stringValue:x}]}}}),ke={traceId:r.traceId,spanId:r.spanId,name:r.traceName,kind:1,startTimeUnixNano:r.startNs,endTimeUnixNano:o,attributes:Oe,status:{code:d>0?2:1}},we=U(c("service.name",process.env.LANGFUSE_PROJECT_NAME||"claude-code"),c("deployment.environment",process.env.LANGFUSE_ENVIRONMENT||"default")),Rt=[...u,ke];a("Stop",`sid=${e}`,`totalTools=${T}`,`errorTools=${d}`,`spans=${Rt.length}`,`inputTokens=${_}`,`outputTokens=${h}`,`traceOutput="${rt(E,80)}"`);let Le=await Ee(ce(we,Rt));a("Stop",`POST status=${Le}`,`traceId=${r.traceId}`),At(e),O(t);}async function bn(){let t=process.argv[2];if(!await Jt()){let n=[];process.stdin.on("data",r=>n.push(r)),process.stdin.on("end",()=>process.stdout.write(n.join("")));return}let e=await qt();switch(t){case "UserPromptSubmit":await ie(e);break;case "PreToolUse":await ae(e);break;case "PostToolUse":await Te(e);break;case "Stop":await Ae(e);break;default:process.stderr.write(`[flow-obs] unknown event: ${t}
|
|
19
19
|
`),process.stdout.write(JSON.stringify(e));}}bn().catch(t=>{process.stderr.write(`[flow-obs] fatal: ${t.message}
|
|
20
20
|
`),process.exit(0);});
|
package/dist/setup.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
'use strict';var child_process=require('child_process'),util=require('util'),s=require('fs'),p=require('path'),F=require('os');function _interopNamespace(e){if(e&&e.__esModule)return e;var n=Object.create(null);if(e){Object.keys(e).forEach(function(k){if(k!=='default'){var d=Object.getOwnPropertyDescriptor(e,k);Object.defineProperty(n,k,d.get?d:{enumerable:true,get:function(){return e[k]}});}})}n.default=e;return Object.freeze(n)}var s__namespace=/*#__PURE__*/_interopNamespace(s);var p__namespace=/*#__PURE__*/_interopNamespace(p);var F__namespace=/*#__PURE__*/_interopNamespace(F);var re=Object.defineProperty;var T=(t=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(t,{get:(e,r)=>(typeof require<"u"?require:e)[r]}):t)(function(t){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+t+'" is not supported')});var A=(t,e)=>()=>(t&&(e=t(t=0)),e);var O=(t,e)=>{for(var r in e)re(t,r,{get:e[r],enumerable:true});};var
|
|
2
|
+
'use strict';var child_process=require('child_process'),util=require('util'),s=require('fs'),p=require('path'),F=require('os');function _interopNamespace(e){if(e&&e.__esModule)return e;var n=Object.create(null);if(e){Object.keys(e).forEach(function(k){if(k!=='default'){var d=Object.getOwnPropertyDescriptor(e,k);Object.defineProperty(n,k,d.get?d:{enumerable:true,get:function(){return e[k]}});}})}n.default=e;return Object.freeze(n)}var s__namespace=/*#__PURE__*/_interopNamespace(s);var p__namespace=/*#__PURE__*/_interopNamespace(p);var F__namespace=/*#__PURE__*/_interopNamespace(F);var re=Object.defineProperty;var T=(t=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(t,{get:(e,r)=>(typeof require<"u"?require:e)[r]}):t)(function(t){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+t+'" is not supported')});var A=(t,e)=>()=>(t&&(e=t(t=0)),e);var O=(t,e)=>{for(var r in e)re(t,r,{get:e[r],enumerable:true});};var Y={};O(Y,{MacOsKeyVaultProvider:()=>N});var v,N,W=A(()=>{v=util.promisify(child_process.execFile),N=class{static async isAvailable(){try{return s.accessSync("/usr/bin/security",s.constants.X_OK),!0}catch{return false}}async getSecret(e,r){try{let{stdout:n}=await v("security",["find-generic-password","-w","-a",r,"-s",e]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await v("security",["add-generic-password","-U","-a",r,"-s",e,"-w",n]);}async deleteSecret(e,r){try{return await v("security",["delete-generic-password","-a",r,"-s",e]),!0}catch{return false}}getStoragePath(){return "macOS Keychain"}};});var V={};O(V,{LinuxKeyVaultProvider:()=>I});var G,I,B=A(()=>{G=util.promisify(child_process.execFile),I=class{static async isAvailable(){let e=["/usr/bin/secret-tool","/bin/secret-tool","/usr/local/bin/secret-tool"];for(let r of e)try{return s.accessSync(r,s.constants.X_OK),!0}catch{}return false}async getSecret(e,r){try{let{stdout:n}=await G("secret-tool",["lookup","service",e,"account",r]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await new Promise((o,i)=>{let a=child_process.spawn("secret-tool",["store","--label",e,"service",e,"account",r]);a.on("error",i),a.on("close",f=>{f===0?o():i(new Error(`secret-tool exited with code ${f}`));}),a.stdin.write(n),a.stdin.end();});}async deleteSecret(e,r){try{return await G("secret-tool",["clear","service",e,"account",r]),!0}catch{return false}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var x={};O(x,{WindowsKeyVaultProvider:()=>P});var P,K=A(()=>{P=class{static async isAvailable(){try{return await T("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return false}}async getSecret(e,r){return T("keytar").getPassword(e,r)}async setSecret(e,r,n){await T("keytar").setPassword(e,r,n);}async deleteSecret(e,r){return T("keytar").deletePassword(e,r)}getStoragePath(){return "Windows Credential Manager"}};});var l=process.env.FLOW_BASE_URL||"https://flow.ciandt.com",L={AUTH_ENGINE:process.env.FLOW_AUTH_ENGINE_URL||`${l}/auth-engine-api/v2/api-key/token`,GATEWAY_TRACES:process.env.FLOW_GATEWAY_TRACES_URL||`${l}/flow-langfuse-gateway/v1/traces`,GATEWAY_HEALTH:process.env.FLOW_GATEWAY_HEALTH_URL||`${l}/flow-langfuse-gateway/v1/health`,OTEL_ENDPOINT:process.env.FLOW_OTEL_ENDPOINT_URL||`${l}/otel`},g={SERVICE:"flow-plugins-cli",ACCOUNT_CREDS:"credentials"},y="FLOW-nodejs",S="config.json";var U={ANTHROPIC_BASE_URL:process.env.FLOW_LLM_PROXY_URL??`${l}/flow-llm-proxy/`,ANTHROPIC_MODEL:process.env.FLOW_LLM_PROXY_MODEL??"anthropic.claude-4-6-sonnet",ANTHROPIC_SMALL_FAST_MODEL:process.env.FLOW_LLM_PROXY_SMALL_MODEL??"anthropic.claude-4-6-sonnet",CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS:"1"},b={CLAUDE_CODE_ENABLE_TELEMETRY:"1",OTEL_EXPORTER_OTLP_ENDPOINT:L.OTEL_ENDPOINT,OTEL_EXPORTER_OTLP_PROTOCOL:"http/json",OTEL_METRICS_EXPORTER:"otlp",OTEL_LOGS_EXPORTER:"otlp",OTEL_LOG_TOOL_DETAILS:"1",OTEL_LOG_USER_PROMPTS:"1"},d={FLOW_TELEMETRY:"FLOW_TELEMETRY",FLOW_TELEMETRY_GATEWAY:"FLOW_TELEMETRY_GATEWAY_URL",LANGFUSE_BASE_URL:"LANGFUSE_BASE_URL",LANGFUSE_PUBLIC_KEY:"LANGFUSE_PUBLIC_KEY",LANGFUSE_SECRET_KEY:"LANGFUSE_SECRET_KEY",ANTHROPIC_MODEL:"ANTHROPIC_MODEL",ANTHROPIC_AUTH_TOKEN:"ANTHROPIC_AUTH_TOKEN",FLOW_OBS_DEBUG:"FLOW_TELEMETRY_DEBUG",FLOW_OBS_ALLOW_HTTP:"FLOW_TELEMETRY_ALLOW_HTTP",BUFFER_TTL_DAYS:"FLOW_TELEMETRY_BUFFER_TTL_DAYS",BUFFER_MAX_FILES:"FLOW_TELEMETRY_BUFFER_MAX_FILES"};var D={LOCK_STALE_MS:3e4},M={UserPromptSubmit:5,PreToolUse:3,PostToolUse:10,Stop:15};var H="flow-ai-obs-debug.log";({API_URL:process.env.FLOW_METRICS_URL||`${l}/metrics-collector-api/log-event`});var w={credentials:"credentials","token-cache":"tokenCache"};function E(){let t=F__namespace.default.homedir();if(process.platform==="darwin")return p__namespace.default.join(t,"Library","Preferences",y,S);if(process.platform==="win32"){let r=process.env.APPDATA??p__namespace.default.join(t,"AppData","Roaming");return p__namespace.default.join(r,y,S)}let e=process.env.XDG_CONFIG_HOME??p__namespace.default.join(t,".config");return p__namespace.default.join(e,y,S)}function R(){try{let t=s__namespace.default.readFileSync(E(),"utf8");return JSON.parse(t)}catch{return {}}}function $(t){let e=E();s__namespace.default.mkdirSync(p__namespace.default.dirname(e),{recursive:true}),s__namespace.default.writeFileSync(e,JSON.stringify(t,null,2),{encoding:"utf8",mode:384});}var h=class{static isAvailable(){return true}static hasExistingData(){try{if(!s__namespace.default.existsSync(E()))return !1;let e=JSON.parse(s__namespace.default.readFileSync(E(),"utf8"));return !!(e&&e.credentials)}catch{return false}}async getSecret(e,r){let n=R(),o=w[r]??r,i=n[o];return i?typeof i=="string"?i:JSON.stringify(i):null}async setSecret(e,r,n){let o=R(),i=w[r]??r;if(r==="token-cache")try{o[i]=JSON.parse(n);}catch{o[i]=n;}else o[i]=n;$(o);}async deleteSecret(e,r){let n=R(),o=w[r]??r;return o in n?(delete n[o],$(n),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${E()}`}};async function X(){return await de()??new h}async function de(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:t}=await Promise.resolve().then(()=>(W(),Y));return await t.isAvailable()?new t:null}case "linux":{let{LinuxKeyVaultProvider:t}=await Promise.resolve().then(()=>(B(),V));return await t.isAvailable()?new t:null}case "win32":{let{WindowsKeyVaultProvider:t}=await Promise.resolve().then(()=>(K(),x));return await t.isAvailable()?new t:null}default:return null}}var Ee=g.SERVICE,_e=g.ACCOUNT_CREDS,C=null;function me(){return C||(C=X()),C}async function k(){let e=await(await me()).getSecret(Ee,_e);if(!e)return null;try{return JSON.parse(e)}catch{return null}}p.join(F.tmpdir(),H);function j(){return process.platform==="win32"?p__namespace.join(process.env.APPDATA||p__namespace.join(F__namespace.homedir(),"AppData","Roaming"),"Claude","settings.json"):p__namespace.join(F__namespace.homedir(),".claude","settings.json")}var he=D.LOCK_STALE_MS;function J(t){try{let e=s__namespace.statSync(t);Date.now()-e.mtimeMs>he&&s__namespace.unlinkSync(t);}catch{}try{s__namespace.writeFileSync(t,String(process.pid),{flag:"wx"});}catch(e){throw e.code==="EEXIST"?new Error("Another install is already in progress. If this is stale, remove: "+t):e}}function q(t){try{s__namespace.unlinkSync(t);}catch{}}function Ae(t,e){let n=(Array.isArray(t)?t:[]).map(o=>{if(!Array.isArray(o?.hooks))return null;let i=o.hooks.filter(a=>!a.command?.startsWith?.("flow-ai-obs "));return i.length>0?{...o,hooks:i}:null}).filter(o=>o!=null);return [e,...n]}function z(){let t=j(),e=t+".lock",r=[];s__namespace.mkdirSync(p__namespace.dirname(t),{recursive:true}),J(e);try{if(s__namespace.existsSync(t)){s__namespace.copyFileSync(t,t+".bkp");try{s__namespace.chmodSync(t+".bkp",384);}catch{}}let n={};try{n=JSON.parse(s__namespace.readFileSync(t,"utf8"));}catch{}let o=n.env&&typeof n.env=="object"?n.env:{};n.env={...b,...U,...o},n.otelHeadersHelper="flow-ai-obs otel-headers",(!n.hooks||typeof n.hooks!="object"||Array.isArray(n.hooks))&&(n.hooks={});let i=(c,m)=>({matcher:"",hooks:[{type:"command",command:`flow-ai-obs ${c}`,timeout:m}]}),a=["UserPromptSubmit","PreToolUse","PostToolUse","Stop"],f=n.hooks;for(let c of a){let m=Ae(f[c],i(c,M[c]));m.length>1&&r.push(c),f[c]=m;}s__namespace.writeFileSync(t,JSON.stringify(n,null,2)+`
|
|
3
3
|
`,{encoding:"utf8",mode:384});try{s__namespace.chmodSync(t,384);}catch{}}finally{q(e);}return {settingsPath:t,preserved:r}}function Z(t){let e=j(),r=e+".lock";s__namespace.mkdirSync(p__namespace.dirname(e),{recursive:true}),J(r);try{let n={};try{n=JSON.parse(s__namespace.readFileSync(e,"utf8"));}catch{}(!n.env||typeof n.env!="object")&&(n.env={}),Object.assign(n.env,t),s__namespace.writeFileSync(e,JSON.stringify(n,null,2)+`
|
|
4
|
-
`,{encoding:"utf8",mode:384});try{s__namespace.chmodSync(e,384);}catch{}}finally{q(r);}}function Q(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8")),{clientId:n,clientSecret:o,tenant:i}=r;return !n||!o||!i?null:{clientId:n,clientSecret:o,tenant:i}}catch{return null}}function ee(t){let e=Buffer.from(JSON.stringify({alg:"none",typ:"JWT"})).toString("base64url"),r=Buffer.from(JSON.stringify({clientId:t.clientId,clientSecret:t.clientSecret,tenant:t.tenant})).toString("base64url");return `${e}.${r}.`}var Oe=p__namespace.default.resolve(__dirname,".."),Le=process.env.INIT_CWD?p__namespace.default.resolve(process.env.INIT_CWD):null;Le===Oe&&process.exit(0);async function we(){try{z();}catch{}let t=await
|
|
4
|
+
`,{encoding:"utf8",mode:384});try{s__namespace.chmodSync(e,384);}catch{}}finally{q(r);}}function Q(t){if(!t)return null;try{let e=t.split(".");if(e.length<2)return null;let r=JSON.parse(Buffer.from(e[1].replace(/-/g,"+").replace(/_/g,"/"),"base64").toString("utf8")),{clientId:n,clientSecret:o,tenant:i}=r;return !n||!o||!i?null:{clientId:n,clientSecret:o,tenant:i}}catch{return null}}function ee(t){let e=Buffer.from(JSON.stringify({alg:"none",typ:"JWT"})).toString("base64url"),r=Buffer.from(JSON.stringify({clientId:t.clientId,clientSecret:t.clientSecret,tenant:t.tenant})).toString("base64url");return `${e}.${r}.`}var Oe=p__namespace.default.resolve(__dirname,".."),Le=process.env.INIT_CWD?p__namespace.default.resolve(process.env.INIT_CWD):null;Le===Oe&&process.exit(0);async function we(){try{z();}catch{}let t=await k();if(!t){process.stderr.write(`
|
|
5
5
|
[flow-ai-obs] No credentials found.
|
|
6
6
|
Run \`flow-ai-obs auth login\` to authenticate and enable telemetry.
|
|
7
7
|
|