@renxqoo/renx-code-linux-x64 0.0.61

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/README.md ADDED
@@ -0,0 +1,108 @@
1
+ # @renxqoo/renx-code
2
+
3
+ Renx Code terminal AI coding assistant for the command line.
4
+
5
+ ## Install
6
+
7
+ ```bash
8
+ npm install -g @renxqoo/renx-code
9
+ ```
10
+
11
+ ## Usage
12
+
13
+ ```bash
14
+ renx
15
+ renx --help
16
+ renx --version
17
+ ```
18
+
19
+ ## Supported Platforms
20
+
21
+ - macOS arm64
22
+ - macOS x64
23
+ - Linux arm64
24
+ - Linux x64
25
+ - Windows x64
26
+
27
+ Windows arm64 is not bundled yet because the current Bun compiler target matrix does not provide a native `bun-windows-arm64` executable target.
28
+
29
+ ## Runtime Cache
30
+
31
+ The launcher copies installed native binaries into a user-scoped cache before execution. This keeps active Windows processes from locking files inside `node_modules` during upgrades.
32
+
33
+ - Default cache path on Windows: `%LOCALAPPDATA%\Renx\binary-cache`
34
+ - Override cache path: `RENX_BINARY_CACHE_DIR`
35
+ - Disable the cache for debugging: `RENX_DISABLE_BINARY_CACHE=1`
36
+
37
+ ## Release
38
+
39
+ ### GitHub Actions workflow
40
+
41
+ Use the manual GitHub Actions workflow at `.github/workflows/cli-release.yml`.
42
+
43
+ - Workflow name: `CLI Release`
44
+ - Trigger: `workflow_dispatch`
45
+ - Inputs:
46
+ - `npm_tag`: optional npm dist-tag. Leave empty to publish with the default npm tag.
47
+ - `otp`: optional one-time password for npm publish when your npm setup requires it.
48
+
49
+ The workflow publishes platform packages first, then publishes the main package only after all platform publishes succeed.
50
+
51
+ ### Required secrets and permissions
52
+
53
+ Configure these before running the workflow:
54
+
55
+ - `NPM_TOKEN`: required. The workflow exposes it as `NODE_AUTH_TOKEN` for npm publish.
56
+ - npm package publish permission for `@renxqoo/renx-code` and the platform packages under the same scope.
57
+ - If your npm publish flow requires OTP, provide it through the `otp` workflow input when triggering the run.
58
+
59
+ ### First release recommendation
60
+
61
+ For the first public release of a new version, prefer this sequence:
62
+
63
+ 1. Run the workflow with `npm_tag=next`.
64
+ 2. Verify install and execution from the published `next` tag on the platforms you care about.
65
+ 3. Run the workflow again with an empty `npm_tag` value to publish to the default tag, or set `npm_tag=latest` explicitly if you want to be explicit.
66
+
67
+ This reduces the chance of breaking users on `latest` before the new platform packages are validated.
68
+
69
+ ### Dist-tag usage
70
+
71
+ - Stable release: leave `npm_tag` empty, or set `npm_tag=latest`.
72
+ - Preview / canary release: set `npm_tag=next`.
73
+
74
+ Example installs:
75
+
76
+ ```bash
77
+ npm install -g @renxqoo/renx-code@latest
78
+ npm install -g @renxqoo/renx-code@next
79
+ ```
80
+
81
+ ### Local verification commands
82
+
83
+ Before triggering the publish workflow, these local commands are useful:
84
+
85
+ ```bash
86
+ pnpm --filter @renxqoo/renx-code release:pack -- --single --dry-run
87
+ pnpm --filter @renxqoo/renx-code release:pack -- --target darwin-arm64 --dry-run
88
+ pnpm --filter @renxqoo/renx-code release:pack -- --target darwin-x64 --dry-run
89
+ pnpm --filter @renxqoo/renx-code release:pack -- --target linux-arm64 --dry-run
90
+ pnpm --filter @renxqoo/renx-code release:pack -- --target linux-x64 --dry-run
91
+ pnpm --filter @renxqoo/renx-code release:pack -- --target win32-x64 --dry-run
92
+ pnpm --filter @renxqoo/renx-code release:pack -- --all --dry-run
93
+ ```
94
+
95
+ For local npm authentication checks, run:
96
+
97
+ ```bash
98
+ pnpm --filter @renxqoo/renx-code release:preflight
99
+ ```
100
+
101
+ ### Local manual publish
102
+
103
+ If you need to publish outside GitHub Actions, use the same unified script entrypoints:
104
+
105
+ ```bash
106
+ pnpm --filter @renxqoo/renx-code release:publish -- --target darwin-arm64 --tag next
107
+ pnpm --filter @renxqoo/renx-code release:publish -- --single --tag next
108
+ ```
package/bin/renx ADDED
Binary file
package/bin/rg ADDED
@@ -0,0 +1,79 @@
1
+ #!/usr/bin/env dotslash
2
+
3
+ {
4
+ "name": "rg",
5
+ "platforms": {
6
+ "macos-aarch64": {
7
+ "size": 1777930,
8
+ "hash": "sha256",
9
+ "digest": "378e973289176ca0c6054054ee7f631a065874a352bf43f0fa60ef079b6ba715",
10
+ "format": "tar.gz",
11
+ "path": "ripgrep-15.1.0-aarch64-apple-darwin/rg",
12
+ "providers": [
13
+ {
14
+ "url": "https://github.com/BurntSushi/ripgrep/releases/download/15.1.0/ripgrep-15.1.0-aarch64-apple-darwin.tar.gz"
15
+ }
16
+ ]
17
+ },
18
+ "linux-aarch64": {
19
+ "size": 1869959,
20
+ "hash": "sha256",
21
+ "digest": "2b661c6ef508e902f388e9098d9c4c5aca72c87b55922d94abdba830b4dc885e",
22
+ "format": "tar.gz",
23
+ "path": "ripgrep-15.1.0-aarch64-unknown-linux-gnu/rg",
24
+ "providers": [
25
+ {
26
+ "url": "https://github.com/BurntSushi/ripgrep/releases/download/15.1.0/ripgrep-15.1.0-aarch64-unknown-linux-gnu.tar.gz"
27
+ }
28
+ ]
29
+ },
30
+ "macos-x86_64": {
31
+ "size": 1894127,
32
+ "hash": "sha256",
33
+ "digest": "64811cb24e77cac3057d6c40b63ac9becf9082eedd54ca411b475b755d334882",
34
+ "format": "tar.gz",
35
+ "path": "ripgrep-15.1.0-x86_64-apple-darwin/rg",
36
+ "providers": [
37
+ {
38
+ "url": "https://github.com/BurntSushi/ripgrep/releases/download/15.1.0/ripgrep-15.1.0-x86_64-apple-darwin.tar.gz"
39
+ }
40
+ ]
41
+ },
42
+ "linux-x86_64": {
43
+ "size": 2263077,
44
+ "hash": "sha256",
45
+ "digest": "1c9297be4a084eea7ecaedf93eb03d058d6faae29bbc57ecdaf5063921491599",
46
+ "format": "tar.gz",
47
+ "path": "ripgrep-15.1.0-x86_64-unknown-linux-musl/rg",
48
+ "providers": [
49
+ {
50
+ "url": "https://github.com/BurntSushi/ripgrep/releases/download/15.1.0/ripgrep-15.1.0-x86_64-unknown-linux-musl.tar.gz"
51
+ }
52
+ ]
53
+ },
54
+ "windows-x86_64": {
55
+ "size": 1810687,
56
+ "hash": "sha256",
57
+ "digest": "124510b94b6baa3380d051fdf4650eaa80a302c876d611e9dba0b2e18d87493a",
58
+ "format": "zip",
59
+ "path": "ripgrep-15.1.0-x86_64-pc-windows-msvc/rg.exe",
60
+ "providers": [
61
+ {
62
+ "url": "https://github.com/BurntSushi/ripgrep/releases/download/15.1.0/ripgrep-15.1.0-x86_64-pc-windows-msvc.zip"
63
+ }
64
+ ]
65
+ },
66
+ "windows-aarch64": {
67
+ "size": 1675460,
68
+ "hash": "sha256",
69
+ "digest": "00d931fb5237c9696ca49308818edb76d8eb6fc132761cb2a1bd616b2df02f8e",
70
+ "format": "zip",
71
+ "path": "ripgrep-15.1.0-aarch64-pc-windows-msvc/rg.exe",
72
+ "providers": [
73
+ {
74
+ "url": "https://github.com/BurntSushi/ripgrep/releases/download/15.1.0/ripgrep-15.1.0-aarch64-pc-windows-msvc.zip"
75
+ }
76
+ ]
77
+ }
78
+ }
79
+ }
package/package.json ADDED
@@ -0,0 +1,27 @@
1
+ {
2
+ "name": "@renxqoo/renx-code-linux-x64",
3
+ "version": "0.0.61",
4
+ "description": "Renx Code terminal AI coding assistant (linux-x64)",
5
+ "type": "commonjs",
6
+ "private": false,
7
+ "os": [
8
+ "linux"
9
+ ],
10
+ "cpu": [
11
+ "x64"
12
+ ],
13
+ "bin": {
14
+ "renx": "./bin/renx"
15
+ },
16
+ "files": [
17
+ "bin",
18
+ "scripts",
19
+ "README.md"
20
+ ],
21
+ "scripts": {
22
+ "postinstall": "node ./scripts/install-ripgrep.mjs"
23
+ },
24
+ "engines": {
25
+ "node": ">=20.0.0"
26
+ }
27
+ }
@@ -0,0 +1,195 @@
1
+ #!/usr/bin/env node
2
+
3
+ import { spawnSync } from 'node:child_process';
4
+ import { createHash } from 'node:crypto';
5
+ import { createWriteStream } from 'node:fs';
6
+ import fs from 'node:fs/promises';
7
+ import https from 'node:https';
8
+ import os from 'node:os';
9
+ import path from 'node:path';
10
+ import { fileURLToPath } from 'node:url';
11
+
12
+ const __filename = fileURLToPath(import.meta.url);
13
+ const __dirname = path.dirname(__filename);
14
+ const packageRoot = path.resolve(__dirname, '..');
15
+ const manifestPath = path.join(packageRoot, 'bin', 'rg');
16
+
17
+ const TARGETS = {
18
+ 'darwin:arm64': { target: 'aarch64-apple-darwin', platformKey: 'macos-aarch64' },
19
+ 'darwin:x64': { target: 'x86_64-apple-darwin', platformKey: 'macos-x86_64' },
20
+ 'linux:arm64': { target: 'aarch64-unknown-linux-musl', platformKey: 'linux-aarch64' },
21
+ 'linux:x64': { target: 'x86_64-unknown-linux-musl', platformKey: 'linux-x86_64' },
22
+ 'win32:arm64': { target: 'aarch64-pc-windows-msvc', platformKey: 'windows-aarch64' },
23
+ 'win32:x64': { target: 'x86_64-pc-windows-msvc', platformKey: 'windows-x86_64' },
24
+ };
25
+
26
+ async function main() {
27
+ if (process.env.RENX_SKIP_RIPGREP_INSTALL === '1') {
28
+ console.log('[renx] skipping bundled ripgrep install (RENX_SKIP_RIPGREP_INSTALL=1)');
29
+ return;
30
+ }
31
+
32
+ const targetInfo = TARGETS[`${process.platform}:${process.arch}`];
33
+ if (!targetInfo) {
34
+ console.warn(
35
+ `[renx] no bundled ripgrep target for ${process.platform}/${process.arch}; falling back to system rg if available`
36
+ );
37
+ return;
38
+ }
39
+
40
+ const manifest = await loadManifest(manifestPath);
41
+ const platformInfo = manifest.platforms?.[targetInfo.platformKey];
42
+ if (!platformInfo) {
43
+ throw new Error(`ripgrep manifest is missing platform ${targetInfo.platformKey}`);
44
+ }
45
+
46
+ const binaryName = process.platform === 'win32' ? 'rg.exe' : 'rg';
47
+ const installDir = path.join(packageRoot, 'vendor', 'ripgrep', targetInfo.target, 'path');
48
+ const binaryPath = path.join(installDir, binaryName);
49
+ if (await fileExists(binaryPath)) {
50
+ return;
51
+ }
52
+
53
+ await fs.mkdir(installDir, { recursive: true });
54
+
55
+ const provider = platformInfo.providers?.[0];
56
+ const url = provider?.url;
57
+ if (!url) {
58
+ throw new Error(`ripgrep manifest has no provider URL for ${targetInfo.platformKey}`);
59
+ }
60
+
61
+ const tempDir = await fs.mkdtemp(path.join(os.tmpdir(), 'renx-ripgrep-'));
62
+ try {
63
+ const archivePath = path.join(tempDir, path.basename(new URL(url).pathname));
64
+ console.log(`[renx] downloading ripgrep for ${targetInfo.target}`);
65
+ await downloadFile(url, archivePath);
66
+ await verifyArchive(archivePath, platformInfo);
67
+
68
+ const extractDir = path.join(tempDir, 'extract');
69
+ await fs.mkdir(extractDir, { recursive: true });
70
+ await extractArchive(archivePath, platformInfo.format, extractDir);
71
+
72
+ const memberPath = path.join(extractDir, platformInfo.path);
73
+ await fs.copyFile(memberPath, binaryPath);
74
+ if (process.platform !== 'win32') {
75
+ await fs.chmod(binaryPath, 0o755);
76
+ }
77
+ console.log(`[renx] installed bundled ripgrep to ${binaryPath}`);
78
+ } finally {
79
+ await fs.rm(tempDir, { recursive: true, force: true });
80
+ }
81
+ }
82
+
83
+ async function loadManifest(filePath) {
84
+ const raw = await fs.readFile(filePath, 'utf8');
85
+ const json = raw.startsWith('#!') ? raw.split('\n').slice(1).join('\n') : raw;
86
+ return JSON.parse(json);
87
+ }
88
+
89
+ async function fileExists(filePath) {
90
+ try {
91
+ await fs.access(filePath);
92
+ return true;
93
+ } catch {
94
+ return false;
95
+ }
96
+ }
97
+
98
+ async function downloadFile(url, destination) {
99
+ await new Promise((resolve, reject) => {
100
+ const request = https.get(url, (response) => {
101
+ if (
102
+ response.statusCode &&
103
+ response.statusCode >= 300 &&
104
+ response.statusCode < 400 &&
105
+ response.headers.location
106
+ ) {
107
+ response.resume();
108
+ downloadFile(response.headers.location, destination).then(resolve, reject);
109
+ return;
110
+ }
111
+
112
+ if (response.statusCode !== 200) {
113
+ reject(new Error(`download failed with status ${response.statusCode ?? 'unknown'}`));
114
+ return;
115
+ }
116
+
117
+ const output = createWriteStream(destination);
118
+ response.pipe(output);
119
+ output.on('finish', () => {
120
+ output.close();
121
+ resolve(undefined);
122
+ });
123
+ output.on('error', reject);
124
+ });
125
+ request.on('error', reject);
126
+ });
127
+ }
128
+
129
+ async function verifyArchive(archivePath, platformInfo) {
130
+ const stats = await fs.stat(archivePath);
131
+ if (typeof platformInfo.size === 'number' && stats.size !== platformInfo.size) {
132
+ throw new Error(
133
+ `unexpected ripgrep archive size: expected ${platformInfo.size}, got ${stats.size}`
134
+ );
135
+ }
136
+
137
+ if (platformInfo.hash === 'sha256' && platformInfo.digest) {
138
+ const file = await fs.readFile(archivePath);
139
+ const digest = createHash('sha256').update(file).digest('hex');
140
+ if (digest !== platformInfo.digest) {
141
+ throw new Error('ripgrep archive sha256 digest mismatch');
142
+ }
143
+ }
144
+ }
145
+
146
+ async function extractArchive(archivePath, format, destination) {
147
+ if (format === 'zip') {
148
+ const command = resolvePowerShellExecutable();
149
+ const result = spawnSync(
150
+ command,
151
+ [
152
+ '-NoProfile',
153
+ '-Command',
154
+ `Expand-Archive -LiteralPath '${escapePowerShell(archivePath)}' -DestinationPath '${escapePowerShell(destination)}' -Force`,
155
+ ],
156
+ {
157
+ stdio: 'inherit',
158
+ windowsHide: true,
159
+ }
160
+ );
161
+ if (result.error || result.status !== 0) {
162
+ throw new Error('failed to extract ripgrep zip archive');
163
+ }
164
+ return;
165
+ }
166
+
167
+ if (format === 'tar.gz') {
168
+ const result = spawnSync('tar', ['-xzf', archivePath, '-C', destination], {
169
+ stdio: 'inherit',
170
+ windowsHide: true,
171
+ });
172
+ if (result.error || result.status !== 0) {
173
+ throw new Error('failed to extract ripgrep tar.gz archive');
174
+ }
175
+ return;
176
+ }
177
+
178
+ throw new Error(`unsupported ripgrep archive format: ${format}`);
179
+ }
180
+
181
+ function resolvePowerShellExecutable() {
182
+ return process.env.SystemRoot
183
+ ? path.join(process.env.SystemRoot, 'System32', 'WindowsPowerShell', 'v1.0', 'powershell.exe')
184
+ : 'powershell.exe';
185
+ }
186
+
187
+ function escapePowerShell(value) {
188
+ return value.replace(/'/g, "''");
189
+ }
190
+
191
+ main().catch((error) => {
192
+ console.warn(
193
+ `[renx] bundled ripgrep install skipped: ${error instanceof Error ? error.message : String(error)}`
194
+ );
195
+ });