Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions .claude/skills/bump-coana/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,13 @@ fi
2. Find the line `const COANA_CLI_VERSION = '<version>'` and note the version as `CURRENT_VERSION`.
3. Replace the version on that line with the new one.

Socket CLI downloads that version through the Socket API, so it has to be a
release Coana published to its GCS bucket, not one that only exists on npm.

Don't edit `src/vendor/coana-cache.mjs`. It is generated in
coana-package-manager, and Coana's release workflow refreshes it in its own bump
PRs.

🚨 **Do NOT touch `package.json`'s top-level `version` field.** The release workflow owns it:
between releases the manifest holds the last released version, and
`scripts/release/bump.mts` derives and writes the next one in-run. Hand-writing
Expand Down
9 changes: 9 additions & 0 deletions .config/rollup.dist.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,14 @@ function relativeBlessedPath(filepath) {
)
}

// The cache script vendored from coana-package-manager, which coana-release.mts
// runs with `node`.
async function copyCoanaCache() {
const filepath = path.join(constants.srcPath, 'vendor/coana-cache.mjs')
const destPath = path.join(constants.distPath, 'coana-cache.mjs')
await fs.copyFile(filepath, destPath)
}

async function copyInitGradle() {
const filepath = path.join(constants.srcPath, 'commands/manifest/init.gradle')
const destPath = path.join(constants.distPath, 'init.gradle')
Expand Down Expand Up @@ -534,6 +542,7 @@ export default async () => {
{
async writeBundle() {
await Promise.all([
copyCoanaCache(),
copyInitGradle(),
copyManifestScripts(),
copyBashCompletion(),
Expand Down
1 change: 1 addition & 0 deletions .oxlintignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
package-lock.json
.claude/worktrees/
.pnpm-store/
src/vendor/coana-cache.mjs
8 changes: 8 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,14 @@ All notable changes to this project will be documented in this file.

The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/).

## [Unreleased]

### Changed
- The Coana CLI is now downloaded from Socket's servers instead of npm, and is now cached in `$XDG_CACHE_HOME/socket/coana` (`~/.cache/socket/coana` by default).

### Removed
- The `SOCKET_CLI_COANA_LAUNCHER` environment variable no longer has an effect.

## [1.8.4](https://github.com/SocketDev/socket-cli/releases/tag/v1.8.4) - 2026-10-16

### Changed
Expand Down
1 change: 0 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,6 @@ npm exec socket
- `SOCKET_CLI_API_BASE_URL` - API base URL (default: `https://api.socket.dev/v0/`)
- `SOCKET_CLI_API_PROXY` - Proxy for API requests (aliases: `HTTPS_PROXY`, `https_proxy`, `HTTP_PROXY`, `http_proxy`)
- `SOCKET_CLI_API_TIMEOUT` - API request timeout in milliseconds
- `SOCKET_CLI_COANA_LAUNCHER` - How the reachability engine (`@coana-tech/cli`) is launched: `auto` (default; try `npx`, fall back to `npm install` + `node` if the launcher fails), `npx` (never fall back), or `npm-install` (skip `npx` entirely)
- `SOCKET_CLI_DEBUG` - Enable debug logging
- `DEBUG` - Enable [`debug`](https://socket.dev/npm/package/debug) package logging

Expand Down
1 change: 1 addition & 0 deletions biome.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
"!**/.vscode",
"!.claude/worktrees",
"!**/coverage",
"!src/vendor/coana-cache.mjs",
"!**/package.json",
"!**/package-lock.json"
],
Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -189,6 +189,7 @@
"rollup": "4.50.1",
"semver": "7.7.2",
"synp": "1.9.14",
"tar": "7.5.16",
"taze": "19.6.0",
"terminal-link": "2.1.1",
"tiny-updater": "3.5.3",
Expand Down
17 changes: 10 additions & 7 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

16 changes: 8 additions & 8 deletions src/commands/fix/coana-fix-dynamic-sbom-inference.test.mts
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import { coanaFix } from './coana-fix.mts'

import type { FixConfig } from './types.mts'

const mockSpawnCoanaDlx = vi.hoisted(() => vi.fn())
const mockSpawnCoana = vi.hoisted(() => vi.fn())
const mockSetupSdk = vi.hoisted(() => vi.fn())
const mockFetchSupportedScanFileNames = vi.hoisted(() => vi.fn())
const mockGetPackageFilesForScan = vi.hoisted(() => vi.fn())
Expand All @@ -23,8 +23,8 @@ const mockGitUntrackedFiles = vi.hoisted(() =>
const mockGitCommit = vi.hoisted(() => vi.fn())
const mockGenerateSocketFactsForFix = vi.hoisted(() => vi.fn())

vi.mock('../../utils/dlx.mts', () => ({
spawnCoanaDlx: mockSpawnCoanaDlx,
vi.mock('../../utils/coana-release.mts', () => ({
spawnCoana: mockSpawnCoana,
}))

vi.mock('../../utils/sdk.mts', () => ({
Expand Down Expand Up @@ -86,7 +86,7 @@ vi.mock('./branch-cleanup.mts', () => ({
const FACTS = '/test/cwd/app/gradle.socket.facts.json'

function coanaCalls(command: string): string[][] {
return mockSpawnCoanaDlx.mock.calls
return mockSpawnCoana.mock.calls
.map(call => call[0] as string[])
.filter(args => args[0] === command)
}
Expand Down Expand Up @@ -139,7 +139,7 @@ describe('socket fix --dynamic-sbom-inference', () => {
mockGetFixEnv.mockResolvedValue({ isCi: false, repoInfo: null })
mockGitUnstagedModifiedFiles.mockResolvedValue({ ok: true, data: [] })
mockGitCommit.mockResolvedValue(true)
mockSpawnCoanaDlx.mockResolvedValue({ ok: true, data: '' })
mockSpawnCoana.mockResolvedValue({ ok: true, data: '' })
})

it('uploads the generated facts, restricts Maven artifacts to them and removes them', async () => {
Expand All @@ -161,7 +161,7 @@ describe('socket fix --dynamic-sbom-inference', () => {
})

it('discovers vulnerabilities only through the generated facts', async () => {
mockSpawnCoanaDlx.mockImplementation(async (args: string[]) => {
mockSpawnCoana.mockImplementation(async (args: string[]) => {
if (args[0] === 'find-vulnerabilities') {
await fs.writeFile(
args[args.indexOf('--output-file') + 1]!,
Expand Down Expand Up @@ -249,7 +249,7 @@ describe('socket fix --dynamic-sbom-inference', () => {
})

it('commits the files the fix reports writing', async () => {
mockSpawnCoanaDlx.mockImplementation(async (args: string[]) => {
mockSpawnCoana.mockImplementation(async (args: string[]) => {
await fs.writeFile(
args[args.indexOf('--output-file') + 1]!,
JSON.stringify({
Expand All @@ -275,7 +275,7 @@ describe('socket fix --dynamic-sbom-inference', () => {
})

it('commits files the fix creates', async () => {
mockSpawnCoanaDlx.mockImplementation(async (args: string[]) => {
mockSpawnCoana.mockImplementation(async (args: string[]) => {
await fs.writeFile(
args[args.indexOf('--output-file') + 1]!,
JSON.stringify({
Expand Down
8 changes: 4 additions & 4 deletions src/commands/fix/coana-fix-pr-files.test.mts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import { coanaFix } from './coana-fix.mts'

import type { FixConfig } from './types.mts'

const mockSpawnCoanaDlx = vi.hoisted(() => vi.fn())
const mockSpawnCoana = vi.hoisted(() => vi.fn())
const mockSetupSdk = vi.hoisted(() => vi.fn())
const mockFetchSupportedScanFileNames = vi.hoisted(() => vi.fn())
const mockGetPackageFilesForScan = vi.hoisted(() => vi.fn())
Expand All @@ -18,8 +18,8 @@ const mockGitUnstagedModifiedFiles = vi.hoisted(() => vi.fn())
const mockGitUntrackedFiles = vi.hoisted(() => vi.fn())
const mockGitCommit = vi.hoisted(() => vi.fn())

vi.mock('../../utils/dlx.mts', () => ({
spawnCoanaDlx: mockSpawnCoanaDlx,
vi.mock('../../utils/coana-release.mts', () => ({
spawnCoana: mockSpawnCoana,
}))

vi.mock('../../utils/sdk.mts', () => ({
Expand Down Expand Up @@ -117,7 +117,7 @@ describe('socket fix PR mode commits', () => {
changes: Worktree,
modifiedFiles: string[] | undefined,
): void {
mockSpawnCoanaDlx.mockImplementation(async (args: string[]) => {
mockSpawnCoana.mockImplementation(async (args: string[]) => {
worktree = {
modified: [...new Set([...worktree.modified, ...changes.modified])],
untracked: [...new Set([...worktree.untracked, ...changes.untracked])],
Expand Down
10 changes: 5 additions & 5 deletions src/commands/fix/coana-fix.mts
Original file line number Diff line number Diff line change
Expand Up @@ -28,12 +28,12 @@ import {
GQL_PR_STATE_OPEN,
} from '../../constants.mts'
import { handleApiCall } from '../../utils/api.mts'
import { spawnCoana } from '../../utils/coana-release.mts'
import {
isReachabilityReportPath,
isSocketFactsFile,
} from '../../utils/coana.mts'
import { findSocketYmlSync } from '../../utils/config.mts'
import { spawnCoanaDlx } from '../../utils/dlx.mts'
import { getErrorCause } from '../../utils/errors.mts'
import { withTmpDir } from '../../utils/fs.mts'
import {
Expand Down Expand Up @@ -163,7 +163,7 @@ async function discoverGhsaIds(
`socket-fix-discovery-${Date.now()}.json`,
)

const foundCResult = await spawnCoanaDlx(
const foundCResult = await spawnCoana(
[
'find-vulnerabilities',
cwd,
Expand All @@ -182,8 +182,8 @@ async function discoverGhsaIds(
cwd,
spinner: silence ? undefined : spinner,
coanaVersion: options?.coanaVersion,
stdio: 'pipe',
},
{ stdio: 'pipe' },
)

if (!foundCResult.ok) {
Expand Down Expand Up @@ -512,7 +512,7 @@ async function coanaFixWithFacts(
const tmpFile = path.join(tmpDir, `socket-fix-${Date.now()}.json`)

try {
const fixCResult = await spawnCoanaDlx(
const fixCResult = await spawnCoana(
[
'compute-fixes-and-upgrade-purls',
cwd,
Expand Down Expand Up @@ -705,7 +705,7 @@ async function coanaFixWithFacts(

// Apply fix for single GHSA ID.
// eslint-disable-next-line no-await-in-loop
const fixCResult = await spawnCoanaDlx(
const fixCResult = await spawnCoana(
[
'compute-fixes-and-upgrade-purls',
cwd,
Expand Down
Loading
Loading