@adep/cli 0.4.1 → 0.4.4

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/dist/vite.js CHANGED
@@ -15,6 +15,8 @@ var DB_RPC = {
15
15
  query: "query",
16
16
  /** 写路径(CF-013):`(method=writeQuery, args=[sql, params])` → `{ changes }`。 */
17
17
  writeQuery: "writeQuery",
18
+ /** 通用执行(BUG-4,2026-10-14):`(method=execute, args=[sql, params?])` → `{ changes }`。 */
19
+ execute: "execute",
18
20
  /** 读取 owned 表变更流(DB-006):`(method=changes, args=[table, query])`。 */
19
21
  changes: "changes",
20
22
  /** 开启事务:`begin → txId`。 */
@@ -62,6 +64,30 @@ function normalizeHttpStatus(status) {
62
64
  }
63
65
 
64
66
  // packages/runtime/src/shared/http-envelope.ts
67
+ function coerceAdepHttpEnvelope(value) {
68
+ if (typeof value !== "object" || value === null || Array.isArray(value)) return null;
69
+ if (isAdepHttpEnvelope(value)) return value;
70
+ const keys = Object.keys(value);
71
+ if (keys.length === 0) return null;
72
+ if (!keys.every((key) => key === "status" || key === "body" || key === "headers")) return null;
73
+ const candidate = value;
74
+ const status = candidate.status;
75
+ if (typeof status !== "number" || !Number.isInteger(status) || status < 100 || status > 599) {
76
+ return null;
77
+ }
78
+ if ("headers" in candidate && candidate.headers !== void 0) {
79
+ const headers = candidate.headers;
80
+ if (typeof headers !== "object" || headers === null || Array.isArray(headers)) return null;
81
+ if (!Object.values(headers).every((headerValue2) => typeof headerValue2 === "string")) return null;
82
+ }
83
+ return {
84
+ __adepHttp: {
85
+ status,
86
+ ...candidate.headers === void 0 ? {} : { headers: candidate.headers },
87
+ body: candidate.body
88
+ }
89
+ };
90
+ }
65
91
  function isAdepHttpEnvelope(value) {
66
92
  if (typeof value !== "object" || value === null) return false;
67
93
  const envelope = value.__adepHttp;
@@ -454,6 +480,14 @@ function assertWriteQuery(sql) {
454
480
  );
455
481
  }
456
482
  }
483
+ function classifyStatement(sql) {
484
+ const head = sqlHead(stripLiterals(sql));
485
+ if (head.startsWith("SELECT") || head.startsWith("WITH")) return "read";
486
+ if (head.startsWith("INSERT") || head.startsWith("UPDATE") || head.startsWith("DELETE")) {
487
+ return "write";
488
+ }
489
+ return "ddl";
490
+ }
457
491
 
458
492
  // packages/runtime/src/database/builder/owned.ts
459
493
  var OWNED_PK = "id";
@@ -1006,6 +1040,21 @@ function createCloudDb(driver, options = {}) {
1006
1040
  assertWriteQuery(sql);
1007
1041
  return driver.run(sql, params);
1008
1042
  },
1043
+ async execute(sql, params = []) {
1044
+ if (sql.trim() === "") {
1045
+ throw unsafeOperation("execute \u7684 sql \u4E0D\u80FD\u4E3A\u7A7A");
1046
+ }
1047
+ if (!Array.isArray(params)) {
1048
+ throw unsafeOperation("execute \u7684 params \u5FC5\u987B\u662F\u6570\u7EC4\uFF08\u65E0\u53C2\u53EF\u4E0D\u4F20\uFF09");
1049
+ }
1050
+ guardWrite();
1051
+ const kind = classifyStatement(sql);
1052
+ if (kind === "read") {
1053
+ await driver.all(sql, params);
1054
+ return { changes: 0 };
1055
+ }
1056
+ return driver.run(sql, params);
1057
+ },
1009
1058
  async changes(table, query = {}) {
1010
1059
  return readChanges(driver, table, query);
1011
1060
  }
@@ -1081,6 +1130,10 @@ function createDbCapability(driver, options = {}) {
1081
1130
  const [sql, params] = args;
1082
1131
  return await db.writeQuery(sql, params);
1083
1132
  }
1133
+ case DB_RPC.execute: {
1134
+ const [sql, params] = args;
1135
+ return await db.execute(sql, params ?? []);
1136
+ }
1084
1137
  case DB_RPC.changes: {
1085
1138
  const [table, query] = args;
1086
1139
  return await db.changes(table, query);
@@ -3211,6 +3264,15 @@ function parseAdepConfig(raw) {
3211
3264
  data.environment = rec;
3212
3265
  }
3213
3266
  }
3267
+ if (input.db_environment !== void 0) {
3268
+ if (input.db_environment !== "dev" && input.db_environment !== "prod") {
3269
+ errors.push(
3270
+ `db_environment \u53EA\u63A5\u53D7 'dev' \u6216 'prod'\uFF0C\u6536\u5230 ${typeNameOf(input.db_environment)}\uFF08\u6CE8\u610F\u522B\u4E0E environment \u6DF7\u7528\uFF1A\u540E\u8005\u662F\u6CE8\u5165\u51FD\u6570\u8FD0\u884C\u65F6\u7684\u53D8\u91CF\u8868\uFF09`
3271
+ );
3272
+ } else {
3273
+ data.db_environment = input.db_environment;
3274
+ }
3275
+ }
3214
3276
  if (input.runtime !== void 0) {
3215
3277
  const rec = asRecord(input.runtime);
3216
3278
  if (rec === null) {
@@ -4340,7 +4402,9 @@ function errorMessageOf2(error) {
4340
4402
  return String(error);
4341
4403
  }
4342
4404
  async function normalizeResultBody(value) {
4343
- if (!(value instanceof Response)) return value;
4405
+ if (!(value instanceof Response)) {
4406
+ return coerceAdepHttpEnvelope(value) ?? value;
4407
+ }
4344
4408
  const contentType = value.headers.get("content-type") ?? "";
4345
4409
  const text = await value.text();
4346
4410
  let payload = text;
@@ -4588,7 +4652,7 @@ function createBearerUserResolver(issuer) {
4588
4652
  function isRuntimeSource(name) {
4589
4653
  return (name.endsWith(".ts") || name.endsWith(".js")) && !name.endsWith(".d.ts") && !name.endsWith(".test.ts");
4590
4654
  }
4591
- async function collectFunctions(dir) {
4655
+ async function collectFunctions(dir, readImpl = (path) => readFile6(path, "utf8")) {
4592
4656
  const files = {};
4593
4657
  const walk = async (sub, prefix) => {
4594
4658
  let entries;
@@ -4603,7 +4667,8 @@ async function collectFunctions(dir) {
4603
4667
  if (entry.isDirectory()) {
4604
4668
  await walk(full, rel);
4605
4669
  } else if (entry.isFile() && isRuntimeSource(entry.name)) {
4606
- files[rel] = await readFile6(full, "utf8");
4670
+ const content = await readImpl(full).catch(() => null);
4671
+ if (content !== null) files[rel] = content;
4607
4672
  }
4608
4673
  }
4609
4674
  };
@@ -4679,7 +4744,8 @@ async function loadConfig(cwd) {
4679
4744
  name: config?.name ?? name,
4680
4745
  functionsDir: config?.functionsDir ?? "functions",
4681
4746
  functionsPrefix: config?.functions_prefix ?? "",
4682
- ...config?.environment === void 0 ? {} : { environment: config.environment }
4747
+ ...config?.environment === void 0 ? {} : { environment: config.environment },
4748
+ ...config?.db_environment === void 0 ? {} : { dbEnvironment: config.db_environment }
4683
4749
  };
4684
4750
  }
4685
4751
  var parseEnvFile = parseEnv;
@@ -594,6 +594,8 @@ var DB_RPC = {
594
594
  query: "query",
595
595
  /** 写路径(CF-013):`(method=writeQuery, args=[sql, params])` → `{ changes }`。 */
596
596
  writeQuery: "writeQuery",
597
+ /** 通用执行(BUG-4,2026-10-14):`(method=execute, args=[sql, params?])` → `{ changes }`。 */
598
+ execute: "execute",
597
599
  /** 读取 owned 表变更流(DB-006):`(method=changes, args=[table, query])`。 */
598
600
  changes: "changes",
599
601
  /** 开启事务:`begin → txId`。 */
@@ -732,6 +734,39 @@ function createChainClient(capability, port, pending, nextId, spec) {
732
734
  return makeRoot(void 0);
733
735
  }
734
736
 
737
+ // packages/runtime/src/shared/http-envelope.ts
738
+ function coerceAdepHttpEnvelope(value) {
739
+ if (typeof value !== "object" || value === null || Array.isArray(value)) return null;
740
+ if (isAdepHttpEnvelope(value)) return value;
741
+ const keys = Object.keys(value);
742
+ if (keys.length === 0) return null;
743
+ if (!keys.every((key) => key === "status" || key === "body" || key === "headers")) return null;
744
+ const candidate = value;
745
+ const status = candidate.status;
746
+ if (typeof status !== "number" || !Number.isInteger(status) || status < 100 || status > 599) {
747
+ return null;
748
+ }
749
+ if ("headers" in candidate && candidate.headers !== void 0) {
750
+ const headers = candidate.headers;
751
+ if (typeof headers !== "object" || headers === null || Array.isArray(headers)) return null;
752
+ if (!Object.values(headers).every((headerValue2) => typeof headerValue2 === "string")) return null;
753
+ }
754
+ return {
755
+ __adepHttp: {
756
+ status,
757
+ ...candidate.headers === void 0 ? {} : { headers: candidate.headers },
758
+ body: candidate.body
759
+ }
760
+ };
761
+ }
762
+ function isAdepHttpEnvelope(value) {
763
+ if (typeof value !== "object" || value === null) return false;
764
+ const envelope = value.__adepHttp;
765
+ if (typeof envelope !== "object" || envelope === null) return false;
766
+ const status = envelope.status;
767
+ return typeof status === "number" && Number.isInteger(status) && status >= 100 && status <= 599;
768
+ }
769
+
735
770
  // packages/runtime/src/functions/deps/manifest.ts
736
771
  function splitBareSpecifier(request) {
737
772
  if (request.startsWith("@")) {
@@ -751,7 +786,9 @@ function errorMessageOf2(error) {
751
786
  return String(error);
752
787
  }
753
788
  async function normalizeResultBody(value) {
754
- if (!(value instanceof Response)) return value;
789
+ if (!(value instanceof Response)) {
790
+ return coerceAdepHttpEnvelope(value) ?? value;
791
+ }
755
792
  const contentType = value.headers.get("content-type") ?? "";
756
793
  const text = await value.text();
757
794
  let payload = text;
package/package.json CHANGED
@@ -7,7 +7,7 @@
7
7
  },
8
8
  "homepage": "https://adep.top",
9
9
  "bugs": "https://gitcode.com/yunqiang_wu/ai-yunke/issues",
10
- "version": "0.4.1",
10
+ "version": "0.4.4",
11
11
  "type": "module",
12
12
  "description": "`adep` 命令行工具包位:登录 / 初始化 / 本地调试 / 部署 / 数据库维护 / 云存储 / 静态托管 / 微前端组件(widget),实现见任务单 CLI-001 ~ CLI-003 与 FE-002;子路径 `@adep/cli/vite` 提供云函数 vite 插件(CLI-014)",
13
13
  "bin": {
@@ -30,13 +30,13 @@
30
30
  "esbuild": "0.25.12",
31
31
  "yaml": "2.9.1",
32
32
  "zod": "^4.4.3",
33
- "@adep/cf-compat": "0.1.2",
34
- "@adep/runtime": "0.3.3",
33
+ "@adep/cf-compat": "0.1.3",
34
+ "@adep/runtime": "0.3.4",
35
35
  "@adep/crypto": "0.1.1",
36
36
  "@adep/vite-plugin": "0.1.9"
37
37
  },
38
38
  "devDependencies": {
39
- "@adep/types": "0.3.1"
39
+ "@adep/types": "0.3.2"
40
40
  },
41
41
  "scripts": {
42
42
  "test": "vitest run",
@@ -0,0 +1,48 @@
1
+ // swift-tools-version: 5.9
2
+ //
3
+ // adep-bridge 的 Swift Package Manager 清单(APP-015)。
4
+ //
5
+ // ⚠️ **这是双形态中的一支,不是替代品**:CocoaPods 形态(`ios/AdepBridge.podspec`)**必须同时保留**——
6
+ // Capacitor 官方口径是「插件同时是 CocoaPods 与 SPM 库」;自 Capacitor 8 起 `cap add ios` 默认建 SPM 工程,
7
+ // 没有本文件的插件会被静默跳过(运行时表现为 "plugin is not implemented")。两支并存,各管一条消费路径。
8
+ //
9
+ // 命名与布局**不能随意改**(改了 Capacitor CLI 就找不到这个包):
10
+ // - 本文件必须在 **npm 包根**:`cap sync ios` 按 npm 包根路径写入 `.package(name:path:)`
11
+ // (`path: ".../node_modules/@adep/bridge"`),落在 `ios/` 下不会被消费。
12
+ // - `name` / product 名 = `AdepBridge`:由 npm 名 `@adep/bridge` 按官方规则派生
13
+ // (剥 `@`、`/`→`_`、分段首字母大写)。用别的名字会在 app 侧报
14
+ // "product 'X' required by package 'capapp-spm' target 'CapApp-SPM' not found"。
15
+ // 与既有 `s.name = 'AdepBridge'`(podspec)、`@objc(AdepBridge)` 一致。
16
+ // - `path: "ios/Sources"`:既有 Swift 源码就平铺在这(与 podspec 的 `source_files` glob 同一目录),
17
+ // 避免为 SPM 搬目录而牵动 podspec 与 capacitor.plugin.json。
18
+ //
19
+ // 版本与平台下限**两形态必须一致**(本仓判据见 `packages/cli/src/__tests__/adep-bridge-spm.test.ts`):
20
+ // - `platforms: [.iOS(.v14)]` ↔ podspec 的 `s.ios.deployment_target = '14.0'`。
21
+ // Capacitor 7 官方迁移要求把 iOS 下限从 13 抬到 14;两端不一致 = 同一插件对同一消费方给出不同平台约束。
22
+ // - `capacitor-swift-pm` 用 `from: "7.0.0"`(区间):app 侧按自己装的 `@capacitor/ios` 钉 exact 版本,
23
+ // 这里给区间让 SPM 能同时解析两者;写 `branch:` / `exact:` 会与 app 侧冲突。
24
+ // 与 podspec 的 `s.dependency 'Capacitor'`(无版本约束)对应——语义都是「跟随消费方的 Capacitor 版本」。
25
+ // - `Capacitor` **与** `Cordova` 两个 product 都要声明:只写 `Capacitor` 会报
26
+ // `fatal error: module 'Cordova' not found`(Capacitor.framework 的头文件里 `@_exported import Cordova`)。
27
+ import PackageDescription
28
+
29
+ let package = Package(
30
+ name: "AdepBridge",
31
+ platforms: [.iOS(.v14)],
32
+ products: [
33
+ .library(name: "AdepBridge", targets: ["AdepBridge"])
34
+ ],
35
+ dependencies: [
36
+ .package(url: "https://github.com/ionic-team/capacitor-swift-pm.git", from: "7.0.0")
37
+ ],
38
+ targets: [
39
+ .target(
40
+ name: "AdepBridge",
41
+ dependencies: [
42
+ .product(name: "Capacitor", package: "capacitor-swift-pm"),
43
+ .product(name: "Cordova", package: "capacitor-swift-pm"),
44
+ ],
45
+ path: "ios/Sources"
46
+ )
47
+ ]
48
+ )
@@ -7,7 +7,10 @@ Pod::Spec.new do |s|
7
7
  s.license = 'MIT'
8
8
  s.author = 'AgentDeploy'
9
9
  s.source = { :git => 'https://adep.top/adep-bridge.git', :tag => s.version.to_s }
10
- s.ios.deployment_target = '13.0'
10
+ # iOS 下限与 SPM 形态(包根 Package.swift 的 platforms)**必须一致**:
11
+ # Capacitor 7 官方迁移要求抬到 14(原 13)。两端不一致 = 同一插件对两条消费路径给出不同平台约束。
12
+ # 一致性由 packages/cli/src/__tests__/adep-bridge-spm.test.ts 钉住。
13
+ s.ios.deployment_target = '14.0'
11
14
  s.source_files = 'Sources/**/*.swift'
12
15
  s.swift_version = '5.1'
13
16
  s.dependency 'Capacitor'