@youcan/cli-kit 2.4.1 → 2.4.3

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.
@@ -29,6 +29,7 @@ export declare function archived(path: string, name: string, glob?: string): Pro
29
29
  export declare function unlink(path: string): Promise<void>;
30
30
  export declare function readdir(path: string): Promise<string[]>;
31
31
  export declare function stat(path: string): Promise<Stats>;
32
+ export declare function chmod(path: string, mode: number): Promise<void>;
32
33
  export declare const watch: typeof import("chokidar").watch;
33
34
  export declare function decompressGzip(file: string, destination: string, mode?: number): Promise<void>;
34
35
  export declare function extractTar(file: string, cwd: string, mode: number): Promise<void>;
@@ -121,6 +121,9 @@ async function readdir(path) {
121
121
  async function stat(path) {
122
122
  return await FilesystemPromises.stat(path);
123
123
  }
124
+ async function chmod(path, mode) {
125
+ return await FilesystemPromises.chmod(path, mode);
126
+ }
124
127
  const watch = chokidar.watch;
125
128
  async function decompressGzip(file, destination, mode = 0o755) {
126
129
  const unzip = createGunzip();
@@ -132,4 +135,4 @@ async function extractTar(file, cwd, mode) {
132
135
  await tar.extract({ cwd, file, mode });
133
136
  }
134
137
 
135
- export { archived, decompressGzip, exists, extractTar, glob, isDirectory, isExecutable, mkdir, move, readFile, readJsonFile, readdir, rm, stat, tapIntoTmp, unlink, watch, writeFile, writeJsonFile };
138
+ export { archived, chmod, decompressGzip, exists, extractTar, glob, isDirectory, isExecutable, mkdir, move, readFile, readJsonFile, readdir, rm, stat, tapIntoTmp, unlink, watch, writeFile, writeJsonFile };
@@ -8,7 +8,7 @@ import 'change-case';
8
8
  import '../node/cli.js';
9
9
  import 'conf';
10
10
  import 'env-paths';
11
- import { isExecutable, tapIntoTmp, mkdir, decompressGzip, extractTar, move } from '../node/filesystem.js';
11
+ import { isExecutable, tapIntoTmp, mkdir, decompressGzip, extractTar, move, chmod } from '../node/filesystem.js';
12
12
  import 'formdata-node';
13
13
  import 'formdata-node/file-from-path';
14
14
  import 'simple-git';
@@ -85,6 +85,7 @@ async function installForLinux(url, destination) {
85
85
  const parentDir = dirname(destination);
86
86
  await mkdir(parentDir);
87
87
  await downloadFromRelease(url, destination);
88
+ await chmod(destination, 0o755);
88
89
  }
89
90
  async function installForWindows(url, destination) {
90
91
  const parentDir = dirname(destination);
@@ -146,6 +147,9 @@ class OutputStream extends Writable {
146
147
  clearBuffer() {
147
148
  this.buffer = '';
148
149
  }
150
+ getBuffer() {
151
+ return this.buffer;
152
+ }
149
153
  }
150
154
  class Cloudflared {
151
155
  bin;
@@ -174,6 +178,9 @@ class Cloudflared {
174
178
  }
175
179
  const downloadUrl = composeDownloadUrl(this.system.platform, this.system.arch);
176
180
  await install(this.system.platform, downloadUrl, this.bin);
181
+ if (!(await isExecutable(this.bin))) {
182
+ throw new Error(`Failed to install executable cloudflared binary at ${this.bin}. Check file permissions and platform compatibility.`);
183
+ }
177
184
  }
178
185
  composeTunnelingCommand(port, host = 'localhost') {
179
186
  return {
@@ -186,14 +193,19 @@ class Cloudflared {
186
193
  return;
187
194
  }
188
195
  if (maxRetries === 0) {
189
- throw new Error(this.output.extractError() ?? 'cloudflared failed for unknown reason');
196
+ const extractedError = this.output.extractError();
197
+ const errorMessage = extractedError
198
+ ? `cloudflared failed: ${extractedError}`
199
+ : `cloudflared failed for unknown reason. Binary: ${bin}, Args: ${args.join(' ')}, Buffer: ${this.output.getBuffer()}`;
200
+ throw new Error(errorMessage);
190
201
  }
191
202
  this.output.clearBuffer();
192
203
  await exec(bin, args, {
193
204
  // Weird choice of cloudflared to write to stderr.
194
205
  stderr: this.output,
195
206
  signal,
196
- errorHandler: async () => {
207
+ errorHandler: async (error) => {
208
+ console.error(`cloudflared execution error (retries left: ${maxRetries - 1}):`, error);
197
209
  await this.exec(bin, args, maxRetries - 1, signal);
198
210
  },
199
211
  });
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@youcan/cli-kit",
3
3
  "type": "module",
4
- "version": "2.4.1",
4
+ "version": "2.4.3",
5
5
  "description": "Utilities for the YouCan CLI",
6
6
  "author": "YouCan <contact@youcan.shop> (https://youcan.shop)",
7
7
  "license": "MIT",