@ciandt-flow/flow-ai-obs 0.7.0-beta.398 → 0.7.0-beta.403
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 +44 -44
- package/dist/index.js +9 -9
- package/dist/setup.js +4 -4
- package/package.json +4 -1
package/dist/cli.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
'use strict';var _e=require('readline/promises'),is=require('https'),T=require('fs'),
|
|
3
|
-
`);}catch(i){throw r.close(),i}if(r.close(),e!==void 0)return e;throw new Error("Too many invalid attempts for yes/no prompt")}async function lr(t,e){let r=_e__namespace.createInterface({input:process.stdin,output:process.stdout});try{let n=(await r.question(`${t}: `)).trim();if(e);return n}catch(n){throw n}finally{r.close();}}var ke=m(()=>{});var
|
|
2
|
+
'use strict';var _e=require('readline/promises'),is=require('https'),T=require('fs'),tt=require('os'),At=require('path'),child_process=require('child_process'),As=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 _e__namespace=/*#__PURE__*/_interopNamespace(_e);var is__namespace=/*#__PURE__*/_interopNamespace(is);var T__namespace=/*#__PURE__*/_interopNamespace(T);var tt__namespace=/*#__PURE__*/_interopNamespace(tt);var At__namespace=/*#__PURE__*/_interopNamespace(At);var As__namespace=/*#__PURE__*/_interopNamespace(As);var Te=Object.defineProperty;var Qn=Object.getOwnPropertyDescriptor;var ts=Object.getOwnPropertyNames;var es=Object.prototype.hasOwnProperty;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 m=(t,e,r)=>()=>{if(r)throw r[0];try{return t&&(e=t(t=0)),e}catch(n){throw r=[n],n}};var rs=(t,e)=>()=>{try{return e||t((e={exports:{}}).exports,e),e.exports}catch(r){throw e=0,r}},M=(t,e)=>{for(var r in e)Te(t,r,{get:e[r],enumerable:true});},ns=(t,e,r,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let s of ts(e))!es.call(t,s)&&s!==r&&Te(t,s,{get:()=>e[s],enumerable:!(n=Qn(e,s))||n.enumerable});return t};var L=t=>ns(Te({},"__esModule",{value:true}),t);var re=rs((Jo,ss)=>{ss.exports={name:"@ciandt-flow/flow-ai-obs",version:"0.7.0-beta.403",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:!1,dependencies:{},optionalDependencies:{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"},overrides:{esbuild:"^0.28.1"},publishConfig:{registry:"https://registry.npmjs.org",access:"public"},repository:{type:"git",url:"git+https://github.com/CI-T-HyperX/flow-codeassistant-observability.git"}};});var ye={};M(ye,{bold:()=>j,cyan:()=>H,dim:()=>w,green:()=>I,red:()=>B,yellow:()=>_});function ft(t,e){return os?r=>`\x1B[${t}m${r}\x1B[${e}m`:r=>r}var os,I,B,_,H,j,w,mt=m(()=>{"use strict";os=!process.env.NO_COLOR&&process.stdout.isTTY;I=ft("32","39"),B=ft("31","39"),_=ft("33","39"),H=ft("36","39"),j=ft("1","22"),w=ft("2","22");});function gt(){return process.stdout.isTTY===true&&process.stdin.isTTY===true&&!process.argv.includes("--no-interactive")}async function Ae(t,e){let r=_e__namespace.createInterface({input:process.stdin,output:process.stdout}),s=`${t} ${e===true?"(Y/n)":e===false?"(y/N)":"(y/n)"}: `;for(let o=1;o<=3;o++)try{let i=(await r.question(s)).trim().toLowerCase();if(i===""&&e!==void 0)return r.close(),e;if(i==="y"||i==="yes")return r.close(),!0;if(i==="n"||i==="no")return r.close(),!1;o<3&&process.stdout.write(` Invalid input. Please answer "y" or "n".
|
|
3
|
+
`);}catch(i){throw r.close(),i}if(r.close(),e!==void 0)return e;throw new Error("Too many invalid attempts for yes/no prompt")}async function lr(t,e){let r=_e__namespace.createInterface({input:process.stdin,output:process.stdout});try{let n=(await r.question(`${t}: `)).trim();if(e);return n}catch(n){throw n}finally{r.close();}}var ke=m(()=>{"use strict";});var ht={};M(ht,{checkForUpdate:()=>fs,checkForUpdateInteractive:()=>ms,isNewer:()=>xt,primeUpdateCache:()=>gs});function U(){return Oe||(Oe=re()),Oe}function xt(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 Ie(){try{let t=JSON.parse(T__namespace.default.readFileSync(pr,"utf8"));return typeof t.latestVersion!="string"||Date.now()-t.checkedAt>=ls?null:t}catch{return null}}function fr(t,e,r=Date.now()){try{T__namespace.default.writeFileSync(pr,JSON.stringify({latestVersion:t,updatePriority:e??null,checkedAt:r}),{mode:384});}catch{}}function mr(t){let e=U().name,r=is__namespace.default.get(`https://registry.npmjs.org/${encodeURIComponent(e)}/latest`,{timeout:us},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 ve(t){let e=U().name,n=` Update available: ${U().version} \u2192 ${t}`,s=` Run: npm install -g ${e}`,o=Math.max(n.length,s.length)+2,i="\u2500".repeat(o);process.stderr.write(`
|
|
4
4
|
\u256D${i}\u256E
|
|
5
5
|
\u2502${n.padEnd(o)}\u2502
|
|
6
6
|
\u2502${s.padEnd(o)}\u2502
|
|
@@ -20,30 +20,30 @@
|
|
|
20
20
|
|
|
21
21
|
`),r();}),n.on("error",()=>{process.stderr.write(` \u2717 Update failed \u2014 continuing with current version.
|
|
22
22
|
|
|
23
|
-
`),r();});})}function fs(){try{let t=Ie();if(t){xt(U().version,t.latestVersion)&&(t.updatePriority==="auto"?Le(t.latestVersion):ve(t.latestVersion));return}setImmediate(()=>{mr((e,r)=>{e||!r||(fr(r.version,r.updatePriority),xt(U().version,r.version)&&(r.updatePriority==="auto"?Le(r.version):ve(r.version)));});});}catch{}}async function ms(t={}){try{let e=Ie();if(!e||!xt(U().version,e.latestVersion))return;if(e.updatePriority==="auto"){Le(e.latestVersion);return}if(!
|
|
23
|
+
`),r();});})}function fs(){try{let t=Ie();if(t){xt(U().version,t.latestVersion)&&(t.updatePriority==="auto"?Le(t.latestVersion):ve(t.latestVersion));return}setImmediate(()=>{mr((e,r)=>{e||!r||(fr(r.version,r.updatePriority),xt(U().version,r.version)&&(r.updatePriority==="auto"?Le(r.version):ve(r.version)));});});}catch{}}async function ms(t={}){try{let e=Ie();if(!e||!xt(U().version,e.latestVersion))return;if(e.updatePriority==="auto"){Le(e.latestVersion);return}if(!gt()){ve(e.latestVersion);return}await ds(e.latestVersion,t.timeoutMs)&&await ps(e.latestVersion);}catch{}}function gs(){try{if(Ie())return;setImmediate(()=>{mr((t,e)=>{t||!e||xt(U().version,e.version)&&fr(e.version,e.updatePriority,0);});});}catch{}}var Oe,pr,ls,us,wt=m(()=>{"use strict";ke();pr=At__namespace.default.join(tt__namespace.default.tmpdir(),"flow-obs-update-cache.json"),ls=1440*60*1e3,us=3e3;});function gr(){if(process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER){let e=child_process.spawnSync("getent",["passwd",process.env.SUDO_USER],{encoding:"utf8",timeout:5e3}).stdout?.split(":")[5]?.trim();if(e)return {home:e,username:process.env.SUDO_USER}}return {home:tt__namespace.homedir(),username:process.env.SUDO_USER||process.env.USER||tt__namespace.userInfo().username}}function G(){if(process.env.WSL_DISTRO_NAME&&process.platform==="linux"){let t=process.env.USERPROFILE;if(!t){let r=child_process.spawnSync("cmd.exe",["/c","echo","%USERPROFILE%"],{encoding:"utf8",timeout:5e3}).stdout?.trim();r&&/^[A-Za-z]:\\/.test(r)&&(t=r);}if(t){let e=t.replace(/^([A-Za-z]):/,(r,n)=>`/mnt/${n.toLowerCase()}`).replace(/\\/g,"/");return At__namespace.join(e,".claude","settings.json")}return At__namespace.join(tt__namespace.homedir(),".claude","settings.json")}if(process.platform==="win32"){let t=process.env.USERPROFILE||tt__namespace.homedir();return At__namespace.join(t,".claude","settings.json")}if(process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER){let e=child_process.spawnSync("getent",["passwd",process.env.SUDO_USER],{encoding:"utf8",timeout:5e3}).stdout?.split(":")[5]?.trim();if(e)return At__namespace.join(e,".claude","settings.json")}return At__namespace.join(tt__namespace.homedir(),".claude","settings.json")}function hr(){return process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER?`Running as root via sudo is not recommended.
|
|
24
24
|
Configure npm to install globals without sudo:
|
|
25
25
|
npm config set prefix '~/.npm-global'
|
|
26
|
-
export PATH=~/.npm-global/bin:$PATH`:null}var ne=m(()=>{});function Tr(){if(process.platform==="win32"){let r=process.env.APPDATA||At__namespace.join(
|
|
27
|
-
`,{encoding:"utf8",mode:384});
|
|
26
|
+
export PATH=~/.npm-global/bin:$PATH`:null}var ne=m(()=>{"use strict";});function Tr(){if(process.platform==="win32"){let r=process.env.APPDATA||At__namespace.join(tt__namespace.homedir(),"AppData","Roaming");return At__namespace.join(r,wr,Er)}let t=gr(),e=process.env.XDG_CONFIG_HOME||At__namespace.join(t.home,".config");return At__namespace.join(e,wr,Er)}function yr(){try{let t=T__namespace.readFileSync(Tr(),"utf8");return JSON.parse(t)}catch{return {}}}function rt(){let{baseUrl:t}=yr();return typeof t!="string"||t.trim()===""?null:t.trim().replace(/\/$/,"")}function _r(t){let e=Tr();T__namespace.mkdirSync(At__namespace.dirname(e),{recursive:true});let n={...yr(),baseUrl:t};T__namespace.writeFileSync(e,JSON.stringify(n,null,2)+`
|
|
27
|
+
`,{encoding:"utf8",mode:384});}var wr,Er,Re=m(()=>{"use strict";ne();wr="flow-ai-obs",Er="config.json";});function nt(){return rt()??process.env.FLOW_BASE_URL??hs}function st(){let t=nt();return {AUTH_ENGINE:process.env.FLOW_AUTH_ENGINE_URL||`${t}/auth-engine-api/v2/api-key/token`,GATEWAY_TRACES:process.env.FLOW_GATEWAY_TRACES_URL||`${t}/flow-langfuse-gateway/v1/traces`,GATEWAY_HEALTH:process.env.FLOW_GATEWAY_HEALTH_URL||`${t}/flow-langfuse-gateway/v1/health`,OTEL_ENDPOINT:process.env.FLOW_OTEL_ENDPOINT_URL||`${t}/otel`}}function Dt(){let t=nt();return {ANTHROPIC_BASE_URL:process.env.FLOW_LLM_PROXY_URL??`${t}/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"}}function Ne(){let t=nt();return {API_URL:process.env.FLOW_METRICS_URL||`${t}/metrics-collector-api/log-event`,BOOSTER:"flow-ai-obs"}}var hs,ws,se,oe,ie,Pe,ot,f,ae,Tt,Ar,F,kr,V,A=m(()=>{"use strict";Re();hs="https://flow.ciandt.com";ws=st(),se={SERVICE:"flow-plugins-cli",ACCOUNT_CREDS:"credentials",ACCOUNT_TOKEN:"token-cache"},oe="FLOW-nodejs",ie="config.json",Pe={SCOPE_NAME:"flow-ai-obs",SCOPE_VERSION:"0.1.0"};ot={CLAUDE_CODE_ENABLE_TELEMETRY:"1",OTEL_EXPORTER_OTLP_ENDPOINT:ws.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"},ae={KEYCHAIN_ENABLED:!1},Tt={LOCK_STALE_MS:3e4,CONNECTIVITY_MAX_RETRY:3,CONNECTIVITY_RETRY_MS:2e3},Ar={UserPromptSubmit:5,PreToolUse:3,PostToolUse:10,Stop:15},F={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},kr="flow-ai-obs-debug.log",V={TOOL_INPUT:2e4,TOOL_OUTPUT:2e4,TRACE_OUTPUT:2e4,USER_INSTRUCTION:1e4,TRACE_INPUT:5e4,TOOL_BRIEF:60};});function u(...t){if(process.env[f.FLOW_OBS_DEBUG]!=="1")return;let e=`[${new Date().toISOString()}] ${t.join(" ")}
|
|
28
28
|
`;try{T.writeFileSync(ys,e,{flag:"a"});}catch(r){process.stderr.write(`[flow-obs debug ERROR] ${r.message}
|
|
29
|
-
`);}}var ys,$=m(()=>{A();ys=At.join(
|
|
30
|
-
`,{encoding:"utf8",mode:384});try{T__namespace.chmodSync(t,384);}catch{}}finally{Lr(e);}return {settingsPath:t,preserved:r}}async function br(t){let e;try{e=(await x(t)).accessToken;}catch{return false}return e?new Promise(r=>{Ce(`Bearer ${e}`,r,1);}):false}function Ce(t,e,r){let n=new URL(
|
|
31
|
-
`,{encoding:"utf8",mode:384});try{T__namespace.chmodSync(e,384);}catch{}}finally{Lr(r);}}var bs,Mt=m(()=>{A();yt();ne();bs=Tt.LOCK_STALE_MS;});function Bt(){let t=et__namespace.default.homedir();if(process.platform==="darwin")return At__namespace.default.join(t,"Library","Preferences",oe,ie);if(process.platform==="win32"){let r=process.env.APPDATA??At__namespace.default.join(t,"AppData","Roaming");return At__namespace.default.join(r,oe,ie)}let e=process.env.XDG_CONFIG_HOME??At__namespace.default.join(t,".config");return At__namespace.default.join(e,oe,ie)}function $e(){try{let t=T__namespace.default.readFileSync(Bt(),"utf8");return JSON.parse(t)}catch{return {}}}function Rr(t){let e=Bt();T__namespace.default.mkdirSync(At__namespace.default.dirname(e),{recursive:true}),T__namespace.default.writeFileSync(e,JSON.stringify(t,null,2),{encoding:"utf8",mode:384});}var Fe,ce,Pr=m(()=>{A();Fe={credentials:"credentials","token-cache":"tokenCache"};ce=class{static isAvailable(){return true}static hasExistingData(){try{if(!T__namespace.default.existsSync(Bt()))return !1;let e=JSON.parse(T__namespace.default.readFileSync(Bt(),"utf8"));return !!(e&&e.credentials)}catch{return false}}async getSecret(e,r){let n=$e(),s=Fe[r]??r,o=n[s];return o?typeof o=="string"?o:JSON.stringify(o):null}async setSecret(e,r,n){let s=$e(),o=Fe[r]??r;if(r==="token-cache")try{s[o]=JSON.parse(n);}catch{s[o]=n;}else s[o]=n;Rr(s);}async deleteSecret(e,r){let n=$e(),s=Fe[r]??r;return s in n?(delete n[s],Rr(n),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${Bt()}`}};});var Nr={};M(Nr,{MacOsKeyVaultProvider:()=>De});var xe,De,Cr=m(()=>{xe=util.promisify(child_process.execFile),De=class{static async isAvailable(){try{return T.accessSync("/usr/bin/security",T.constants.X_OK),!0}catch{return false}}async getSecret(e,r){try{let{stdout:n}=await xe("security",["find-generic-password","-w","-a",r,"-s",e]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await xe("security",["add-generic-password","-U","-a",r,"-s",e,"-w",n]);}async deleteSecret(e,r){try{return await xe("security",["delete-generic-password","-a",r,"-s",e]),!0}catch{return false}}getStoragePath(){return "macOS Keychain"}};});var Fr={};M(Fr,{LinuxKeyVaultProvider:()=>Me});var Ur,Me,$r=m(()=>{Ur=util.promisify(child_process.execFile),Me=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 T.accessSync(r,T.constants.X_OK),!0}catch{}return false}async getSecret(e,r){try{let{stdout:n}=await Ur("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 Ur("secret-tool",["clear","service",e,"account",r]),!0}catch{return false}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var xr={};M(xr,{WindowsKeyVaultProvider:()=>Be});var Be,Dr=m(()=>{Be=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"}};});async function Mr(){return await Hs()??new ce}async function Hs(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:t}=await Promise.resolve().then(()=>(Cr(),Nr));return await t.isAvailable()?new t:null}case "linux":{let{LinuxKeyVaultProvider:t}=await Promise.resolve().then(()=>($r(),Fr));return await t.isAvailable()?new t:null}case "win32":{let{WindowsKeyVaultProvider:t}=await Promise.resolve().then(()=>(Dr(),xr));return await t.isAvailable()?new t:null}default:return null}}var Br=m(()=>{Pr();});function Ot(){return He||(He=Mr()),He}async function O(){let e=await(await Ot()).getSecret(kt,je);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 Ot()).setSecret(kt,je,JSON.stringify(t));}async function Hr(){let t=await Ot();await t.deleteSecret(kt,je),await t.deleteSecret(kt,Ve);}async function jt(t){await(await Ot()).setSecret(kt,Ve,JSON.stringify({accessToken:t.accessToken,expiresAt:t.expiresAt,lastAuthCheckAt:t.lastAuthCheckAt}));}async function vt(){let e=await(await Ot()).getSecret(kt,Ve);if(!e)return null;try{let r=JSON.parse(e);return {accessToken:r.accessToken,expiresAt:r.expiresAt,lastAuthCheckAt:r.lastAuthCheckAt}}catch{return null}}async function le(){let t=await vt();return t?new Date(t.expiresAt)>new Date:false}async function ct(){let t=await vt();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 We(){let t=await Ot();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 jr(){let t=await O();return !!(t&&t.clientId&&t.clientSecret&&t.tenant)}var kt,je,Ve,He,Lt=m(()=>{Br();A();kt=se.SERVICE,je=se.ACCOUNT_CREDS,Ve=se.ACCOUNT_TOKEN,He=null;});function Vs(t){return js.some(e=>e.test(t))}function Ys(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 b(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 Vr(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 It(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&&Vs(e.hostname))throw new Error(`SSRF: private/loopback host not allowed: ${e.hostname}`);return t}async function Yr(){let t=b(process.env[f.ANTHROPIC_AUTH_TOKEN]);if(t)return {user:await ct().catch(()=>null)??t.clientId,tenant:t.tenant};if(ae.KEYCHAIN_ENABLED)try{let e=await O();if(!e)return {user:"",tenant:""};let r=await ct()??e.clientId??"",n=e.tenant??"";return {user:r,tenant:n}}catch{return {user:"",tenant:""}}return {user:"",tenant:""}}function Ws(){return new Date().toISOString().slice(0,10)}async function Gs(t){let e=Ws(),r=await vt();if(r?.lastAuthCheckAt!==e){u("getOrRefreshToken",`daily auth check (last: ${r?.lastAuthCheckAt??"never"})`);try{let o=await x(t);try{await jt({...o,lastAuthCheckAt:e});}catch{}return u("getOrRefreshToken",`daily check passed, expires=${o.expiresAt}`),o.accessToken}catch(o){if(o instanceof at)throw o;u("getOrRefreshToken",`daily check network error \u2014 using cache: ${o.message}`);}}let n=r!=null&&new Date(r.expiresAt)>new Date;if(u("getOrRefreshToken",`cacheValid=${n}`),n)return u("getOrRefreshToken",`using cached token, expires=${r.expiresAt}`),r.accessToken;u("getOrRefreshToken",`token expired \u2014 refreshing via auth-engine (tenant=${t.tenant} clientId=${t.clientId})`);let s=await x(t);try{await jt({...s,lastAuthCheckAt:e});}catch(o){u("getOrRefreshToken",`token cache save failed (non-fatal): ${o.message}`);}return u("getOrRefreshToken",`token refreshed, expires=${s.expiresAt}`),s.accessToken}function Ks(t,e){let r=e&&e.accessToken?e.accessToken:"";return {endpoint:t.replace(/\/$/,"")+"/flow-langfuse-gateway/v1/traces",authHeader:`Bearer ${r}`}}function qs(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 K(){let t=[],e=process.env[f.ANTHROPIC_MODEL]??"",r=b(process.env[f.ANTHROPIC_AUTH_TOKEN]);u("resolveCredentials",r?"credentials resolved from ANTHROPIC_AUTH_TOKEN":"ANTHROPIC_AUTH_TOKEN absent or invalid"),r&&u("resolveCredentials",`clientId=${r.clientId}`,`tenant=${r.tenant}`),!r&&ae.KEYCHAIN_ENABLED&&(r=await O(),r&&u("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 E="",S=n;if(r)E=await ct().catch(()=>null)??r.clientId;else if(ae.KEYCHAIN_ENABLED)try{let k=await O();k&&(E=await ct()??k.clientId,S=k.tenant);}catch{}let v={user:E??"",tenant:S??"",team:"",project:"",model:e};t.push({mode:"direct",...qs(It(o),i,a),...v}),u("resolveCredentials","direct mode active",`user=${v.user}`,`tenant=${v.tenant}`);}if(!r){if(t.length===0){let E=[];return E.authError=false,E}return t}let c;try{c=await Gs(r);}catch(E){if(u("resolveCredentials",`token refresh failed: ${E.message}`,`(tenant=${r.tenant} clientId=${r.clientId})`),t.length>0)return t.authError=true,t;let S=[];return S.authError=true,S}let d={user:Ys(c)??r.clientId,tenant:n,team:"",project:"",model:e},y=process.env[f.FLOW_TELEMETRY_GATEWAY]??st();return t.push({mode:"gateway",...Ks(It(y),{accessToken:c}),...d}),t}async function Wr(){return (await K()).length>0}var js,Y=m(()=>{Lt();yt();A();$();js=[/^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 Ge(){return At__namespace.default.join(et__namespace.default.homedir(),".claude","flow-obs",".logged-out")}function Kr(){try{let t=Ge();T__namespace.default.mkdirSync(At__namespace.default.dirname(t),{recursive:!0}),T__namespace.default.writeFileSync(t,"",{mode:384});}catch{}}function qr(){try{T__namespace.default.unlinkSync(Ge());}catch{}}function de(){try{return T__namespace.default.existsSync(Ge())}catch{return false}}var Jr=m(()=>{});var Ke={};M(Ke,{runLogin:()=>bt,runLogout:()=>to,runStatus:()=>eo});function J(t){return typeof t=="string"?t.replace(zs,""):t}function Vt(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=d=>{if(d===""){l(),n(new Error("SIGINT"));return}if(d==="\r"||d===`
|
|
29
|
+
`);}}var ys,$=m(()=>{"use strict";A();ys=At.join(tt.tmpdir(),kr);});function Os(t){if(!ks.test(t))throw new Error(`Invalid tenant value: "${t}". Tenant must be lowercase alphanumeric and hyphens (1-64 chars).`)}function vs(t,e){let r=e.length>400?e.slice(0,400)+"\u2026":e;u("toAuthError",`status=${t} body=${r}`);try{let n=JSON.parse(e);if(typeof n.error=="string"&&(u("toAuthError",`api_error_code=${n.error}`+(n.message?` api_message=${n.message}`:"")),Or[n.error]))return new it(Or[n.error])}catch{}return t===401||t===403||t===500?new it("Invalid credentials"):t>=400&&t<500?new it("Authentication request was rejected"):new Error("Authentication service unavailable, please try again later")}function x(t){return new Promise((e,r)=>{try{Os(t.tenant);}catch(l){return r(l)}let n=JSON.stringify({clientSecret:t.clientSecret}),s=new URL(st().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}};u("getToken",`requesting token tenant=${t.tenant} host=${i.hostname} path=${i.path}`);let c=(o?is__namespace.default:As__namespace.default).request(i,l=>{let d=[];l.on("data",y=>d.push(y)),l.on("end",()=>{let y=d.join("");if((l.statusCode??0)>=400)return r(vs(l.statusCode??0,y));let E;try{E=JSON.parse(y);}catch{return r(new Error("Invalid response from auth engine"))}let S=E.expires_at??new Date(Date.now()+(E.expires_in??3600)*1e3).toISOString();e({accessToken:E.access_token??"",expiresAt:S});});});c.on("error",l=>r(new Error(`Network error: ${l.message}`))),c.write(n),c.end();})}var it,ks,Or,yt=m(()=>{"use strict";A();$();it=class extends Error{constructor(e){super(e),this.name="AuthError";}},ks=/^[a-z0-9][a-z0-9-]{0,62}[a-z0-9]$|^[a-z0-9]$/;Or={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 vr(t){try{let e=T__namespace.statSync(t);Date.now()-e.mtimeMs>bs&&T__namespace.unlinkSync(t);}catch{}try{T__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 Lr(t){try{T__namespace.unlinkSync(t);}catch{}}function Rs(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 Ir(){let t=G(),e=t+".lock",r=[];T__namespace.mkdirSync(At__namespace.dirname(t),{recursive:true}),vr(e);try{if(T__namespace.existsSync(t)){T__namespace.copyFileSync(t,t+".bkp");try{T__namespace.chmodSync(t+".bkp",384);}catch{}}let n={};try{n=JSON.parse(T__namespace.readFileSync(t,"utf8"));}catch{}let s=n.env&&typeof n.env=="object"?n.env:{};n.env={...ot,...Dt(),...s},n.otelHeadersHelper="flow-ai-obs otel-headers",(!n.hooks||typeof n.hooks!="object"||Array.isArray(n.hooks))&&(n.hooks={});let o=(c,l)=>({matcher:"",hooks:[{type:"command",command:`flow-ai-obs ${c}`,timeout:l}]}),i=["UserPromptSubmit","PreToolUse","PostToolUse","Stop"],a=n.hooks;for(let c of i){let l=Rs(a[c],o(c,Ar[c]));l.length>1&&r.push(c),a[c]=l;}T__namespace.writeFileSync(t,JSON.stringify(n,null,2)+`
|
|
30
|
+
`,{encoding:"utf8",mode:384});try{T__namespace.chmodSync(t,384);}catch{}}finally{Lr(e);}return {settingsPath:t,preserved:r}}async function br(t){let e;try{e=(await x(t)).accessToken;}catch{return false}return e?new Promise(r=>{Ce(`Bearer ${e}`,r,1);}):false}function Ce(t,e,r){let n=new URL(st().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?is__namespace:As__namespace).request(i,l=>{l.resume(),l.statusCode===200||l.statusCode===204?e(true):r<Tt.CONNECTIVITY_MAX_RETRY?setTimeout(()=>Ce(t,e,r+1),Tt.CONNECTIVITY_RETRY_MS):e(false);});c.on("error",()=>{r<Tt.CONNECTIVITY_MAX_RETRY?setTimeout(()=>Ce(t,e,r+1),Tt.CONNECTIVITY_RETRY_MS):e(false);}),c.write(s),c.end();}function _t(t){let e=G(),r=e+".lock";T__namespace.mkdirSync(At__namespace.dirname(e),{recursive:true}),vr(r);try{let n={};try{n=JSON.parse(T__namespace.readFileSync(e,"utf8"));}catch{}(!n.env||typeof n.env!="object")&&(n.env={}),Object.assign(n.env,t),T__namespace.writeFileSync(e,JSON.stringify(n,null,2)+`
|
|
31
|
+
`,{encoding:"utf8",mode:384});try{T__namespace.chmodSync(e,384);}catch{}}finally{Lr(r);}}var bs,Mt=m(()=>{"use strict";A();yt();ne();bs=Tt.LOCK_STALE_MS;});function Bt(){let t=tt__namespace.default.homedir();if(process.platform==="darwin")return At__namespace.default.join(t,"Library","Preferences",oe,ie);if(process.platform==="win32"){let r=process.env.APPDATA??At__namespace.default.join(t,"AppData","Roaming");return At__namespace.default.join(r,oe,ie)}let e=process.env.XDG_CONFIG_HOME??At__namespace.default.join(t,".config");return At__namespace.default.join(e,oe,ie)}function $e(){try{let t=T__namespace.default.readFileSync(Bt(),"utf8");return JSON.parse(t)}catch{return {}}}function Rr(t){let e=Bt();T__namespace.default.mkdirSync(At__namespace.default.dirname(e),{recursive:true}),T__namespace.default.writeFileSync(e,JSON.stringify(t,null,2),{encoding:"utf8",mode:384});}var Fe,ce,Pr=m(()=>{"use strict";A();Fe={credentials:"credentials","token-cache":"tokenCache"};ce=class{static isAvailable(){return !0}static hasExistingData(){try{if(!T__namespace.default.existsSync(Bt()))return !1;let e=JSON.parse(T__namespace.default.readFileSync(Bt(),"utf8"));return !!(e&&e.credentials)}catch{return !1}}async getSecret(e,r){let n=$e(),s=Fe[r]??r,o=n[s];return o?typeof o=="string"?o:JSON.stringify(o):null}async setSecret(e,r,n){let s=$e(),o=Fe[r]??r;if(r==="token-cache")try{s[o]=JSON.parse(n);}catch{s[o]=n;}else s[o]=n;Rr(s);}async deleteSecret(e,r){let n=$e(),s=Fe[r]??r;return s in n?(delete n[s],Rr(n),!0):!1}getStoragePath(){return `config.json (unencrypted) \u2014 ${Bt()}`}};});var Nr={};M(Nr,{MacOsKeyVaultProvider:()=>De});var xe,De,Cr=m(()=>{"use strict";xe=util.promisify(child_process.execFile),De=class{static async isAvailable(){try{return T.accessSync("/usr/bin/security",T.constants.X_OK),!0}catch{return !1}}async getSecret(e,r){try{let{stdout:n}=await xe("security",["find-generic-password","-w","-a",r,"-s",e]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await xe("security",["add-generic-password","-U","-a",r,"-s",e,"-w",n]);}async deleteSecret(e,r){try{return await xe("security",["delete-generic-password","-a",r,"-s",e]),!0}catch{return !1}}getStoragePath(){return "macOS Keychain"}};});var Fr={};M(Fr,{LinuxKeyVaultProvider:()=>Me});var Ur,Me,$r=m(()=>{"use strict";Ur=util.promisify(child_process.execFile),Me=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 T.accessSync(r,T.constants.X_OK),!0}catch{}return !1}async getSecret(e,r){try{let{stdout:n}=await Ur("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 Ur("secret-tool",["clear","service",e,"account",r]),!0}catch{return !1}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var xr={};M(xr,{WindowsKeyVaultProvider:()=>Be});var Be,Dr=m(()=>{"use strict";Be=class{static async isAvailable(){try{return await $t("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return !1}}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"}};});async function Mr(){return await Hs()??new ce}async function Hs(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:t}=await Promise.resolve().then(()=>(Cr(),Nr));return await t.isAvailable()?new t:null}case "linux":{let{LinuxKeyVaultProvider:t}=await Promise.resolve().then(()=>($r(),Fr));return await t.isAvailable()?new t:null}case "win32":{let{WindowsKeyVaultProvider:t}=await Promise.resolve().then(()=>(Dr(),xr));return await t.isAvailable()?new t:null}default:return null}}var Br=m(()=>{"use strict";Pr();});function Ot(){return He||(He=Mr()),He}async function O(){let e=await(await Ot()).getSecret(kt,je);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 Ot()).setSecret(kt,je,JSON.stringify(t));}async function Hr(){let t=await Ot();await t.deleteSecret(kt,je),await t.deleteSecret(kt,Ve);}async function jt(t){await(await Ot()).setSecret(kt,Ve,JSON.stringify({accessToken:t.accessToken,expiresAt:t.expiresAt,lastAuthCheckAt:t.lastAuthCheckAt}));}async function vt(){let e=await(await Ot()).getSecret(kt,Ve);if(!e)return null;try{let r=JSON.parse(e);return {accessToken:r.accessToken,expiresAt:r.expiresAt,lastAuthCheckAt:r.lastAuthCheckAt}}catch{return null}}async function le(){let t=await vt();return t?new Date(t.expiresAt)>new Date:false}async function at(){let t=await vt();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 We(){let t=await Ot();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 jr(){let t=await O();return !!(t&&t.clientId&&t.clientSecret&&t.tenant)}var kt,je,Ve,He,Lt=m(()=>{"use strict";Br();A();kt=se.SERVICE,je=se.ACCOUNT_CREDS,Ve=se.ACCOUNT_TOKEN,He=null;});function Vs(t){return js.some(e=>e.test(t))}function Ys(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 b(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 Vr(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 It(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&&Vs(e.hostname))throw new Error(`SSRF: private/loopback host not allowed: ${e.hostname}`);return t}async function Yr(){let t=b(process.env[f.ANTHROPIC_AUTH_TOKEN]);if(t)return {user:await at().catch(()=>null)??t.clientId,tenant:t.tenant};if(ae.KEYCHAIN_ENABLED)try{let e=await O();if(!e)return {user:"",tenant:""};let r=await at()??e.clientId??"",n=e.tenant??"";return {user:r,tenant:n}}catch{return {user:"",tenant:""}}return {user:"",tenant:""}}function Ws(){return new Date().toISOString().slice(0,10)}async function Gs(t){let e=Ws(),r=await vt();if(r?.lastAuthCheckAt!==e){u("getOrRefreshToken",`daily auth check (last: ${r?.lastAuthCheckAt??"never"})`);try{let o=await x(t);try{await jt({...o,lastAuthCheckAt:e});}catch{}return u("getOrRefreshToken",`daily check passed, expires=${o.expiresAt}`),o.accessToken}catch(o){if(o instanceof it)throw o;u("getOrRefreshToken",`daily check network error \u2014 using cache: ${o.message}`);}}let n=r!=null&&new Date(r.expiresAt)>new Date;if(u("getOrRefreshToken",`cacheValid=${n}`),n)return u("getOrRefreshToken",`using cached token, expires=${r.expiresAt}`),r.accessToken;u("getOrRefreshToken",`token expired \u2014 refreshing via auth-engine (tenant=${t.tenant} clientId=${t.clientId})`);let s=await x(t);try{await jt({...s,lastAuthCheckAt:e});}catch(o){u("getOrRefreshToken",`token cache save failed (non-fatal): ${o.message}`);}return u("getOrRefreshToken",`token refreshed, expires=${s.expiresAt}`),s.accessToken}function Ks(t,e){let r=e&&e.accessToken?e.accessToken:"";return {endpoint:t.replace(/\/$/,"")+"/flow-langfuse-gateway/v1/traces",authHeader:`Bearer ${r}`}}function qs(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 K(){let t=[],e=process.env[f.ANTHROPIC_MODEL]??"",r=b(process.env[f.ANTHROPIC_AUTH_TOKEN]);u("resolveCredentials",r?"credentials resolved from ANTHROPIC_AUTH_TOKEN":"ANTHROPIC_AUTH_TOKEN absent or invalid"),r&&u("resolveCredentials",`clientId=${r.clientId}`,`tenant=${r.tenant}`),!r&&ae.KEYCHAIN_ENABLED&&(r=await O(),r&&u("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 E="",S=n;if(r)E=await at().catch(()=>null)??r.clientId;else if(ae.KEYCHAIN_ENABLED)try{let k=await O();k&&(E=await at()??k.clientId,S=k.tenant);}catch{}let v={user:E??"",tenant:S??"",team:"",project:"",model:e};t.push({mode:"direct",...qs(It(o),i,a),...v}),u("resolveCredentials","direct mode active",`user=${v.user}`,`tenant=${v.tenant}`);}if(!r){if(t.length===0){let E=[];return E.authError=false,E}return t}let c;try{c=await Gs(r);}catch(E){if(u("resolveCredentials",`token refresh failed: ${E.message}`,`(tenant=${r.tenant} clientId=${r.clientId})`),t.length>0)return t.authError=true,t;let S=[];return S.authError=true,S}let d={user:Ys(c)??r.clientId,tenant:n,team:"",project:"",model:e},y=process.env[f.FLOW_TELEMETRY_GATEWAY]??nt();return t.push({mode:"gateway",...Ks(It(y),{accessToken:c}),...d}),t}async function Wr(){return (await K()).length>0}var js,Y=m(()=>{"use strict";Lt();yt();A();$();js=[/^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 Ge(){return At__namespace.default.join(tt__namespace.default.homedir(),".claude","flow-obs",".logged-out")}function Kr(){try{let t=Ge();T__namespace.default.mkdirSync(At__namespace.default.dirname(t),{recursive:!0}),T__namespace.default.writeFileSync(t,"",{mode:384});}catch{}}function qr(){try{T__namespace.default.unlinkSync(Ge());}catch{}}function de(){try{return T__namespace.default.existsSync(Ge())}catch{return false}}var Jr=m(()=>{"use strict";});var Ke={};M(Ke,{runLogin:()=>bt,runLogout:()=>to,runStatus:()=>eo});function q(t){return typeof t=="string"?t.replace(zs,""):t}function Vt(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=d=>{if(d===""){l(),n(new Error("SIGINT"));return}if(d==="\r"||d===`
|
|
32
32
|
`){l(),process.stdout.write(`
|
|
33
|
-
`),r(i);return}if(d==="\x7F"){i.length>0&&(i=i.slice(0,-1),process.stdout.write("\b \b"));return}d.startsWith("\x1B")||(i+=d,process.stdout.write(s?"*".repeat(d.length):d));};function l(){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 zr(t){if(!de())try{await O()||await Ye(t);}catch{}}async function Xr(t){let{accessToken:e,expiresAt:r}=await x(t);await Ye(t),await jt({accessToken:e,expiresAt:r}),qr();try{let n=Vr(t);_t({[f.ANTHROPIC_AUTH_TOKEN]:n});}catch{}}async function Xs(t){try{return await Xr(t),process.stdout.write(I(` \u2713 Setup complete. Tenant: ${
|
|
33
|
+
`),r(i);return}if(d==="\x7F"){i.length>0&&(i=i.slice(0,-1),process.stdout.write("\b \b"));return}d.startsWith("\x1B")||(i+=d,process.stdout.write(s?"*".repeat(d.length):d));};function l(){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 zr(t){if(!de())try{await O()||await Ye(t);}catch{}}async function Xr(t){let{accessToken:e,expiresAt:r}=await x(t);await Ye(t),await jt({accessToken:e,expiresAt:r}),qr();try{let n=Vr(t);_t({[f.ANTHROPIC_AUTH_TOKEN]:n});}catch{}}async function Xs(t){try{return await Xr(t),process.stdout.write(I(` \u2713 Setup complete. Tenant: ${q(t.tenant)}
|
|
34
34
|
|
|
35
|
-
`)),0}catch(e){return process.stderr.write(B(` \u2717 Authentication failed: ${
|
|
35
|
+
`)),0}catch(e){return process.stderr.write(B(` \u2717 Authentication failed: ${q(e.message)}
|
|
36
36
|
`)),1}}async function Zs(){try{process.stdout.write(`
|
|
37
37
|
`);let t=(await Vt(H(" ? ")+"Client ID: ")).trim(),e=(await Vt(H(" ? ")+"Client Secret: ",{masked:!0})).trim(),r=(await Vt(H(" ? ")+"Tenant: ")).trim();if(!t||!e||!r)return process.stderr.write(B(` \u2717 All fields are required
|
|
38
|
-
`)),1;try{await Xr({clientId:t,clientSecret:e,tenant:r});}catch(n){return process.stderr.write(B(` \u2717 Authentication failed: ${
|
|
39
|
-
`)),1}return process.stdout.write(I(` \u2713 Setup complete. Tenant: ${
|
|
38
|
+
`)),1;try{await Xr({clientId:t,clientSecret:e,tenant:r});}catch(n){return process.stderr.write(B(` \u2717 Authentication failed: ${q(n.message)}
|
|
39
|
+
`)),1}return process.stdout.write(I(` \u2713 Setup complete. Tenant: ${q(r)}
|
|
40
40
|
`)),process.stdout.write(` Storage: ${await We()}
|
|
41
41
|
|
|
42
42
|
`),0}catch(t){if(t.message==="SIGINT")throw t;return process.stderr.write(B(` \u2717 Unexpected error: ${t.message}
|
|
43
43
|
`)),1}}async function bt(t={}){if(t.clientId&&t.clientSecret&&t.tenant)return Xs({clientId:t.clientId,clientSecret:t.clientSecret,tenant:t.tenant});let e=de()?null:b(process.env[f.ANTHROPIC_AUTH_TOKEN]);e&&await zr(e);let r=e||await O();if(r){process.stdout.write(`
|
|
44
44
|
`),process.stdout.write(j(` Already authenticated
|
|
45
|
-
`)),process.stdout.write(w(" Tenant: ")+
|
|
46
|
-
`),process.stdout.write(w(" Client ID: ")+
|
|
45
|
+
`)),process.stdout.write(w(" Tenant: ")+q(r.tenant)+`
|
|
46
|
+
`),process.stdout.write(w(" Client ID: ")+q(r.clientId)+`
|
|
47
47
|
`),process.stdout.write(`
|
|
48
48
|
`);let n;try{n=await Vt(H(" ? ")+"Re-authenticate? (y/N): ");}catch(s){if(s.message==="SIGINT")return process.stdout.write(`
|
|
49
49
|
`),130;throw s}if(n.trim().toLowerCase()!=="y")return process.stdout.write(I(` \u2713 Using existing credentials.
|
|
@@ -57,12 +57,12 @@
|
|
|
57
57
|
`)),0}catch{return process.stderr.write(B(` \u2717 Error removing credentials
|
|
58
58
|
`)),1}}async function eo(){if(de())return process.stdout.write(_(" \u26A0 Not authenticated. Run `flow-ai-obs auth login` to set up.\n")),0;let t=b(process.env[f.ANTHROPIC_AUTH_TOKEN]);t&&await zr(t);let e=t||await O();if(!e)return process.stdout.write(_(" \u26A0 Not authenticated. Run `flow-ai-obs auth login` to set up.\n")),0;if(!t&&!await le())return process.stdout.write(_(" \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 We();return process.stdout.write(`
|
|
59
59
|
`+j(` Authenticated
|
|
60
|
-
`)),process.stdout.write(w(" Tenant: ")+
|
|
61
|
-
`),process.stdout.write(w(" Client ID: ")+
|
|
60
|
+
`)),process.stdout.write(w(" Tenant: ")+q(e.tenant)+`
|
|
61
|
+
`),process.stdout.write(w(" Client ID: ")+q(e.clientId)+`
|
|
62
62
|
`),process.stdout.write(w(" Client Secret: ")+r+`
|
|
63
63
|
`),process.stdout.write(w(" Storage: ")+n+`
|
|
64
64
|
|
|
65
|
-
`),0}var zs,Yt=m(()=>{Lt();Jr();yt();Y();Mt();A();
|
|
65
|
+
`),0}var zs,Yt=m(()=>{"use strict";Lt();Jr();yt();Y();Mt();A();mt();zs=/[\x00-\x08\x0B-\x1F\x7F]|\x1b\[[0-9;]*[a-zA-Z]/g;});var nn={};M(nn,{runInstall:()=>qe});function ro(){if(process.env.WSL_DISTRO_NAME&&process.platform==="linux")return child_process.spawnSync("cmd.exe",["/c","where","claude"],{encoding:"utf8",timeout:5e3}).status===0;let t=process.platform==="win32"?"where":"which";return child_process.spawnSync(t,["claude"],{encoding:"utf8",timeout:5e3}).status===0}function no(){try{let t=T__namespace.readFileSync(G(),"utf8"),e=JSON.parse(t);return !!(e.env&&e.env[f.ANTHROPIC_AUTH_TOKEN])}catch{return false}}function rn(t){let e;try{e=new URL(t);}catch{throw new Error(`Invalid URL: ${t}`)}if(e.protocol!=="https:")throw new Error(`Custom URL must use HTTPS: ${t}`);let r=process.env[f.FLOW_OBS_ALLOW_HTTP];try{delete process.env[f.FLOW_OBS_ALLOW_HTTP],It(t);}finally{r!==void 0&&(process.env[f.FLOW_OBS_ALLOW_HTTP]=r);}if(e.pathname!=="/"&&e.pathname!=="")throw new Error(`Custom URL must be a base URL with no path beyond the root.
|
|
66
66
|
Received: ${t}
|
|
67
67
|
Expected: https://tenant.example.com`);if(e.search)throw new Error(`Custom URL must not contain query parameters.
|
|
68
68
|
Received: ${t}
|
|
@@ -84,18 +84,18 @@
|
|
|
84
84
|
`)+_(" on Windows too: ")+H(`npm install -g @ciandt-flow/flow-ai-obs
|
|
85
85
|
`)+_(` Running Claude (Windows) + flow-ai-obs (WSL) is not a supported configuration.
|
|
86
86
|
|
|
87
|
-
`)),!e&&!t.noInteractive&&
|
|
87
|
+
`)),!e&&!t.noInteractive&>()){let l=rt();try{l?(process.stdout.write(`
|
|
88
88
|
Current base URL: ${j(l)}
|
|
89
89
|
`),await Ae(" Keep this URL?",!0)||(e=await tn())):(process.stdout.write(`
|
|
90
90
|
`),await Ae(" Does your organization use a custom Flow URL?",!1)&&(e=await tn()));}catch{return 1}process.stdout.write(`
|
|
91
|
-
`);}if(!e&&!t.noInteractive&&!
|
|
91
|
+
`);}if(!e&&!t.noInteractive&&!gt()){let l=rt(),d=process.env.FLOW_BASE_URL,y=l??d??"https://flow.ciandt.com",E=!!(l??d);process.stdout.write(_(` \u26A0 Non-interactive environment detected.
|
|
92
92
|
`)+w(` Using URL: ${y}
|
|
93
93
|
`)+(E?"":w(` Run with --custom-url to configure a custom domain.
|
|
94
94
|
`))+`
|
|
95
95
|
`);}let r=null,n=null;if(e){let l;try{l=rn(e);}catch(y){return process.stderr.write(`
|
|
96
96
|
\u2717 Invalid --custom-url: ${y.message}
|
|
97
97
|
|
|
98
|
-
`),1}let d=
|
|
98
|
+
`),1}let d=rt();try{_r(l);}catch(y){return process.stderr.write(`
|
|
99
99
|
\u2717 Failed to persist custom URL: ${y.message}
|
|
100
100
|
|
|
101
101
|
`),1}r=l,n={OTEL_EXPORTER_OTLP_ENDPOINT:`${l}/otel`,ANTHROPIC_BASE_URL:`${l}/flow-llm-proxy/`},d&&d!==l?process.stdout.write(_(` \u26A0 Base URL updated.
|
|
@@ -104,12 +104,12 @@
|
|
|
104
104
|
|
|
105
105
|
`)):process.stdout.write(I(` \u2713 Base URL configured: ${l}
|
|
106
106
|
|
|
107
|
-
`));}if(!no())if(t.noInteractive||!
|
|
107
|
+
`));}if(!no())if(t.noInteractive||!gt())process.stdout.write(_(" \u26A0 No credentials found in settings.json \u2014 run `flow-ai-obs auth login` to authenticate.\n\n"));else {process.stdout.write(_(` \u26A0 No credentials found in settings.json \u2014 authentication required.
|
|
108
108
|
|
|
109
109
|
`));let{runLogin:l}=await Promise.resolve().then(()=>(Yt(),Ke)),d=await l();if(d!==0)return d}let s,o;try{(({settingsPath:s,preserved:o}=Ir())),n&&_t(n);}catch(l){return process.stderr.write(` \u2717 Failed to write settings: ${l.message}
|
|
110
110
|
`),1}process.stdout.write(`
|
|
111
111
|
`+j(" Native OTEL configured")+` (metrics & logs)
|
|
112
|
-
`);let i=n?{...
|
|
112
|
+
`);let i=n?{...ot,OTEL_EXPORTER_OTLP_ENDPOINT:n.OTEL_EXPORTER_OTLP_ENDPOINT}:ot;for(let[l,d]of Object.entries(i))process.stdout.write(w(` ${l.padEnd(36)}`)+d+`
|
|
113
113
|
`);process.stdout.write(`
|
|
114
114
|
`),process.stdout.write(j(" Hooks registered")+` (Langfuse trace capture)
|
|
115
115
|
`),process.stdout.write(w(" UserPromptSubmit")+` \u2192 flow-ai-obs UserPromptSubmit (timeout: 5s)
|
|
@@ -123,12 +123,12 @@
|
|
|
123
123
|
`),process.stdout.write(w(" Settings: ")+s+`
|
|
124
124
|
`),process.stdout.write(w(" Backup: ")+s+`.bkp
|
|
125
125
|
`),process.stdout.write(w(" OTEL auth: flow-ai-obs otel-headers")+w(` (reads keychain at runtime)
|
|
126
|
-
`));let a=r??
|
|
126
|
+
`));let a=r??rt()??process.env.FLOW_BASE_URL??"https://flow.ciandt.com";process.stdout.write(w(" Base URL: ")+a+`
|
|
127
127
|
`),process.stdout.write(`
|
|
128
128
|
`),process.stdout.write(I(` \u2713 Ready. Native OTEL + Langfuse trace capture active.
|
|
129
129
|
`)),process.stdout.write(w(" Run `flow-ai-obs setup` to also configure the Flow LLM Proxy.\n\n"));let c=hr();return c&&process.stdout.write(_(` \u26A0 ${c}
|
|
130
130
|
|
|
131
|
-
`)),0}var Qr,Je=m(()=>{Mt();A();
|
|
131
|
+
`)),0}var Qr,Je=m(()=>{"use strict";Mt();A();mt();ne();Re();Y();ke();Qr={darwin:`npm install -g @anthropic-ai/claude-code
|
|
132
132
|
or visit: https://claude.ai/download`,linux:"npm install -g @anthropic-ai/claude-code",win32:`npm install -g @anthropic-ai/claude-code
|
|
133
133
|
or visit: https://claude.ai/download`};});var sn={};M(sn,{runSetup:()=>so});async function so(t={}){process.stdout.write(`
|
|
134
134
|
\u2554\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2550\u2557
|
|
@@ -153,12 +153,12 @@
|
|
|
153
153
|
`)),process.stdout.write(I(` \u2713 Setup complete!
|
|
154
154
|
`)),process.stdout.write(w(` Settings: ${G()}
|
|
155
155
|
|
|
156
|
-
`)),0}var on=m(()=>{A();
|
|
156
|
+
`)),0}var on=m(()=>{"use strict";A();mt();Yt();Je();Mt();Lt();});var an={};M(an,{runOtelHeaders:()=>oo});async function oo(){let t=b(process.env[f.ANTHROPIC_AUTH_TOKEN]);if(!t)try{t=await O();}catch{return process.stderr.write(`[flow-ai-obs otel-headers] Failed to read credentials
|
|
157
157
|
`),1}if(!t)return process.stderr.write(`[flow-ai-obs otel-headers] Not authenticated \u2014 run: flow-ai-obs auth login
|
|
158
158
|
`),1;let e;try{e=(await x(t)).accessToken;}catch(r){return process.stderr.write(`[flow-ai-obs otel-headers] Token fetch failed: ${r.message}
|
|
159
159
|
`),1}return e?(process.stdout.write(`{"Authorization": "Bearer ${e}"}
|
|
160
160
|
`),0):(process.stderr.write(`[flow-ai-obs otel-headers] Empty token received
|
|
161
|
-
`),1)}var cn=m(()=>{Lt();yt();Y();A();});var un={};M(un,{runCheck:()=>io});function ze(t){return !t||t.length<=8?"****":t.slice(0,4)+"****...****"+t.slice(-4)}function Wt(t){process.stdout.write(` \u2713 ${t}
|
|
161
|
+
`),1)}var cn=m(()=>{"use strict";Lt();yt();Y();A();});var un={};M(un,{runCheck:()=>io});function ze(t){return !t||t.length<=8?"****":t.slice(0,4)+"****...****"+t.slice(-4)}function Wt(t){process.stdout.write(` \u2713 ${t}
|
|
162
162
|
`);}function pe(t){process.stdout.write(` \u26A0 ${t}
|
|
163
163
|
`);}function fe(t){process.stdout.write(` \u2717 ${t}
|
|
164
164
|
`);}function R(t){process.stdout.write(` ${t}
|
|
@@ -167,24 +167,24 @@
|
|
|
167
167
|
`),P(),process.stdout.write(` Auth
|
|
168
168
|
`);let t=b(process.env[f.ANTHROPIC_AUTH_TOKEN]),e=t||await O();if(!e){pe("Not authenticated \u2014 starting setup..."),P();let a=await bt();if(a!==0)return a;if(t=b(process.env[f.ANTHROPIC_AUTH_TOKEN]),e=t||await O(),!e)return fe("Authentication failed"),P(),1;P(),process.stdout.write(` Auth
|
|
169
169
|
`);}if(!t&&!await le()){pe("Session expired \u2014 re-authenticating..."),P();let a=await bt();if(a!==0)return a;P(),process.stdout.write(` Auth
|
|
170
|
-
`);}let r=await
|
|
171
|
-
`);let n={};try{let a=T__namespace.readFileSync(G(),"utf8");n=JSON.parse(a).env||{};}catch{}let s=Object.keys(
|
|
170
|
+
`);}let r=await at()||e.clientId;Wt("Authenticated"),R(`Tenant: ${e.tenant}`),R(`User: ${r}`),P(),process.stdout.write(` Native OTEL
|
|
171
|
+
`);let n={};try{let a=T__namespace.readFileSync(G(),"utf8");n=JSON.parse(a).env||{};}catch{}let s=Object.keys(ot).filter(a=>!n[a]);if(s.length===0?(Wt("All OTEL env vars present in settings.json"),R(`Endpoint: ${n.OTEL_EXPORTER_OTLP_ENDPOINT}`)):(pe(`${s.length} OTEL var(s) missing from settings.json \u2014 native metrics/logs disabled`),s.forEach(a=>fe(`Missing: ${a}`)),R("Run: flow-ai-obs install (restores missing vars automatically)")),P(),process.stdout.write(` Tracing
|
|
172
172
|
`),process.env[f.FLOW_TELEMETRY]==="true"){Wt("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=>pe(`Missing: ${c}`));}else R("FLOW_TELEMETRY not set \u2014 direct mode inactive (gateway mode may still be active)");let i=await K();if(!i||i.length===0)return i&&i.authError?fe("Token refresh failed \u2014 gateway mode could not activate"):(fe("No active destinations \u2014 no traces will be sent"),R("For direct mode: set FLOW_TELEMETRY=true + LANGFUSE_BASE_URL + LANGFUSE_PUBLIC_KEY + LANGFUSE_SECRET_KEY"),R("For gateway mode: run flow-claude-observability auth login")),P(),1;for(let a of i)if(a.mode==="gateway"){let c=await vt();Wt("Mode: gateway"),R(`Endpoint: ${a.endpoint}`),R(`Token: ${ze(c?.accessToken)}`);}else a.mode==="direct"&&(Wt("Mode: direct"),R(`Endpoint: ${a.endpoint}`),R(`PK: ${ze(process.env[f.LANGFUSE_PUBLIC_KEY])}`),R(`SK: ${ze(process.env[f.LANGFUSE_SECRET_KEY])}`));return P(),process.stdout.write(` All checks passed \u2014 observability is active.
|
|
173
|
-
`),P(),0}var dn=m(()=>{Lt();Y();Mt();A();Yt();});function W(t,e){let r=typeof t=="object"?JSON.stringify(t):String(t??"");return r.length>e?r.slice(0,e)+" \u2026[truncated]":r}function me(t,e=100){return String(t??"").split(`
|
|
174
|
-
`)[0].slice(0,e).trim()}function Xe(){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 D(t){process.stdout.write(JSON.stringify(t));}var Rt=m(()=>{});function
|
|
173
|
+
`),P(),0}var dn=m(()=>{"use strict";Lt();Y();Mt();A();Yt();});function W(t,e){let r=typeof t=="object"?JSON.stringify(t):String(t??"");return r.length>e?r.slice(0,e)+" \u2026[truncated]":r}function me(t,e=100){return String(t??"").split(`
|
|
174
|
+
`)[0].slice(0,e).trim()}function Xe(){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 D(t){process.stdout.write(JSON.stringify(t));}var Rt=m(()=>{"use strict";});function J(){return String(BigInt(Date.now())*1000000n)}var Ze,ct,Gt=m(()=>{"use strict";Ze=()=>crypto.randomBytes(16).toString("hex"),ct=()=>crypto.randomBytes(8).toString("hex");});function Eo(t,e){let r=At.resolve(t);if(!r.startsWith(e))throw new Error(`Path traversal detected: ${t}`);return r}function Qe(t){if(!ho.test(t))throw new Error(`Invalid session ID: ${t}`);return Eo(At.join(tt.tmpdir(),`flow-obs-${t}.json`),wo)}function Pt(t){let e=Qe(t);if(!T.existsSync(e))return null;try{return JSON.parse(T.readFileSync(e,"utf8"))}catch{return null}}function Nt(t,e){T.writeFileSync(Qe(t),JSON.stringify(e),{encoding:"utf8",mode:384});}function tr(t){try{T.unlinkSync(Qe(t));}catch{}}var ho,wo,Kt=m(()=>{"use strict";ho=/^[0-9a-f-]{1,64}$/i,wo=At.normalize(tt.tmpdir())+At.sep;});function hn(t){if(!t||!T.existsSync(t))return null;try{let e=T.readFileSync(t,"utf8").trimEnd().split(`
|
|
175
175
|
`);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 er(t){if(!t||!T.existsSync(t))return null;try{let e=T.readFileSync(t,"utf8").trimEnd().split(`
|
|
176
176
|
`),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(d=>d.type==="text").map(d=>d.text??"").join("");c&&r.unshift(c);let l=i.message?.usage??{};n+=(l.input_tokens??0)+(l.cache_read_input_tokens??0)+(l.cache_creation_input_tokens??0),s+=l.output_tokens??0;}}catch{}return !r.length&&n===0?null:{text:r.join(`
|
|
177
177
|
|
|
178
|
-
`),inputTokens:n,outputTokens:s}}catch{}return null}var rr=m(()=>{});function Sn(t){return t.replace(":","/")}function ge(t,e){if(!t)return null;let r=Sn(t),n=[At.join(
|
|
179
|
-
`)[0].match(/^\/([a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?)(?:\s.*)?$/i)?.[1]??null}function yn(t){return !!t.slashSkill||t.toolCalls.some(n=>n.tool==="Skill")?t.toolCalls.some(n=>n.tool==="Skill"&&!n.synthetic||Oo.has(n.tool))?"complete":"prerequisite_required":null}function he(t,e){if(!t)return null;let r=Sn(t),n=[At.join(
|
|
180
|
-
`);return}let n=!!(await K()).authError,s=t.session_id||"unknown",o=t.prompt||"",i=t.cwd||"",a=hn(t.transcript_path)||Ze(),c=Tn(o),l=c?ge(c,i):null,d=c?he(c,i):null;Nt(s,{traceId:Ze(),spanId:
|
|
181
|
-
`,{flag:"a",encoding:"utf8",mode:384}),u("sendTraces:dump",`request appendada em ${Ln}`);}catch(i){u("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function xo(t){let e=new URL(t),r=new URL(
|
|
178
|
+
`),inputTokens:n,outputTokens:s}}catch{}return null}var rr=m(()=>{"use strict";});function Sn(t){return t.replace(":","/")}function ge(t,e){if(!t)return null;let r=Sn(t),n=[At.join(tt.homedir(),".claude","skills",r,"SKILL.md"),At.join(e??"",".claude","skills",r,"SKILL.md")];for(let s of n)if(T.existsSync(s))try{return T.readFileSync(s,"utf8")}catch{}return null}function Tn(t){return t.split(`
|
|
179
|
+
`)[0].match(/^\/([a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?)(?:\s.*)?$/i)?.[1]??null}function yn(t){return !!t.slashSkill||t.toolCalls.some(n=>n.tool==="Skill")?t.toolCalls.some(n=>n.tool==="Skill"&&!n.synthetic||Oo.has(n.tool))?"complete":"prerequisite_required":null}function he(t,e){if(!t)return null;let r=Sn(t),n=[At.join(tt.homedir(),".claude","skills",r),At.join(e??"",".claude","skills",r)],s=null;for(let a of n)if(T.existsSync(At.join(a,"SKILL.md"))){s=a;break}if(!s)return null;let o=[];function i(a,c){for(let l of T.readdirSync(a,{withFileTypes:true})){if(_o.has(l.name)||ko.has(l.name)||Ao.has(At.extname(l.name)))continue;let d=c?`${c}/${l.name}`:l.name;l.isDirectory()?i(At.join(a,l.name),d):o.push(d);}}return i(s,""),o.length>0?o:null}var _o,Ao,ko,Oo,we=m(()=>{"use strict";_o=new Set([".venv","__pycache__",".git","node_modules"]),Ao=new Set([".pyc",".pyo"]),ko=new Set(["SKILL.md",".DS_Store",".gitignore"]);Oo=new Set(["Read","Write","Edit","MultiEdit","Bash","Glob","Grep","TodoWrite","WebFetch","WebSearch","Agent","Task"]);});function Io(t){try{let e=t.split(".")[1].replace(/-/g,"+").replace(/_/g,"/");return JSON.parse(Buffer.from(e,"base64").toString())}catch{return null}}function bo(t,e,r,n){return new Promise(s=>{let o=new URL(t),i=o.protocol==="https:",a=(i?is__namespace.default:As__namespace.default).request({hostname:o.hostname,port:o.port||(i?443:80),path:o.pathname+o.search,method:"POST",headers:{"Content-Type":"application/json","Content-Length":Buffer.byteLength(e),Authorization:`Bearer ${String(r).replace(/[\r\n]/g,"")}`,FlowTenant:String(n).replace(/[\r\n]/g,"")}},c=>{c.resume(),s(c.statusCode??0);});a.on("error",()=>s(0)),a.setTimeout(5e3,()=>{a.destroy(),s(0);}),a.write(e),a.end();})}async function lt(t,e={}){try{let r=b(process.env[f.ANTHROPIC_AUTH_TOKEN]);if(!r)return;let n,s=new Promise((y,E)=>{n=setTimeout(()=>E(new Error("getToken timeout")),4e3),n.unref();}),{accessToken:o}=await Promise.race([x(r),s]);clearTimeout(n);let i=Io(o);if(!i)return;let a=i.tenant||r.tenant,c=JSON.stringify({action:t,booster:Ne().BOOSTER,metadata:e,success:!0,tenant:a,timestamp:new Date().toISOString(),os:process.platform,user:{email:i.email||"",id:i.sub||"",name:i.name||i.email||""}}),l=It(Ne().API_URL),d=await bo(l,c,o,a);u("metrics.logEvent",`action=${t} status=${d}`);}catch(r){u("metrics.logEvent",`silenced error: ${r.message}`);}}var Ee=m(()=>{"use strict";A();yt();Y();$();});async function nr(t,e=false){if(e){process.stdout.write(JSON.stringify({decision:"block",reason:Ro})+`
|
|
180
|
+
`);return}let n=!!(await K()).authError,s=t.session_id||"unknown",o=t.prompt||"",i=t.cwd||"",a=hn(t.transcript_path)||Ze(),c=Tn(o),l=c?ge(c,i):null,d=c?he(c,i):null;Nt(s,{traceId:Ze(),spanId:ct(),startNs:J(),sessionId:s,prompt:o,cwd:i,traceName:a,transcriptPath:t.transcript_path||"",model:process.env[f.ANTHROPIC_MODEL]||"",toolCalls:[],spans:[],pendingTool:null,slashSkill:c,skillContent:l,skillArtifacts:d}),lt("SESSION_STARTED",{traceType:c?"skill":"prompt",slashSkill:c,clientIdExpired:n}),u("UserPromptSubmit",`sid=${s}`,`traceName=${a}`,`slashSkill=${c}`),D(t);}var Ro,_n=m(()=>{"use strict";Gt();Kt();rr();we();Rt();$();A();Y();Ee();Ro=`\u26D4 Your Flow API key has expired. You no longer have access to Claude Code through the Flow platform. To restore observability and access, visit ${nt()}/settings/api-keys to generate a new API key, then run: flow-ai-obs auth login`;});async function An(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},s=Pt(e);s&&(s.pendingTool={name:r,inputStr:W(n,V.TOOL_INPUT),startNs:J()},Nt(e,s)),u("PreToolUse",`sid=${e}`,`tool=${r}`,`stateFound=${!!s}`),D(t);}var kn=m(()=>{"use strict";Gt();Kt();Rt();$();A();});function p(t,e){return e==null||e===""?null:{key:t,value:{stringValue:String(e)}}}function ut(...t){return t.filter(e=>e!==null)}function On(t,e){return {resourceSpans:[{resource:{attributes:t},scopeSpans:[{scope:Po,spans:Array.isArray(e)?e:[e]}]}]}}var Po,h,vn=m(()=>{"use strict";A();Po={name:Pe.SCOPE_NAME,version:Pe.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 In(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{T.writeFileSync(Ln,o+`
|
|
181
|
+
`,{flag:"a",encoding:"utf8",mode:384}),u("sendTraces:dump",`request appendada em ${Ln}`);}catch(i){u("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function xo(t){let e=new URL(t),r=new URL(st().GATEWAY_HEALTH);return r.hostname=e.hostname,r.port=e.port,r.protocol=e.protocol,r}function bn(t,e){return new Promise((r,n)=>{let s=t._isSSL?is__namespace.default:As__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 Rn(t,e){let r;try{r=xo(t);}catch{return false}let n=r.protocol==="https:";try{let s={};e&&(s.Authorization=String(e).replace(/[\r\n]/g,""));let o=await bn({hostname:r.hostname,port:r.port||(n?443:80),path:r.pathname,method:"GET",headers:s,_isSSL:n},null);return u("checkHealth",`url=${r.href} status=${o.statusCode}`),o.statusCode>=200&&o.statusCode<300}catch{return false}}async function Se(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)};u("sendTraces:request",`POST ${e}`),u("sendTraces:request",`headers=${JSON.stringify({...a,Authorization:i.slice(0,20)+"\u2026"})}`),u("sendTraces:request",`body=${n.slice(0,500)}${n.length>500?"\u2026":""}`);try{let c=await bn({hostname:s.hostname,port:s.port||(o?443:80),path:s.pathname,method:"POST",headers:a,_isSSL:o},n);return u("sendTraces:response",`status=${c.statusCode}`),In(e,a,n,c.statusCode,c.body),c.statusCode}catch(c){return u("sendTraces:error",c.message),In(e,a,n,0,c.message),0}}var Ln,Pn=m(()=>{"use strict";A();$();Ln=At.join(tt.tmpdir(),"flow-obs-requests.ndjson");});function Do(){let t=parseInt(process.env[f.BUFFER_TTL_DAYS]??"",10);return (Number.isFinite(t)?Math.max(F.MIN_TTL_DAYS,Math.min(F.MAX_TTL_DAYS,t)):F.DEFAULT_TTL_DAYS)*24*60*60*1e3}function Mo(){let t=parseInt(process.env[f.BUFFER_MAX_FILES]??"",10);return Number.isFinite(t)?Math.max(F.MIN_MAX_FILES,Math.min(F.MAX_MAX_FILES,t)):F.DEFAULT_MAX_FILES}function Cn(t){if(/[/\\]/.test(t))throw new Error(`Invalid buffer fileId: ${t}`);return At__namespace.default.join(tt__namespace.default.tmpdir(),`${F.FILE_PREFIX}${t}.json`)}function or(){let t=tt__namespace.default.tmpdir(),e;try{e=T__namespace.default.readdirSync(t);}catch{return []}return e.filter(r=>r.startsWith(F.FILE_PREFIX)&&r.endsWith(".json")).map(r=>{let n=At__namespace.default.join(t,r),s=0;try{s=T__namespace.default.statSync(n).mtimeMs;}catch{}return {full:n,mtime:s}}).sort((r,n)=>r.mtime-n.mtime).map(r=>r.full)}function qt(t){try{let e=Mo(),r=or();if(r.length>=e){let o=r.slice(0,r.length-e+1);for(let i of o)try{T__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 T__namespace.default.writeFileSync(Cn(n),JSON.stringify(s),{encoding:"utf8",mode:384}),u("buffer",`saved fileId=${n}`),n}catch(e){return u("buffer",`saveToBuffer failed: ${e.message}`),null}}function Un(t){let e=or(),r=t!=null&&t>0?t:e.length,n=[];for(let s of e){if(n.length>=r)break;try{let o=T__namespace.default.readFileSync(s,"utf8"),i=JSON.parse(o);i&&i.fileId&&i.payload&&n.push(i);}catch{u("buffer",`skipping malformed file: ${s}`);}}return n}function Fn(t){try{T__namespace.default.unlinkSync(Cn(t)),u("buffer",`deleted fileId=${t}`);}catch{}}function $n(){let t=Date.now()-Do();for(let e of or())try{let{mtimeMs:r}=T__namespace.default.statSync(e);r<t&&(T__namespace.default.unlinkSync(e),u("buffer",`evicted stale: ${At__namespace.default.basename(e)}`));}catch{}}var xn=m(()=>{"use strict";A();$();});async function Bo(t){$n();let e=Un(F.REPLAY_BATCH_SIZE);e.length&&(u("replayBufferedTraces",`replaying ${e.length} buffered trace(s)`),await Promise.allSettled(e.map(async r=>{try{let n=await Se(r.payload,t.endpoint,t.authHeader);n>=200&&n<300?(Fn(r.fileId),u("replayBufferedTraces",`replayed fileId=${r.fileId} status=${n}`)):u("replayBufferedTraces",`replay failed fileId=${r.fileId} status=${n}`);}catch(n){u("replayBufferedTraces",`replay error fileId=${r.fileId}: ${n.message}`);}})));}async function Dn(t){let e=await K();if(!e.length)return e.authError&&(u("postToLangfuse","auth refresh failed \u2014 buffering trace"),qt(t)),0;let r=await Promise.all(e.map(async o=>{if(o.mode!=="gateway")return {creds:o,healthy:true};let i=await Rn(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 Bo(n),(await Promise.all(r.map(async({creds:o,healthy:i})=>{if(o.mode==="gateway"){if(!i)return u("postToLangfuse","gateway health check failed \u2014 buffering trace"),qt(t),0;let c=await Se(t,o.endpoint,o.authHeader);return (c===0||c>=500)&&(u("postToLangfuse",`gateway send failed (status ${c}) \u2014 buffering trace`),qt(t)),c}let a=await Se(t,o.endpoint,o.authHeader);return (a===0||a>=500)&&(u("postToLangfuse",`direct endpoint unavailable (status ${a}) \u2014 buffering trace`),qt(t)),a}))).find(o=>o!==0)??0}var Mn=m(()=>{"use strict";Y();$();Pn();xn();A();});var ir=m(()=>{"use strict";vn();Mn();});function X(t){if(t==null)return "";let e=typeof t=="string"?t:JSON.stringify(t);return Yo.reduce((r,{re:n,replace:s})=>r.replace(n,s),e)}var N,Ho,jo,Vo,Bn,Yo,ar=m(()=>{"use strict";N="[REDACTED]",Ho="[REDACTED-EMAIL]",jo="[REDACTED-CPF]",Vo="[REDACTED-CNPJ]",Bn="[REDACTED-PHONE]",Yo=[{re:/\b(sk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`sk-${N}`},{re:/\b(pk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`pk-${N}`},{re:/\b(Bearer\s+)[A-Za-z0-9\-._~+/]+=*/gi,replace:(t,e)=>`${e}${N}`},{re:/\b(Basic\s+)[A-Za-z0-9+/]+=*/gi,replace:(t,e)=>`${e}${N}`},{re:/(-----BEGIN [A-Z ]+-----)[^-]*(-----END [A-Z ]+-----)/g,replace:(t,e,r)=>`${e}
|
|
182
182
|
${N}
|
|
183
|
-
${r}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${N}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${N}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${N}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${N}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${N}`},{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}${N}${r}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${N}@`},{re:/[a-zA-Z0-9._%+\-]+@[a-zA-Z0-9.\-]+\.[a-zA-Z]{2,}/g,replace:()=>Ho},{re:/\b\d{3}\.\d{3}\.\d{3}-\d{2}\b/g,replace:()=>jo},{re:/\b\d{2}\.\d{3}\.\d{3}\/\d{4}-\d{2}\b/g,replace:()=>Vo},{re:/\(\d{2}\)\s?\d{4,5}[-\s]?\d{4}/g,replace:()=>Bn},{re:/\+55[\s-]?\d{2}[\s-]?\d{4,5}[-\s]?\d{4}/g,replace:()=>Bn}];});async function Hn(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},s=t.tool_response,o=s!==null&&typeof s=="object"?s.output??JSON.stringify(s):s??"",i=Pt(e);if(!i){D(t);return}let a=
|
|
184
|
-
`)),v=l?.inputTokens??0,k=l?.outputTokens??0,zt=i.map((g,
|
|
185
|
-
`),process.stdout.write(JSON.stringify(e));}}var qn=m(()=>{Y();Rt();_n();kn();jn();Kn();Wo().catch(t=>{process.stderr.write(`[flow-obs] fatal: ${t.message}
|
|
186
|
-
`),process.exit(0);});});var Ko=new Set(["UserPromptSubmit","PreToolUse","PostToolUse","Stop"]),[,,C,Jt]=process.argv;function
|
|
187
|
-
`),process.exit(0);}else if(C==="--help"||C==="-h"){let{bold:t,cyan:e,dim:r}=(
|
|
183
|
+
${r}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${N}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${N}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${N}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${N}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${N}`},{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}${N}${r}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${N}@`},{re:/[a-zA-Z0-9._%+\-]+@[a-zA-Z0-9.\-]+\.[a-zA-Z]{2,}/g,replace:()=>Ho},{re:/\b\d{3}\.\d{3}\.\d{3}-\d{2}\b/g,replace:()=>jo},{re:/\b\d{2}\.\d{3}\.\d{3}\/\d{4}-\d{2}\b/g,replace:()=>Vo},{re:/\(\d{2}\)\s?\d{4,5}[-\s]?\d{4}/g,replace:()=>Bn},{re:/\+55[\s-]?\d{2}[\s-]?\d{4,5}[-\s]?\d{4}/g,replace:()=>Bn}];});async function Hn(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},s=t.tool_response,o=s!==null&&typeof s=="object"?s.output??JSON.stringify(s):s??"",i=Pt(e);if(!i){D(t);return}let a=J(),c=i.pendingTool,l=c?.name===r,d=l?c.startNs:String(BigInt(a)-200000000n),y=l?c.inputStr:W(n,V.TOOL_INPUT),E=y,S=null;if(r==="Skill"){let ee=typeof n=="object"&&n!==null?n.skill||n.name||n.skillName||n.commandName||String(Object.values(n)[0]??""):String(n);S=ee?String(ee).trim():null;let Z=S?ge(S,i.cwd):null;Z&&(E=Z,i.skillContent||(i.skillContent=Z),i.skillArtifacts||(i.skillArtifacts=he(S,i.cwd))),S&&!i.slashSkill&&(i.slashSkill=S),u("PostToolUse","Skill tool detected",`skillName=${S}`,`contentFound=${!!Z}`);}let v=X(W(o,V.TOOL_OUTPUT)),k=/\b(error|exception|failed|failure|traceback|errno)\b/i.test(v.slice(0,500)),zt=k?"ERROR":"DEFAULT",Ut=ct(),Xt=Math.round(Number(BigInt(a)-BigInt(d))/1e6),Qt={Agent:"AGENT",Task:"AGENT"}[r]??"TOOL",te=r==="Skill"&&S?S:me(y,60);i.toolCalls.push({tool:r,brief:te,error:k,durationMs:Xt});let Ft=i.spans;Ft.push({traceId:i.traceId,spanId:Ut,parentSpanId:i.spanId,name:r,kind:3,startTimeUnixNano:d,endTimeUnixNano:a,attributes:ut(p(h.OBS_NAME,r),p(h.OBS_TYPE,Qt),p(h.OBS_LEVEL,zt),p(h.OBS_INPUT,X(E)),p(h.OBS_OUTPUT,v),p("tool.name",r),p("tool.error",String(k)),r==="Skill"&&S?p("skill.name",S):null,r==="Skill"?p("skill.invocation","slash-command"):null),status:{code:k?2:1}}),i.pendingTool=null,Nt(e,i),k&<("TOOL_ERROR",{toolName:r}),u("PostToolUse",`sid=${e}`,`tool=${r}`,`error=${k}`,`durationMs=${Xt}`,`totalSpans=${Ft.length}`),D(t);}var jn=m(()=>{"use strict";Gt();Kt();ir();Rt();we();$();A();ar();Ee();});function Yn(t,e,r){let n=Object.keys(Vn).find(i=>(t??"").toLowerCase().includes(i));if(!n)return;let s=Vn[n],o=(e*s.input+r*s.output)/1e6;return Math.round(o*1e6)/1e6}var Vn,Wn=m(()=>{"use strict";Vn={"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 Gn(t){let e=t.session_id||"unknown",r=t.stop_reason||"end_turn",n=Pt(e);if(!n){D(t);return}n.slashSkill&&!/^[a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?$/i.test(n.slashSkill)&&(u("Stop",`sid=${e}`,`slashSkill rejected post-disk: "${n.slashSkill}"`),n.slashSkill=null);let s=J(),o=await Yr(),i=n.toolCalls,a=n.spans;if(n.slashSkill&&!i.some(g=>g.tool==="Skill")){let g=ct(),Q=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:ut(p(h.OBS_NAME,"Skill"),p(h.OBS_TYPE,"TOOL"),p(h.OBS_LEVEL,"DEFAULT"),p(h.OBS_INPUT,Q),p(h.OBS_OUTPUT,"loaded via slash command"),p("tool.name","Skill"),p("tool.error","false"),p("skill.name",n.slashSkill),p("skill.invocation","slash-command")),status:{code:1}}),u("Stop",`slashSkill=${n.slashSkill}`,"synthetic span injected");}let c=t.transcript_path||n.transcriptPath||"",l=er(c);if(c&&(i.some(g=>g.tool==="Skill"&&!g.synthetic)||!!n.slashSkill)&&!l?.text){await new Promise(Q=>setTimeout(Q,500));let g=er(c);g?.text&&(l=g);}u("Stop",`transcriptPath=${c||"(empty)"}`,`assistantOut=${l?`text=${l.text.length}chars`:"null"}`);let y=i.length,E=i.filter(g=>g.error).length,S=X(l?.text?W(l.text,V.TRACE_OUTPUT):y===0?"No tools used":i.map((g,Q)=>`${Q+1}. ${g.tool}${g.brief?` \u2192 ${g.brief}`:""}${g.error?" [ERROR]":""}`).join(`
|
|
184
|
+
`)),v=l?.inputTokens??0,k=l?.outputTokens??0,zt=i.map((g,Q)=>`${Q+1}. ${g.tool}${g.brief?` \u2192 ${g.brief}`:""}${g.error?" [ERROR]":""} (${g.durationMs}ms)`),Ut=!!(n.slashSkill||i.some(g=>g.tool==="Skill")),Xt=i.some(g=>g.tool==="Agent");if(!Ut&&!Xt){u("Stop",`sid=${e}`,"skipping trace \u2014 no Skill or Agent calls found"),lt("TRACE_SKIPPED",{reason:"no_skill_or_agent"}),tr(e),D(t);return}let Zt=Ut?"skill":"agent",Qt=Math.round(Number(BigInt(s)-BigInt(n.startNs))/1e6),te=Yn(n.model,v,k),pt=yn(n);pt==="prerequisite_required"&&l?.text&&(pt="complete"),pt==="prerequisite_required"&&(a.push({traceId:n.traceId,spanId:ct(),parentSpanId:n.spanId,name:"prerequisite-check",kind:3,startTimeUnixNano:n.startNs,endTimeUnixNano:s,attributes:ut(p(h.OBS_NAME,"prerequisite-check"),p(h.OBS_TYPE,"EVENT"),p(h.OBS_LEVEL,"WARNING"),p(h.OBS_OUTPUT,S),p("skill.name",n.slashSkill||void 0),p("execution_status","prerequisite_required")),status:{code:1}}),u("Stop",`sid=${e}`,"prerequisite-check span injected",`skill=${n.slashSkill}`));let Ft=(()=>{if(!(!Ut||!n.prompt)){if(n.slashSkill){let g=n.prompt.replace(new RegExp(`^\\/${n.slashSkill}\\s*`,"i"),"").trim();return g?W(X(g),V.USER_INSTRUCTION):void 0}return W(X(n.prompt),V.USER_INSTRUCTION)||void 0}})(),ee=JSON.stringify({trace_type:Zt,...pt!==null&&{execution_status:pt},...n.slashSkill?{skill_name:n.slashSkill}:{},...n.skillArtifacts?.length&&{skill_artifacts:n.skillArtifacts},...Ft!==void 0&&{user_instruction:Ft},latency_ms:Qt,...v&&{tokens_input:v},...k&&{tokens_output:k},cost_usd:te,...n.model?{model:n.model}:{},toolCount:y,errorCount:E,stopReason:r,sessionId:n.sessionId,tools:zt.length?zt:void 0}),Z=X(W(n.prompt,V.TRACE_INPUT)),Jn=ut(p(h.TRACE_NAME,n.traceName),p(h.TRACE_INPUT,Z),p(h.TRACE_OUTPUT,S),p(h.OBS_INPUT,Z),p(h.OBS_OUTPUT,S),p(h.TRACE_METADATA,ee),p(h.SESSION_ID,n.sessionId),p(h.USER_ID,o.user),p(h.OBS_TYPE,"GENERATION"),p(h.MODEL,n.model),v?p(h.INPUT_TOKENS,v):null,k?p(h.OUTPUT_TOKENS,k):null,p("claude.stop_reason",r),p("claude.tool_count",String(y)),p("claude.error_count",String(E)),p("claude.session_id",n.sessionId),p("flow.trace_type",Zt),{key:h.TRACE_TAGS,value:{arrayValue:{values:[{stringValue:Zt}]}}}),zn={traceId:n.traceId,spanId:n.spanId,name:n.traceName,kind:1,startTimeUnixNano:n.startNs,endTimeUnixNano:s,attributes:Jn,status:{code:E>0?2:1}},Xn=ut(p("service.name",process.env.LANGFUSE_PROJECT_NAME||"claude-code"),p("deployment.environment",process.env.LANGFUSE_ENVIRONMENT||"default")),cr=[...a,zn];u("Stop",`sid=${e}`,`totalTools=${y}`,`errorTools=${E}`,`spans=${cr.length}`,`inputTokens=${v}`,`outputTokens=${k}`,`traceOutput="${me(S,80)}"`);let Zn=await Dn(On(Xn,cr));u("Stop",`POST status=${Zn}`,`traceId=${n.traceId}`),lt("TRACE_SENT",{latencyMs:Qt,totalTools:y,errorTools:E,inputTokens:v,outputTokens:k,costUsd:te}),tr(e),D(t);}var Kn=m(()=>{"use strict";Gt();Kt();ir();Y();Wn();rr();Rt();$();we();ar();A();Ee();});async function Wo(){let t=process.argv[2];if(t==="UserPromptSubmit"){let r=await Xe(),n;try{n=await K();}catch{process.stdout.write(JSON.stringify(r));return}n.authError?await nr(r,true):n.length>0?await nr(r):process.stdout.write(JSON.stringify(r));return}if(!await Wr()){let r=[];process.stdin.on("data",n=>r.push(n)),process.stdin.on("end",()=>process.stdout.write(r.join("")));return}let e=await Xe();switch(t){case "PreToolUse":await An(e);break;case "PostToolUse":await Hn(e);break;case "Stop":await Gn(e);break;default:process.stderr.write(`[flow-obs] unknown event: ${t}
|
|
185
|
+
`),process.stdout.write(JSON.stringify(e));}}var qn=m(()=>{"use strict";Y();Rt();_n();kn();jn();Kn();Wo().catch(t=>{process.stderr.write(`[flow-obs] fatal: ${t.message}
|
|
186
|
+
`),process.exit(0);});});var Ko=new Set(["UserPromptSubmit","PreToolUse","PostToolUse","Stop"]),[,,C,Jt]=process.argv;function dt(t,e){let r=t.indexOf(e);return r!==-1?t[r+1]:void 0}if(C==="--version"||C==="-v"){let{version:t}=re();process.stdout.write(t+`
|
|
187
|
+
`),process.exit(0);}else if(C==="--help"||C==="-h"){let{bold:t,cyan:e,dim:r}=(mt(),L(ye)),{version:n}=re();process.stdout.write(`
|
|
188
188
|
`+t(" flow-ai-obs")+r(" v"+n)+`
|
|
189
189
|
|
|
190
190
|
`),process.stdout.write(e(" init")+r(` Auth (if needed) + hooks + native OTEL
|
|
@@ -205,12 +205,12 @@ ${r}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${N}`},{re:/(aws_secret_ac
|
|
|
205
205
|
`)),process.stdout.write(r(` (Hook events: UserPromptSubmit | PreToolUse | PostToolUse | Stop)
|
|
206
206
|
|
|
207
207
|
`)),process.exit(0);}else if(C==="init"||C==="install")(async()=>{C==="install"&&process.stderr.write(`Warning: "install" is deprecated, use "init" instead
|
|
208
|
-
`),await(
|
|
209
|
-
`),process.exit(1);});else if(C==="setup")(async()=>{await(
|
|
210
|
-
`),process.exit(1);});else if(C==="auth")(async()=>{let{runLogin:t,runLogout:e,runStatus:r}=(Yt(),L(Ke)),n=0;if(Jt==="login"||!Jt){await(
|
|
208
|
+
`),await(wt(),L(ht)).checkForUpdateInteractive();let{runInstall:t}=(Je(),L(nn)),e=process.argv.slice(3);process.exit(await t({url:dt(e,"--custom-url"),noInteractive:e.includes("--no-interactive")}));})().catch(t=>{process.stderr.write(`Unexpected error: ${t.message}
|
|
209
|
+
`),process.exit(1);});else if(C==="setup")(async()=>{await(wt(),L(ht)).checkForUpdateInteractive();let{runSetup:t}=(on(),L(sn)),e=process.argv.slice(3);process.exit(await t({clientId:dt(e,"--client-id"),clientSecret:dt(e,"--client-secret"),tenant:dt(e,"--tenant")}));})().catch(t=>{process.stderr.write(`Unexpected error: ${t.message}
|
|
210
|
+
`),process.exit(1);});else if(C==="auth")(async()=>{let{runLogin:t,runLogout:e,runStatus:r}=(Yt(),L(Ke)),n=0;if(Jt==="login"||!Jt){await(wt(),L(ht)).checkForUpdateInteractive();let s=process.argv.slice(4);n=await t({clientId:dt(s,"--client-id"),clientSecret:dt(s,"--client-secret"),tenant:dt(s,"--tenant")});}else if(Jt==="logout"){let s=process.argv.includes("--force");n=await e(s);}else Jt==="status"?(await(wt(),L(ht)).checkForUpdateInteractive(),n=await r()):(process.stderr.write(`Unknown auth subcommand: ${Jt}
|
|
211
211
|
`),process.stderr.write(`Usage: flow-ai-obs auth [login|logout|status]
|
|
212
|
-
`),n=1);process.exit(n);})();else if(C==="otel-headers"){let{runOtelHeaders:t}=(cn(),L(an));t().then(e=>process.exit(e)).catch(()=>process.exit(1));}else if(C==="check")(async()=>{await(
|
|
213
|
-
`),process.exit(1);});else if(Ko.has(C))qn();else {let{bold:t,cyan:e,dim:r}=(
|
|
212
|
+
`),n=1);process.exit(n);})();else if(C==="otel-headers"){let{runOtelHeaders:t}=(cn(),L(an));t().then(e=>process.exit(e)).catch(()=>process.exit(1));}else if(C==="check")(async()=>{await(wt(),L(ht)).checkForUpdateInteractive();let{runCheck:t}=(dn(),L(un));process.exit(await t());})().catch(t=>{process.stderr.write(`Unexpected error: ${t.message}
|
|
213
|
+
`),process.exit(1);});else if(Ko.has(C))qn();else {let{bold:t,cyan:e,dim:r}=(mt(),L(ye));process.stdout.write(`
|
|
214
214
|
`+t(" flow-ai-obs")+`
|
|
215
215
|
|
|
216
216
|
`),process.stdout.write(e(" init")+r(` Auth (if needed) + hooks + native OTEL
|
package/dist/index.js
CHANGED
|
@@ -1,16 +1,16 @@
|
|
|
1
|
-
'use strict';var child_process=require('child_process'),util=require('util'),L=require('fs'),B=require('path'),
|
|
1
|
+
'use strict';var child_process=require('child_process'),util=require('util'),L=require('fs'),B=require('path'),st=require('os'),ir=require('https'),ar=require('http'),crypto=require('crypto');function _interopDefault(e){return e&&e.__esModule?e:{default:e}}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 L__namespace=/*#__PURE__*/_interopNamespace(L);var B__namespace=/*#__PURE__*/_interopNamespace(B);var st__namespace=/*#__PURE__*/_interopNamespace(st);var ir__default=/*#__PURE__*/_interopDefault(ir);var ar__default=/*#__PURE__*/_interopDefault(ar);var xe=Object.defineProperty;var nt=(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 Et=(t,e,r)=>()=>{if(r)throw r[0];try{return t&&(e=t(t=0)),e}catch(n){throw r=[n],n}};var Tt=(t,e)=>{for(var r in e)xe(t,r,{get:e[r],enumerable:true});};var qt={};Tt(qt,{MacOsKeyVaultProvider:()=>kt});var wt,kt,zt=Et(()=>{"use strict";wt=util.promisify(child_process.execFile),kt=class{static async isAvailable(){try{return L.accessSync("/usr/bin/security",L.constants.X_OK),!0}catch{return !1}}async getSecret(e,r){try{let{stdout:n}=await wt("security",["find-generic-password","-w","-a",r,"-s",e]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await wt("security",["add-generic-password","-U","-a",r,"-s",e,"-w",n]);}async deleteSecret(e,r){try{return await wt("security",["delete-generic-password","-a",r,"-s",e]),!0}catch{return !1}}getStoragePath(){return "macOS Keychain"}};});var Zt={};Tt(Zt,{LinuxKeyVaultProvider:()=>It});var Xt,It,Qt=Et(()=>{"use strict";Xt=util.promisify(child_process.execFile),It=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 L.accessSync(r,L.constants.X_OK),!0}catch{}return !1}async getSecret(e,r){try{let{stdout:n}=await Xt("secret-tool",["lookup","service",e,"account",r]);return n.trim()||null}catch{return null}}async setSecret(e,r,n){await new Promise((o,s)=>{let i=child_process.spawn("secret-tool",["store","--label",e,"service",e,"account",r]);i.on("error",s),i.on("close",l=>{l===0?o():s(new Error(`secret-tool exited with code ${l}`));}),i.stdin.write(n),i.stdin.end();});}async deleteSecret(e,r){try{return await Xt("secret-tool",["clear","service",e,"account",r]),!0}catch{return !1}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var te={};Tt(te,{WindowsKeyVaultProvider:()=>Lt});var Lt,ee=Et(()=>{"use strict";Lt=class{static async isAvailable(){try{return await nt("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return !1}}async getSecret(e,r){return nt("keytar").getPassword(e,r)}async setSecret(e,r,n){await nt("keytar").setPassword(e,r,n);}async deleteSecret(e,r){return nt("keytar").deletePassword(e,r)}getStoragePath(){return "Windows Credential Manager"}};});function Yt(){if(process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER){let e=child_process.spawnSync("getent",["passwd",process.env.SUDO_USER],{encoding:"utf8",timeout:5e3}).stdout?.split(":")[5]?.trim();if(e)return {home:e,username:process.env.SUDO_USER}}return {home:st__namespace.homedir(),username:process.env.SUDO_USER||process.env.USER||st__namespace.userInfo().username}}var Gt="flow-ai-obs",jt="config.json";function Me(){if(process.platform==="win32"){let r=process.env.APPDATA||B__namespace.join(st__namespace.homedir(),"AppData","Roaming");return B__namespace.join(r,Gt,jt)}let t=Yt(),e=process.env.XDG_CONFIG_HOME||B__namespace.join(t.home,".config");return B__namespace.join(e,Gt,jt)}function He(){try{let t=L__namespace.readFileSync(Me(),"utf8");return JSON.parse(t)}catch{return {}}}function Wt(){let{baseUrl:t}=He();return typeof t!="string"||t.trim()===""?null:t.trim().replace(/\/$/,"")}var Ye="https://flow.ciandt.com";function x(){return Wt()??process.env.FLOW_BASE_URL??Ye}function V(){let t=x();return {AUTH_ENGINE:process.env.FLOW_AUTH_ENGINE_URL||`${t}/auth-engine-api/v2/api-key/token`,GATEWAY_TRACES:process.env.FLOW_GATEWAY_TRACES_URL||`${t}/flow-langfuse-gateway/v1/traces`,GATEWAY_HEALTH:process.env.FLOW_GATEWAY_HEALTH_URL||`${t}/flow-langfuse-gateway/v1/health`,OTEL_ENDPOINT:process.env.FLOW_OTEL_ENDPOINT_URL||`${t}/otel`}}V();var it={SERVICE:"flow-plugins-cli",ACCOUNT_TOKEN:"token-cache"},at="FLOW-nodejs",ct="config.json",ht={SCOPE_NAME:"flow-ai-obs",SCOPE_VERSION:"0.1.0"};var S={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 y={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},Jt="flow-ai-obs-debug.log",w={TOOL_INPUT:2e4,TOOL_OUTPUT:2e4,TRACE_OUTPUT:2e4,USER_INSTRUCTION:1e4,TRACE_INPUT:5e4};function At(){let t=x();return {API_URL:process.env.FLOW_METRICS_URL||`${t}/metrics-collector-api/log-event`,BOOSTER:"flow-ai-obs"}}var yt={credentials:"credentials","token-cache":"tokenCache"};function W(){let t=st__namespace.default.homedir();if(process.platform==="darwin")return B__namespace.default.join(t,"Library","Preferences",at,ct);if(process.platform==="win32"){let r=process.env.APPDATA??B__namespace.default.join(t,"AppData","Roaming");return B__namespace.default.join(r,at,ct)}let e=process.env.XDG_CONFIG_HOME??B__namespace.default.join(t,".config");return B__namespace.default.join(e,at,ct)}function Ot(){try{let t=L__namespace.default.readFileSync(W(),"utf8");return JSON.parse(t)}catch{return {}}}function Kt(t){let e=W();L__namespace.default.mkdirSync(B__namespace.default.dirname(e),{recursive:true}),L__namespace.default.writeFileSync(e,JSON.stringify(t,null,2),{encoding:"utf8",mode:384});}var ut=class{static isAvailable(){return true}static hasExistingData(){try{if(!L__namespace.default.existsSync(W()))return !1;let e=JSON.parse(L__namespace.default.readFileSync(W(),"utf8"));return !!(e&&e.credentials)}catch{return false}}async getSecret(e,r){let n=Ot(),o=yt[r]??r,s=n[o];return s?typeof s=="string"?s:JSON.stringify(s):null}async setSecret(e,r,n){let o=Ot(),s=yt[r]??r;if(r==="token-cache")try{o[s]=JSON.parse(n);}catch{o[s]=n;}else o[s]=n;Kt(o);}async deleteSecret(e,r){let n=Ot(),o=yt[r]??r;return o in n?(delete n[o],Kt(n),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${W()}`}};async function re(){return await tr()??new ut}async function tr(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:t}=await Promise.resolve().then(()=>(zt(),qt));return await t.isAvailable()?new t:null}case "linux":{let{LinuxKeyVaultProvider:t}=await Promise.resolve().then(()=>(Qt(),Zt));return await t.isAvailable()?new t:null}case "win32":{let{WindowsKeyVaultProvider:t}=await Promise.resolve().then(()=>(ee(),te));return await t.isAvailable()?new t:null}default:return null}}var Nt=it.SERVICE,ne=it.ACCOUNT_TOKEN,Rt=null;function Pt(){return Rt||(Rt=re()),Rt}async function bt(t){await(await Pt()).setSecret(Nt,ne,JSON.stringify({accessToken:t.accessToken,expiresAt:t.expiresAt,lastAuthCheckAt:t.lastAuthCheckAt}));}async function Ut(){let e=await(await Pt()).getSecret(Nt,ne);if(!e)return null;try{let r=JSON.parse(e);return {accessToken:r.accessToken,expiresAt:r.expiresAt,lastAuthCheckAt:r.lastAuthCheckAt}}catch{return null}}async function K(){let t=await Ut();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}}var or=B.join(st.tmpdir(),Jt);function a(...t){if(process.env[S.FLOW_OBS_DEBUG]!=="1")return;let e=`[${new Date().toISOString()}] ${t.join(" ")}
|
|
2
2
|
`;try{L.writeFileSync(or,e,{flag:"a"});}catch(r){process.stderr.write(`[flow-obs debug ERROR] ${r.message}
|
|
3
|
-
`);}}var b=class extends Error{constructor(e){super(e),this.name="AuthError";}},cr=/^[a-z0-9][a-z0-9-]{0,62}[a-z0-9]$|^[a-z0-9]$/;function lr(t){if(!cr.test(t))throw new Error(`Invalid tenant value: "${t}". Tenant must be lowercase alphanumeric and hyphens (1-64 chars).`)}var se={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 ur(t,e){let r=e.length>400?e.slice(0,400)+"\u2026":e;a("toAuthError",`status=${t} body=${r}`);try{let n=JSON.parse(e);if(typeof n.error=="string"&&(a("toAuthError",`api_error_code=${n.error}`+(n.message?` api_message=${n.message}`:"")),se[n.error]))return new b(se[n.error])}catch{}return t===401||t===403||t===500?new b("Invalid credentials"):t>=400&&t<500?new b("Authentication request was rejected"):new Error("Authentication service unavailable, please try again later")}function
|
|
4
|
-
`)[0].slice(0,e).trim()}function Ct(){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 O(t){process.stdout.write(JSON.stringify(t));}var vt=()=>crypto.randomBytes(16).toString("hex"),C=()=>crypto.randomBytes(8).toString("hex");function I(){return String(BigInt(Date.now())*1000000n)}var Ir=/^[0-9a-f-]{1,64}$/i,Lr=B.normalize(
|
|
3
|
+
`);}}var b=class extends Error{constructor(e){super(e),this.name="AuthError";}},cr=/^[a-z0-9][a-z0-9-]{0,62}[a-z0-9]$|^[a-z0-9]$/;function lr(t){if(!cr.test(t))throw new Error(`Invalid tenant value: "${t}". Tenant must be lowercase alphanumeric and hyphens (1-64 chars).`)}var se={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 ur(t,e){let r=e.length>400?e.slice(0,400)+"\u2026":e;a("toAuthError",`status=${t} body=${r}`);try{let n=JSON.parse(e);if(typeof n.error=="string"&&(a("toAuthError",`api_error_code=${n.error}`+(n.message?` api_message=${n.message}`:"")),se[n.error]))return new b(se[n.error])}catch{}return t===401||t===403||t===500?new b("Invalid credentials"):t>=400&&t<500?new b("Authentication request was rejected"):new Error("Authentication service unavailable, please try again later")}function q(t){return new Promise((e,r)=>{try{lr(t.tenant);}catch(p){return r(p)}let n=JSON.stringify({clientSecret:t.clientSecret}),o=new URL(V().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(n),FlowTenant:t.tenant}};a("getToken",`requesting token tenant=${t.tenant} host=${i.hostname} path=${i.path}`);let c=(s?ir__default.default:ar__default.default).request(i,p=>{let _=[];p.on("data",T=>_.push(T)),p.on("end",()=>{let T=_.join("");if((p.statusCode??0)>=400)return r(ur(p.statusCode??0,T));let m;try{m=JSON.parse(T);}catch{return r(new Error("Invalid response from auth engine"))}let g=m.expires_at??new Date(Date.now()+(m.expires_in??3600)*1e3).toISOString();e({accessToken:m.access_token??"",expiresAt:g});});});c.on("error",p=>r(new Error(`Network error: ${p.message}`))),c.write(n),c.end();})}var pr=[/^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 dr(t){return pr.some(e=>e.test(t))}function fr(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 ft(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:s}=r;return !n||!o||!s?null:{clientId:n,clientSecret:o,tenant:s}}catch{return null}}function dt(t){let e;try{e=new URL(t);}catch{throw new Error(`Invalid URL: ${t}`)}let r=process.env[S.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&&dr(e.hostname))throw new Error(`SSRF: private/loopback host not allowed: ${e.hostname}`);return t}async function oe(){let t=ft(process.env[S.ANTHROPIC_AUTH_TOKEN]);if(t)return {user:await K().catch(()=>null)??t.clientId,tenant:t.tenant};return {user:"",tenant:""}}function mr(){return new Date().toISOString().slice(0,10)}async function gr(t){let e=mr(),r=await Ut();if(r?.lastAuthCheckAt!==e){a("getOrRefreshToken",`daily auth check (last: ${r?.lastAuthCheckAt??"never"})`);try{let s=await q(t);try{await bt({...s,lastAuthCheckAt:e});}catch{}return a("getOrRefreshToken",`daily check passed, expires=${s.expiresAt}`),s.accessToken}catch(s){if(s instanceof b)throw s;a("getOrRefreshToken",`daily check network error \u2014 using cache: ${s.message}`);}}let n=r!=null&&new Date(r.expiresAt)>new Date;if(a("getOrRefreshToken",`cacheValid=${n}`),n)return a("getOrRefreshToken",`using cached token, expires=${r.expiresAt}`),r.accessToken;a("getOrRefreshToken",`token expired \u2014 refreshing via auth-engine (tenant=${t.tenant} clientId=${t.clientId})`);let o=await q(t);try{await bt({...o,lastAuthCheckAt:e});}catch(s){a("getOrRefreshToken",`token cache save failed (non-fatal): ${s.message}`);}return a("getOrRefreshToken",`token refreshed, expires=${o.expiresAt}`),o.accessToken}function Sr(t,e){let r=e&&e.accessToken?e.accessToken:"";return {endpoint:t.replace(/\/$/,"")+"/flow-langfuse-gateway/v1/traces",authHeader:`Bearer ${r}`}}function _r(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 U(){let t=[],e=process.env[S.ANTHROPIC_MODEL]??"",r=ft(process.env[S.ANTHROPIC_AUTH_TOKEN]);a("resolveCredentials",r?"credentials resolved from ANTHROPIC_AUTH_TOKEN":"ANTHROPIC_AUTH_TOKEN absent or invalid"),r&&a("resolveCredentials",`clientId=${r.clientId}`,`tenant=${r.tenant}`);let n=r?r.tenant:"",o=process.env[S.FLOW_TELEMETRY]==="true",s=process.env[S.LANGFUSE_BASE_URL],i=process.env[S.LANGFUSE_PUBLIC_KEY],l=process.env[S.LANGFUSE_SECRET_KEY];if(o&&s&&i&&l){let m="",g=n;if(r)m=await K().catch(()=>null)??r.clientId;let h={user:m??"",tenant:g??"",team:"",project:"",model:e};t.push({mode:"direct",..._r(dt(s),i,l),...h}),a("resolveCredentials","direct mode active",`user=${h.user}`,`tenant=${h.tenant}`);}if(!r){if(t.length===0){let m=[];return m.authError=false,m}return t}let c;try{c=await gr(r);}catch(m){if(a("resolveCredentials",`token refresh failed: ${m.message}`,`(tenant=${r.tenant} clientId=${r.clientId})`),t.length>0)return t.authError=true,t;let g=[];return g.authError=true,g}let _={user:fr(c)??r.clientId,tenant:n,team:"",project:"",model:e},T=process.env[S.FLOW_TELEMETRY_GATEWAY]??x();return t.push({mode:"gateway",...Sr(dt(T),{accessToken:c}),..._}),t}async function ie(){return (await U()).length>0}function k(t,e){let r=typeof t=="object"?JSON.stringify(t):String(t??"");return r.length>e?r.slice(0,e)+" \u2026[truncated]":r}function mt(t,e=100){return String(t??"").split(`
|
|
4
|
+
`)[0].slice(0,e).trim()}function Ct(){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 O(t){process.stdout.write(JSON.stringify(t));}var vt=()=>crypto.randomBytes(16).toString("hex"),C=()=>crypto.randomBytes(8).toString("hex");function I(){return String(BigInt(Date.now())*1000000n)}var Ir=/^[0-9a-f-]{1,64}$/i,Lr=B.normalize(st.tmpdir())+B.sep;function Rr(t,e){let r=B.resolve(t);if(!r.startsWith(e))throw new Error(`Path traversal detected: ${t}`);return r}function Ft(t){if(!Ir.test(t))throw new Error(`Invalid session ID: ${t}`);return Rr(B.join(st.tmpdir(),`flow-obs-${t}.json`),Lr)}function M(t){let e=Ft(t);if(!L.existsSync(e))return null;try{return JSON.parse(L.readFileSync(e,"utf8"))}catch{return null}}function H(t,e){L.writeFileSync(Ft(t),JSON.stringify(e),{encoding:"utf8",mode:384});}function $t(t){try{L.unlinkSync(Ft(t));}catch{}}function pe(t){if(!t||!L.existsSync(t))return null;try{let e=L.readFileSync(t,"utf8").trimEnd().split(`
|
|
5
5
|
`);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 Dt(t){if(!t||!L.existsSync(t))return null;try{let e=L.readFileSync(t,"utf8").trimEnd().split(`
|
|
6
6
|
`),r=[],n=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 c=(i.message?.content??[]).filter(_=>_.type==="text").map(_=>_.text??"").join("");c&&r.unshift(c);let p=i.message?.usage??{};n+=(p.input_tokens??0)+(p.cache_read_input_tokens??0)+(p.cache_creation_input_tokens??0),o+=p.output_tokens??0;}}catch{}return !r.length&&n===0?null:{text:r.join(`
|
|
7
7
|
|
|
8
|
-
`),inputTokens:n,outputTokens:o}}catch{}return null}var Ur=new Set([".venv","__pycache__",".git","node_modules"]),Cr=new Set([".pyc",".pyo"]),vr=new Set(["SKILL.md",".DS_Store",".gitignore"]);function me(t){return t.replace(":","/")}function gt(t,e){if(!t)return null;let r=me(t),n=[B.join(
|
|
9
|
-
`)[0].match(/^\/([a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?)(?:\s.*)?$/i)?.[1]??null}var Fr=new Set(["Read","Write","Edit","MultiEdit","Bash","Glob","Grep","TodoWrite","WebFetch","WebSearch","Agent","Task"]);function Se(t){return !!t.slashSkill||t.toolCalls.some(n=>n.tool==="Skill")?t.toolCalls.some(n=>n.tool==="Skill"&&!n.synthetic||Fr.has(n.tool))?"complete":"prerequisite_required":null}function St(t,e){if(!t)return null;let r=me(t),n=[B.join(
|
|
10
|
-
`);return}let n=!!(await U()).authError,o=t.session_id||"unknown",s=t.prompt||"",i=t.cwd||"",l=pe(t.transcript_path)||vt(),c=ge(s),p=c?gt(c,i):null,_=c?St(c,i):null;H(o,{traceId:vt(),spanId:C(),startNs:I(),sessionId:o,prompt:s,cwd:i,traceName:l,transcriptPath:t.transcript_path||"",model:process.env[S.ANTHROPIC_MODEL]||"",toolCalls:[],spans:[],pendingTool:null,slashSkill:c,skillContent:p,skillArtifacts:_}),v("SESSION_STARTED",{traceType:c?"skill":"prompt",slashSkill:c,clientIdExpired:n}),a("UserPromptSubmit",`sid=${o}`,`traceName=${l}`,`slashSkill=${c}`),O(t);}async function _e(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},o=M(e);o&&(o.pendingTool={name:r,inputStr:k(n,w.TOOL_INPUT),startNs:I()},H(e,o)),a("PreToolUse",`sid=${e}`,`tool=${r}`,`stateFound=${!!o}`),O(t);}var Hr={name:ht.SCOPE_NAME,version:ht.SCOPE_VERSION},f={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 u(t,e){return e==null||e===""?null:{key:t,value:{stringValue:String(e)}}}function F(...t){return t.filter(e=>e!==null)}function Ee(t,e){return {resourceSpans:[{resource:{attributes:t},scopeSpans:[{scope:Hr,spans:Array.isArray(e)?e:[e]}]}]}}var Te=B.join(
|
|
11
|
-
`,{flag:"a",encoding:"utf8",mode:384}),a("sendTraces:dump",`request appendada em ${Te}`);}catch(i){a("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function Jr(t){let e=new URL(t),r=new URL(
|
|
8
|
+
`),inputTokens:n,outputTokens:o}}catch{}return null}var Ur=new Set([".venv","__pycache__",".git","node_modules"]),Cr=new Set([".pyc",".pyo"]),vr=new Set(["SKILL.md",".DS_Store",".gitignore"]);function me(t){return t.replace(":","/")}function gt(t,e){if(!t)return null;let r=me(t),n=[B.join(st.homedir(),".claude","skills",r,"SKILL.md"),B.join(e??"",".claude","skills",r,"SKILL.md")];for(let o of n)if(L.existsSync(o))try{return L.readFileSync(o,"utf8")}catch{}return null}function ge(t){return t.split(`
|
|
9
|
+
`)[0].match(/^\/([a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?)(?:\s.*)?$/i)?.[1]??null}var Fr=new Set(["Read","Write","Edit","MultiEdit","Bash","Glob","Grep","TodoWrite","WebFetch","WebSearch","Agent","Task"]);function Se(t){return !!t.slashSkill||t.toolCalls.some(n=>n.tool==="Skill")?t.toolCalls.some(n=>n.tool==="Skill"&&!n.synthetic||Fr.has(n.tool))?"complete":"prerequisite_required":null}function St(t,e){if(!t)return null;let r=me(t),n=[B.join(st.homedir(),".claude","skills",r),B.join(e??"",".claude","skills",r)],o=null;for(let l of n)if(L.existsSync(B.join(l,"SKILL.md"))){o=l;break}if(!o)return null;let s=[];function i(l,c){for(let p of L.readdirSync(l,{withFileTypes:true})){if(Ur.has(p.name)||vr.has(p.name)||Cr.has(B.extname(p.name)))continue;let _=c?`${c}/${p.name}`:p.name;p.isDirectory()?i(B.join(l,p.name),_):s.push(_);}}return i(o,""),s.length>0?s:null}function xr(t){try{let e=t.split(".")[1].replace(/-/g,"+").replace(/_/g,"/");return JSON.parse(Buffer.from(e,"base64").toString())}catch{return null}}function Br(t,e,r,n){return new Promise(o=>{let s=new URL(t),i=s.protocol==="https:",l=(i?ir__default.default:ar__default.default).request({hostname:s.hostname,port:s.port||(i?443:80),path:s.pathname+s.search,method:"POST",headers:{"Content-Type":"application/json","Content-Length":Buffer.byteLength(e),Authorization:`Bearer ${String(r).replace(/[\r\n]/g,"")}`,FlowTenant:String(n).replace(/[\r\n]/g,"")}},c=>{c.resume(),o(c.statusCode??0);});l.on("error",()=>o(0)),l.setTimeout(5e3,()=>{l.destroy(),o(0);}),l.write(e),l.end();})}async function v(t,e={}){try{let r=ft(process.env[S.ANTHROPIC_AUTH_TOKEN]);if(!r)return;let n,o=new Promise((T,m)=>{n=setTimeout(()=>m(new Error("getToken timeout")),4e3),n.unref();}),{accessToken:s}=await Promise.race([q(r),o]);clearTimeout(n);let i=xr(s);if(!i)return;let l=i.tenant||r.tenant,c=JSON.stringify({action:t,booster:At().BOOSTER,metadata:e,success:!0,tenant:l,timestamp:new Date().toISOString(),os:process.platform,user:{email:i.email||"",id:i.sub||"",name:i.name||i.email||""}}),p=dt(At().API_URL),_=await Br(p,c,s,l);a("metrics.logEvent",`action=${t} status=${_}`);}catch(r){a("metrics.logEvent",`silenced error: ${r.message}`);}}var Mr=`\u26D4 Your Flow API key has expired. You no longer have access to Claude Code through the Flow platform. To restore observability and access, visit ${x()}/settings/api-keys to generate a new API key, then run: flow-ai-obs auth login`;async function xt(t,e=false){if(e){process.stdout.write(JSON.stringify({decision:"block",reason:Mr})+`
|
|
10
|
+
`);return}let n=!!(await U()).authError,o=t.session_id||"unknown",s=t.prompt||"",i=t.cwd||"",l=pe(t.transcript_path)||vt(),c=ge(s),p=c?gt(c,i):null,_=c?St(c,i):null;H(o,{traceId:vt(),spanId:C(),startNs:I(),sessionId:o,prompt:s,cwd:i,traceName:l,transcriptPath:t.transcript_path||"",model:process.env[S.ANTHROPIC_MODEL]||"",toolCalls:[],spans:[],pendingTool:null,slashSkill:c,skillContent:p,skillArtifacts:_}),v("SESSION_STARTED",{traceType:c?"skill":"prompt",slashSkill:c,clientIdExpired:n}),a("UserPromptSubmit",`sid=${o}`,`traceName=${l}`,`slashSkill=${c}`),O(t);}async function _e(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},o=M(e);o&&(o.pendingTool={name:r,inputStr:k(n,w.TOOL_INPUT),startNs:I()},H(e,o)),a("PreToolUse",`sid=${e}`,`tool=${r}`,`stateFound=${!!o}`),O(t);}var Hr={name:ht.SCOPE_NAME,version:ht.SCOPE_VERSION},f={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 u(t,e){return e==null||e===""?null:{key:t,value:{stringValue:String(e)}}}function F(...t){return t.filter(e=>e!==null)}function Ee(t,e){return {resourceSpans:[{resource:{attributes:t},scopeSpans:[{scope:Hr,spans:Array.isArray(e)?e:[e]}]}]}}var Te=B.join(st.tmpdir(),"flow-obs-requests.ndjson");function he(t,e,r,n,o){if(process.env[S.FLOW_OBS_DEBUG]!=="1")return;let s=JSON.stringify({ts:new Date().toISOString(),request:{method:"POST",url:t,headers:e,body:JSON.parse(r)},response:{status:n,body:o}});try{L.writeFileSync(Te,s+`
|
|
11
|
+
`,{flag:"a",encoding:"utf8",mode:384}),a("sendTraces:dump",`request appendada em ${Te}`);}catch(i){a("sendTraces:dump",`falha ao salvar: ${i.message}`);}}function Jr(t){let e=new URL(t),r=new URL(V().GATEWAY_HEALTH);return r.hostname=e.hostname,r.port=e.port,r.protocol=e.protocol,r}function Ae(t,e){return new Promise((r,n)=>{let o=t._isSSL?ir__default.default:ar__default.default;t.headers=Object.assign({},t.headers,{Connection:"close"});let s=o.request(t,i=>{let l=[];i.on("data",c=>l.push(c)),i.on("end",()=>r({statusCode:i.statusCode??0,body:l.join("")}));});s.setTimeout(1e4,()=>{s.destroy(new Error("Request timeout"));}),s.on("error",i=>n(new Error(`Network error: ${i.message}`))),e&&s.write(e),s.end();})}async function ye(t,e){let r;try{r=Jr(t);}catch{return false}let n=r.protocol==="https:";try{let o={};e&&(o.Authorization=String(e).replace(/[\r\n]/g,""));let s=await Ae({hostname:r.hostname,port:r.port||(n?443:80),path:r.pathname,method:"GET",headers:o,_isSSL:n},null);return a("checkHealth",`url=${r.href} status=${s.statusCode}`),s.statusCode>=200&&s.statusCode<300}catch{return false}}async function _t(t,e,r){let n=JSON.stringify(t),o=new URL(e),s=o.protocol==="https:",i=String(r).replace(/[\r\n]/g,""),l={"Content-Type":"application/json",Authorization:i,"Content-Length":Buffer.byteLength(n)};a("sendTraces:request",`POST ${e}`),a("sendTraces:request",`headers=${JSON.stringify({...l,Authorization:i.slice(0,20)+"\u2026"})}`),a("sendTraces:request",`body=${n.slice(0,500)}${n.length>500?"\u2026":""}`);try{let c=await Ae({hostname:o.hostname,port:o.port||(s?443:80),path:o.pathname,method:"POST",headers:l,_isSSL:s},n);return a("sendTraces:response",`status=${c.statusCode}`),he(e,l,n,c.statusCode,c.body),c.statusCode}catch(c){return a("sendTraces:error",c.message),he(e,l,n,0,c.message),0}}function Kr(){let t=parseInt(process.env[S.BUFFER_TTL_DAYS]??"",10);return (Number.isFinite(t)?Math.max(y.MIN_TTL_DAYS,Math.min(y.MAX_TTL_DAYS,t)):y.DEFAULT_TTL_DAYS)*24*60*60*1e3}function qr(){let t=parseInt(process.env[S.BUFFER_MAX_FILES]??"",10);return Number.isFinite(t)?Math.max(y.MIN_MAX_FILES,Math.min(y.MAX_MAX_FILES,t)):y.DEFAULT_MAX_FILES}function we(t){if(/[/\\]/.test(t))throw new Error(`Invalid buffer fileId: ${t}`);return B__namespace.default.join(st__namespace.default.tmpdir(),`${y.FILE_PREFIX}${t}.json`)}function Mt(){let t=st__namespace.default.tmpdir(),e;try{e=L__namespace.default.readdirSync(t);}catch{return []}return e.filter(r=>r.startsWith(y.FILE_PREFIX)&&r.endsWith(".json")).map(r=>{let n=B__namespace.default.join(t,r),o=0;try{o=L__namespace.default.statSync(n).mtimeMs;}catch{}return {full:n,mtime:o}}).sort((r,n)=>r.mtime-n.mtime).map(r=>r.full)}function z(t){try{let e=qr(),r=Mt();if(r.length>=e){let s=r.slice(0,r.length-e+1);for(let i of s)try{L__namespace.default.unlinkSync(i);}catch{}}let n=`${Date.now()}-${Math.random().toString(36).slice(2,8)}`,o={fileId:n,bufferedAt:Date.now(),payload:t};return L__namespace.default.writeFileSync(we(n),JSON.stringify(o),{encoding:"utf8",mode:384}),a("buffer",`saved fileId=${n}`),n}catch(e){return a("buffer",`saveToBuffer failed: ${e.message}`),null}}function ke(t){let e=Mt(),r=t,n=[];for(let o of e){if(n.length>=r)break;try{let s=L__namespace.default.readFileSync(o,"utf8"),i=JSON.parse(s);i&&i.fileId&&i.payload&&n.push(i);}catch{a("buffer",`skipping malformed file: ${o}`);}}return n}function Ie(t){try{L__namespace.default.unlinkSync(we(t)),a("buffer",`deleted fileId=${t}`);}catch{}}function Le(){let t=Date.now()-Kr();for(let e of Mt())try{let{mtimeMs:r}=L__namespace.default.statSync(e);r<t&&(L__namespace.default.unlinkSync(e),a("buffer",`evicted stale: ${B__namespace.default.basename(e)}`));}catch{}}async function zr(t){Le();let e=ke(y.REPLAY_BATCH_SIZE);e.length&&(a("replayBufferedTraces",`replaying ${e.length} buffered trace(s)`),await Promise.allSettled(e.map(async r=>{try{let n=await _t(r.payload,t.endpoint,t.authHeader);n>=200&&n<300?(Ie(r.fileId),a("replayBufferedTraces",`replayed fileId=${r.fileId} status=${n}`)):a("replayBufferedTraces",`replay failed fileId=${r.fileId} status=${n}`);}catch(n){a("replayBufferedTraces",`replay error fileId=${r.fileId}: ${n.message}`);}})));}async function Re(t){let e=await U();if(!e.length)return e.authError&&(a("postToLangfuse","auth refresh failed \u2014 buffering trace"),z(t)),0;let r=await Promise.all(e.map(async s=>{if(s.mode!=="gateway")return {creds:s,healthy:true};let i=await ye(s.endpoint,s.authHeader);return {creds:s,healthy:i}})),n=r.find(s=>s.creds.mode==="gateway"&&s.healthy)?.creds??r.find(s=>s.creds.mode==="direct")?.creds;return n&&await zr(n),(await Promise.all(r.map(async({creds:s,healthy:i})=>{if(s.mode==="gateway"){if(!i)return a("postToLangfuse","gateway health check failed \u2014 buffering trace"),z(t),0;let c=await _t(t,s.endpoint,s.authHeader);return (c===0||c>=500)&&(a("postToLangfuse",`gateway send failed (status ${c}) \u2014 buffering trace`),z(t)),c}let l=await _t(t,s.endpoint,s.authHeader);return (l===0||l>=500)&&(a("postToLangfuse",`direct endpoint unavailable (status ${l}) \u2014 buffering trace`),z(t)),l}))).find(s=>s!==0)??0}var A="[REDACTED]",Xr="[REDACTED-EMAIL]",Zr="[REDACTED-CPF]",Qr="[REDACTED-CNPJ]",Ne="[REDACTED-PHONE]",tn=[{re:/\b(sk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`sk-${A}`},{re:/\b(pk-[A-Za-z0-9_\-]{20,})/g,replace:()=>`pk-${A}`},{re:/\b(Bearer\s+)[A-Za-z0-9\-._~+/]+=*/gi,replace:(t,e)=>`${e}${A}`},{re:/\b(Basic\s+)[A-Za-z0-9+/]+=*/gi,replace:(t,e)=>`${e}${A}`},{re:/(-----BEGIN [A-Z ]+-----)[^-]*(-----END [A-Z ]+-----)/g,replace:(t,e,r)=>`${e}
|
|
12
12
|
${A}
|
|
13
|
-
${r}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${A}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${A}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${A}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${A}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${A}`},{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}${A}${r}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${A}@`},{re:/[a-zA-Z0-9._%+\-]+@[a-zA-Z0-9.\-]+\.[a-zA-Z]{2,}/g,replace:()=>Xr},{re:/\b\d{3}\.\d{3}\.\d{3}-\d{2}\b/g,replace:()=>Zr},{re:/\b\d{2}\.\d{3}\.\d{3}\/\d{4}-\d{2}\b/g,replace:()=>Qr},{re:/\(\d{2}\)\s?\d{4,5}[-\s]?\d{4}/g,replace:()=>Ne},{re:/\+55[\s-]?\d{2}[\s-]?\d{4,5}[-\s]?\d{4}/g,replace:()=>Ne}];function R(t){if(t==null)return "";let e=typeof t=="string"?t:JSON.stringify(t);return tn.reduce((r,{re:n,replace:o})=>r.replace(n,o),e)}async function Pe(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},o=t.tool_response,s=o!==null&&typeof o=="object"?o.output??JSON.stringify(o):o??"",i=M(e);if(!i){O(t);return}let l=I(),c=i.pendingTool,p=c?.name===r,_=p?c.startNs:String(BigInt(l)-200000000n),T=p?c.inputStr:k(n,w.TOOL_INPUT),m=T,g=null;if(r==="Skill"){let
|
|
14
|
-
`)),h=p?.inputTokens??0,E=p?.outputTokens??0,
|
|
13
|
+
${r}`},{re:/\b(AKIA[0-9A-Z]{16})\b/g,replace:()=>`AKIA${A}`},{re:/(aws_secret_access_key\s*[=:]\s*)([A-Za-z0-9/+]{40})/gi,replace:(t,e)=>`${e}${A}`},{re:/\b(ghp_[A-Za-z0-9]{36,})/g,replace:()=>`ghp_${A}`},{re:/\b(github_pat_[A-Za-z0-9_]{36,})/gi,replace:()=>`github_pat_${A}`},{re:/\b(eyJ[A-Za-z0-9_\-]+\.eyJ[A-Za-z0-9_\-]+\.[A-Za-z0-9_\-]+)/g,replace:()=>`eyJ.${A}`},{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}${A}${r}`},{re:/([a-z][a-z0-9+\-.]*:\/\/[^:/?#\s]*):([^@\s]+)@/gi,replace:(t,e)=>`${e}:${A}@`},{re:/[a-zA-Z0-9._%+\-]+@[a-zA-Z0-9.\-]+\.[a-zA-Z]{2,}/g,replace:()=>Xr},{re:/\b\d{3}\.\d{3}\.\d{3}-\d{2}\b/g,replace:()=>Zr},{re:/\b\d{2}\.\d{3}\.\d{3}\/\d{4}-\d{2}\b/g,replace:()=>Qr},{re:/\(\d{2}\)\s?\d{4,5}[-\s]?\d{4}/g,replace:()=>Ne},{re:/\+55[\s-]?\d{2}[\s-]?\d{4,5}[-\s]?\d{4}/g,replace:()=>Ne}];function R(t){if(t==null)return "";let e=typeof t=="string"?t:JSON.stringify(t);return tn.reduce((r,{re:n,replace:o})=>r.replace(n,o),e)}async function Pe(t){let e=t.session_id||"unknown",r=t.tool_name||"unknown",n=t.tool_input||{},o=t.tool_response,s=o!==null&&typeof o=="object"?o.output??JSON.stringify(o):o??"",i=M(e);if(!i){O(t);return}let l=I(),c=i.pendingTool,p=c?.name===r,_=p?c.startNs:String(BigInt(l)-200000000n),T=p?c.inputStr:k(n,w.TOOL_INPUT),m=T,g=null;if(r==="Skill"){let rt=typeof n=="object"&&n!==null?n.skill||n.name||n.skillName||n.commandName||String(Object.values(n)[0]??""):String(n);g=rt?String(rt).trim():null;let N=g?gt(g,i.cwd):null;N&&(m=N,i.skillContent||(i.skillContent=N),i.skillArtifacts||(i.skillArtifacts=St(g,i.cwd))),g&&!i.slashSkill&&(i.slashSkill=g),a("PostToolUse","Skill tool detected",`skillName=${g}`,`contentFound=${!!N}`);}let h=R(k(s,w.TOOL_OUTPUT)),E=/\b(error|exception|failed|failure|traceback|errno)\b/i.test(h.slice(0,500)),X=E?"ERROR":"DEFAULT",G=C(),Z=Math.round(Number(BigInt(l)-BigInt(_))/1e6),tt={Agent:"AGENT",Task:"AGENT"}[r]??"TOOL",et=r==="Skill"&&g?g:mt(T,60);i.toolCalls.push({tool:r,brief:et,error:E,durationMs:Z});let j=i.spans;j.push({traceId:i.traceId,spanId:G,parentSpanId:i.spanId,name:r,kind:3,startTimeUnixNano:_,endTimeUnixNano:l,attributes:F(u(f.OBS_NAME,r),u(f.OBS_TYPE,tt),u(f.OBS_LEVEL,X),u(f.OBS_INPUT,R(m)),u(f.OBS_OUTPUT,h),u("tool.name",r),u("tool.error",String(E)),r==="Skill"&&g?u("skill.name",g):null,r==="Skill"?u("skill.invocation","slash-command"):null),status:{code:E?2:1}}),i.pendingTool=null,H(e,i),E&&v("TOOL_ERROR",{toolName:r}),a("PostToolUse",`sid=${e}`,`tool=${r}`,`error=${E}`,`durationMs=${Z}`,`totalSpans=${j.length}`),O(t);}var be={"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 Ue(t,e,r){let n=Object.keys(be).find(i=>(t??"").toLowerCase().includes(i));if(!n)return;let o=be[n],s=(e*o.input+r*o.output)/1e6;return Math.round(s*1e6)/1e6}async function Ce(t){let e=t.session_id||"unknown",r=t.stop_reason||"end_turn",n=M(e);if(!n){O(t);return}n.slashSkill&&!/^[a-z][a-z0-9-]*(?::[a-z][a-z0-9-]*)?$/i.test(n.slashSkill)&&(a("Stop",`sid=${e}`,`slashSkill rejected post-disk: "${n.slashSkill}"`),n.slashSkill=null);let o=I(),s=await oe(),i=n.toolCalls,l=n.spans;if(n.slashSkill&&!i.some(d=>d.tool==="Skill")){let d=C(),P=n.skillContent?n.skillContent:JSON.stringify({skill:n.slashSkill});i.push({tool:"Skill",brief:n.slashSkill,error:false,durationMs:0,synthetic:true}),l.push({traceId:n.traceId,spanId:d,parentSpanId:n.spanId,name:"Skill",kind:3,startTimeUnixNano:n.startNs,endTimeUnixNano:n.startNs,attributes:F(u(f.OBS_NAME,"Skill"),u(f.OBS_TYPE,"TOOL"),u(f.OBS_LEVEL,"DEFAULT"),u(f.OBS_INPUT,P),u(f.OBS_OUTPUT,"loaded via slash command"),u("tool.name","Skill"),u("tool.error","false"),u("skill.name",n.slashSkill),u("skill.invocation","slash-command")),status:{code:1}}),a("Stop",`slashSkill=${n.slashSkill}`,"synthetic span injected");}let c=t.transcript_path||n.transcriptPath||"",p=Dt(c);if(c&&(i.some(d=>d.tool==="Skill"&&!d.synthetic)||!!n.slashSkill)&&!p?.text){await new Promise(P=>setTimeout(P,500));let d=Dt(c);d?.text&&(p=d);}a("Stop",`transcriptPath=${c||"(empty)"}`,`assistantOut=${p?`text=${p.text.length}chars`:"null"}`);let T=i.length,m=i.filter(d=>d.error).length,g=R(p?.text?k(p.text,w.TRACE_OUTPUT):T===0?"No tools used":i.map((d,P)=>`${P+1}. ${d.tool}${d.brief?` \u2192 ${d.brief}`:""}${d.error?" [ERROR]":""}`).join(`
|
|
14
|
+
`)),h=p?.inputTokens??0,E=p?.outputTokens??0,X=i.map((d,P)=>`${P+1}. ${d.tool}${d.brief?` \u2192 ${d.brief}`:""}${d.error?" [ERROR]":""} (${d.durationMs}ms)`),G=!!(n.slashSkill||i.some(d=>d.tool==="Skill")),Z=i.some(d=>d.tool==="Agent");if(!G&&!Z){a("Stop",`sid=${e}`,"skipping trace \u2014 no Skill or Agent calls found"),v("TRACE_SKIPPED",{reason:"no_skill_or_agent"}),$t(e),O(t);return}let Q=G?"skill":"agent",tt=Math.round(Number(BigInt(o)-BigInt(n.startNs))/1e6),et=Ue(n.model,h,E),$=Se(n);$==="prerequisite_required"&&p?.text&&($="complete"),$==="prerequisite_required"&&(l.push({traceId:n.traceId,spanId:C(),parentSpanId:n.spanId,name:"prerequisite-check",kind:3,startTimeUnixNano:n.startNs,endTimeUnixNano:o,attributes:F(u(f.OBS_NAME,"prerequisite-check"),u(f.OBS_TYPE,"EVENT"),u(f.OBS_LEVEL,"WARNING"),u(f.OBS_OUTPUT,g),u("skill.name",n.slashSkill||void 0),u("execution_status","prerequisite_required")),status:{code:1}}),a("Stop",`sid=${e}`,"prerequisite-check span injected",`skill=${n.slashSkill}`));let j=(()=>{if(!(!G||!n.prompt)){if(n.slashSkill){let d=n.prompt.replace(new RegExp(`^\\/${n.slashSkill}\\s*`,"i"),"").trim();return d?k(R(d),w.USER_INSTRUCTION):void 0}return k(R(n.prompt),w.USER_INSTRUCTION)||void 0}})(),rt=JSON.stringify({trace_type:Q,...$!==null&&{execution_status:$},...n.slashSkill?{skill_name:n.slashSkill}:{},...n.skillArtifacts?.length&&{skill_artifacts:n.skillArtifacts},...j!==void 0&&{user_instruction:j},latency_ms:tt,...h&&{tokens_input:h},...E&&{tokens_output:E},cost_usd:et,...n.model?{model:n.model}:{},toolCount:T,errorCount:m,stopReason:r,sessionId:n.sessionId,tools:X.length?X:void 0}),N=R(k(n.prompt,w.TRACE_INPUT)),ve=F(u(f.TRACE_NAME,n.traceName),u(f.TRACE_INPUT,N),u(f.TRACE_OUTPUT,g),u(f.OBS_INPUT,N),u(f.OBS_OUTPUT,g),u(f.TRACE_METADATA,rt),u(f.SESSION_ID,n.sessionId),u(f.USER_ID,s.user),u(f.OBS_TYPE,"GENERATION"),u(f.MODEL,n.model),h?u(f.INPUT_TOKENS,h):null,E?u(f.OUTPUT_TOKENS,E):null,u("claude.stop_reason",r),u("claude.tool_count",String(T)),u("claude.error_count",String(m)),u("claude.session_id",n.sessionId),u("flow.trace_type",Q),{key:f.TRACE_TAGS,value:{arrayValue:{values:[{stringValue:Q}]}}}),Fe={traceId:n.traceId,spanId:n.spanId,name:n.traceName,kind:1,startTimeUnixNano:n.startNs,endTimeUnixNano:o,attributes:ve,status:{code:m>0?2:1}},$e=F(u("service.name",process.env.LANGFUSE_PROJECT_NAME||"claude-code"),u("deployment.environment",process.env.LANGFUSE_ENVIRONMENT||"default")),Ht=[...l,Fe];a("Stop",`sid=${e}`,`totalTools=${T}`,`errorTools=${m}`,`spans=${Ht.length}`,`inputTokens=${h}`,`outputTokens=${E}`,`traceOutput="${mt(g,80)}"`);let De=await Re(Ee($e,Ht));a("Stop",`POST status=${De}`,`traceId=${n.traceId}`),v("TRACE_SENT",{latencyMs:tt,totalTools:T,errorTools:m,inputTokens:h,outputTokens:E,costUsd:et}),$t(e),O(t);}async function en(){let t=process.argv[2];if(t==="UserPromptSubmit"){let r=await Ct(),n;try{n=await U();}catch{process.stdout.write(JSON.stringify(r));return}n.authError?await xt(r,true):n.length>0?await xt(r):process.stdout.write(JSON.stringify(r));return}if(!await ie()){let r=[];process.stdin.on("data",n=>r.push(n)),process.stdin.on("end",()=>process.stdout.write(r.join("")));return}let e=await Ct();switch(t){case "PreToolUse":await _e(e);break;case "PostToolUse":await Pe(e);break;case "Stop":await Ce(e);break;default:process.stderr.write(`[flow-obs] unknown event: ${t}
|
|
15
15
|
`),process.stdout.write(JSON.stringify(e));}}en().catch(t=>{process.stderr.write(`[flow-obs] fatal: ${t.message}
|
|
16
16
|
`),process.exit(0);});
|
package/dist/setup.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
'use strict';var child_process=require('child_process'),util=require('util'),i=require('fs'),f=require('path'),l=require('os'),Be=require('https');require('readline/promises');function _interopDefault(e){return e&&e.__esModule?e:{default:e}}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 i__namespace=/*#__PURE__*/_interopNamespace(i);var f__namespace=/*#__PURE__*/_interopNamespace(f);var l__namespace=/*#__PURE__*/_interopNamespace(l);var Be__default=/*#__PURE__*/_interopDefault(Be);var Ee=Object.defineProperty;var T=(e=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(e,{get:(t,r)=>(typeof require<"u"?require:t)[r]}):e)(function(e){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+e+'" is not supported')});var v=(e,t)=>()=>(e&&(t=e(e=0)),t);var ye=(e,t)=>()=>(t||e((t={exports:{}}).exports,t),t.exports),O=(e,t)=>{for(var r in t)Ee(e,r,{get:t[r],enumerable:true});};var z={};O(z,{MacOsKeyVaultProvider:()=>U});var N,U,Z=v(()=>{N=util.promisify(child_process.execFile),U=class{static async isAvailable(){try{return i.accessSync("/usr/bin/security",i.constants.X_OK),!0}catch{return false}}async getSecret(t,r){try{let{stdout:n}=await N("security",["find-generic-password","-w","-a",r,"-s",t]);return n.trim()||null}catch{return null}}async setSecret(t,r,n){await N("security",["add-generic-password","-U","-a",r,"-s",t,"-w",n]);}async deleteSecret(t,r){try{return await N("security",["delete-generic-password","-a",r,"-s",t]),!0}catch{return false}}getStoragePath(){return "macOS Keychain"}};});var ee={};O(ee,{LinuxKeyVaultProvider:()=>b});var Q,b,te=v(()=>{Q=util.promisify(child_process.execFile),b=class{static async isAvailable(){let t=["/usr/bin/secret-tool","/bin/secret-tool","/usr/local/bin/secret-tool"];for(let r of t)try{return i.accessSync(r,i.constants.X_OK),!0}catch{}return false}async getSecret(t,r){try{let{stdout:n}=await Q("secret-tool",["lookup","service",t,"account",r]);return n.trim()||null}catch{return null}}async setSecret(t,r,n){await new Promise((s,o)=>{let a=child_process.spawn("secret-tool",["store","--label",t,"service",t,"account",r]);a.on("error",o),a.on("close",d=>{d===0?s():o(new Error(`secret-tool exited with code ${d}`));}),a.stdin.write(n),a.stdin.end();});}async deleteSecret(t,r){try{return await Q("secret-tool",["clear","service",t,"account",r]),!0}catch{return false}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var re={};O(re,{WindowsKeyVaultProvider:()=>F});var F,ne=v(()=>{F=class{static async isAvailable(){try{return await T("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return false}}async getSecret(t,r){return T("keytar").getPassword(t,r)}async setSecret(t,r,n){await T("keytar").setPassword(t,r,n);}async deleteSecret(t,r){return T("keytar").deletePassword(t,r)}getStoragePath(){return "Windows Credential Manager"}};});var pe=ye((qt,Ge)=>{Ge.exports={name:"@ciandt-flow/flow-ai-obs",version:"0.7.0-beta.398",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:{},optionalDependencies:{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"}};});function x(){if(process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER){let t=child_process.spawnSync("getent",["passwd",process.env.SUDO_USER],{encoding:"utf8",timeout:5e3}).stdout?.split(":")[5]?.trim();if(t)return {home:t,username:process.env.SUDO_USER}}return {home:l__namespace.homedir(),username:process.env.SUDO_USER||process.env.USER||l__namespace.userInfo().username}}function R(){if(process.env.WSL_DISTRO_NAME&&process.platform==="linux"){let e=process.env.USERPROFILE;if(!e){let r=child_process.spawnSync("cmd.exe",["/c","echo","%USERPROFILE%"],{encoding:"utf8",timeout:5e3}).stdout?.trim();r&&/^[A-Za-z]:\\/.test(r)&&(e=r);}if(e){let t=e.replace(/^([A-Za-z]):/,(r,n)=>`/mnt/${n.toLowerCase()}`).replace(/\\/g,"/");return f__namespace.join(t,".claude","settings.json")}return f__namespace.join(l__namespace.homedir(),".claude","settings.json")}if(process.platform==="win32"){let e=process.env.USERPROFILE||l__namespace.homedir();return f__namespace.join(e,".claude","settings.json")}if(process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER){let t=child_process.spawnSync("getent",["passwd",process.env.SUDO_USER],{encoding:"utf8",timeout:5e3}).stdout?.split(":")[5]?.trim();if(t)return f__namespace.join(t,".claude","settings.json")}return f__namespace.join(l__namespace.homedir(),".claude","settings.json")}var V="flow-ai-obs",Y="config.json";function Te(){if(process.platform==="win32"){let r=process.env.APPDATA||f__namespace.join(l__namespace.homedir(),"AppData","Roaming");return f__namespace.join(r,V,Y)}let e=x(),t=process.env.XDG_CONFIG_HOME||f__namespace.join(e.home,".config");return f__namespace.join(t,V,Y)}function _e(){try{let e=i__namespace.readFileSync(Te(),"utf8");return JSON.parse(e)}catch{return {}}}function G(){let{baseUrl:e}=_e();return typeof e!="string"||e.trim()===""?null:e.trim().replace(/\/$/,"")}var Se="https://flow.ciandt.com";function I(){return G()??process.env.FLOW_BASE_URL??Se}function P(){let e=I();return {AUTH_ENGINE:process.env.FLOW_AUTH_ENGINE_URL||`${e}/auth-engine-api/v2/api-key/token`,GATEWAY_TRACES:process.env.FLOW_GATEWAY_TRACES_URL||`${e}/flow-langfuse-gateway/v1/traces`,GATEWAY_HEALTH:process.env.FLOW_GATEWAY_HEALTH_URL||`${e}/flow-langfuse-gateway/v1/health`,OTEL_ENDPOINT:process.env.FLOW_OTEL_ENDPOINT_URL||`${e}/otel`}}var we=P(),_={SERVICE:"flow-plugins-cli",ACCOUNT_CREDS:"credentials"},S="FLOW-nodejs",w="config.json";function B(){let e=I();return {ANTHROPIC_BASE_URL:process.env.FLOW_LLM_PROXY_URL??`${e}/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"}}var W={CLAUDE_CODE_ENABLE_TELEMETRY:"1",OTEL_EXPORTER_OTLP_ENDPOINT:we.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"},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 K={LOCK_STALE_MS:3e4},J={UserPromptSubmit:5,PreToolUse:3,PostToolUse:10,Stop:15};var X="flow-ai-obs-debug.log";var C={credentials:"credentials","token-cache":"tokenCache"};function h(){let e=l__namespace.default.homedir();if(process.platform==="darwin")return f__namespace.default.join(e,"Library","Preferences",S,w);if(process.platform==="win32"){let r=process.env.APPDATA??f__namespace.default.join(e,"AppData","Roaming");return f__namespace.default.join(r,S,w)}let t=process.env.XDG_CONFIG_HOME??f__namespace.default.join(e,".config");return f__namespace.default.join(t,S,w)}function k(){try{let e=i__namespace.default.readFileSync(h(),"utf8");return JSON.parse(e)}catch{return {}}}function q(e){let t=h();i__namespace.default.mkdirSync(f__namespace.default.dirname(t),{recursive:true}),i__namespace.default.writeFileSync(t,JSON.stringify(e,null,2),{encoding:"utf8",mode:384});}var A=class{static isAvailable(){return true}static hasExistingData(){try{if(!i__namespace.default.existsSync(h()))return !1;let t=JSON.parse(i__namespace.default.readFileSync(h(),"utf8"));return !!(t&&t.credentials)}catch{return false}}async getSecret(t,r){let n=k(),s=C[r]??r,o=n[s];return o?typeof o=="string"?o:JSON.stringify(o):null}async setSecret(t,r,n){let s=k(),o=C[r]??r;if(r==="token-cache")try{s[o]=JSON.parse(n);}catch{s[o]=n;}else s[o]=n;q(s);}async deleteSecret(t,r){let n=k(),s=C[r]??r;return s in n?(delete n[s],q(n),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${h()}`}};async function se(){return await Ue()??new A}async function Ue(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:e}=await Promise.resolve().then(()=>(Z(),z));return await e.isAvailable()?new e:null}case "linux":{let{LinuxKeyVaultProvider:e}=await Promise.resolve().then(()=>(te(),ee));return await e.isAvailable()?new e:null}case "win32":{let{WindowsKeyVaultProvider:e}=await Promise.resolve().then(()=>(ne(),re));return await e.isAvailable()?new e:null}default:return null}}var be=_.SERVICE,Fe=_.ACCOUNT_CREDS,D=null;function De(){return D||(D=se()),D}async function $(){let t=await(await De()).getSecret(be,Fe);if(!t)return null;try{return JSON.parse(t)}catch{return null}}f.join(l.tmpdir(),X);var Ve=K.LOCK_STALE_MS;function oe(e){try{let t=i__namespace.statSync(e);Date.now()-t.mtimeMs>Ve&&i__namespace.unlinkSync(e);}catch{}try{i__namespace.writeFileSync(e,String(process.pid),{flag:"wx"});}catch(t){throw t.code==="EEXIST"?new Error("Another install is already in progress. If this is stale, remove: "+e):t}}function ie(e){try{i__namespace.unlinkSync(e);}catch{}}function Ye(e,t){let n=(Array.isArray(e)?e:[]).map(s=>{if(!Array.isArray(s?.hooks))return null;let o=s.hooks.filter(a=>!a.command?.startsWith?.("flow-ai-obs "));return o.length>0?{...s,hooks:o}:null}).filter(s=>s!=null);return [t,...n]}function ae(){let e=R(),t=e+".lock",r=[];i__namespace.mkdirSync(f__namespace.dirname(e),{recursive:true}),oe(t);try{if(i__namespace.existsSync(e)){i__namespace.copyFileSync(e,e+".bkp");try{i__namespace.chmodSync(e+".bkp",384);}catch{}}let n={};try{n=JSON.parse(i__namespace.readFileSync(e,"utf8"));}catch{}let s=n.env&&typeof n.env=="object"?n.env:{};n.env={...W,...B(),...s},n.otelHeadersHelper="flow-ai-obs otel-headers",(!n.hooks||typeof n.hooks!="object"||Array.isArray(n.hooks))&&(n.hooks={});let o=(c,y)=>({matcher:"",hooks:[{type:"command",command:`flow-ai-obs ${c}`,timeout:y}]}),a=["UserPromptSubmit","PreToolUse","PostToolUse","Stop"],d=n.hooks;for(let c of a){let y=Ye(d[c],o(c,J[c]));y.length>1&&r.push(c),d[c]=y;}i__namespace.writeFileSync(e,JSON.stringify(n,null,2)+`
|
|
3
|
-
`,{encoding:"utf8",mode:384});try{i__namespace.chmodSync(e,384);}catch{}}finally{ie(t);}return {settingsPath:e,preserved:r}}function ce(e){let t=R(),r=t+".lock";i__namespace.mkdirSync(
|
|
4
|
-
`,{encoding:"utf8",mode:384});try{i__namespace.chmodSync(t,384);}catch{}}finally{ie(r);}}function le(e){if(!e)return null;try{let t=e.split(".");if(t.length<2)return null;let r=JSON.parse(Buffer.from(t[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 ue(e){let t=Buffer.from(JSON.stringify({alg:"none",typ:"JWT"})).toString("base64url"),r=Buffer.from(JSON.stringify({clientId:e.clientId,clientSecret:e.clientSecret,tenant:e.tenant})).toString("base64url");return `${t}.${r}.`}var M;function
|
|
2
|
+
'use strict';var child_process=require('child_process'),util=require('util'),i=require('fs'),d=require('path'),l=require('os'),Be=require('https');require('readline/promises');function _interopDefault(e){return e&&e.__esModule?e:{default:e}}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 i__namespace=/*#__PURE__*/_interopNamespace(i);var d__namespace=/*#__PURE__*/_interopNamespace(d);var l__namespace=/*#__PURE__*/_interopNamespace(l);var Be__default=/*#__PURE__*/_interopDefault(Be);var Ee=Object.defineProperty;var y=(e=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(e,{get:(t,r)=>(typeof require<"u"?require:t)[r]}):e)(function(e){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+e+'" is not supported')});var v=(e,t,r)=>()=>{if(r)throw r[0];try{return e&&(t=e(e=0)),t}catch(n){throw r=[n],n}};var ye=(e,t)=>()=>{try{return t||e((t={exports:{}}).exports,t),t.exports}catch(r){throw t=0,r}},O=(e,t)=>{for(var r in t)Ee(e,r,{get:t[r],enumerable:true});};var z={};O(z,{MacOsKeyVaultProvider:()=>U});var N,U,Z=v(()=>{"use strict";N=util.promisify(child_process.execFile),U=class{static async isAvailable(){try{return i.accessSync("/usr/bin/security",i.constants.X_OK),!0}catch{return !1}}async getSecret(t,r){try{let{stdout:n}=await N("security",["find-generic-password","-w","-a",r,"-s",t]);return n.trim()||null}catch{return null}}async setSecret(t,r,n){await N("security",["add-generic-password","-U","-a",r,"-s",t,"-w",n]);}async deleteSecret(t,r){try{return await N("security",["delete-generic-password","-a",r,"-s",t]),!0}catch{return !1}}getStoragePath(){return "macOS Keychain"}};});var ee={};O(ee,{LinuxKeyVaultProvider:()=>b});var Q,b,te=v(()=>{"use strict";Q=util.promisify(child_process.execFile),b=class{static async isAvailable(){let t=["/usr/bin/secret-tool","/bin/secret-tool","/usr/local/bin/secret-tool"];for(let r of t)try{return i.accessSync(r,i.constants.X_OK),!0}catch{}return !1}async getSecret(t,r){try{let{stdout:n}=await Q("secret-tool",["lookup","service",t,"account",r]);return n.trim()||null}catch{return null}}async setSecret(t,r,n){await new Promise((s,o)=>{let a=child_process.spawn("secret-tool",["store","--label",t,"service",t,"account",r]);a.on("error",o),a.on("close",f=>{f===0?s():o(new Error(`secret-tool exited with code ${f}`));}),a.stdin.write(n),a.stdin.end();});}async deleteSecret(t,r){try{return await Q("secret-tool",["clear","service",t,"account",r]),!0}catch{return !1}}getStoragePath(){return "Linux Secret Service (libsecret)"}};});var re={};O(re,{WindowsKeyVaultProvider:()=>F});var F,ne=v(()=>{"use strict";F=class{static async isAvailable(){try{return await y("keytar").getPassword("__flow_probe__","__flow_probe__"),!0}catch{return !1}}async getSecret(t,r){return y("keytar").getPassword(t,r)}async setSecret(t,r,n){await y("keytar").setPassword(t,r,n);}async deleteSecret(t,r){return y("keytar").deletePassword(t,r)}getStoragePath(){return "Windows Credential Manager"}};});var pe=ye((qt,Ge)=>{Ge.exports={name:"@ciandt-flow/flow-ai-obs",version:"0.7.0-beta.403",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:!1,dependencies:{},optionalDependencies:{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"},overrides:{esbuild:"^0.28.1"},publishConfig:{registry:"https://registry.npmjs.org",access:"public"},repository:{type:"git",url:"git+https://github.com/CI-T-HyperX/flow-codeassistant-observability.git"}};});function x(){if(process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER){let t=child_process.spawnSync("getent",["passwd",process.env.SUDO_USER],{encoding:"utf8",timeout:5e3}).stdout?.split(":")[5]?.trim();if(t)return {home:t,username:process.env.SUDO_USER}}return {home:l__namespace.homedir(),username:process.env.SUDO_USER||process.env.USER||l__namespace.userInfo().username}}function R(){if(process.env.WSL_DISTRO_NAME&&process.platform==="linux"){let e=process.env.USERPROFILE;if(!e){let r=child_process.spawnSync("cmd.exe",["/c","echo","%USERPROFILE%"],{encoding:"utf8",timeout:5e3}).stdout?.trim();r&&/^[A-Za-z]:\\/.test(r)&&(e=r);}if(e){let t=e.replace(/^([A-Za-z]):/,(r,n)=>`/mnt/${n.toLowerCase()}`).replace(/\\/g,"/");return d__namespace.join(t,".claude","settings.json")}return d__namespace.join(l__namespace.homedir(),".claude","settings.json")}if(process.platform==="win32"){let e=process.env.USERPROFILE||l__namespace.homedir();return d__namespace.join(e,".claude","settings.json")}if(process.platform==="linux"&&process.getuid?.()===0&&process.env.SUDO_USER){let t=child_process.spawnSync("getent",["passwd",process.env.SUDO_USER],{encoding:"utf8",timeout:5e3}).stdout?.split(":")[5]?.trim();if(t)return d__namespace.join(t,".claude","settings.json")}return d__namespace.join(l__namespace.homedir(),".claude","settings.json")}var V="flow-ai-obs",Y="config.json";function Te(){if(process.platform==="win32"){let r=process.env.APPDATA||d__namespace.join(l__namespace.homedir(),"AppData","Roaming");return d__namespace.join(r,V,Y)}let e=x(),t=process.env.XDG_CONFIG_HOME||d__namespace.join(e.home,".config");return d__namespace.join(t,V,Y)}function _e(){try{let e=i__namespace.readFileSync(Te(),"utf8");return JSON.parse(e)}catch{return {}}}function G(){let{baseUrl:e}=_e();return typeof e!="string"||e.trim()===""?null:e.trim().replace(/\/$/,"")}var Se="https://flow.ciandt.com";function I(){return G()??process.env.FLOW_BASE_URL??Se}function P(){let e=I();return {AUTH_ENGINE:process.env.FLOW_AUTH_ENGINE_URL||`${e}/auth-engine-api/v2/api-key/token`,GATEWAY_TRACES:process.env.FLOW_GATEWAY_TRACES_URL||`${e}/flow-langfuse-gateway/v1/traces`,GATEWAY_HEALTH:process.env.FLOW_GATEWAY_HEALTH_URL||`${e}/flow-langfuse-gateway/v1/health`,OTEL_ENDPOINT:process.env.FLOW_OTEL_ENDPOINT_URL||`${e}/otel`}}var we=P(),_={SERVICE:"flow-plugins-cli",ACCOUNT_CREDS:"credentials"},S="FLOW-nodejs",w="config.json";function B(){let e=I();return {ANTHROPIC_BASE_URL:process.env.FLOW_LLM_PROXY_URL??`${e}/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"}}var W={CLAUDE_CODE_ENABLE_TELEMETRY:"1",OTEL_EXPORTER_OTLP_ENDPOINT:we.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"},m={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 K={LOCK_STALE_MS:3e4},J={UserPromptSubmit:5,PreToolUse:3,PostToolUse:10,Stop:15};var X="flow-ai-obs-debug.log";var C={credentials:"credentials","token-cache":"tokenCache"};function g(){let e=l__namespace.default.homedir();if(process.platform==="darwin")return d__namespace.default.join(e,"Library","Preferences",S,w);if(process.platform==="win32"){let r=process.env.APPDATA??d__namespace.default.join(e,"AppData","Roaming");return d__namespace.default.join(r,S,w)}let t=process.env.XDG_CONFIG_HOME??d__namespace.default.join(e,".config");return d__namespace.default.join(t,S,w)}function k(){try{let e=i__namespace.default.readFileSync(g(),"utf8");return JSON.parse(e)}catch{return {}}}function q(e){let t=g();i__namespace.default.mkdirSync(d__namespace.default.dirname(t),{recursive:true}),i__namespace.default.writeFileSync(t,JSON.stringify(e,null,2),{encoding:"utf8",mode:384});}var A=class{static isAvailable(){return true}static hasExistingData(){try{if(!i__namespace.default.existsSync(g()))return !1;let t=JSON.parse(i__namespace.default.readFileSync(g(),"utf8"));return !!(t&&t.credentials)}catch{return false}}async getSecret(t,r){let n=k(),s=C[r]??r,o=n[s];return o?typeof o=="string"?o:JSON.stringify(o):null}async setSecret(t,r,n){let s=k(),o=C[r]??r;if(r==="token-cache")try{s[o]=JSON.parse(n);}catch{s[o]=n;}else s[o]=n;q(s);}async deleteSecret(t,r){let n=k(),s=C[r]??r;return s in n?(delete n[s],q(n),true):false}getStoragePath(){return `config.json (unencrypted) \u2014 ${g()}`}};async function se(){return await Ue()??new A}async function Ue(){switch(process.platform){case "darwin":{let{MacOsKeyVaultProvider:e}=await Promise.resolve().then(()=>(Z(),z));return await e.isAvailable()?new e:null}case "linux":{let{LinuxKeyVaultProvider:e}=await Promise.resolve().then(()=>(te(),ee));return await e.isAvailable()?new e:null}case "win32":{let{WindowsKeyVaultProvider:e}=await Promise.resolve().then(()=>(ne(),re));return await e.isAvailable()?new e:null}default:return null}}var be=_.SERVICE,Fe=_.ACCOUNT_CREDS,D=null;function De(){return D||(D=se()),D}async function $(){let t=await(await De()).getSecret(be,Fe);if(!t)return null;try{return JSON.parse(t)}catch{return null}}d.join(l.tmpdir(),X);var Ve=K.LOCK_STALE_MS;function oe(e){try{let t=i__namespace.statSync(e);Date.now()-t.mtimeMs>Ve&&i__namespace.unlinkSync(e);}catch{}try{i__namespace.writeFileSync(e,String(process.pid),{flag:"wx"});}catch(t){throw t.code==="EEXIST"?new Error("Another install is already in progress. If this is stale, remove: "+e):t}}function ie(e){try{i__namespace.unlinkSync(e);}catch{}}function Ye(e,t){let n=(Array.isArray(e)?e:[]).map(s=>{if(!Array.isArray(s?.hooks))return null;let o=s.hooks.filter(a=>!a.command?.startsWith?.("flow-ai-obs "));return o.length>0?{...s,hooks:o}:null}).filter(s=>s!=null);return [t,...n]}function ae(){let e=R(),t=e+".lock",r=[];i__namespace.mkdirSync(d__namespace.dirname(e),{recursive:true}),oe(t);try{if(i__namespace.existsSync(e)){i__namespace.copyFileSync(e,e+".bkp");try{i__namespace.chmodSync(e+".bkp",384);}catch{}}let n={};try{n=JSON.parse(i__namespace.readFileSync(e,"utf8"));}catch{}let s=n.env&&typeof n.env=="object"?n.env:{};n.env={...W,...B(),...s},n.otelHeadersHelper="flow-ai-obs otel-headers",(!n.hooks||typeof n.hooks!="object"||Array.isArray(n.hooks))&&(n.hooks={});let o=(c,E)=>({matcher:"",hooks:[{type:"command",command:`flow-ai-obs ${c}`,timeout:E}]}),a=["UserPromptSubmit","PreToolUse","PostToolUse","Stop"],f=n.hooks;for(let c of a){let E=Ye(f[c],o(c,J[c]));E.length>1&&r.push(c),f[c]=E;}i__namespace.writeFileSync(e,JSON.stringify(n,null,2)+`
|
|
3
|
+
`,{encoding:"utf8",mode:384});try{i__namespace.chmodSync(e,384);}catch{}}finally{ie(t);}return {settingsPath:e,preserved:r}}function ce(e){let t=R(),r=t+".lock";i__namespace.mkdirSync(d__namespace.dirname(t),{recursive:true}),oe(r);try{let n={};try{n=JSON.parse(i__namespace.readFileSync(t,"utf8"));}catch{}(!n.env||typeof n.env!="object")&&(n.env={}),Object.assign(n.env,e),i__namespace.writeFileSync(t,JSON.stringify(n,null,2)+`
|
|
4
|
+
`,{encoding:"utf8",mode:384});try{i__namespace.chmodSync(t,384);}catch{}}finally{ie(r);}}function le(e){if(!e)return null;try{let t=e.split(".");if(t.length<2)return null;let r=JSON.parse(Buffer.from(t[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 ue(e){let t=Buffer.from(JSON.stringify({alg:"none",typ:"JWT"})).toString("base64url"),r=Buffer.from(JSON.stringify({clientId:e.clientId,clientSecret:e.clientSecret,tenant:e.tenant})).toString("base64url");return `${t}.${r}.`}var M;function fe(){return M||(M=pe()),M}var me=d__namespace.default.join(l__namespace.default.tmpdir(),"flow-obs-update-cache.json"),Je=1440*60*1e3,Xe=3e3;function qe(e,t){let r=o=>{let a=String(o).replace(/^v/,"").match(/^(\d+)\.(\d+)\.(\d+)/);return a?[+a[1],+a[2],+a[3]]:null},n=r(e),s=r(t);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 ze(){try{let e=JSON.parse(i__namespace.default.readFileSync(me,"utf8"));return typeof e.latestVersion!="string"||Date.now()-e.checkedAt>=Je?null:e}catch{return null}}function Ze(e,t,r=Date.now()){try{i__namespace.default.writeFileSync(me,JSON.stringify({latestVersion:e,updatePriority:t??null,checkedAt:r}),{mode:384});}catch{}}function Qe(e){let t=fe().name,r=Be__default.default.get(`https://registry.npmjs.org/${encodeURIComponent(t)}/latest`,{timeout:Xe},n=>{if(n.statusCode!==200)return n.resume(),e(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");e(null,{version:o.version,updatePriority:typeof o.updatePriority=="string"?o.updatePriority:null});}catch(o){e(o);}});});r.on("error",e),r.on("timeout",()=>{r.destroy(new Error("timeout"));});}function ge(){try{if(ze())return;setImmediate(()=>{Qe((e,t)=>{e||!t||qe(fe().version,t.version)&&Ze(t.version,t.updatePriority,0);});});}catch{}}var et=d__namespace.default.resolve(__dirname,".."),tt=process.env.INIT_CWD?d__namespace.default.resolve(process.env.INIT_CWD):null;tt===et&&process.exit(0);async function rt(){try{ae();}catch{}let e=await $();if(!e){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
|
|
|
8
|
-
`);return}let t=le(process.env[
|
|
8
|
+
`);return}let t=le(process.env[m.ANTHROPIC_AUTH_TOKEN]);if(!t||t.clientId!==e.clientId||t.clientSecret!==e.clientSecret||t.tenant!==e.tenant)try{let n=ue(e);ce({[m.ANTHROPIC_AUTH_TOKEN]:n});}catch{}}rt().catch(()=>{}).finally(()=>ge());
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ciandt-flow/flow-ai-obs",
|
|
3
|
-
"version": "0.7.0-beta.
|
|
3
|
+
"version": "0.7.0-beta.403",
|
|
4
4
|
"description": "Claude Code hooks for Langfuse OTLP tracing — cross-platform",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"bin": {
|
|
@@ -65,6 +65,9 @@
|
|
|
65
65
|
"engines": {
|
|
66
66
|
"node": ">=18.0.0"
|
|
67
67
|
},
|
|
68
|
+
"overrides": {
|
|
69
|
+
"esbuild": "^0.28.1"
|
|
70
|
+
},
|
|
68
71
|
"publishConfig": {
|
|
69
72
|
"registry": "https://registry.npmjs.org",
|
|
70
73
|
"access": "public"
|