@xano/cli 0.0.95-beta.11 → 0.0.95-beta.12

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.
@@ -0,0 +1,12 @@
1
+ import BaseCommand from '../../../base-command.js';
2
+ export default class SandboxDelete extends BaseCommand {
3
+ static description: string;
4
+ static examples: string[];
5
+ static flags: {
6
+ force: import("@oclif/core/interfaces").BooleanFlag<boolean>;
7
+ profile: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
8
+ verbose: import("@oclif/core/interfaces").BooleanFlag<boolean>;
9
+ };
10
+ run(): Promise<void>;
11
+ private confirm;
12
+ }
@@ -0,0 +1,71 @@
1
+ import { Flags } from '@oclif/core';
2
+ import BaseCommand from '../../../base-command.js';
3
+ export default class SandboxDelete extends BaseCommand {
4
+ static description = 'Delete your sandbox environment completely (debugging only — it will be re-created on next access)';
5
+ static examples = [
6
+ `$ xano sandbox delete
7
+ Are you sure you want to DELETE your sandbox environment? This destroys all data. (y/N) y
8
+ Sandbox environment deleted.
9
+ `,
10
+ `$ xano sandbox delete --force`,
11
+ ];
12
+ static flags = {
13
+ ...BaseCommand.baseFlags,
14
+ force: Flags.boolean({
15
+ char: 'f',
16
+ default: false,
17
+ description: 'Skip confirmation prompt',
18
+ required: false,
19
+ }),
20
+ };
21
+ async run() {
22
+ const { flags } = await this.parse(SandboxDelete);
23
+ const { profile } = this.resolveProfile(flags);
24
+ if (!flags.force) {
25
+ const confirmed = await this.confirm(`Are you sure you want to DELETE your sandbox environment? This destroys all data and the tenant will be re-created on next access.`);
26
+ if (!confirmed) {
27
+ this.log('Delete cancelled.');
28
+ return;
29
+ }
30
+ }
31
+ const apiUrl = `${profile.instance_origin}/api:meta/sandbox/me`;
32
+ try {
33
+ const response = await this.verboseFetch(apiUrl, {
34
+ headers: {
35
+ accept: 'application/json',
36
+ Authorization: `Bearer ${profile.access_token}`,
37
+ 'Content-Type': 'application/json',
38
+ },
39
+ method: 'DELETE',
40
+ }, flags.verbose, profile.access_token);
41
+ if (!response.ok) {
42
+ const message = await this.parseApiError(response, 'Failed to delete sandbox environment');
43
+ this.error(message);
44
+ }
45
+ this.log('Sandbox environment deleted.');
46
+ }
47
+ catch (error) {
48
+ if (error instanceof Error && 'oclif' in error)
49
+ throw error;
50
+ if (error instanceof Error) {
51
+ this.error(`Failed to delete sandbox environment: ${error.message}`);
52
+ }
53
+ else {
54
+ this.error(`Failed to delete sandbox environment: ${String(error)}`);
55
+ }
56
+ }
57
+ }
58
+ async confirm(message) {
59
+ const readline = await import('node:readline');
60
+ const rl = readline.createInterface({
61
+ input: process.stdin,
62
+ output: process.stdout,
63
+ });
64
+ return new Promise((resolve) => {
65
+ rl.question(`${message} (y/N) `, (answer) => {
66
+ rl.close();
67
+ resolve(answer.toLowerCase() === 'y' || answer.toLowerCase() === 'yes');
68
+ });
69
+ });
70
+ }
71
+ }
@@ -63,6 +63,8 @@ Environment variable 'DATABASE_URL' deleted
63
63
  }
64
64
  }
65
65
  catch (error) {
66
+ if (error instanceof Error && 'oclif' in error)
67
+ throw error;
66
68
  if (error instanceof Error) {
67
69
  this.error(`Failed to delete sandbox environment variable: ${error.message}`);
68
70
  }
@@ -52,6 +52,8 @@ postgres://localhost:5432/mydb
52
52
  }
53
53
  }
54
54
  catch (error) {
55
+ if (error instanceof Error && 'oclif' in error)
56
+ throw error;
55
57
  if (error instanceof Error) {
56
58
  this.error(`Failed to get sandbox environment variable: ${error.message}`);
57
59
  }
@@ -65,6 +65,8 @@ Environment variables saved to env_<tenant>.yaml
65
65
  }
66
66
  }
67
67
  catch (error) {
68
+ if (error instanceof Error && 'oclif' in error)
69
+ throw error;
68
70
  if (error instanceof Error) {
69
71
  this.error(`Failed to get sandbox environment variables: ${error.message}`);
70
72
  }
@@ -54,6 +54,8 @@ Environment variables for sandbox environment:
54
54
  }
55
55
  }
56
56
  catch (error) {
57
+ if (error instanceof Error && 'oclif' in error)
58
+ throw error;
57
59
  if (error instanceof Error) {
58
60
  this.error(`Failed to list sandbox environment variables: ${error.message}`);
59
61
  }
@@ -61,6 +61,8 @@ Environment variable 'DATABASE_URL' set
61
61
  }
62
62
  }
63
63
  catch (error) {
64
+ if (error instanceof Error && 'oclif' in error)
65
+ throw error;
64
66
  if (error instanceof Error) {
65
67
  this.error(`Failed to set sandbox environment variable: ${error.message}`);
66
68
  }
@@ -73,6 +73,8 @@ Reads from env_<tenant>.yaml
73
73
  }
74
74
  }
75
75
  catch (error) {
76
+ if (error instanceof Error && 'oclif' in error)
77
+ throw error;
76
78
  if (error instanceof Error) {
77
79
  this.error(`Failed to set sandbox environment variables: ${error.message}`);
78
80
  }
@@ -50,6 +50,8 @@ Sandbox Environment: (tc24-abcd-x1y2)
50
50
  }
51
51
  }
52
52
  catch (error) {
53
+ if (error instanceof Error && 'oclif' in error)
54
+ throw error;
53
55
  if (error instanceof Error) {
54
56
  this.error(`Failed to get sandbox environment: ${error.message}`);
55
57
  }
@@ -65,6 +65,8 @@ License saved to license_<tenant>.yaml
65
65
  }
66
66
  }
67
67
  catch (error) {
68
+ if (error instanceof Error && 'oclif' in error)
69
+ throw error;
68
70
  if (error instanceof Error) {
69
71
  this.error(`Failed to get sandbox environment license: ${error.message}`);
70
72
  }
@@ -82,6 +82,8 @@ Reads from license_<tenant>.yaml
82
82
  }
83
83
  }
84
84
  catch (error) {
85
+ if (error instanceof Error && 'oclif' in error)
86
+ throw error;
85
87
  if (error instanceof Error) {
86
88
  this.error(`Failed to set sandbox environment license: ${error.message}`);
87
89
  }
@@ -61,6 +61,8 @@ Pulled 42 documents from sandbox environment to ./my-sandbox
61
61
  responseText = await response.text();
62
62
  }
63
63
  catch (error) {
64
+ if (error instanceof Error && 'oclif' in error)
65
+ throw error;
64
66
  if (error instanceof Error) {
65
67
  this.error(`Failed to fetch multidoc: ${error.message}`);
66
68
  }
@@ -124,6 +124,8 @@ Pushed 42 documents to sandbox environment from ./my-workspace
124
124
  }
125
125
  }
126
126
  catch (error) {
127
+ if (error instanceof Error && 'oclif' in error)
128
+ throw error;
127
129
  if (error instanceof Error) {
128
130
  this.error(`Failed to push multidoc: ${error.message}`);
129
131
  }
@@ -45,6 +45,8 @@ Sandbox environment has been reset.
45
45
  this.log('Sandbox environment has been reset.');
46
46
  }
47
47
  catch (error) {
48
+ if (error instanceof Error && 'oclif' in error)
49
+ throw error;
48
50
  if (error instanceof Error) {
49
51
  this.error(`Failed to reset sandbox environment: ${error.message}`);
50
52
  }
@@ -68,6 +68,8 @@ Review session started!
68
68
  process.exit(0);
69
69
  }
70
70
  catch (error) {
71
+ if (error instanceof Error && 'oclif' in error)
72
+ throw error;
71
73
  if (error instanceof Error) {
72
74
  this.error(`Failed to open sandbox review: ${error.message}`);
73
75
  }
@@ -78,6 +78,8 @@ Unit tests:
78
78
  }
79
79
  }
80
80
  catch (error) {
81
+ if (error instanceof Error && 'oclif' in error)
82
+ throw error;
81
83
  if (error instanceof Error) {
82
84
  this.error(`Failed to list unit tests: ${error.message}`);
83
85
  }
@@ -66,6 +66,8 @@ Result: PASS
66
66
  }
67
67
  }
68
68
  catch (error) {
69
+ if (error instanceof Error && 'oclif' in error)
70
+ throw error;
69
71
  if (error instanceof Error) {
70
72
  this.error(`Failed to run unit test: ${error.message}`);
71
73
  }
@@ -128,6 +128,8 @@ Results: 4 passed, 1 failed
128
128
  }
129
129
  }
130
130
  catch (error) {
131
+ if (error instanceof Error && 'oclif' in error)
132
+ throw error;
131
133
  const message = error instanceof Error ? error.message : String(error);
132
134
  results.push({
133
135
  message,
@@ -156,6 +158,8 @@ Results: 4 passed, 1 failed
156
158
  }
157
159
  }
158
160
  catch (error) {
161
+ if (error instanceof Error && 'oclif' in error)
162
+ throw error;
159
163
  if (error instanceof Error) {
160
164
  this.error(`Failed to run unit tests: ${error.message}`);
161
165
  }
@@ -48,6 +48,8 @@ Deleted workflow test 42
48
48
  }
49
49
  }
50
50
  catch (error) {
51
+ if (error instanceof Error && 'oclif' in error)
52
+ throw error;
51
53
  if (error instanceof Error) {
52
54
  this.error(`Failed to delete workflow test: ${error.message}`);
53
55
  }
@@ -47,6 +47,8 @@ export default class SandboxWorkflowTestGet extends BaseCommand {
47
47
  }
48
48
  }
49
49
  catch (error) {
50
+ if (error instanceof Error && 'oclif' in error)
51
+ throw error;
50
52
  if (error instanceof Error) {
51
53
  this.error(`Failed to get workflow test: ${error.message}`);
52
54
  }
@@ -71,6 +71,8 @@ Workflow tests:
71
71
  }
72
72
  }
73
73
  catch (error) {
74
+ if (error instanceof Error && 'oclif' in error)
75
+ throw error;
74
76
  if (error instanceof Error) {
75
77
  this.error(`Failed to list workflow tests: ${error.message}`);
76
78
  }
@@ -64,6 +64,8 @@ Result: PASS (0.25s)
64
64
  }
65
65
  }
66
66
  catch (error) {
67
+ if (error instanceof Error && 'oclif' in error)
68
+ throw error;
67
69
  if (error instanceof Error) {
68
70
  this.error(`Failed to run workflow test: ${error.message}`);
69
71
  }
@@ -116,6 +116,8 @@ Results: 2 passed, 1 failed
116
116
  }
117
117
  }
118
118
  catch (error) {
119
+ if (error instanceof Error && 'oclif' in error)
120
+ throw error;
119
121
  const message = error instanceof Error ? error.message : String(error);
120
122
  results.push({
121
123
  message,
@@ -142,6 +144,8 @@ Results: 2 passed, 1 failed
142
144
  }
143
145
  }
144
146
  catch (error) {
147
+ if (error instanceof Error && 'oclif' in error)
148
+ throw error;
145
149
  if (error instanceof Error) {
146
150
  this.error(`Failed to run workflow tests: ${error.message}`);
147
151
  }
@@ -20,6 +20,14 @@ const REFERENCE_PATTERNS = [
20
20
  regex: /^\s*workflow_test\.call\s+("(?:[^"\\]|\\.)*"|[^\s{]+)/gm,
21
21
  targetType: 'workflow_test',
22
22
  },
23
+ // db.* statements reference tables: db.get, db.query, db.add, db.edit, db.add_or_edit, db.delete, db.bulk_add, db.bulk_delete, db.count
24
+ {
25
+ keyword: 'db.*',
26
+ regex: /^\s*db\.(?:get|query|add|edit|add_or_edit|delete|bulk_add|bulk_delete|count)\s+("(?:[^"\\]|\\.)*"|[^\s{]+)/gm,
27
+ targetType: 'table',
28
+ },
29
+ // Schema foreign key references: table = "name" inside field definitions
30
+ { keyword: 'table (FK)', regex: /\btable\s*=\s*"([^"]*)"/gm, targetType: 'table' },
23
31
  ];
24
32
  /**
25
33
  * Strip surrounding quotes from a name if present.
@@ -116,8 +124,8 @@ export function checkReferences(documents, serverOperations) {
116
124
  let match;
117
125
  while ((match = pattern.regex.exec(doc.content)) !== null) {
118
126
  const rawName = stripQuotes(match[1]);
119
- // Skip empty names (e.g., action.call "" is valid for integration actions)
120
- if (!rawName)
127
+ // Skip empty names only for action.call (valid for integration actions)
128
+ if (!rawName && pattern.keyword === 'action.call')
121
129
  continue;
122
130
  const { targetType } = pattern;
123
131
  const knownNames = registry.get(targetType);