bdy 1.24.8 → 1.25.0-dev
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/distTs/detect-rules.json +351 -0
- package/distTs/package.json +7 -2
- package/distTs/src/cliIndex.js +2 -0
- package/distTs/src/command/yaml/actions/detect.js +268 -0
- package/distTs/src/command/yaml/actions/info.js +79 -0
- package/distTs/src/command/yaml/actions/list.js +96 -0
- package/distTs/src/command/yaml/actions/schema.js +104 -0
- package/distTs/src/command/yaml/actions.js +16 -0
- package/distTs/src/command/yaml/cache.js +106 -0
- package/distTs/src/command/yaml/pipeline.js +53 -0
- package/distTs/src/command/yaml/render.js +111 -0
- package/distTs/src/command/yaml/schemaUtils.js +164 -0
- package/distTs/src/command/yaml/validate.js +300 -0
- package/distTs/src/command/yaml.js +20 -0
- package/distTs/src/diskCache.js +200 -0
- package/distTs/src/openapi.js +10 -81
- package/distTs/src/texts.js +66 -1
- package/distTs/src/utils.js +18 -13
- package/package.json +7 -2
package/distTs/src/openapi.js
CHANGED
|
@@ -1,83 +1,15 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
-
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
-
};
|
|
5
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
3
|
exports.fetchOpenApiSchema = fetchOpenApiSchema;
|
|
7
4
|
const bundle_1 = require("@scalar/json-magic/bundle");
|
|
8
5
|
const node_1 = require("@scalar/json-magic/bundle/plugins/node");
|
|
9
6
|
const openapi_parser_1 = require("@scalar/openapi-parser");
|
|
10
|
-
const node_crypto_1 = require("node:crypto");
|
|
11
7
|
const node_fs_1 = require("node:fs");
|
|
12
|
-
const node_path_1 = __importDefault(require("node:path"));
|
|
13
8
|
const node_v8_1 = require("node:v8");
|
|
14
9
|
const texts_1 = require("./texts");
|
|
15
10
|
const utils_1 = require("./utils");
|
|
11
|
+
const diskCache_1 = require("./diskCache");
|
|
16
12
|
const BUNDLE_PLUGINS = [(0, node_1.readFiles)(), (0, node_1.fetchUrls)(), (0, node_1.parseYaml)(), (0, node_1.parseJson)()];
|
|
17
|
-
// Hard cache window: within this period the cached schema is served with no
|
|
18
|
-
// network at all. After it expires the schema is revalidated (conditional GET),
|
|
19
|
-
// and a successful revalidation (304/200) resets the window.
|
|
20
|
-
const CACHE_TTL_MS = 60 * 60 * 1000;
|
|
21
|
-
// One cache set per schema URL (region/stage differ), keyed by a URL hash.
|
|
22
|
-
function cachePaths(url) {
|
|
23
|
-
const dir = node_path_1.default.join((0, utils_1.getHomeDirectory)(), 'openapi');
|
|
24
|
-
if (!(0, node_fs_1.existsSync)(dir))
|
|
25
|
-
(0, node_fs_1.mkdirSync)(dir, { recursive: true });
|
|
26
|
-
const key = (0, node_crypto_1.createHash)('sha256').update(url).digest('hex').slice(0, 16);
|
|
27
|
-
return {
|
|
28
|
-
raw: node_path_1.default.join(dir, `${key}.json`),
|
|
29
|
-
schema: node_path_1.default.join(dir, `${key}.v8`),
|
|
30
|
-
meta: node_path_1.default.join(dir, `${key}.meta.json`),
|
|
31
|
-
};
|
|
32
|
-
}
|
|
33
|
-
function readMeta(metaPath) {
|
|
34
|
-
try {
|
|
35
|
-
return JSON.parse((0, node_fs_1.readFileSync)(metaPath, 'utf8'));
|
|
36
|
-
}
|
|
37
|
-
catch {
|
|
38
|
-
return {};
|
|
39
|
-
}
|
|
40
|
-
}
|
|
41
|
-
// Write via temp + rename so a Ctrl+C can't leave a truncated cache file.
|
|
42
|
-
function writeAtomic(filePath, data) {
|
|
43
|
-
const tmp = `${filePath}.${process.pid}.tmp`;
|
|
44
|
-
(0, node_fs_1.writeFileSync)(tmp, data);
|
|
45
|
-
(0, node_fs_1.renameSync)(tmp, filePath);
|
|
46
|
-
}
|
|
47
|
-
/**
|
|
48
|
-
* Refresh the cached raw schema body via a single conditional GET.
|
|
49
|
-
* 304 → keep cache ('unchanged'); 200 → rewrite raw + validators ('updated');
|
|
50
|
-
* network error → reuse any cached body ('unchanged') or report 'none'.
|
|
51
|
-
*/
|
|
52
|
-
async function refresh(url, paths) {
|
|
53
|
-
const hasRaw = (0, node_fs_1.existsSync)(paths.raw);
|
|
54
|
-
const meta = hasRaw ? readMeta(paths.meta) : {};
|
|
55
|
-
// The server serves a strong content-based ETag (identical across instances),
|
|
56
|
-
// so revalidate with If-None-Match.
|
|
57
|
-
const headers = {};
|
|
58
|
-
if (hasRaw && meta.etag)
|
|
59
|
-
headers['If-None-Match'] = meta.etag;
|
|
60
|
-
try {
|
|
61
|
-
const res = await fetch(url, { headers });
|
|
62
|
-
if (res.status === 304 && hasRaw) {
|
|
63
|
-
// Reset the hard-cache window; keep the existing validator.
|
|
64
|
-
writeAtomic(paths.meta, JSON.stringify({ etag: meta.etag, fetchedAt: Date.now() }));
|
|
65
|
-
return 'unchanged';
|
|
66
|
-
}
|
|
67
|
-
if (res.ok) {
|
|
68
|
-
writeAtomic(paths.raw, await res.text());
|
|
69
|
-
writeAtomic(paths.meta, JSON.stringify({
|
|
70
|
-
etag: res.headers.get('etag') ?? undefined,
|
|
71
|
-
fetchedAt: Date.now(),
|
|
72
|
-
}));
|
|
73
|
-
return 'updated';
|
|
74
|
-
}
|
|
75
|
-
}
|
|
76
|
-
catch {
|
|
77
|
-
// network error — fall back to the cached body if present
|
|
78
|
-
}
|
|
79
|
-
return hasRaw ? 'unchanged' : 'none';
|
|
80
|
-
}
|
|
81
13
|
// Bundle + dereference a schema source (local path or remote URL).
|
|
82
14
|
async function buildSchema(source) {
|
|
83
15
|
const data = await (0, bundle_1.bundle)(source, {
|
|
@@ -88,8 +20,8 @@ async function buildSchema(source) {
|
|
|
88
20
|
return schema ?? null;
|
|
89
21
|
}
|
|
90
22
|
// The dereferenced schema has circular refs, so it is cached with v8
|
|
91
|
-
// serialization (JSON.stringify can't handle cycles). The blob is
|
|
92
|
-
//
|
|
23
|
+
// serialization (JSON.stringify can't handle cycles). The blob is Node-version
|
|
24
|
+
// specific, so a failed load just rebuilds from the raw body.
|
|
93
25
|
function loadCachedSchema(schemaPath) {
|
|
94
26
|
try {
|
|
95
27
|
return (0, node_v8_1.deserialize)((0, node_fs_1.readFileSync)(schemaPath));
|
|
@@ -100,7 +32,7 @@ function loadCachedSchema(schemaPath) {
|
|
|
100
32
|
}
|
|
101
33
|
function saveCachedSchema(schemaPath, schema) {
|
|
102
34
|
try {
|
|
103
|
-
writeAtomic(schemaPath, (0, node_v8_1.serialize)(schema));
|
|
35
|
+
(0, diskCache_1.writeAtomic)(schemaPath, (0, node_v8_1.serialize)(schema));
|
|
104
36
|
}
|
|
105
37
|
catch {
|
|
106
38
|
// caching is best-effort
|
|
@@ -109,20 +41,18 @@ function saveCachedSchema(schemaPath, schema) {
|
|
|
109
41
|
async function fetchOpenApiSchema(baseUrl) {
|
|
110
42
|
try {
|
|
111
43
|
const url = (0, utils_1.getOpenApiEndpointByApiBaseUrl)(baseUrl);
|
|
112
|
-
const paths = cachePaths(url);
|
|
44
|
+
const paths = (0, diskCache_1.cachePaths)('openapi', url);
|
|
113
45
|
// Hard cache: within the TTL, serve the cached schema with no network call.
|
|
114
|
-
|
|
115
|
-
if (meta.fetchedAt && Date.now() - meta.fetchedAt < CACHE_TTL_MS) {
|
|
46
|
+
if ((0, diskCache_1.isHardFresh)((0, diskCache_1.readMeta)(paths.meta))) {
|
|
116
47
|
const cached = loadCachedSchema(paths.schema);
|
|
117
48
|
if (cached)
|
|
118
49
|
return cached;
|
|
119
50
|
}
|
|
120
|
-
const state = await refresh(url, paths);
|
|
51
|
+
const state = await (0, diskCache_1.refresh)(url, paths);
|
|
121
52
|
let schema;
|
|
122
53
|
if (state === 'unchanged') {
|
|
123
|
-
//
|
|
124
|
-
//
|
|
125
|
-
// body if the v8 blob is missing or unreadable (e.g. Node upgrade).
|
|
54
|
+
// Reuse the cached dereferenced schema, skipping download/bundle/dereference.
|
|
55
|
+
// Rebuild from the raw body if the v8 blob is missing or unreadable.
|
|
126
56
|
schema = loadCachedSchema(paths.schema);
|
|
127
57
|
if (!schema) {
|
|
128
58
|
schema = await buildSchema(paths.raw);
|
|
@@ -136,8 +66,7 @@ async function fetchOpenApiSchema(baseUrl) {
|
|
|
136
66
|
saveCachedSchema(paths.schema, schema);
|
|
137
67
|
}
|
|
138
68
|
else {
|
|
139
|
-
// No cache and no usable response —
|
|
140
|
-
// directly (preserves the original cold/offline behaviour).
|
|
69
|
+
// No cache and no usable response — bundle the remote URL directly.
|
|
141
70
|
schema = await buildSchema(url);
|
|
142
71
|
}
|
|
143
72
|
if (schema)
|
package/distTs/src/texts.js
CHANGED
|
@@ -21,7 +21,7 @@ exports.OPT_COMMAND_DOMAIN_ONLY_AVAILABLE = exports.OPT_COMMAND_DOMAIN_SORT = ex
|
|
|
21
21
|
exports.TXT_COMMAND_PROJECT_LINK_GIT_REPO_INITIALIZED = exports.TXT_COMMAND_PROJECT_LINK_GIT_REPO = exports.TXT_COMMAND_PROJECT_LINK_DIR_CONFIRM = exports.TXT_COMMAND_PROJECT_LINK_DIR_LINKED = exports.ERR_COMMAND_PROJECT_LINK_DIR_CREATE = exports.OPT_COMMAND_PROJECT_LINK_TRY_NOW = exports.OPT_COMMAND_PROJECT_LINK_SET_GIT_REMOTE = exports.OPT_COMMAND_PROJECT_LINK_HAS_REMOTE = exports.OPT_COMMAND_PROJECT_LINK_DIRECTORY = exports.OPT_COMMAND_PROJECT_LINK_GIT = exports.OPT_COMMAND_PROJECT_LINK_RELINK = exports.DESC_COMMAND_PROJECT_LINK = exports.DESC_COMMAND_PROJECT_LIST = exports.DESC_COMMAND_PROJECT_GIT = exports.DESC_COMMAND_PROJECT_GIT_CREDENTIAL = exports.DESC_COMMAND_PROJECT = exports.TXT_ARTIFACT_VERSION_DOWNLOAD = exports.TXT_ARTIFACT_PUBLISH = exports.TXT_ARTIFACT_CREATED = exports.TXT_ARTIFACT_VERSION_DELETED = exports.TXT_ARTIFACT_DELETED = exports.ERR_COMMAND_ARTIFACT_TYPE = exports.OPT_COMMAND_ARTIFACT_VERSION = exports.OPT_COMMAND_ARTIFACT_IDENTIFIER = exports.OPT_COMMAND_ARTIFACT_CREATE_IDENTIFIER = exports.OPT_COMMAND_ARTIFACT_NAME = exports.OPT_COMMAND_ARTIFACT_TYPE = exports.DESC_COMMAND_ARTIFACT_CREATE = exports.DESC_COMMAND_ARTIFACT_COMPOSER_PUBLISH = exports.DESC_COMMAND_ARTIFACT_GET = exports.TXT_ARTIFACT_DOCKER_LOGIN_FAILED = exports.TXT_ARTIFACT_DOCKER_LOGIN_SUCCESS = exports.TXT_ARTIFACT_VERSION_DELETE_CONFIRM = exports.TXT_ARTIFACT_DELETE_CONFIRM = exports.DESC_COMMAND_ARTIFACT_DELETE = exports.ERR_COMMAND_ARTIFACT_NO_PROJECTS = exports.DESC_COMMAND_ARTIFACT_VERSION_GET = exports.DESC_COMMAND_ARTIFACT_VERSION_LIST = exports.DESC_COMMAND_ARTIFACT_VERSION_DELETE = exports.DESC_COMMAND_ARTIFACT_DOCKER_LOGIN = exports.DESC_COMMAND_ARTIFACT_LIST = exports.DESC_COMMAND_ARTIFACT_COMPOSER = exports.DESC_COMMAND_ARTIFACT_VERSION = exports.ERR_COMMAND_DOMAIN_UNAVAILABLE = exports.OPTION_COMMAND_DOMAIN_IDENTIFIER = exports.ERR_COMMAND_DOMAIN_NO_DOMAINS = exports.TXT_COMMAND_DOMAIN_PROMPT_REQUIRED = exports.TXT_COMMAND_DOMAIN_BUY_SELECT_DOMAIN = exports.TXT_COMMAND_DOMAIN_PROVIDE_PROMPT = exports.ERR_COMMAND_DOMAIN_NOT_FOUND = void 0;
|
|
22
22
|
exports.EXAMPLE_TARGET_LIST = exports.EXAMPLE_SANDBOX_SNAPSHOT_LIST = exports.EXAMPLE_SANDBOX_SNAPSHOT_GET = exports.EXAMPLE_SANDBOX_SNAPSHOT_DELETE = exports.EXAMPLE_SANDBOX_SNAPSHOT_CREATE = exports.EXAMPLE_SANDBOX_EXEC_STATUS = exports.EXAMPLE_SANDBOX_EXEC_LOGS = exports.EXAMPLE_SANDBOX_APP_STATUS = exports.EXAMPLE_SANDBOX_APP_STOP = exports.EXAMPLE_SANDBOX_APP_REMOVE = exports.EXAMPLE_SANDBOX_APP_ADD = exports.EXAMPLE_SANDBOX_APP_START = exports.EXAMPLE_SANDBOX_APP_LOGS = exports.EXAMPLE_SANDBOX_EXEC_LIST = exports.EXAMPLE_SANDBOX_APP_LIST = exports.EXAMPLE_SANDBOX_EXEC_KILL = exports.EXAMPLE_SANDBOX_SSH = exports.EXAMPLE_SANDBOX_EXEC_COMMAND = exports.EXAMPLE_TUNNEL_START = exports.EXAMPLE_TUNNEL_TCP = exports.EXAMPLE_TUNNEL_TLS = exports.EXAMPLE_AGENT_TUNNEL_START = exports.EXAMPLE_AGENT_TUNNEL_STATUS = exports.EXAMPLE_AGENT_TUNNEL_REMOVE = exports.EXAMPLE_AGENT_TUNNEL_LIST = exports.EXAMPLE_TUNNEL_HTTP = exports.EXAMPLE_SANDBOX_CREATE = exports.EXAMPLE_DISTRO_CREATE = exports.EXAMPLE_ROUTE_CREATE = exports.EXAMPLE_ROUTE_LIST = exports.EXAMPLE_ROUTE_UPDATE = exports.EXAMPLE_ROUTE_DELETE = exports.EXAMPLE_DISTRO_DELETE = exports.EXAMPLE_ROUTE_GET = exports.EXAMPLE_DISTRO_UPDATE = exports.EXAMPLE_DISTRO_GET = exports.EXAMPLE_DISTRO_LIST = exports.EXAMPLE_SANDBOX_CP = exports.ERR_PROJECT_NO_PROJECTS = exports.TXT_LOGIN_SELECT_PROJECT = exports.TXT_COMMAND_PROJECT_CREATED = exports.TXT_COMMAND_PROJECT_LINK_NOT_FOUND = exports.TXT_COMMAND_PROJECT_LINK_NAME = exports.TXT_COMMAND_PROJECT_LINK_SELECT_PROJECT = exports.TXT_COMMAND_PROJECT_LINK_TO = exports.TXT_COMMAND_PROJECT_LINK_EXISTING_DESC = exports.TXT_COMMAND_PROJECT_LINK_EXISTING = exports.TXT_COMMAND_PROJECT_LINK_CREATE_NEW_DESC = exports.TXT_COMMAND_PROJECT_LINK_CREATE_NEW = exports.ERR_COMMAND_PROJECT_LINK_DIR_NOT_DIR = void 0;
|
|
23
23
|
exports.EXAMPLE_CRAWL_RUN = exports.EXAMPLE_TESTS_CAPTURE = exports.EXAMPLE_TESTS_VISUAL_SESSION_CLOSE = exports.EXAMPLE_TESTS_VISUAL_SESSION_CREATE = exports.EXAMPLE_TESTS_VISUAL_LINK = exports.EXAMPLE_TESTS_VISUAL_UPLOAD = exports.EXAMPLE_TESTS_VISUAL_SETUP = exports.EXAMPLE_TESTS_UNIT_LINK = exports.EXAMPLE_TESTS_UNIT_UPLOAD = exports.EXAMPLE_ARTIFACT_VERSION_DELETE = exports.EXAMPLE_ARTIFACT_VERSION_GET = exports.EXAMPLE_ARTIFACT_VERSION_LIST = exports.EXAMPLE_ARTIFACT_CREATE = exports.EXAMPLE_ARTIFACT_DELETE = exports.EXAMPLE_ARTIFACT_DOWNLOAD = exports.EXAMPLE_ARTIFACT_PUBLISH = exports.EXAMPLE_ARTIFACT_COMPOSER_PUBLISH = exports.EXAMPLE_ARTIFACT_VERSION_CREATE = exports.EXAMPLE_PIPELINE_RUN_RETRY = exports.EXAMPLE_PIPELINE_RUN_LIST = exports.EXAMPLE_PIPELINE_LIST = exports.EXAMPLE_PIPELINE_YML = exports.EXAMPLE_PIPELINE_GET = exports.EXAMPLE_PIPELINE_UPDATE = exports.EXAMPLE_PIPELINE_DELETE = exports.EXAMPLE_PIPELINE_CREATE = exports.EXAMPLE_PIPELINE_RUN_CANCEL = exports.EXAMPLE_PIPELINE_RUN_APPLY = exports.EXAMPLE_PIPELINE_RUN_LOGS = exports.EXAMPLE_PIPELINE_RUN_JSONL = exports.EXAMPLE_PIPELINE_RUN_STATUS = exports.EXAMPLE_PIPELINE_RUN_START = exports.EXAMPLE_SANDBOX_ENDPOINT_LIST = exports.EXAMPLE_SANDBOX_ENDPOINT_GET = exports.EXAMPLE_SANDBOX_ENDPOINT_DELETE = exports.EXAMPLE_SANDBOX_ENDPOINT_CREATE = exports.EXAMPLE_ENVIRONMENT_DELETE = exports.EXAMPLE_ENVIRONMENT_UPDATE = exports.EXAMPLE_ENVIRONMENT_CREATE = exports.EXAMPLE_ENVIRONMENT_GET = exports.EXAMPLE_ENVIRONMENT_LIST = exports.EXAMPLE_TARGET_EXEC_LOGS = exports.EXAMPLE_TARGET_EXEC_LIST = exports.EXAMPLE_TARGET_EXEC_KILL = exports.EXAMPLE_TARGET_EXEC_STATUS = exports.EXAMPLE_TARGET_EXEC_COMMAND = exports.EXAMPLE_TARGET_DELETE = exports.EXAMPLE_TARGET_UPDATE = exports.EXAMPLE_TARGET_CREATE = exports.EXAMPLE_TARGET_GET = void 0;
|
|
24
|
-
exports.EXAMPLE_CRAWL_LINK = void 0;
|
|
24
|
+
exports.ERR_YAML_SCHEMA_READ_FAILED = exports.ERR_YAML_SCHEMA_FETCH_FAILED = exports.TXT_YAML_UNKNOWN_TOP_LEVEL_KEYS = exports.ERR_YAML_ITEM_UNKNOWN = exports.ERR_YAML_ITEM_MISSING = exports.ERR_YAML_MUST_BE = exports.ERR_YAML_PIPELINE_NOT_OBJECT = exports.ERR_YAML_EMPTY_ARRAY = exports.ERR_YAML_PLAIN_OBJECT = exports.ERR_YAML_NOT_ARRAY = exports.ERR_YAML_PARSE = exports.ERR_YAML_VALIDATE_FAILED_COUNT = exports.TXT_YAML_VALIDATE_ALL_PASS = exports.ERR_YAML_VALIDATE_FAILED = exports.ERR_YAML_VALIDATE_FILE_NOT_FOUND = exports.OPTION_YAML_VALIDATE_FILE = exports.DESC_COMMAND_YAML_VALIDATE = exports.DESC_COMMAND_YAML_ACTIONS_INFO = exports.DESC_COMMAND_YAML_ACTIONS_LIST = exports.DESC_COMMAND_YAML_ACTIONS = exports.DESC_COMMAND_YAML_PIPELINE = exports.DESC_COMMAND_YAML = exports.TXT_ACTION_SUGGESTED_FROM_REPO = exports.TXT_ACTION_USE_LIST = exports.TXT_ACTION_DID_YOU_MEAN = exports.ERR_ACTION_SEARCH_NO_RESULTS = exports.ERR_ACTION_NOT_FOUND = exports.OPTION_ACTION_TYPE = exports.OPTION_ACTION_SEARCH = exports.EXAMPLE_YAML_VALIDATE = exports.EXAMPLE_YAML_ACTIONS_INFO = exports.EXAMPLE_YAML_ACTIONS_LIST = exports.EXAMPLE_YAML_PIPELINE = exports.EXAMPLE_CRAWL_LINK = void 0;
|
|
25
25
|
const utils_1 = require("./utils");
|
|
26
26
|
exports.ERR_CANCELLED = 'Cancelled';
|
|
27
27
|
exports.ERR_REST_API_GENERAL_ERROR = 'Something went wrong';
|
|
@@ -1893,3 +1893,68 @@ exports.EXAMPLE_CRAWL_LINK = `
|
|
|
1893
1893
|
bdy crawl link
|
|
1894
1894
|
### link non-interactively to a specific suite:
|
|
1895
1895
|
bdy crawl link -w workspace -p project -s suite-identifier`;
|
|
1896
|
+
exports.EXAMPLE_YAML_PIPELINE = `
|
|
1897
|
+
### show pipeline schema and examples:
|
|
1898
|
+
bdy yaml pipeline
|
|
1899
|
+
### the same schema as json:
|
|
1900
|
+
bdy yaml pipeline --format json`;
|
|
1901
|
+
exports.EXAMPLE_YAML_ACTIONS_LIST = `
|
|
1902
|
+
### list all action types:
|
|
1903
|
+
bdy yaml actions list
|
|
1904
|
+
### search action types:
|
|
1905
|
+
bdy yaml actions list --search kubernetes
|
|
1906
|
+
### list as json, for an editor plugin or an agent:
|
|
1907
|
+
bdy yaml actions list --format json`;
|
|
1908
|
+
exports.EXAMPLE_YAML_ACTIONS_INFO = `
|
|
1909
|
+
### show action schema and example:
|
|
1910
|
+
bdy yaml actions info KUBERNETES_CLI
|
|
1911
|
+
### the same schema as json:
|
|
1912
|
+
bdy yaml actions info KUBERNETES_CLI --format json`;
|
|
1913
|
+
exports.EXAMPLE_YAML_VALIDATE = `
|
|
1914
|
+
### validate a pipeline file:
|
|
1915
|
+
bdy yaml validate buddy.yml`;
|
|
1916
|
+
// action texts (used by yaml/action commands)
|
|
1917
|
+
exports.OPTION_ACTION_SEARCH = 'Search by name, type, or description';
|
|
1918
|
+
exports.OPTION_ACTION_TYPE = 'Action type or slug (e.g. BUILD, KUBERNETES_CLI, transfer)';
|
|
1919
|
+
const ERR_ACTION_NOT_FOUND = (type) => `Action "${type}" not found`;
|
|
1920
|
+
exports.ERR_ACTION_NOT_FOUND = ERR_ACTION_NOT_FOUND;
|
|
1921
|
+
const ERR_ACTION_SEARCH_NO_RESULTS = (query) => `No actions found for "${query}"`;
|
|
1922
|
+
exports.ERR_ACTION_SEARCH_NO_RESULTS = ERR_ACTION_SEARCH_NO_RESULTS;
|
|
1923
|
+
const TXT_ACTION_DID_YOU_MEAN = (types) => `Did you mean: ${types}`;
|
|
1924
|
+
exports.TXT_ACTION_DID_YOU_MEAN = TXT_ACTION_DID_YOU_MEAN;
|
|
1925
|
+
exports.TXT_ACTION_USE_LIST = 'Use "bdy yaml actions list" to browse all actions';
|
|
1926
|
+
const TXT_ACTION_SUGGESTED_FROM_REPO = (actions) => `Suggested based on your repo: ${actions}`;
|
|
1927
|
+
exports.TXT_ACTION_SUGGESTED_FROM_REPO = TXT_ACTION_SUGGESTED_FROM_REPO;
|
|
1928
|
+
// yaml commands
|
|
1929
|
+
exports.DESC_COMMAND_YAML = 'Browse and validate Buddy pipeline YAML';
|
|
1930
|
+
exports.DESC_COMMAND_YAML_PIPELINE = 'Show pipeline YAML schema and examples';
|
|
1931
|
+
exports.DESC_COMMAND_YAML_ACTIONS = 'Browse Buddy YAML action types';
|
|
1932
|
+
exports.DESC_COMMAND_YAML_ACTIONS_LIST = 'List all action types';
|
|
1933
|
+
exports.DESC_COMMAND_YAML_ACTIONS_INFO = 'Show action schema and example for a type';
|
|
1934
|
+
exports.DESC_COMMAND_YAML_VALIDATE = 'Validate a pipeline YAML file';
|
|
1935
|
+
exports.OPTION_YAML_VALIDATE_FILE = 'Path to YAML pipeline file';
|
|
1936
|
+
const ERR_YAML_VALIDATE_FILE_NOT_FOUND = (file) => `File not found: ${file}`;
|
|
1937
|
+
exports.ERR_YAML_VALIDATE_FILE_NOT_FOUND = ERR_YAML_VALIDATE_FILE_NOT_FOUND;
|
|
1938
|
+
exports.ERR_YAML_VALIDATE_FAILED = 'Pipeline validation failed';
|
|
1939
|
+
exports.TXT_YAML_VALIDATE_ALL_PASS = 'Pipeline validation passed';
|
|
1940
|
+
const ERR_YAML_VALIDATE_FAILED_COUNT = (count) => `${exports.ERR_YAML_VALIDATE_FAILED} (${count} ${count === 1 ? 'error' : 'errors'})`;
|
|
1941
|
+
exports.ERR_YAML_VALIDATE_FAILED_COUNT = ERR_YAML_VALIDATE_FAILED_COUNT;
|
|
1942
|
+
const ERR_YAML_PARSE = (message) => `YAML parse error: ${message}`;
|
|
1943
|
+
exports.ERR_YAML_PARSE = ERR_YAML_PARSE;
|
|
1944
|
+
exports.ERR_YAML_NOT_ARRAY = 'Invalid pipeline YAML: expected an array of pipeline objects';
|
|
1945
|
+
exports.ERR_YAML_PLAIN_OBJECT = 'Invalid pipeline YAML: expected an array (e.g. "- pipeline: my-pipeline"), got a plain object';
|
|
1946
|
+
exports.ERR_YAML_EMPTY_ARRAY = 'Invalid pipeline YAML: empty array';
|
|
1947
|
+
const ERR_YAML_PIPELINE_NOT_OBJECT = (index) => `Pipeline #${index}: expected an object`;
|
|
1948
|
+
exports.ERR_YAML_PIPELINE_NOT_OBJECT = ERR_YAML_PIPELINE_NOT_OBJECT;
|
|
1949
|
+
const ERR_YAML_MUST_BE = (expected, got) => `must be an ${expected}, got ${got}`;
|
|
1950
|
+
exports.ERR_YAML_MUST_BE = ERR_YAML_MUST_BE;
|
|
1951
|
+
const ERR_YAML_ITEM_MISSING = (field) => `missing "${field}"`;
|
|
1952
|
+
exports.ERR_YAML_ITEM_MISSING = ERR_YAML_ITEM_MISSING;
|
|
1953
|
+
const ERR_YAML_ITEM_UNKNOWN = (field, value) => `unknown ${field} "${value}"`;
|
|
1954
|
+
exports.ERR_YAML_ITEM_UNKNOWN = ERR_YAML_ITEM_UNKNOWN;
|
|
1955
|
+
const TXT_YAML_UNKNOWN_TOP_LEVEL_KEYS = (keys) => `Unknown top-level keys: ${keys}`;
|
|
1956
|
+
exports.TXT_YAML_UNKNOWN_TOP_LEVEL_KEYS = TXT_YAML_UNKNOWN_TOP_LEVEL_KEYS;
|
|
1957
|
+
const ERR_YAML_SCHEMA_FETCH_FAILED = (url) => `Failed to fetch yaml-schema from ${url} and no cached copy is available`;
|
|
1958
|
+
exports.ERR_YAML_SCHEMA_FETCH_FAILED = ERR_YAML_SCHEMA_FETCH_FAILED;
|
|
1959
|
+
const ERR_YAML_SCHEMA_READ_FAILED = (path) => `Failed to read yaml-schema from ${path}`;
|
|
1960
|
+
exports.ERR_YAML_SCHEMA_READ_FAILED = ERR_YAML_SCHEMA_READ_FAILED;
|
package/distTs/src/utils.js
CHANGED
|
@@ -48,6 +48,7 @@ exports.getDockerRegistryHostByApiBaseUrl = getDockerRegistryHostByApiBaseUrl;
|
|
|
48
48
|
exports.getMcpUrlByApiBaseUrl = getMcpUrlByApiBaseUrl;
|
|
49
49
|
exports.getMcpToolCategory = getMcpToolCategory;
|
|
50
50
|
exports.openApiPrepareUrl = openApiPrepareUrl;
|
|
51
|
+
exports.getApiEnv = getApiEnv;
|
|
51
52
|
exports.getOpenApiEndpointByApiBaseUrl = getOpenApiEndpointByApiBaseUrl;
|
|
52
53
|
exports.isValidDomain = isValidDomain;
|
|
53
54
|
exports.isInSandbox = isInSandbox;
|
|
@@ -1022,24 +1023,28 @@ function openApiPrepareUrl(url, workspace, project) {
|
|
|
1022
1023
|
preparedUrl = preparedUrl.replaceAll('{project_name}', project);
|
|
1023
1024
|
return preparedUrl;
|
|
1024
1025
|
}
|
|
1025
|
-
function
|
|
1026
|
-
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
|
|
1026
|
+
function getApiEnv(baseUrl) {
|
|
1027
|
+
const host = baseUrl.hostname;
|
|
1028
|
+
if (host.includes('api.buddy.works') ||
|
|
1029
|
+
host.includes('api.eu.buddy.works') ||
|
|
1030
|
+
host.includes('api.asia.buddy.works')) {
|
|
1031
|
+
return 'production';
|
|
1032
|
+
}
|
|
1033
|
+
else if (host.includes('api.awsstage.net') ||
|
|
1034
|
+
host.includes('api.eu.awsstage.net') ||
|
|
1035
|
+
host.includes('api.buddy.mom')) {
|
|
1036
|
+
return 'stage';
|
|
1035
1037
|
}
|
|
1036
|
-
else if (
|
|
1037
|
-
return '
|
|
1038
|
+
else if (host.includes('api.awsmaster.net')) {
|
|
1039
|
+
return 'master';
|
|
1038
1040
|
}
|
|
1039
1041
|
else {
|
|
1040
|
-
return '
|
|
1042
|
+
return 'dev';
|
|
1041
1043
|
}
|
|
1042
1044
|
}
|
|
1045
|
+
function getOpenApiEndpointByApiBaseUrl(baseUrl) {
|
|
1046
|
+
return `https://es.buddy.works/openapi/${getApiEnv(baseUrl)}/restapi.json`;
|
|
1047
|
+
}
|
|
1043
1048
|
function isValidDomain(prompt) {
|
|
1044
1049
|
return /^(?=.{1,253}$)(?:[a-z0-9](?:[a-z0-9-]{0,61}[a-z0-9])?\.)+[a-z]{2,}$/i.test(prompt);
|
|
1045
1050
|
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "bdy",
|
|
3
3
|
"preferGlobal": false,
|
|
4
|
-
"version": "1.
|
|
4
|
+
"version": "1.25.0-dev",
|
|
5
5
|
"type": "commonjs",
|
|
6
6
|
"license": "MIT",
|
|
7
7
|
"homepage": "https://buddy.works/docs/cli",
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
"lint": "eslint \"*/**\"",
|
|
13
13
|
"lint:types": "tsc --skipLibCheck --noEmit --project tsconfig.json && tsc --skipLibCheck --project test/tsconfig.json && tsc --skipLibCheck --project e2e/tsconfig.json",
|
|
14
14
|
"watch": "tsc --watch --project tsconfig.json & tsc --watch --project src/visualTest/utils/tsconfig.json",
|
|
15
|
-
"buildTs": "(tsc --project tsconfig.json & tsc --project src/visualTest/utils/tsconfig.json & wait) && cp package.json distTs/package.json && curl -fsSL https://raw.githubusercontent.com/buddy/cli/main/README.md -o README.md",
|
|
15
|
+
"buildTs": "(tsc --project tsconfig.json & tsc --project src/visualTest/utils/tsconfig.json & wait) && cp package.json distTs/package.json && cp detect-rules.json distTs/detect-rules.json && curl -fsSL https://raw.githubusercontent.com/buddy/cli/main/README.md -o README.md",
|
|
16
16
|
"e2e": "npm run buildTs && vitest run --config e2e/vitest.config.ts",
|
|
17
17
|
"e2e:version": "vitest run --config e2e/vitest.config.ts e2e/modules/version/",
|
|
18
18
|
"e2e:tunnel-config": "vitest run --config e2e/vitest.config.ts e2e/modules/tunnel-config/",
|
|
@@ -29,6 +29,7 @@
|
|
|
29
29
|
"e2e:distro": "vitest run --config e2e/vitest.config.ts e2e/modules/distro/",
|
|
30
30
|
"e2e:target": "vitest run --config e2e/vitest.config.ts e2e/modules/target/",
|
|
31
31
|
"e2e:environment": "vitest run --config e2e/vitest.config.ts e2e/modules/environment/",
|
|
32
|
+
"e2e:yaml": "vitest run --config e2e/vitest.config.ts e2e/modules/yaml/",
|
|
32
33
|
"unit": "vitest run --config vitest.config.ts"
|
|
33
34
|
},
|
|
34
35
|
"files": [
|
|
@@ -58,6 +59,8 @@
|
|
|
58
59
|
"@scalar/openapi-parser": "0.28.7",
|
|
59
60
|
"@scalar/openapi-types": "0.9.1",
|
|
60
61
|
"@xhmikosr/decompress": "11.1.3",
|
|
62
|
+
"ajv": "8.20.0",
|
|
63
|
+
"ajv-formats": "3.0.1",
|
|
61
64
|
"basic-auth": "2.0.1",
|
|
62
65
|
"chalk": "5.6.2",
|
|
63
66
|
"commander": "15.0.0",
|
|
@@ -74,6 +77,7 @@
|
|
|
74
77
|
"jsonwebtoken": "9.0.3",
|
|
75
78
|
"mime-db": "1.54.0",
|
|
76
79
|
"mime-types": "3.0.2",
|
|
80
|
+
"minisearch": "7.2.0",
|
|
77
81
|
"netmask": "2.1.1",
|
|
78
82
|
"node-forge": "1.4.0",
|
|
79
83
|
"open": "11.0.0",
|
|
@@ -92,6 +96,7 @@
|
|
|
92
96
|
"uuid": "14.0.0",
|
|
93
97
|
"which": "4.0.0",
|
|
94
98
|
"ws": "8.21.0",
|
|
99
|
+
"yaml": "2.8.3",
|
|
95
100
|
"zod": "3.25.76"
|
|
96
101
|
},
|
|
97
102
|
"devDependencies": {
|