{"_id":"@appthreat/chennai","_rev":"11-5e63e42949658b39d81ee9b4d4c4185f","name":"@appthreat/chennai","dist-tags":{"latest":"1.0.2"},"versions":{"0.0.1":{"name":"@appthreat/chennai","version":"0.0.1","author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.0.1","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"dist":{"shasum":"e0889fe134efbb2ce6dbca6625e3198fba697a09","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.0.1.tgz","fileCount":3,"integrity":"sha512-/kvbWXxflKf3P/SHaElDvO80OB/h3PhtdF6JSH9iMMnaHxgfDezr2kNd2tyd61vC4eo7izZKMPi0es8Qoffo+w==","signatures":[{"sig":"MEUCIH0PIYYshsIXhVbDQEqAeIbI842UByp5DxiV7BFm64N3AiEA6k7MffwwXc9pUdbd6b5m+yL5B2loUwMJtKmQL2UNOls=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":1698},"gitHead":"68bf0586b365b0012aab3c3f9b2fca75c311ccc5","_npmUser":{"name":"prabhus","email":"cloud@appthreat.com"},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"[placeholder] Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.16.0","_hasShrinkwrap":false,"_npmOperationalInternal":{"tmp":"tmp/chennai_0.0.1_1782586587680_0.745690809009786","host":"s3://npm-registry-packages-npm-production"}},"0.1.0":{"name":"@appthreat/chennai","version":"0.1.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.1.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"d01dc75b6e77b88315da4787bed21e5d2571bdbc","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.1.0.tgz","fileCount":5,"integrity":"sha512-lIKPEdSsiwAciXR6tHeFm5jPdQmru8lJ3vGm1+jxKhNEAQ8fzOlhGmihMRww+kf97iY+QJ03YXeQAYAtaxyb6w==","signatures":[{"sig":"MEQCIHQWEpq2/aMj0vMD2ohUD7EI9eoPYZDKH96LE9aa7Tf7AiBqJAHBPKnj5Ff/xpAzXNwYPpuKKBLDTOPBcDJ+qEnaTA==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@0.1.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":28689},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"8a07042eccd1b20dba42f6c583c0115046cd1331","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"0.1.0","@appthreat/chennai-linux-arm64":"0.1.0","@appthreat/chennai-darwin-amd64":"0.1.0","@appthreat/chennai-darwin-arm64":"0.1.0","@appthreat/chennai-windows-amd64":"0.1.0","@appthreat/chennai-windows-arm64":"0.1.0","@appthreat/chennai-linux-amd64-musl":"0.1.0","@appthreat/chennai-linux-arm64-musl":"0.1.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_0.1.0_1782622455575_0.6723540305433375","host":"s3://npm-registry-packages-npm-production"}},"0.3.0":{"name":"@appthreat/chennai","version":"0.3.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.3.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"b8283e5f0cdda8fd6e7b447e59beb895578b20b2","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.3.0.tgz","fileCount":5,"integrity":"sha512-UnozMtFeck3DUGx1O5RCSEP8l999qabVQmb3iJbHpVvPxqzs/My9sywoAQwSV2vk7CVGUefjaqqxdYpHS55mMA==","signatures":[{"sig":"MEUCIH2O/aPoFHinZWIYwMEnjN2MoVKTlXpp839xkcdMNOSDAiEA1w7Pd4462Yyg93nQSjr+9/PKa0mV9jvHMhdojiSEcek=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@0.3.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":28689},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"2acbb553059d61796c55d7287ad1f76efdef30e9","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"0.3.0","@appthreat/chennai-linux-arm64":"0.3.0","@appthreat/chennai-darwin-amd64":"0.3.0","@appthreat/chennai-darwin-arm64":"0.3.0","@appthreat/chennai-windows-amd64":"0.3.0","@appthreat/chennai-windows-arm64":"0.3.0","@appthreat/chennai-linux-amd64-musl":"0.3.0","@appthreat/chennai-linux-arm64-musl":"0.3.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_0.3.0_1782626389100_0.08535911188635015","host":"s3://npm-registry-packages-npm-production"}},"0.4.0":{"name":"@appthreat/chennai","version":"0.4.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.4.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"482cfdc711699a458aac64baff35ac247acbffa7","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.4.0.tgz","fileCount":5,"integrity":"sha512-EuK5DvVB4bCQ14E9tY7c22q9ekEthmgRZScDDwrmPCYK6pZB6j/tDM4CqwkXhcOR+xWiPzxOXtQyWaQgps7rvQ==","signatures":[{"sig":"MEQCIBbE/u060tzuQ4fxtVgMqrJiv3JK2Za0gH6BH/NFRm4SAiBQ1QIx3iB6Ss4Nl9BfvA5XNfF2dxbW1xnOFk+o+25CMQ==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@0.4.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":41922},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"8d5e69bd6176ec0f45139e4e3d75ada1f31a0fe7","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"0.4.0","@appthreat/chennai-linux-arm64":"0.4.0","@appthreat/chennai-darwin-amd64":"0.4.0","@appthreat/chennai-darwin-arm64":"0.4.0","@appthreat/chennai-windows-amd64":"0.4.0","@appthreat/chennai-windows-arm64":"0.4.0","@appthreat/chennai-linux-amd64-musl":"0.4.0","@appthreat/chennai-linux-arm64-musl":"0.4.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_0.4.0_1782645920861_0.4460480272885605","host":"s3://npm-registry-packages-npm-production"}},"0.5.0":{"name":"@appthreat/chennai","version":"0.5.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.5.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"a9dc2f4a0db4db7af3918d0c38e88833dbb4ca13","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.5.0.tgz","fileCount":5,"integrity":"sha512-CJK/NVhU9BtQI+JlEm93Lz0/iHMyZaBXC42lHrob2XhykJOv3LXXypoWoJWKTLDCeibrYV1Elburv0DY5walfw==","signatures":[{"sig":"MEUCIQCgMWDPKQkydcdI1UAvfXdG75IiwmO0erAkaY6fLHgGXgIgCMLW7cmO1nIexvlj2UvCeTM6riRxFLME2tHR4PAwCLs=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@0.5.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":45135},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"e74b691fef5cb8d2725892b0553cf33052f6a04d","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"0.5.0","@appthreat/chennai-linux-arm64":"0.5.0","@appthreat/chennai-darwin-amd64":"0.5.0","@appthreat/chennai-darwin-arm64":"0.5.0","@appthreat/chennai-windows-amd64":"0.5.0","@appthreat/chennai-windows-arm64":"0.5.0","@appthreat/chennai-linux-amd64-musl":"0.5.0","@appthreat/chennai-linux-arm64-musl":"0.5.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_0.5.0_1782654548432_0.15145639932552646","host":"s3://npm-registry-packages-npm-production"}},"0.6.0":{"name":"@appthreat/chennai","version":"0.6.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.6.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"e0d70866d2a1e395965c09d3a47d445bb81dcffc","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.6.0.tgz","fileCount":5,"integrity":"sha512-Y3f4aizkL+qyK3Z+oUlzqGcLr2YbMvcOOq6hjXEzASvk1y53xLTorb7jFgKCdpnJszILA8/IMxoFhLpnZDiTcA==","signatures":[{"sig":"MEUCIQCaebSFusW904QRLES9O6ZQguFFbayF3oGWobEgOTgBUgIgbRcTfERgEUVOB9c20l+Zb6vq07iWTXkq+WIi8KSQxp8=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@0.6.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":45135},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"aeffe9da2ae293efc7f858396c3c7ae495f80110","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"0.6.0","@appthreat/chennai-linux-arm64":"0.6.0","@appthreat/chennai-darwin-amd64":"0.6.0","@appthreat/chennai-darwin-arm64":"0.6.0","@appthreat/chennai-windows-amd64":"0.6.0","@appthreat/chennai-windows-arm64":"0.6.0","@appthreat/chennai-linux-amd64-musl":"0.6.0","@appthreat/chennai-linux-arm64-musl":"0.6.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_0.6.0_1782661560104_0.7075361721708102","host":"s3://npm-registry-packages-npm-production"}},"0.7.0":{"name":"@appthreat/chennai","version":"0.7.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.7.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"4e1dc36c855bcc46820706a1680530b7317089ae","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.7.0.tgz","fileCount":5,"integrity":"sha512-vTlD7aaXapibMF6caNmlYcm3P0YS8xeO9BdM56Y6+tMOg4hH2DR6ieeAtktCI4mxTpzcibmdg/Z8SXc3YTwd0A==","signatures":[{"sig":"MEQCIFcKWbdbsNO7oD1OYRahXIv22n7210A8cy6P4L6Uxoh7AiBhJTcSlAt6DGT8LDxMSi6Ura9mt4dgfBmNYy1yKodGzA==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@0.7.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":45135},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"0a34aa2eeab1ce1370004362555a3a079a706fe4","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"0.7.0","@appthreat/chennai-linux-arm64":"0.7.0","@appthreat/chennai-darwin-amd64":"0.7.0","@appthreat/chennai-darwin-arm64":"0.7.0","@appthreat/chennai-windows-amd64":"0.7.0","@appthreat/chennai-windows-arm64":"0.7.0","@appthreat/chennai-linux-amd64-musl":"0.7.0","@appthreat/chennai-linux-arm64-musl":"0.7.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_0.7.0_1782679074614_0.674667353629886","host":"s3://npm-registry-packages-npm-production"}},"0.8.0":{"name":"@appthreat/chennai","version":"0.8.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@0.8.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"13423d88c0fc5c80dc0e619220daf6814ed8e6ab","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-0.8.0.tgz","fileCount":5,"integrity":"sha512-c/ss9A7PiINAXQW3iBPT4IpakqM6Ou1H5b9QUw4DycMr6jPfWOMsfQBkt7AuDPE3hi9aJPB2xb4VIsQrGCAYyg==","signatures":[{"sig":"MEUCIQC6HSQpsdT9NuOX1m9k8tKT4iNRSITbQmxotC7zVoEM7AIgL/PfhSRKegVjpsCHHVN1SedcIcOv+GEfZ8m3FLBH3yI=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@0.8.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":45782},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"4068e79b0ed16cd19d509914698dcd54fc1cbb96","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"0.8.0","@appthreat/chennai-linux-arm64":"0.8.0","@appthreat/chennai-darwin-amd64":"0.8.0","@appthreat/chennai-darwin-arm64":"0.8.0","@appthreat/chennai-windows-amd64":"0.8.0","@appthreat/chennai-windows-arm64":"0.8.0","@appthreat/chennai-linux-amd64-musl":"0.8.0","@appthreat/chennai-linux-arm64-musl":"0.8.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_0.8.0_1782687041260_0.8892826490218653","host":"s3://npm-registry-packages-npm-production"}},"1.0.0":{"name":"@appthreat/chennai","version":"1.0.0","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@1.0.0","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"a5c8a05bc48b8f2e9fd5add7431ecead57706435","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-1.0.0.tgz","fileCount":5,"integrity":"sha512-BpDtSPy1w6kAfCCb12hvPNNPTJh6V3T0yRvDNZssQQsphRgqHL5NgXbCtjkW4e2tkw6vU95JOOYg1b9mz80lCw==","signatures":[{"sig":"MEYCIQDUBFiFo0S5KyCBGe4UJ9ESwTYdRElGaUaR2gGARih/HQIhAJttdWj4eIBwLMUfyJ5CHRKb0ZHFvytnvLZb0PsnwX/M","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@1.0.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":46654},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"eaad90998c24a510df677953f7a77b8eeec1bb8d","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"1.0.0","@appthreat/chennai-linux-arm64":"1.0.0","@appthreat/chennai-darwin-amd64":"1.0.0","@appthreat/chennai-darwin-arm64":"1.0.0","@appthreat/chennai-windows-amd64":"1.0.0","@appthreat/chennai-windows-arm64":"1.0.0","@appthreat/chennai-linux-amd64-musl":"1.0.0","@appthreat/chennai-linux-arm64-musl":"1.0.0"},"_npmOperationalInternal":{"tmp":"tmp/chennai_1.0.0_1782726779814_0.7745672982945508","host":"s3://npm-registry-packages-npm-production"}},"1.0.1":{"name":"@appthreat/chennai","version":"1.0.1","keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","_id":"@appthreat/chennai@1.0.1","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"homepage":"https://github.com/AppThreat/chennai#readme","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"bin":{"chennai":"index.js"},"dist":{"shasum":"e8e8831a8ac58622f1bbdeb92dca17807faf02c0","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-1.0.1.tgz","fileCount":5,"integrity":"sha512-qOXattf9YjUSrqZstLOoC/yfz6fAKeAXCP5ZXLX+83371gWKrRJflxdEgF3xmpDBXb+Yaz0vWoA+QwxnyyrkzQ==","signatures":[{"sig":"MEQCIBtA09AkvpIW+rviLihJe24UNeQZXLDzAkaZYHKEv7JVAiAfEn4L8S8sqQ6o16WGFqVvcuiwl5X2HDda/+lf+5M+5g==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@1.0.1","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":51191},"type":"module","engines":{"node":">=18"},"exports":"./index.js","gitHead":"c7423ee0d2c4970476ba96dc8d6ef9aa32619d67","_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"repository":{"url":"git+https://github.com/AppThreat/chennai.git","type":"git"},"_npmVersion":"11.13.0","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","directories":{},"_nodeVersion":"24.17.0","_hasShrinkwrap":false,"optionalDependencies":{"@appthreat/chennai-linux-amd64":"1.0.1","@appthreat/chennai-linux-arm64":"1.0.1","@appthreat/chennai-darwin-amd64":"1.0.1","@appthreat/chennai-darwin-arm64":"1.0.1","@appthreat/chennai-windows-amd64":"1.0.1","@appthreat/chennai-windows-arm64":"1.0.1","@appthreat/chennai-linux-amd64-musl":"1.0.1","@appthreat/chennai-linux-arm64-musl":"1.0.1"},"_npmOperationalInternal":{"tmp":"tmp/chennai_1.0.1_1782792574316_0.2863548320695286","host":"s3://npm-registry-packages-npm-production"}},"1.0.2":{"name":"@appthreat/chennai","version":"1.0.2","description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","exports":"./index.js","type":"module","bin":{"chennai":"index.js"},"engines":{"node":">=18"},"repository":{"type":"git","url":"git+https://github.com/AppThreat/chennai.git"},"keywords":["code","analysis","threat","tui","cpg"],"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"homepage":"https://github.com/AppThreat/chennai#readme","optionalDependencies":{"@appthreat/chennai-linux-amd64":"1.0.2","@appthreat/chennai-linux-arm64":"1.0.2","@appthreat/chennai-darwin-arm64":"1.0.2","@appthreat/chennai-darwin-amd64":"1.0.2","@appthreat/chennai-windows-amd64":"1.0.2","@appthreat/chennai-windows-arm64":"1.0.2","@appthreat/chennai-linux-amd64-musl":"1.0.2","@appthreat/chennai-linux-arm64-musl":"1.0.2"},"gitHead":"517eafe62bf807cf9055109fc9c007e932b7d286","_id":"@appthreat/chennai@1.0.2","_nodeVersion":"24.18.0","_npmVersion":"11.16.0","dist":{"integrity":"sha512-FbLRqZO37TLj194zfgVr05YwiIBEXiCSSF7l5pEiGQG8ky1pgX9SStKxbWFsYx54so5cmMOoJU0ObW+/P2uImQ==","shasum":"d7807d02a81b0a4862b1f966b18969a924a87491","tarball":"https://registry.npmjs.org/@appthreat/chennai/-/chennai-1.0.2.tgz","fileCount":5,"unpackedSize":56694,"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@appthreat%2fchennai@1.0.2","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEUCIQDuYgPpDFJGxLwltrpGvpgX74nn4leDU+iHLloeNrhtRwIgINmaot1x04XMm5MyQVk3T/247nlbkIImgoq9YwkwU3g="}]},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:17259f4e-03ed-4c44-90bc-4bb286436b90"}},"directories":{},"maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/chennai_1.0.2_1783956616808_0.9194475249401499"},"_hasShrinkwrap":false}},"time":{"created":"2026-06-27T18:56:27.301Z","modified":"2026-07-13T15:30:17.228Z","0.0.1":"2026-06-27T18:56:27.814Z","0.1.0":"2026-06-28T04:54:15.702Z","0.3.0":"2026-06-28T05:59:49.227Z","0.4.0":"2026-06-28T11:25:21.011Z","0.5.0":"2026-06-28T13:49:08.560Z","0.6.0":"2026-06-28T15:46:00.246Z","0.7.0":"2026-06-28T20:37:54.746Z","0.8.0":"2026-06-28T22:50:41.415Z","1.0.0":"2026-06-29T09:52:59.940Z","1.0.1":"2026-06-30T04:09:34.446Z","1.0.2":"2026-07-13T15:30:16.947Z"},"bugs":{"url":"https://github.com/AppThreat/chennai/issues"},"author":{"name":"Team AppThreat","email":"cloud@appthreat.com"},"license":"MIT","homepage":"https://github.com/AppThreat/chennai#readme","keywords":["code","analysis","threat","tui","cpg"],"repository":{"type":"git","url":"git+https://github.com/AppThreat/chennai.git"},"description":"Interactive terminal UI for exploring AppThreat atom files with AI agent","maintainers":[{"name":"prabhus","email":"cloud@appthreat.com"}],"readme":"# chennai\n\nchennai (chen N ai) is a hybrid AI agent and terminal user interface for exploring source code, dependencies, and binaries across many languages backed by real static-analysis. It integrates AppThreat [atom](https://github.com/AppThreat/atom) (Java, Scala, JavaScript, Python, PHP, Ruby, C/C++) with dedicated non-atom backends for Rust ([rusi](https://github.com/cdxgen/cdxgen-plugins-bin/tree/main/thirdparty/rusi)), Go ([golem](https://github.com/cdxgen/cdxgen-plugins-bin)), .NET ([dosai](https://github.com/owasp-dep-scan/dosai)), and compiled binaries / Android APK / iOS IPA ([blint](https://github.com/owasp-dep-scan/blint)), all behind one keyboard-driven interface for static analysis, data-flow tracing, and AI-assisted code and security review. It is built on top of the [chen](https://github.com/AppThreat/chen) library (Code Hierarchy Exploratory Network).\n\nUnlike a traditional SAST engine or a generic LLM chatbot, chennai gives you direct access to the underlying analysis data so you can ask arbitrary questions about a program's structure and data flows without leaving the terminal. It runs entirely on your machine with no server backend and no data leaving your environment.\n\nchennai includes a built-in AI agent that uses an atom, language-specific static slices, or binary metadata as grounding context. The agent can run queries, traverse data-flow paths, run graph algorithms, read source files, and search code, all orchestrated from a single chat interface inside the TUI. The agent supports both Anthropic and OpenAI compatible providers and can work either with or without an LLM.\n\n## Supported languages & artifacts\n\n| Backend   | Targets                                                      | Data surfaced                                                                                                      |\n| --------- | ------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------ |\n| **atom**  | Java, Scala, JavaScript/TypeScript, Python, PHP, Ruby, C/C++ | methods, calls, namespaces, tags, literals, data flows, graph algorithms                                           |\n| **rusi**  | Rust source                                                  | Declarations, imports, usages, call graph, data-flow slices, crypto, HTTP endpoints                                |\n| **golem** | Go source                                                    | Packages, declarations, usages, call graph, taint summaries, crypto, HTTP endpoints                                |\n| **dosai** | .NET (C#/VB/F#, assemblies)                                  | Methods, call graph, data-flow nodes/slices, weakness candidates, dangerous-API reachability, API endpoints        |\n| **blint** | ELF/PE/Mach-O/WASM binaries, Android APK/AAB, iOS IPA        | Binary metadata, hardening findings, capability reviews, symbols, strings, SBOM components, Android/iOS behaviours |\n\nThe right backend is selected automatically from the target: atom languages spawn the Scala engine; Rust, Go, and .NET resolve to their standalone analyzers; and a binary/APK/IPA file (detected by extension or magic bytes) routes to blint. Each backend exposes its own grounded tool set and system prompt to the agent.\n\n## Screencasts\n\n### Analysing cdxgen, a JavaScript project\n\n[![asciicast](https://asciinema.org/a/1D6OQ5rn5yRSN393.svg)](https://asciinema.org/a/1D6OQ5rn5yRSN393)\n\n### Analysing Android apks\n\n[![asciicast](https://asciinema.org/a/AjDLPEPUlnI3aCgN.svg)](https://asciinema.org/a/AjDLPEPUlnI3aCgN)\n\n## Use cases\n\n- Interactive exploration of atom files generated by the atom tool for languages such as JavaScript, Python, Java, Scala, PHP, Ruby, and C/C++. Open an atom, browse methods, calls, namespaces, tags, and literals without writing queries by hand.\n- Interactive exploration of Rust, Go, and .NET codebases using rusi, golem, and dosai analysis reports. Browse declarations, imports, usages, call graphs, data flows, API endpoints, and cryptographic evidence with dedicated per-language tools.\n- Binary, Android APK, and iOS IPA review with blint: inspect hardening findings, capability reviews, imported/exported symbols, SBOM components, and Android/iOS behavioural signals — treated as static evidence of presence, not proof of execution.\n- Data-flow analysis with source to sink tracing. The TUI displays flows with grouped paths, sub-flow toggling, and mitigation indicators.\n- Graph algorithm execution including PageRank, strongly connected components, topological sort, dominator trees, and interprocedural path finding.\n- AI-assisted vulnerability analysis with slash commands for security review, code review, explain, and trace. The agent routes tool calls through the underlying analysis engine and returns structured findings.\n- REPL-driven querying with tab completions, command history, and the full chen DSL available through the eval command (atom mode).\n\n## Requirements\n\n- For atom-based analysis: an atom file (from the atom tool) to open. The atom file is a Code Property Graph produced by running atom against a codebase.\n- For Rust and Go analysis: the `rusi` / `golem` binaries, bundled with cdxgen-plugins-bin or built from source. Override resolution with `RUSI_CMD` / `GOLEM_CMD`.\n- For .NET analysis: the `dosai` binary (use the **full** release). Override with `DOSAI_CMD`. The data-flow report is the primary source; the optional methods report is best-effort and will be skipped if dosai cannot load a project's assemblies.\n- For binary / APK / IPA analysis: `blint` on PATH (`uv tool install blint` or `pip install blint[extended]`), plus LLVM for disassembly and the Android SDK for full APK depth. Override with `BLINT_CMD`.\n- Java 23 or newer if running the engine via the JAR fallback distribution (atom mode only).\n- At least 4GB of available memory for the TUI and engine together. Larger codebases may need more. The non-atom backends (rusi, golem, dosai, blint) do not require the Scala engine.\n\n## Installation\n\n### Homebrew (macOS arm64, Linux amd64/arm64)\n\n```\nbrew tap appthreat/tap\nbrew trust --tap appthreat/tap   # only needed if HOMEBREW_REQUIRE_TAP_TRUST is set\nbrew install chennai\n```\n\n### npm (all platforms)\n\n```\nnpm install -g @appthreat/chennai\n```\n\n### Direct download (any platform)\n\nDownload the archive for your platform from the [releases page](https://github.com/AppThreat/chennai/releases), extract it, and add the `chennai` and `chennai-engine` binaries to your PATH:\n\n```bash\n# Example for macOS arm64\ncurl -sL https://github.com/AppThreat/chennai/releases/latest/download/chennai-darwin-arm64.tar.gz | tar xz\nsudo chmod +x chennai chennai-engine\nsudo cp chennai chennai-engine /usr/local/bin/\n```\n\nAfter installation the `chennai` command is available globally.\n\n```\nchennai [path-to-project-or-atom-file] [options]\n```\n\nThe path is optional; when omitted, chennai analyses the current working directory (resolved to an absolute path).\n\n### Container image\n\nA multi-arch (amd64/arm64) image is published to GitHub Container Registry. It bundles everything chennai needs across all modes -- the atom toolchains (Java, Scala, Node, PHP, Ruby), the Android SDK, the chennai engine and TUI, the standalone non-atom backends (`rusi`, `golem`, `dosai`), and `blint` (with LLVM) for binary / APK / IPA analysis. This is the simplest way to get every language and binary backend without installing toolchains locally.\n\n```bash\ndocker pull ghcr.io/appthreat/chennai:latest\n\n# Analyse the current directory (atom, Rust, Go, .NET, or a binary/APK/IPA).\ndocker run --rm -it \\\n  -e ANTHROPIC_API_KEY \\\n  -v \"$(pwd)\":/app:rw -w /app \\\n  ghcr.io/appthreat/chennai:latest /app\n```\n\nNotes:\n\n- Pass your LLM credentials through with `-e ANTHROPIC_API_KEY` (or `-e OPENAI_API_KEY` / `-e OPENAI_BASE_URL` for OpenAI-compatible providers).\n- Mount the project read-write (`-v \"$(pwd)\":/app:rw`) so generated reports (`rusi-report.json`, `golem-report.json`, dosai/blint outputs, the SBOM) are written back to the host.\n- For Android APK / iOS IPA analysis, mount the artifact and point chennai at the file: `-v \"$(pwd)/app.apk\":/app/app.apk ... /app/app.apk`.\n- The image tags follow the convention `:latest`, `:vX.Y.Z` (release tags), and per-arch `:<tag>-amd64` / `:<tag>-arm64` variants.\n\n### Standalone backend binaries\n\nIf you are not using the container image, install the non-atom backend binaries with the bundled script. It detects your OS/arch, downloads `rusi` + `golem` (from cdxgen-plugins-bin) and `dosai` (full build), and installs `blint` via uv/pip:\n\n```bash\n# Installs into $HOME/.local/bin (or /usr/local/bin with --system)\nbash scripts/setup.sh\n\n# Skip blint, or force re-download:\nbash scripts/setup.sh --no-blint\nbash scripts/setup.sh --force\n```\n\nBecause the binaries land on `PATH`, chennai resolves them automatically (the `RUSI_CMD` / `GOLEM_CMD` / `DOSAI_CMD` / `BLINT_CMD` env vars override the lookup). `blint` disassembly additionally needs LLVM, and APK/IPA depth needs the Android SDK -- the container image bundles both.\n\n## Subcommands\n\n### `setup`\n\nInstall or update the required analysis tools (cdxgen, atom, atom-parsetools) via npm:\n\n```\nchennai setup\n```\n\nThis runs `npm install -g --ignore-scripts @cyclonedx/cdxgen @appthreat/atom @appthreat/atom-parsetools`.\n\n### `dump-system-prompt`\n\nBuild and print the full system prompt that would be sent to the LLM agent as a markdown document. This command detects the project language and generates the appropriate prompt (atom-oriented or rusi-oriented). Optionally write it to a file with `-o`:\n\n```\n# Print to stdout (requires a project path for real analysis data)\nchennai dump-system-prompt /path/to/project\n\n# Write to a file\nchennai dump-system-prompt /path/to/project -o prompt.md\n\n# Template only (no project loaded -- shows placeholder values)\nchennai dump-system-prompt\n```\n\n### Tool discovery\n\nchennai auto-detects these tools in the following order:\n\n| Tool   | Env var      | Search path                                       |\n| ------ | ------------ | ------------------------------------------------- |\n| cdxgen | `CDXGEN_CMD` | PATH, node_modules/.bin/cdxgen, npm global        |\n| atom   | `ATOM_CMD`   | ATOM_CMD, PATH                                    |\n| rusi   | `RUSI_CMD`   | RUSI_CMD, PATH (bundled with cdxgen-plugins-bin)  |\n| golem  | `GOLEM_CMD`  | GOLEM_CMD, PATH (bundled with cdxgen-plugins-bin) |\n| dosai  | `DOSAI_CMD`  | DOSAI_CMD, PATH (bundled with cdxgen-plugins-bin) |\n| blint  | `BLINT_CMD`  | BLINT_CMD, PATH (uv venv path is preferred)       |\n| npm    |              | PATH                                              |\n\n### Analysis auto-generation\n\nWhen you point chennai at a project directory that has no pre-existing analysis, it detects the language and offers to generate the appropriate analysis:\n\n**Atom-based languages** (JavaScript, Python, Java, Scala, PHP, Ruby, C/C++):\n\n```\n$ chennai /path/to/project\nNo .atom file found in /path/to/project\nGenerate one for analysis?  This will:\n  1. Run cdxgen to produce a CycloneDX SBOM\n  2. Run atom --with-data-deps to build the atom file\n\nSource: /path/to/project [Y/n]\n```\n\nIf the tools are not installed but `npm` is available, chennai offers to install them automatically before proceeding.\n\n**Rust projects** (detected by `Cargo.toml`):\n\n```\n$ chennai /path/to/rust/project\nNo rusi analysis found. Run rusi to analyze this Rust codebase? [Y/n]\nRunning rusi analysis... done.\n```\n\nRusi analysis runs with the stable backend, static call graph, and security data-flow analysis. The resulting `rusi-report.json` is loaded and available for querying by the AI agent.\n\nIn headless mode (`--ask`), chennai runs the analysis automatically without prompting.\n\n### Software Bill of Materials\n\nchennai integrates with [cdxgen](https://github.com/AppThreat/cdxgen) to automatically generate and load CycloneDX SBOMs for deeper dependency-aware analysis. When you invoke chennai with a source or reports directory, it first looks for any existing `.cdx.json` files. If none are found, it invokes cdxgen to create a BOM with the naming convention `sbom-<language>-<lifecycle>.cdx.json`.\n\n#### Installing cdxgen\n\n```\nnpm install -g @cyclonedx/cdxgen\n```\n\ncdxgen will be auto-detected in PATH. You can also set the `CDXGEN_CMD` environment variable to point to a custom location. Once installed, chennai will automatically generate BOMs on startup when a source directory is available.\n\n### BOM commands\n\n| Command       | Description                                                    |\n| ------------- | -------------------------------------------------------------- |\n| `bom`         | Display all BOM components as a searchable, sortable table     |\n| `bom <query>` | Filter BOM components by name, type, version, PURL, or license |\n\nThe BOM data is also injected into AI agent prompts for security and code reviews, improving the LLM's understanding of third-party dependencies, their licenses, and known vulnerabilities.\n\n### Project facts memory\n\nchennai maintains a **per-project persistent memory** of durable facts (architecture,\nentrypoints, auth boundaries, confirmed/refuted findings, user corrections) under\n`<source_root>/.chen/facts-memory/`.\n\n- Each fact is a markdown file with YAML frontmatter, stored **locally only** and\n  **git-ignored** — facts are never committed or uploaded.\n- The AI agent automatically **saves** grounded facts (preferring callgraph/dataflow\n  results over text matches), loads the index into its system prompt every session,\n  and **recalls** full fact bodies on demand via the `project_memory` tool.\n- Use the `:memory` REPL command to inspect and manage stored facts:\n  `:memory list`, `:memory show <name>`, `:memory forget <name>`,\n  `:memory prune`, `:memory rebuild`.\n- Facts are auto-pruned at session start and after each save (de-duplication,\n  staleness demotion, eviction of low-priority facts when over budget).\n\n### Structured findings with verified proofs\n\nWhen the AI agent identifies a security weakness it records it as a **structured finding**\nrather than free-form prose, using the `report_finding` tool.\n\n- Each finding carries a source and sink location, a severity and confidence, an optional\n  CWE, the sanitizers that were checked, and a chen DSL **proof expression** that demonstrates\n  the untrusted-input-to-sink data flow.\n- The proof is **re-executed against the engine at submission time**. If the flow resolves to\n  one or more real paths the finding is marked verified and keeps its confidence; if it resolves\n  to zero paths the confidence is demoted to low, so an unproven claim is never reported as a\n  high-confidence result. Repeated submissions of the same proof reuse the first result.\n- In headless mode (`--ask`) the accumulated findings are deduplicated, ranked by severity and\n  confidence, and written to `report.md` and `report.json` in the reports directory. A one-line\n  token-usage and finding-count summary is printed when the run finishes.\n\n### Session working memory\n\nDuring a single analysis the agent keeps a **working note** — its confirmed findings, ruled-out\nleads, open questions, discovered entrypoints, and planned next steps — updated through the\n`process_note` tool.\n\n- The note is shown to the model on every turn, so it always sees its own progress and avoids\n  re-investigating a lead it has already dismissed.\n- Long conversations are **compacted automatically** once they grow past a soft budget: older\n  tool results are replaced by short summaries while recent exchanges and the working note are\n  kept in full, keeping token usage bounded on large codebases.\n- The working note and findings are saved under `<source_root>/.chen/agent-state/` (local only\n  and git-ignored) so an interrupted session can resume where it left off.\n\n### Orchestrated audits (`--orchestrate`)\n\nFor a broad audit, `--orchestrate` runs the agent as a coordinator that dispatches focused\n**sub-agents** instead of doing everything in one long conversation. Each sub-agent has a\nsingle job and a minimal toolset:\n\n- **recon** — maps entrypoints, frameworks, untrusted-input tags, and candidate sinks.\n- **sink-hunter** — locates dangerous sink call sites and proves reachability.\n- **taint-prover** — proves end-to-end source→sink data-flow paths.\n- **auth-boundary** — checks whether reachable sinks are guarded by auth/validation.\n- **supply-chain** — reviews dependencies for known-vulnerable or suspicious usage.\n- **reporter** — synthesizes the final report and records each confirmed finding.\n\nEach sub-agent runs in its own isolated conversation and returns only a short summary to the\ncoordinator, so the coordinator's context stays small even across a large audit. The sub-agents\nshare one findings pool and one working note, so results and ruled-out leads accumulate without\nduplicated effort. The role prompts live in `tui/agents/roles/`; drop a file with the same name\nunder `~/.config/chennai/agents/roles/` to override a role for your own workflow.\n\n```bash\nchennai app.atom --source ./app --orchestrate \\\n  --ask \"Audit for command injection and path traversal\"\n```\n\n**Cost and time visibility.** Each sub-agent is timed and its token use measured. During the\nrun you see a compact per-sub-agent line (`[profile] sink-hunter: 18.2k tok · 12 turns · 1m40s |\nrun total: …`), and at the end a per-role table with a reconciling total, written to\n`.chen/agent-state/profile.json`.\n\n**Budgets.** Every sub-agent has a per-role turn budget (a role can be cut off and re-spawned\nwith a narrower objective; its progress persists in the shared note). The whole run also has two\n*advisory* budgets — `--turn-budget` and `--token-budget` — that surface a warning to the\ncoordinator once exceeded but never block a spawn. The single hard stop is `--max-subagents`\n(default 8), which guarantees the run terminates.\n\nSet budgets too tight and you can starve the run: the reporter sub-agent, which crystallizes\nconfirmed vulnerabilities into the findings report, usually runs last, so an over-aggressive\n`--turn-budget` or a small `--max-subagents` may exhaust the allowance on recon and taint-proving\nand leave the reporter too little room to record anything. If a run ends with an empty findings\nreport despite the coordinator describing vulnerabilities, raise these limits (the defaults are\ntuned for a full audit) or spawn the reporter earlier.\n\n### Options\n\n| Option                 | Default               | Description                                                         |\n| ---------------------- | --------------------- | ------------------------------------------------------------------- |\n| `--engine PATH`        | auto                  | Path to the chennai-engine binary (atom mode only)                  |\n| `--theme dark/light`   | dark                  | Color theme                                                         |\n| `--source PATH`        | project dir           | Project source root for file resolution                             |\n| `--ask TEXT`           | --                    | Headless mode: ask a question and print the answer                  |\n| `--orchestrate`        | false                 | Coordinate focused sub-agents for a broad audit (see above)         |\n| `--max-subagents N`    | 8                     | Hard cap on sub-agents per orchestrated run (guarantees termination) |\n| `--turn-budget N`      | 80                    | Advisory total turn budget; warns the coordinator, never blocks     |\n| `--token-budget N`     | 1500000               | Advisory total token budget; warns the coordinator, never blocks    |\n| `--provider STR`       | anthropic             | LLM provider (anthropic or openai)                                  |\n| `--model STR`          | claude-opus-4-8       | LLM model name                                                      |\n| `--api-key STR`        | env var               | API key for the LLM provider                                        |\n| `--base-url STR`       | --                    | Custom API base URL for OpenAI-compatible endpoints                 |\n| `--reports-dir PATH`   | .chen/chennai-reports | Directory for markdown reports and BOM files                        |\n| `--system-prompt PATH` | --                    | Path to a custom system prompt file (overrides the built-in prompt) |\n| `--no-thinking`        | false                 | Omit thinking blocks from the LLM request                           |\n| `--effort STR`         | high                  | Reasoning effort (low, medium, high, xhigh, max)                    |\n\n### Environment variables\n\n- `CHENNAI_ENGINE`: Path to the engine binary. Overrides auto-detection.\n- `ANTHROPIC_API_KEY`: API key for Anthropic provider.\n- `ANTHROPIC_AUTH_TOKEN`: Alternate Anthropic key (as set by Claude Code and Anthropic-compatible gateways). Used when `ANTHROPIC_API_KEY` is unset.\n- `ANTHROPIC_BASE_URL`: Anthropic API base URL. Honored for the anthropic provider when `CHENNAI_BASE_URL` is unset.\n- `OPENAI_API_KEY`: API key for OpenAI-compatible providers.\n- `CHENNAI_PROVIDER`: LLM provider (`anthropic` or `openai`). Same as `--provider`.\n- `CHENNAI_MODEL`: LLM model name. Same as `--model`.\n- `CHENNAI_BASE_URL`: Custom API base URL for OpenAI-compatible endpoints. Same as `--base-url`.\n- `CHENNAI_MAX_SUBAGENTS`: Hard cap on sub-agents per orchestrated run. Same as `--max-subagents`.\n- `CHENNAI_TURN_BUDGET`: Advisory total turn budget. Same as `--turn-budget`.\n- `CHENNAI_TOKEN_BUDGET`: Advisory total token budget. Same as `--token-budget`.\n- `CDXGEN_CMD`: Path to the cdxgen binary.\n- `ATOM_CMD`: Path to the atom CLI binary (e.g. `/path/to/atom/atom.sh`).\n- `RUSI_CMD`: Path to the rusi binary. Overrides PATH lookup.\n- `CHENNAI_DEBUG`: Set to any value to enable resolver diagnostics.\n\n### Platform support\n\n| Platform | Architecture      | Engine        | TUI           |\n| -------- | ----------------- | ------------- | ------------- |\n| Linux    | x64 (glibc)       | native        | native        |\n| Linux    | arm64 (glibc)     | native        | native        |\n| Linux    | x64 (musl/Alpine) | native (musl) | native (musl) |\n| macOS    | Apple Silicon     | native        | native        |\n| Windows  | x64               | native        | native        |\n\nOther platforms fall back to the JAR distribution for the engine while the TUI runs natively where available. Rusi-based Rust analysis does not require the Scala engine.\n\n## Architecture\n\nchennai has two analysis paths depending on the project language.\n\n### Atom mode (JavaScript, Python, Java, Scala, PHP, Ruby, C/C++)\n\nTwo processes communicate over NDJSON on stdin/stdout.\n\n**Engine (chennai-engine):** The engine is a Scala 3 application built with the chen library. It reads atom files and runs queries against the atom file. It is distributed as a GraalVM native-image binary on supported platforms and as a JAR distribution elsewhere. The engine accepts NDJSON request lines on stdin and writes NDJSON response lines to stdout. Each request has an id, a command, and arguments. The engine opens an atom file on startup and keeps it in memory for the duration of the session.\n\n**TUI (chennai):** The TUI is a Rust application using ratatui and crossterm. It spawns the engine as a child process, opens the atom file, and presents a three-panel interface: a summary panel with row counts, a REPL panel for input, and an output panel for results. The TUI auto-detects the engine binary location -- by default it looks for chennai-engine in the same directory, then checks the standard development build paths.\n\n### Rust mode (rusi)\n\nFor Rust projects, chennai uses [rusi](https://github.com/AppThreat/rusi) (Rust Source Inspector) instead of the atom tool and the Scala engine. Rusi produces a structured JSON report containing declarations, imports, usages, security signals, call graph nodes and edges, data-flow slices, and cryptographic evidence. The TUI loads this report and provides a set of rusi-specific tools to the AI agent. No separate engine process is needed -- the analysis data lives in memory within the TUI process.\n\nThe agent has access to six rusi tools: `rusi_summary`, `rusi_query`, `rusi_callgraph`, `rusi_flows`, `rusi_detail`, and `rusi_crypto`. These tools provide the same kind of structured analysis as the atom tools but are backed by the rusi report instead of a Code Property Graph. The system prompt is adapted to describe rusi's data model and instruct the agent to use rusi tools for analysis.\n\n## User interface\n\nThe TUI has three panels navigated with Tab and Shift+Tab.\n\n### Summary panel\n\nIn atom mode, displays the atom summary: language, version, and row counts for files, methods, calls, literals, namespaces, annotations, config files, and dependencies. Pressing Enter on a row runs a query for that type and displays results in the output panel.\n\nIn Rust mode, the summary panel shows placeholder data since there is no engine. The AI agent is the primary interface for exploring the rusi analysis report.\n\n### REPL panel\n\nA command-line input at the bottom of the screen. Enter queries here to run them. The REPL supports:\n\n- Command labels: `files`, `methods`, `calls`, `external methods`, `internal methods`, `namespaces`, `annotations`, `imports`, `literals`, `config files`\n- DSL expressions: any chen DSL expression such as `atom.method.name(\".*Handler\")` (atom mode only)\n- Tag queries: `atom.tag.name(\"crypto.*\")` (atom mode only)\n- Flow presets: `dataflows`, `reachables`, `cryptos` (atom mode only)\n- Custom flow DSL: expressions containing `reachableByFlows` or `.df(` (atom mode only)\n- DSL prefix with `=`: forces raw eval mode (atom mode only)\n- BOM commands: `bom` or `bom <query>` for dependency display\n- Tool commands: `:<tool_name> key=value …` runs any agent tool directly (see [Running tools directly](#running-tools-directly-tool))\n- Natural language: any free text is routed to the AI agent when the agent is enabled\n\nTab completions are available with Ctrl+Space, including tool names and argument keys for `:tool` commands. Command history is accessible with Up and Down arrows.\n\nIn Rust mode, the agent is the recommended interaction method. The rusi tools (`rusi_summary`, `rusi_query`, `rusi_callgraph`, `rusi_flows`, `rusi_detail`, `rusi_crypto`, `rusi_endpoints`) are available to the agent for structured analysis, and can also be run directly from the REPL with `:rusi_*` (see [Running tools directly](#running-tools-directly-tool)).\n\n### Output panel\n\nDisplays query results. The output panel has several display modes:\n\n**Table view**: Query results are shown as a scrollable, sortable table. Columns are sorted by pressing 1 through 9. Filter rows with /. Press Enter to open a detail pane for a row. The detail pane shows node properties, a child table (arguments, parameters, locals), and source code side by side.\n\n**Flow view**: Data-flow paths are displayed as master-detail groups. Each group represents a source to sink path. Groups can be collapsed. Sub-flows are shown with `s` and mitigated flows (passing through sanitizers or validators) can be hidden with `m`.\n\n**Agent view**: The AI agent output is rendered as a streaming transcript with thinking blocks, tool calls, and results. Tools results that return flow data can be installed into the flow view for further exploration.\n\n### Keybindings\n\n| Key                          | Action                              |\n| ---------------------------- | ----------------------------------- |\n| q                            | Quit                                |\n| Tab / Shift+Tab              | Cycle panels forward/backward       |\n| Up/Down (or j/k)             | Navigate lists, scroll output       |\n| PageUp/PageDown (or b/Space) | Page through lists                  |\n| Enter                        | Open detail or execute command      |\n| /                            | Filter table in output panel        |\n| 1-9                          | Sort table by column                |\n| s                            | Toggle sub-flows in flow view       |\n| m                            | Toggle mitigated flows in flow view |\n| d / r                        | Run dataflows or reachables preset  |\n| Ctrl+S                       | Save report to markdown file        |\n\n## DSL queries and traversals (atom mode)\n\nThe full chen DSL is available through the eval command in atom mode. The reference documentation for all traversal steps and node types is maintained in the chen repository at `docs/TRAVERSAL.md`. The atom repository at `docs/lessons/` has nineteen lessons covering everything from frontend setup through data-flow analysis and graph algorithms.\n\nThe entry point for queries is `atom`, representing the root of the Code Property Graph. Common starters include `atom.file`, `atom.method`, `atom.call`, `atom.literal`, `atom.tag`, and `atom.namespace`. These can be chained with steps like `.name(\".*Handler\")`, `.isExternal(false)`, `.callee`, `.caller`, `.cfgNext`, `.dominatedBy`, and many others.\n\nFor type-based filtering the DSL provides `.isCall`, `.isLiteral`, `.isIdentifier`, `.isMethod`, `.isFile`, and similar predicates on any AST node.\n\n## Data-flow analysis\n\n### Atom mode\n\nchennai supports three flow presets accessible from the REPL or the summary panel:\n\n- `dataflows`: Runs reachableByFlows from framework-input tagged sources to framework-output tagged sinks.\n- `reachables`: Runs reachableByFlows using the default reachables configuration.\n- `cryptos`: Runs crypto-related data-flow analysis.\n\nCustom flow queries use the `reachableByFlows` or `df` steps. For example:\n\n```\natom.call.name(\".*execute.*\").reachableByFlows(atom.call.name(\".*getInput.*\"))\n```\n\nThe flow view groups results by source-sink pair, shows each step in the path, and indicates methods that have sanitization or validation tags. The engine supports two reaching-definitions solvers: the default Flux solver (low-allocation, fast on large methods) and a classic solver for comparison.\n\n### Rust mode (rusi)\n\nData-flow analysis in Rust mode is provided by rusi's security data-flow engine. The agent uses `rusi_flows` to query source-to-sink slices from the rusi report. Each slice carries a source name, sink name, source category, sink category, rule name, and path length. The agent can also use `rusi_callgraph` to trace call relationships and `rusi_query` to inspect declarations and usages around a flow.\n\n## Graph algorithms\n\n### Atom mode\n\nRun via the `algo` command in the engine. Available algorithms:\n\n- **PageRank** (`centrality`): Ranks methods by PageRank score and in-degree centrality on the call graph.\n- **Strongly connected components** (`scc`): Finds recursion clusters in the call graph.\n- **Topological sort** (`toposort`): Orders methods callee-before-caller, grouped by SCC.\n- **Dominator tree** (`dominators`): Computes immediate dominators per method over CFG edges.\n- **Interprocedural paths** (`paths`): Finds BFS-limited call paths between a source and target method.\n\n### Rust mode (rusi)\n\nRusi provides call graph analysis through the `rusi_callgraph` tool. The agent can query call graph nodes and edges by name pattern. The rusi report includes call graph mode, node metadata (name, qualified name, kind, file path, local/external status), and edge metadata (source, target, call type, position).\n\n## AI agent\n\nWhen an API key is configured (via environment variable or config file), the slash commands activate. These are entered in the REPL panel like any other command.\n\n### Slash commands\n\n| Command            | Purpose                                                                                                                                             |\n| ------------------ | --------------------------------------------------------------------------------------------------------------------------------------------------- |\n| `/security-review` | Reachability-grounded vulnerability analysis. Finds source-to-sink taint paths, ranks findings, and produces a markdown report. Uses `high` effort. |\n| `/code-review`     | Review code changes (diff or methods) for correctness and security. Uses `medium` effort.                                                           |\n| `/explain`         | Natural-language explanation of a method, data-flow, or code structure. Uses `medium` effort.                                                       |\n| `/trace`           | Prove or disprove a taint path between a given source and sink. Uses `high` effort.                                                                 |\n| `/help`            | List available slash commands.                                                                                                                      |\n\nFree text input (without a slash) is also routed to the agent for ad hoc questions.\n\n### Agent tools\n\nThe agent's available tools depend on the analysis mode. These are the same tools a human can run with `:tool` (see below).\n\n**Atom mode (19 tools):** atom_traversal_docs, atom_summary, atom_query, atom_dsl_eval, atom_flows, atom_flows_through, atom_callsites, atom_callgraph, atom_controlflow, atom_reaches, atom_detail, atom_algorithms, project_memory, bom_query, ripgrep, read_file, git_diff, git_log, git_show.\n\n**Rust/rusi mode (14 tools):** rusi_endpoints, rusi_summary, rusi_query, rusi_callgraph, rusi_flows, rusi_detail, rusi_crypto, project_memory, bom_query, ripgrep, read_file, git_diff, git_log, git_show.\n\n**Go/golem mode:** golem*summary, golem_query, golem_callgraph, golem_flows, golem_sources, golem_sinks, golem_endpoints, golem_crypto, golem_detail, plus the shared tools (project_memory, bom_query, ripgrep, read_file, git*\\*).\n\n**.NET/dosai mode:** dosai_summary, dosai_query, dosai_callgraph, dosai_flows, dosai_endpoints, dosai_trace, dosai_detail, plus the shared tools.\n\n**Binary/APK/IPA (blint):** blint_summary, blint_symbols, blint_strings, blint_capabilities, blint_behaviours, blint_findings, blint_components, blint_callgraph, blint_disassembly, plus the shared tools. When an atom is also present, blint tools are offered alongside the atom toolset.\n\n**Agent-only mode (for any target without structured analysis):** project_memory, bom_query, ripgrep, read_file, git_diff, git_log, git_show.\n\nThe agent uses the streaming API of the configured provider and renders thinking blocks, text deltas, and tool calls in real time. Tool results are truncated to 48 KiB to stay within model token limits. When the agent produces flow results they are automatically installed into the flow view for interactive exploration.\n\nAgent reports can be saved to markdown with Ctrl+S. Reports include the full transcript, token usage, and any generated data-flow paths or analysis results.\n\n### Running tools directly (`:tool`)\n\nEvery agent tool can also be run by hand from the REPL — no API key or LLM round-trip required — by typing a colon, the tool name, and `key=value` arguments. This works in every mode and uses the same tools the agent calls:\n\n```\n:atom_summary\n:atom_query kind=tags pattern=crypto.*\n:atom_callsites name=executeQuery\n:atom_reaches name=executeQuery sourceTags=framework-input,cli-source\n:bom_query query=log4j\n```\n\nArguments are parsed as `key=value` pairs; values that parse as integers or booleans are coerced (`limit=20`, `deep=true`), everything else is a string. For a value that contains spaces, pass a JSON object instead:\n\n```\n:atom_dsl_eval {\"expr\": \"atom.method.name(\\\".*Handler\\\").caller.toJson\"}\n```\n\nType `:` and press Ctrl+Space to autocomplete tool names; after a tool name and a space, Ctrl+Space completes that tool's argument keys. Only the tools for the current analysis mode are offered, so backend tools such as `:blint_strings`, `:rusi_flows`, `:golem_query`, and `:dosai_trace` appear automatically when their backend is loaded.\n\n#### Regex vs. substring matching\n\nThe **atom** traversal tools match with **anchored regex** on their `name`/`code`/`fullName` arguments — wrap partial matches in `.*`, and use `(?i)` for case-insensitivity:\n\n| Command                                                         | Meaning                                               |\n| --------------------------------------------------------------- | ----------------------------------------------------- |\n| `:atom_callsites name=system`                                   | call sites of a method named exactly `system`         |\n| `:atom_callsites name=(?i).*exec.*`                             | any call whose name contains `exec`, case-insensitive |\n| `:atom_callsites fullName=java\\.sql\\.Statement\\.execute.*`      | match on the fully-qualified callee                   |\n| `:atom_callgraph name=(?i).*handler.* direction=callers`        | methods that call any `*handler*` method              |\n| `:atom_controlflow code=.*executeQuery.* relation=controlledBy` | guards that must hold to reach an `executeQuery` call |\n| `:atom_reaches name=(?i).*(system\\|popen\\|exec)`                | prove untrusted input reaches an exec-like sink       |\n| `:atom_query kind=tags pattern=framework.*`                     | tags matching the regex `framework.*`                 |\n\nThe **backend** tools (`blint_*`, `rusi_*`, `golem_*`, `dosai_*`) instead filter with a **case-insensitive substring** `pattern` (not regex):\n\n| Command                                        | Meaning                                      |\n| ---------------------------------------------- | -------------------------------------------- |\n| `:blint_strings pattern=http`                  | strings containing `http`                    |\n| `:blint_symbols pattern=system`                | symbols whose name or type contains `system` |\n| `:rusi_query kind=usages pattern=Command::new` | Rust call usages mentioning `Command::new`   |\n| `:rusi_flows pattern=process-exec`             | rusi taint slices touching `process-exec`    |\n| `:golem_query kind=dataflow pattern=Getenv`    | Go data-flow entries mentioning `Getenv`     |\n| `:dosai_trace pattern=sql`                     | .NET taint slices touching `sql`             |\n\n### Offline operation\n\nThe agent is optional. When no API key is set, chennai operates as a fully offline code analysis tool with all query, data-flow, and algorithm features available through the REPL (atom mode) or through the agent-based interface (Rust mode). The slash commands and free-text agent features only activate when a provider is configured.\n\n## Configuration\n\nThe agent can be configured with a TOML file at `~/.config/chennai/config.toml`, environment variables, or CLI flags. CLI flags take precedence over environment variables, which take precedence over the config file.\n\nExample config file:\n\n```toml\nprovider = \"openai\"\nmodel = \"deepseek-chat\"\napi_key = \"sk-...\"\nbase_url = \"https://api.deepseek.com\"\neffort = \"high\"\n```\n\n## Developing\n\n### Prerequisites\n\n- Rust toolchain (edition 2024)\n- Scala 3.8.4 and sbt (for atom mode engine development)\n- GraalVM Community Edition 25 for native-image builds (optional for development)\n- Rusi binary (for Rust mode development, optional)\n\n### Build\n\n```\n# Engine (staged JAR distribution, atom mode only)\n(cd engine && sbt stage)\n\n# Engine native image (requires GraalVM, atom mode only)\nbash ci/native-image.sh\n\n# TUI (required for all modes)\n(cd tui && cargo build --release)\n\n# Rusi (for Rust mode development, optional)\n(cd /path/to/rusi && cargo build --release -p rusi-cli)\n```\n\n### Build all npm packages locally\n\n```\nbash wrapper/nodejs/scripts/build-local.sh\n```\n\n## Philosophy\n\n### Code analysis, not chat\n\nchennai was built on a simple conviction: an LLM that cannot _run code analysis_ is guessing. Most AI coding tools wrap a chat window around a vector index. They retrieve documentation, sprinkle in a few file contents, and hope the model's training prior is good enough. That works for boilerplate generation but fails for anything that requires precise answers about a real codebase -- reachability, data-flow paths, call graphs, dependency resolution.\n\nchennai is the opposite: the LLM is the _orchestrator_, not the oracle. The code analysis is done by real tools -- the chen DSL for graph traversals, the rusi analysis engine for Rust codebases, the data-flow engine for taint paths, graph algorithms for structural analysis, and ripgrep for source search. The agent's job is to decide _which_ tool to call and how to interpret the result, never to invent an answer from its training data.\n\n### Tools are first-class, not afterthoughts\n\nA typical AI coding tool has tools bolted on: \"search the codebase,\" \"read a file,\" maybe \"run a test.\" The tool list is an implementation detail the user never sees.\n\nIn chennai, the tools _are_ the interface. Every tool is a real analysis capability exposed directly in the TUI as well. Users can run `atom.method.name(\"auth\").callee.toJson` in the REPL (atom mode) or ask the agent to call `rusi_query` (Rust mode), see the exact same result the agent would get, and then ask the agent to explain it. The agent's tool calls are streamed to the transcript in real time -- users watch the agent think, pick tools, and interpret results. Nothing is hidden.\n\nThis design feeds both directions:\n\n- **User to Agent**: You can explore manually, then ask the agent to go deeper. The console history section of the system prompt means the agent knows what queries you already ran and what they returned, so follow-up questions have real context.\n- **Agent to User**: When the agent discovers something interesting, its tool results stay in the transcript. You can inspect the exact query that produced the finding.\n\n### The DSL is the interface (atom mode)\n\nThe chen DSL is a user-facing query language designed for interactive exploration. The agent uses it via `atom_dsl_eval`, and you use it directly in the REPL with the same syntax, the same semantics, and the same results.\n\nThis symmetry means the agent does not have a \"special\" way of querying the atom that is hidden from you. Every query the agent runs is one you could have typed yourself. There is no black box between the agent's reasoning and the actual code analysis -- the full traversal reference is available through `atom_traversal_docs`, and every tool result is visible.\n\n### The report is the interface (Rust mode)\n\nFor Rust codebases, the rusi analysis report plays the same role as the Code Property Graph in atom mode. The agent queries the report using rusi-specific tools, and the results are structured evidence that can be inspected and cross-referenced with source code. The report contains declarations, imports, usages, security signals, call graph data, data-flow slices, and crypto evidence -- all organized into queryable sections.\n\n### Grounding rules and the trust boundary\n\nThe system prompt's grounding rules are not decorative -- they are the contract that makes the tool-based architecture work:\n\n1. **Never invent call graphs, taints, or reachability.** Every claim must trace to a tool result.\n2. **Prefer structured evidence over source text search.** Traversals, report queries, and data-flow slices are structured evidence; text search is for cross-referencing.\n3. **If a tool returns nothing, state it plainly.** The agent must not dress up a grep-based guess as a real finding.\n4. **Concrete file:line references for every finding.** The user must be able to verify every claim.\n\nThese rules mean the agent operates within a strict trust boundary. It is authorized to analyze the user's own code -- it does not need to be \"harmless\" or refuse to look at code. The tool results are the single source of truth, and the agent is explicitly directed to refuse to answer based on its training prior alone.\n\n### Offline-first, agent-optional\n\nThe agent is a feature of chennai, not the product. Every analysis capability -- queries, data-flows, algorithms, graph traversals -- works offline with no API key, no network, and no LLM. In atom mode, the TUI is a fully functional static analysis environment by itself. In Rust mode, the rusi report is loaded and available for agent-driven analysis. The agent layer adds natural-language orchestration on top, but it is strictly additive.\n\nThis means you can:\n\n- Explore code with the REPL during development (atom mode)\n- Run rusi analysis on Rust codebases for structured insights\n- Save queries as reproducible analysis steps\n- Run the agent only when you need natural-language reasoning about what you found\n\nThe architecture ensures that the agent's value is proportional to the quality of the underlying analysis tools, not the size of the LLM's context window or training corpus.\n\n## License\n\nMIT\n","readmeFilename":"README.md"}