bkper 3.8.1 → 4.0.0

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.
Files changed (343) hide show
  1. package/CHANGELOG.md +20 -1
  2. package/README.md +217 -183
  3. package/lib/auth/auth-page.d.ts +14 -0
  4. package/lib/auth/auth-page.d.ts.map +1 -0
  5. package/lib/auth/auth-page.js +110 -0
  6. package/lib/auth/auth-page.js.map +1 -0
  7. package/lib/auth/local-auth-service.d.ts.map +1 -1
  8. package/lib/auth/local-auth-service.js +135 -17
  9. package/lib/auth/local-auth-service.js.map +1 -1
  10. package/lib/bkper-factory.d.ts.map +1 -0
  11. package/lib/{mcp/bkper-factory.js → bkper-factory.js} +5 -2
  12. package/lib/bkper-factory.js.map +1 -0
  13. package/lib/cli.d.ts +1 -1
  14. package/lib/cli.d.ts.map +1 -1
  15. package/lib/cli.js +851 -47
  16. package/lib/cli.js.map +1 -1
  17. package/lib/commands/accounts/create.d.ts +10 -0
  18. package/lib/commands/accounts/create.d.ts.map +1 -0
  19. package/lib/commands/accounts/create.js +42 -0
  20. package/lib/commands/accounts/create.js.map +1 -0
  21. package/lib/commands/accounts/delete.d.ts +3 -0
  22. package/lib/commands/accounts/delete.d.ts.map +1 -0
  23. package/lib/commands/accounts/delete.js +22 -0
  24. package/lib/commands/accounts/delete.js.map +1 -0
  25. package/lib/commands/accounts/get.d.ts +3 -0
  26. package/lib/commands/accounts/get.d.ts.map +1 -0
  27. package/lib/commands/accounts/get.js +22 -0
  28. package/lib/commands/accounts/get.js.map +1 -0
  29. package/lib/commands/accounts/index.d.ts +6 -0
  30. package/lib/commands/accounts/index.d.ts.map +1 -0
  31. package/lib/commands/accounts/index.js +6 -0
  32. package/lib/commands/accounts/index.js.map +1 -0
  33. package/lib/commands/accounts/list.d.ts +3 -0
  34. package/lib/commands/accounts/list.d.ts.map +1 -0
  35. package/lib/commands/accounts/list.js +19 -0
  36. package/lib/commands/accounts/list.js.map +1 -0
  37. package/lib/commands/accounts/update.d.ts +9 -0
  38. package/lib/commands/accounts/update.d.ts.map +1 -0
  39. package/lib/commands/accounts/update.js +40 -0
  40. package/lib/commands/accounts/update.js.map +1 -0
  41. package/lib/commands/apps/build.d.ts +11 -0
  42. package/lib/commands/apps/build.d.ts.map +1 -0
  43. package/lib/commands/apps/build.js +144 -0
  44. package/lib/commands/apps/build.js.map +1 -0
  45. package/lib/commands/apps/bundler.d.ts +34 -0
  46. package/lib/commands/apps/bundler.d.ts.map +1 -0
  47. package/lib/commands/apps/bundler.js +112 -0
  48. package/lib/commands/apps/bundler.js.map +1 -0
  49. package/lib/commands/apps/config.d.ts +51 -0
  50. package/lib/commands/apps/config.d.ts.map +1 -0
  51. package/lib/commands/apps/config.js +146 -0
  52. package/lib/commands/apps/config.js.map +1 -0
  53. package/lib/commands/apps/deploy.d.ts +23 -0
  54. package/lib/commands/apps/deploy.d.ts.map +1 -0
  55. package/lib/commands/apps/deploy.js +344 -0
  56. package/lib/commands/apps/deploy.js.map +1 -0
  57. package/lib/commands/apps/dev.d.ts +28 -0
  58. package/lib/commands/apps/dev.d.ts.map +1 -0
  59. package/lib/commands/apps/dev.js +393 -0
  60. package/lib/commands/apps/dev.js.map +1 -0
  61. package/lib/commands/apps/index.d.ts +12 -0
  62. package/lib/commands/apps/index.d.ts.map +1 -0
  63. package/lib/commands/apps/index.js +24 -0
  64. package/lib/commands/apps/index.js.map +1 -0
  65. package/lib/commands/apps/init.d.ts +7 -0
  66. package/lib/commands/apps/init.d.ts.map +1 -0
  67. package/lib/commands/apps/init.js +249 -0
  68. package/lib/commands/apps/init.js.map +1 -0
  69. package/lib/commands/apps/install.d.ts +3 -0
  70. package/lib/commands/apps/install.d.ts.map +1 -0
  71. package/lib/commands/apps/install.js +18 -0
  72. package/lib/commands/apps/install.js.map +1 -0
  73. package/lib/commands/apps/list.d.ts +7 -0
  74. package/lib/commands/apps/list.d.ts.map +1 -0
  75. package/lib/commands/apps/list.js +23 -0
  76. package/lib/commands/apps/list.js.map +1 -0
  77. package/lib/commands/apps/secrets.d.ts +22 -0
  78. package/lib/commands/apps/secrets.d.ts.map +1 -0
  79. package/lib/commands/apps/secrets.js +209 -0
  80. package/lib/commands/apps/secrets.js.map +1 -0
  81. package/lib/commands/{apps.d.ts → apps/sync.d.ts} +8 -7
  82. package/lib/commands/apps/sync.d.ts.map +1 -0
  83. package/lib/commands/apps/sync.js +76 -0
  84. package/lib/commands/apps/sync.js.map +1 -0
  85. package/lib/commands/apps/types.d.ts +54 -0
  86. package/lib/commands/apps/types.d.ts.map +1 -0
  87. package/lib/commands/apps/types.js +2 -0
  88. package/lib/commands/apps/types.js.map +1 -0
  89. package/lib/commands/apps/uninstall.d.ts +3 -0
  90. package/lib/commands/apps/uninstall.d.ts.map +1 -0
  91. package/lib/commands/apps/uninstall.js +23 -0
  92. package/lib/commands/apps/uninstall.js.map +1 -0
  93. package/lib/commands/balances/get.d.ts +12 -0
  94. package/lib/commands/balances/get.d.ts.map +1 -0
  95. package/lib/commands/balances/get.js +32 -0
  96. package/lib/commands/balances/get.js.map +1 -0
  97. package/lib/commands/balances/index.d.ts +2 -0
  98. package/lib/commands/balances/index.d.ts.map +1 -0
  99. package/lib/commands/balances/index.js +2 -0
  100. package/lib/commands/balances/index.js.map +1 -0
  101. package/lib/commands/books/create.d.ts +12 -0
  102. package/lib/commands/books/create.d.ts.map +1 -0
  103. package/lib/commands/books/create.js +37 -0
  104. package/lib/commands/books/create.js.map +1 -0
  105. package/lib/commands/books/get.d.ts +3 -0
  106. package/lib/commands/books/get.d.ts.map +1 -0
  107. package/lib/commands/books/get.js +17 -0
  108. package/lib/commands/books/get.js.map +1 -0
  109. package/lib/commands/books/index.d.ts +5 -0
  110. package/lib/commands/books/index.d.ts.map +1 -0
  111. package/lib/commands/books/index.js +5 -0
  112. package/lib/commands/books/index.js.map +1 -0
  113. package/lib/commands/books/list.d.ts +3 -0
  114. package/lib/commands/books/list.d.ts.map +1 -0
  115. package/lib/commands/books/list.js +17 -0
  116. package/lib/commands/books/list.js.map +1 -0
  117. package/lib/commands/books/update.d.ts +14 -0
  118. package/lib/commands/books/update.d.ts.map +1 -0
  119. package/lib/commands/books/update.js +46 -0
  120. package/lib/commands/books/update.js.map +1 -0
  121. package/lib/commands/collections/add-book.d.ts +3 -0
  122. package/lib/commands/collections/add-book.d.ts.map +1 -0
  123. package/lib/commands/collections/add-book.js +27 -0
  124. package/lib/commands/collections/add-book.js.map +1 -0
  125. package/lib/commands/collections/create.d.ts +6 -0
  126. package/lib/commands/collections/create.d.ts.map +1 -0
  127. package/lib/commands/collections/create.js +19 -0
  128. package/lib/commands/collections/create.js.map +1 -0
  129. package/lib/commands/collections/delete.d.ts +3 -0
  130. package/lib/commands/collections/delete.d.ts.map +1 -0
  131. package/lib/commands/collections/delete.js +22 -0
  132. package/lib/commands/collections/delete.js.map +1 -0
  133. package/lib/commands/collections/get.d.ts +3 -0
  134. package/lib/commands/collections/get.d.ts.map +1 -0
  135. package/lib/commands/collections/get.js +22 -0
  136. package/lib/commands/collections/get.js.map +1 -0
  137. package/lib/commands/collections/index.d.ts +8 -0
  138. package/lib/commands/collections/index.d.ts.map +1 -0
  139. package/lib/commands/collections/index.js +8 -0
  140. package/lib/commands/collections/index.js.map +1 -0
  141. package/lib/commands/collections/list.d.ts +3 -0
  142. package/lib/commands/collections/list.d.ts.map +1 -0
  143. package/lib/commands/collections/list.js +18 -0
  144. package/lib/commands/collections/list.js.map +1 -0
  145. package/lib/commands/collections/remove-book.d.ts +3 -0
  146. package/lib/commands/collections/remove-book.d.ts.map +1 -0
  147. package/lib/commands/collections/remove-book.js +27 -0
  148. package/lib/commands/collections/remove-book.js.map +1 -0
  149. package/lib/commands/collections/update.d.ts +6 -0
  150. package/lib/commands/collections/update.d.ts.map +1 -0
  151. package/lib/commands/collections/update.js +24 -0
  152. package/lib/commands/collections/update.js.map +1 -0
  153. package/lib/commands/groups/create.d.ts +9 -0
  154. package/lib/commands/groups/create.d.ts.map +1 -0
  155. package/lib/commands/groups/create.js +40 -0
  156. package/lib/commands/groups/create.js.map +1 -0
  157. package/lib/commands/groups/delete.d.ts +3 -0
  158. package/lib/commands/groups/delete.d.ts.map +1 -0
  159. package/lib/commands/groups/delete.js +22 -0
  160. package/lib/commands/groups/delete.js.map +1 -0
  161. package/lib/commands/groups/get.d.ts +3 -0
  162. package/lib/commands/groups/get.d.ts.map +1 -0
  163. package/lib/commands/groups/get.js +22 -0
  164. package/lib/commands/groups/get.js.map +1 -0
  165. package/lib/commands/groups/index.d.ts +6 -0
  166. package/lib/commands/groups/index.d.ts.map +1 -0
  167. package/lib/commands/groups/index.js +6 -0
  168. package/lib/commands/groups/index.js.map +1 -0
  169. package/lib/commands/groups/list.d.ts +3 -0
  170. package/lib/commands/groups/list.d.ts.map +1 -0
  171. package/lib/commands/groups/list.js +19 -0
  172. package/lib/commands/groups/list.js.map +1 -0
  173. package/lib/commands/groups/update.d.ts +8 -0
  174. package/lib/commands/groups/update.d.ts.map +1 -0
  175. package/lib/commands/groups/update.js +38 -0
  176. package/lib/commands/groups/update.js.map +1 -0
  177. package/lib/commands/skills.d.ts +17 -0
  178. package/lib/commands/skills.d.ts.map +1 -0
  179. package/lib/commands/skills.js +248 -0
  180. package/lib/commands/skills.js.map +1 -0
  181. package/lib/commands/transactions/check.d.ts +3 -0
  182. package/lib/commands/transactions/check.d.ts.map +1 -0
  183. package/lib/commands/transactions/check.js +22 -0
  184. package/lib/commands/transactions/check.js.map +1 -0
  185. package/lib/commands/transactions/create.d.ts +13 -0
  186. package/lib/commands/transactions/create.d.ts.map +1 -0
  187. package/lib/commands/transactions/create.js +55 -0
  188. package/lib/commands/transactions/create.js.map +1 -0
  189. package/lib/commands/transactions/index.d.ts +8 -0
  190. package/lib/commands/transactions/index.d.ts.map +1 -0
  191. package/lib/commands/transactions/index.js +8 -0
  192. package/lib/commands/transactions/index.js.map +1 -0
  193. package/lib/commands/transactions/list.d.ts +14 -0
  194. package/lib/commands/transactions/list.d.ts.map +1 -0
  195. package/lib/commands/transactions/list.js +26 -0
  196. package/lib/commands/transactions/list.js.map +1 -0
  197. package/lib/commands/transactions/merge.d.ts +8 -0
  198. package/lib/commands/transactions/merge.d.ts.map +1 -0
  199. package/lib/commands/transactions/merge.js +44 -0
  200. package/lib/commands/transactions/merge.js.map +1 -0
  201. package/lib/commands/transactions/post.d.ts +3 -0
  202. package/lib/commands/transactions/post.d.ts.map +1 -0
  203. package/lib/commands/transactions/post.js +22 -0
  204. package/lib/commands/transactions/post.js.map +1 -0
  205. package/lib/commands/transactions/trash.d.ts +3 -0
  206. package/lib/commands/transactions/trash.d.ts.map +1 -0
  207. package/lib/commands/transactions/trash.js +22 -0
  208. package/lib/commands/transactions/trash.js.map +1 -0
  209. package/lib/commands/transactions/update.d.ts +12 -0
  210. package/lib/commands/transactions/update.d.ts.map +1 -0
  211. package/lib/commands/transactions/update.js +53 -0
  212. package/lib/commands/transactions/update.js.map +1 -0
  213. package/lib/dev/auth-middleware.d.ts +18 -0
  214. package/lib/dev/auth-middleware.d.ts.map +1 -0
  215. package/lib/dev/auth-middleware.js +113 -0
  216. package/lib/dev/auth-middleware.js.map +1 -0
  217. package/lib/dev/cleanup.d.ts +10 -0
  218. package/lib/dev/cleanup.d.ts.map +1 -0
  219. package/lib/dev/cleanup.js +36 -0
  220. package/lib/dev/cleanup.js.map +1 -0
  221. package/lib/dev/cloudflared/constants.d.ts +35 -0
  222. package/lib/dev/cloudflared/constants.d.ts.map +1 -0
  223. package/lib/dev/cloudflared/constants.js +48 -0
  224. package/lib/dev/cloudflared/constants.js.map +1 -0
  225. package/lib/dev/cloudflared/index.d.ts +11 -0
  226. package/lib/dev/cloudflared/index.d.ts.map +1 -0
  227. package/lib/dev/cloudflared/index.js +10 -0
  228. package/lib/dev/cloudflared/index.js.map +1 -0
  229. package/lib/dev/cloudflared/install.d.ts +15 -0
  230. package/lib/dev/cloudflared/install.d.ts.map +1 -0
  231. package/lib/dev/cloudflared/install.js +140 -0
  232. package/lib/dev/cloudflared/install.js.map +1 -0
  233. package/lib/dev/cloudflared/tunnel.d.ts +64 -0
  234. package/lib/dev/cloudflared/tunnel.d.ts.map +1 -0
  235. package/lib/dev/cloudflared/tunnel.js +109 -0
  236. package/lib/dev/cloudflared/tunnel.js.map +1 -0
  237. package/lib/dev/esbuild.d.ts +28 -0
  238. package/lib/dev/esbuild.d.ts.map +1 -0
  239. package/lib/dev/esbuild.js +83 -0
  240. package/lib/dev/esbuild.js.map +1 -0
  241. package/lib/dev/logger.d.ts +51 -0
  242. package/lib/dev/logger.d.ts.map +1 -0
  243. package/lib/dev/logger.js +102 -0
  244. package/lib/dev/logger.js.map +1 -0
  245. package/lib/dev/miniflare.d.ts +32 -0
  246. package/lib/dev/miniflare.d.ts.map +1 -0
  247. package/lib/dev/miniflare.js +111 -0
  248. package/lib/dev/miniflare.js.map +1 -0
  249. package/lib/dev/preflight.d.ts +7 -0
  250. package/lib/dev/preflight.d.ts.map +1 -0
  251. package/lib/dev/preflight.js +61 -0
  252. package/lib/dev/preflight.js.map +1 -0
  253. package/lib/dev/shared.d.ts +7 -0
  254. package/lib/dev/shared.d.ts.map +1 -0
  255. package/lib/dev/shared.js +99 -0
  256. package/lib/dev/shared.js.map +1 -0
  257. package/lib/dev/tunnel.d.ts +31 -0
  258. package/lib/dev/tunnel.d.ts.map +1 -0
  259. package/lib/dev/tunnel.js +110 -0
  260. package/lib/dev/tunnel.js.map +1 -0
  261. package/lib/dev/types.d.ts +53 -0
  262. package/lib/dev/types.d.ts.map +1 -0
  263. package/lib/dev/types.js +223 -0
  264. package/lib/dev/types.js.map +1 -0
  265. package/lib/dev/vite.d.ts +50 -0
  266. package/lib/dev/vite.d.ts.map +1 -0
  267. package/lib/dev/vite.js +114 -0
  268. package/lib/dev/vite.js.map +1 -0
  269. package/lib/dev/webhook-dev.d.ts +9 -0
  270. package/lib/dev/webhook-dev.d.ts.map +1 -0
  271. package/lib/dev/webhook-dev.js +28 -0
  272. package/lib/dev/webhook-dev.js.map +1 -0
  273. package/lib/domain/transaction/merge-operation.d.ts.map +1 -0
  274. package/lib/{mcp/domain → domain}/transaction/merge-operation.js +10 -11
  275. package/lib/domain/transaction/merge-operation.js.map +1 -0
  276. package/lib/domain/transaction/merge-types.d.ts.map +1 -0
  277. package/lib/domain/transaction/merge-types.js.map +1 -0
  278. package/lib/index.d.ts.map +1 -1
  279. package/lib/index.js.map +1 -1
  280. package/lib/platform/client.d.ts +37 -0
  281. package/lib/platform/client.d.ts.map +1 -0
  282. package/lib/platform/client.js +37 -0
  283. package/lib/platform/client.js.map +1 -0
  284. package/lib/render/index.d.ts +3 -0
  285. package/lib/render/index.d.ts.map +1 -0
  286. package/lib/render/index.js +3 -0
  287. package/lib/render/index.js.map +1 -0
  288. package/lib/render/output.d.ts +15 -0
  289. package/lib/render/output.d.ts.map +1 -0
  290. package/lib/render/output.js +30 -0
  291. package/lib/render/output.js.map +1 -0
  292. package/lib/render/table-formatter.d.ts +34 -0
  293. package/lib/render/table-formatter.d.ts.map +1 -0
  294. package/lib/render/table-formatter.js +221 -0
  295. package/lib/render/table-formatter.js.map +1 -0
  296. package/lib/utils/properties.d.ts +12 -0
  297. package/lib/utils/properties.d.ts.map +1 -0
  298. package/lib/utils/properties.js +23 -0
  299. package/lib/utils/properties.js.map +1 -0
  300. package/package.json +23 -23
  301. package/lib/auth/keys.json +0 -12
  302. package/lib/commands/apps.d.ts.map +0 -1
  303. package/lib/commands/apps.js +0 -93
  304. package/lib/commands/apps.js.map +0 -1
  305. package/lib/mcp/bkper-factory.d.ts.map +0 -1
  306. package/lib/mcp/bkper-factory.js.map +0 -1
  307. package/lib/mcp/domain/transaction/merge-operation.d.ts.map +0 -1
  308. package/lib/mcp/domain/transaction/merge-operation.js.map +0 -1
  309. package/lib/mcp/domain/transaction/merge-types.d.ts.map +0 -1
  310. package/lib/mcp/domain/transaction/merge-types.js.map +0 -1
  311. package/lib/mcp/server.d.ts +0 -13
  312. package/lib/mcp/server.d.ts.map +0 -1
  313. package/lib/mcp/server.js +0 -161
  314. package/lib/mcp/server.js.map +0 -1
  315. package/lib/mcp/system-prompt.md +0 -192
  316. package/lib/mcp/tools/create_transactions.d.ts +0 -59
  317. package/lib/mcp/tools/create_transactions.d.ts.map +0 -1
  318. package/lib/mcp/tools/create_transactions.js +0 -163
  319. package/lib/mcp/tools/create_transactions.js.map +0 -1
  320. package/lib/mcp/tools/get_balances.d.ts +0 -26
  321. package/lib/mcp/tools/get_balances.d.ts.map +0 -1
  322. package/lib/mcp/tools/get_balances.js +0 -106
  323. package/lib/mcp/tools/get_balances.js.map +0 -1
  324. package/lib/mcp/tools/get_book.d.ts +0 -21
  325. package/lib/mcp/tools/get_book.d.ts.map +0 -1
  326. package/lib/mcp/tools/get_book.js +0 -126
  327. package/lib/mcp/tools/get_book.js.map +0 -1
  328. package/lib/mcp/tools/list_books.d.ts +0 -21
  329. package/lib/mcp/tools/list_books.d.ts.map +0 -1
  330. package/lib/mcp/tools/list_books.js +0 -67
  331. package/lib/mcp/tools/list_books.js.map +0 -1
  332. package/lib/mcp/tools/list_transactions.d.ts +0 -38
  333. package/lib/mcp/tools/list_transactions.d.ts.map +0 -1
  334. package/lib/mcp/tools/list_transactions.js +0 -109
  335. package/lib/mcp/tools/list_transactions.js.map +0 -1
  336. package/lib/mcp/tools/merge_transactions.d.ts +0 -40
  337. package/lib/mcp/tools/merge_transactions.d.ts.map +0 -1
  338. package/lib/mcp/tools/merge_transactions.js +0 -120
  339. package/lib/mcp/tools/merge_transactions.js.map +0 -1
  340. /package/lib/{mcp/bkper-factory.d.ts → bkper-factory.d.ts} +0 -0
  341. /package/lib/{mcp/domain → domain}/transaction/merge-operation.d.ts +0 -0
  342. /package/lib/{mcp/domain → domain}/transaction/merge-types.d.ts +0 -0
  343. /package/lib/{mcp/domain → domain}/transaction/merge-types.js +0 -0
package/lib/cli.js CHANGED
@@ -8,95 +8,899 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
8
8
  step((generator = generator.apply(thisArg, _arguments || [])).next());
9
9
  });
10
10
  };
11
- import program from "commander";
12
- import { login, logout } from "./auth/local-auth-service.js";
13
- import { setupBkper } from "./mcp/bkper-factory.js";
14
- import { listApps, createApp, updateApp } from "./commands/apps.js";
15
- import dotenv from "dotenv";
16
- dotenv.config();
11
+ import 'dotenv/config'; // Must be first to load env vars before other imports
12
+ import { program } from 'commander';
13
+ import { BooksDataTableBuilder, AccountsDataTableBuilder, GroupsDataTableBuilder, } from 'bkper-js';
14
+ import { login, logout } from './auth/local-auth-service.js';
15
+ import { setupBkper } from './bkper-factory.js';
16
+ import { listApps, syncApp, deployApp, undeployApp, statusApp, initApp, secretsPut, secretsList, secretsDelete, dev, build, installApp, uninstallApp, } from './commands/apps/index.js';
17
+ import { listBooks, getBook, createBook, updateBook } from './commands/books/index.js';
18
+ import { listAccounts, getAccount, createAccount, updateAccount, deleteAccount, } from './commands/accounts/index.js';
19
+ import { listGroups, getGroup, createGroup, updateGroup, deleteGroup, } from './commands/groups/index.js';
20
+ import { listTransactions, createTransaction, updateTransaction, postTransaction, checkTransaction, trashTransaction, mergeTransactions, } from './commands/transactions/index.js';
21
+ import { getBalancesMatrix } from './commands/balances/index.js';
22
+ import { listCollections, getCollection, createCollection, updateCollection, deleteCollection, addBookToCollection, removeBookFromCollection, } from './commands/collections/index.js';
23
+ import { renderTable, renderItem } from './render/index.js';
24
+ function collectProperty(value, previous) {
25
+ return previous ? [...previous, value] : [value];
26
+ }
27
+ // Global --json option
28
+ program.option('--json', 'Output as JSON');
29
+ function isJson() {
30
+ return program.opts().json === true;
31
+ }
17
32
  program
18
- .command("login")
19
- .description("Login Bkper")
33
+ .command('login')
34
+ .description('Login Bkper')
20
35
  .action(() => __awaiter(void 0, void 0, void 0, function* () {
21
36
  yield login();
22
37
  }));
23
38
  program
24
- .command("logout")
25
- .description("Logout Bkper")
39
+ .command('logout')
40
+ .description('Logout Bkper')
26
41
  .action(() => {
27
42
  logout();
28
43
  });
29
- // New 'apps' command group (plural, standard)
30
- const appsCommand = program.command("apps").description("Manage Bkper Apps");
31
- appsCommand
32
- .command("list")
33
- .description("List all apps you have access to")
44
+ // 'app' command group (singular, modern pattern)
45
+ const appCommand = program.command('app').description('Manage Bkper Apps');
46
+ appCommand
47
+ .command('init <name>')
48
+ .description('Create a new Bkper app from template')
49
+ .action((name) => __awaiter(void 0, void 0, void 0, function* () {
50
+ try {
51
+ yield initApp(name);
52
+ }
53
+ catch (err) {
54
+ console.error('Error initializing app:', err);
55
+ process.exit(1);
56
+ }
57
+ }));
58
+ appCommand
59
+ .command('list')
60
+ .description('List all apps you have access to')
34
61
  .action(() => __awaiter(void 0, void 0, void 0, function* () {
35
62
  try {
36
63
  setupBkper();
37
64
  const apps = yield listApps();
65
+ if (isJson()) {
66
+ console.log(JSON.stringify(apps, null, 2));
67
+ return;
68
+ }
38
69
  if (apps.length === 0) {
39
- console.log("No apps found.");
70
+ console.log('No results found.');
40
71
  return;
41
72
  }
42
- // Table-style output
43
- console.log("\nApps:\n");
44
- console.log("ID".padEnd(25) + "Name".padEnd(30) + "Published");
45
- console.log("-".repeat(65));
73
+ const matrix = [['ID', 'Name', 'Published']];
46
74
  for (const app of apps) {
47
- const id = (app.id || "").padEnd(25);
48
- const name = (app.name || "").padEnd(30);
49
- const published = app.published ? "Yes" : "No";
50
- console.log(`${id}${name}${published}`);
75
+ matrix.push([app.id || '', app.name || '', app.published ? 'Yes' : 'No']);
51
76
  }
52
- console.log(`\nTotal: ${apps.length} app(s)`);
77
+ renderTable(matrix, false);
53
78
  }
54
79
  catch (err) {
55
- console.error("Error listing apps:", err);
80
+ console.error('Error listing apps:', err);
56
81
  process.exit(1);
57
82
  }
58
83
  }));
59
- appsCommand
60
- .command("create")
61
- .description("Create a new App from bkperapp.json or bkperapp.yaml")
84
+ appCommand
85
+ .command('sync')
86
+ .description('Sync app config to Bkper (creates if new, updates if exists)')
62
87
  .action(() => __awaiter(void 0, void 0, void 0, function* () {
63
88
  try {
64
89
  setupBkper();
65
- const app = yield createApp();
66
- console.log(`Created ${app.getId()} successfully.`);
90
+ const result = yield syncApp();
91
+ console.log(`Synced ${result.id} (${result.action})`);
92
+ }
93
+ catch (err) {
94
+ console.error('Error syncing app:', err);
95
+ process.exit(1);
96
+ }
97
+ }));
98
+ appCommand
99
+ .command('deploy')
100
+ .description('Deploy app to Bkper Platform')
101
+ .option('-p, --preview', 'Deploy to preview environment')
102
+ .option('--events', 'Deploy events handler instead of web handler')
103
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
104
+ try {
105
+ yield deployApp(options);
67
106
  }
68
107
  catch (err) {
69
- console.error("Error creating app:", err);
108
+ console.error('Error deploying app:', err);
70
109
  process.exit(1);
71
110
  }
72
111
  }));
73
- appsCommand
74
- .command("update")
75
- .description("Update an existing App from bkperapp.json or bkperapp.yaml")
112
+ appCommand
113
+ .command('undeploy')
114
+ .description('Remove app from Bkper Platform')
115
+ .option('-p, --preview', 'Remove from preview environment')
116
+ .option('--events', 'Remove events handler instead of web handler')
117
+ .option('--delete-data', 'Permanently delete all associated data (requires confirmation)')
118
+ .option('--force', 'Skip confirmation prompts (use with --delete-data for automation)')
119
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
120
+ try {
121
+ yield undeployApp(options);
122
+ }
123
+ catch (err) {
124
+ console.error('Error undeploying app:', err);
125
+ process.exit(1);
126
+ }
127
+ }));
128
+ appCommand
129
+ .command('status')
130
+ .description('Show deployment status for all handlers')
76
131
  .action(() => __awaiter(void 0, void 0, void 0, function* () {
132
+ try {
133
+ yield statusApp();
134
+ }
135
+ catch (err) {
136
+ console.error('Error getting app status:', err);
137
+ process.exit(1);
138
+ }
139
+ }));
140
+ // Development server command
141
+ appCommand
142
+ .command('dev')
143
+ .description('Start the development server')
144
+ .option('--cp, --client-port <port>', 'Client dev server port', '5173')
145
+ .option('--sp, --server-port <port>', 'Server simulation port', '8787')
146
+ .option('--ep, --events-port <port>', 'Events handler port', '8791')
147
+ .option('-w, --web', 'Run only the web handler')
148
+ .option('-e, --events', 'Run only the events handler')
149
+ .option('--no-open', 'Do not open browser on startup')
150
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
151
+ try {
152
+ setupBkper();
153
+ yield dev({
154
+ clientPort: parseInt(options.clientPort, 10),
155
+ serverPort: parseInt(options.serverPort, 10),
156
+ eventsPort: parseInt(options.eventsPort, 10),
157
+ web: options.web,
158
+ events: options.events,
159
+ open: options.open,
160
+ });
161
+ }
162
+ catch (err) {
163
+ console.error('Error starting dev server:', err);
164
+ process.exit(1);
165
+ }
166
+ }));
167
+ // Build command
168
+ appCommand
169
+ .command('build')
170
+ .description('Build all configured handlers for deployment')
171
+ .action(() => __awaiter(void 0, void 0, void 0, function* () {
172
+ try {
173
+ yield build();
174
+ }
175
+ catch (err) {
176
+ console.error('Error building app:', err);
177
+ process.exit(1);
178
+ }
179
+ }));
180
+ // Secrets subcommand
181
+ const secretsCommand = appCommand.command('secrets').description('Manage app secrets');
182
+ secretsCommand
183
+ .command('put <name>')
184
+ .description('Set a secret value')
185
+ .option('-p, --preview', 'Set in preview environment')
186
+ .action((name, options) => __awaiter(void 0, void 0, void 0, function* () {
187
+ try {
188
+ yield secretsPut(name, options);
189
+ }
190
+ catch (err) {
191
+ console.error('Error setting secret:', err);
192
+ process.exit(1);
193
+ }
194
+ }));
195
+ secretsCommand
196
+ .command('list')
197
+ .description('List all secrets')
198
+ .option('-p, --preview', 'List from preview environment')
199
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
200
+ try {
201
+ yield secretsList(options);
202
+ }
203
+ catch (err) {
204
+ console.error('Error listing secrets:', err);
205
+ process.exit(1);
206
+ }
207
+ }));
208
+ secretsCommand
209
+ .command('delete <name>')
210
+ .description('Delete a secret')
211
+ .option('-p, --preview', 'Delete from preview environment')
212
+ .action((name, options) => __awaiter(void 0, void 0, void 0, function* () {
213
+ try {
214
+ yield secretsDelete(name, options);
215
+ }
216
+ catch (err) {
217
+ console.error('Error deleting secret:', err);
218
+ process.exit(1);
219
+ }
220
+ }));
221
+ appCommand
222
+ .command('install <appId>')
223
+ .description('Install an app into a book')
224
+ .requiredOption('-b, --book <bookId>', 'Book ID')
225
+ .action((appId, options) => __awaiter(void 0, void 0, void 0, function* () {
226
+ try {
227
+ setupBkper();
228
+ const integration = yield installApp(options.book, appId);
229
+ renderItem(integration.json(), isJson());
230
+ }
231
+ catch (err) {
232
+ console.error('Error installing app:', err);
233
+ process.exit(1);
234
+ }
235
+ }));
236
+ appCommand
237
+ .command('uninstall <appId>')
238
+ .description('Uninstall an app from a book')
239
+ .requiredOption('-b, --book <bookId>', 'Book ID')
240
+ .action((appId, options) => __awaiter(void 0, void 0, void 0, function* () {
241
+ try {
242
+ setupBkper();
243
+ const integration = yield uninstallApp(options.book, appId);
244
+ renderItem(integration.json(), isJson());
245
+ }
246
+ catch (err) {
247
+ console.error('Error uninstalling app:', err);
248
+ process.exit(1);
249
+ }
250
+ }));
251
+ // 'book' command group
252
+ const bookCommand = program.command('book').description('Manage Books');
253
+ bookCommand
254
+ .command('list')
255
+ .description('List all books')
256
+ .option('-q, --query <query>', 'Search query')
257
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
258
+ try {
259
+ setupBkper();
260
+ const books = yield listBooks(options.query);
261
+ if (isJson()) {
262
+ console.log(JSON.stringify(books.map(b => b.json()), null, 2));
263
+ }
264
+ else {
265
+ const matrix = new BooksDataTableBuilder(books).ids(true).build();
266
+ renderTable(matrix, false);
267
+ }
268
+ }
269
+ catch (err) {
270
+ console.error('Error listing books:', err);
271
+ process.exit(1);
272
+ }
273
+ }));
274
+ bookCommand
275
+ .command('get <bookId>')
276
+ .description('Get a book by ID')
277
+ .action((bookId) => __awaiter(void 0, void 0, void 0, function* () {
278
+ try {
279
+ setupBkper();
280
+ const book = yield getBook(bookId);
281
+ renderItem(book.json(), isJson());
282
+ }
283
+ catch (err) {
284
+ console.error('Error getting book:', err);
285
+ process.exit(1);
286
+ }
287
+ }));
288
+ bookCommand
289
+ .command('create')
290
+ .description('Create a new book')
291
+ .requiredOption('--name <name>', 'Book name')
292
+ .option('--fraction-digits <digits>', 'Number of decimal places (0-8)', parseInt)
293
+ .option('--date-pattern <pattern>', 'Date format pattern (dd/MM/yyyy, MM/dd/yyyy, or yyyy/MM/dd)')
294
+ .option('--decimal-separator <separator>', 'Decimal separator (DOT or COMMA)')
295
+ .option('--time-zone <timezone>', 'IANA time zone (e.g. America/New_York, UTC)')
296
+ .option('--period <period>', 'Period (MONTH, QUARTER, or YEAR)')
297
+ .option('-p, --property <key=value>', 'Set a property (repeatable)', collectProperty)
298
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
299
+ try {
300
+ setupBkper();
301
+ const book = yield createBook({
302
+ name: options.name,
303
+ fractionDigits: options.fractionDigits,
304
+ datePattern: options.datePattern,
305
+ decimalSeparator: options.decimalSeparator,
306
+ timeZone: options.timeZone,
307
+ period: options.period,
308
+ property: options.property,
309
+ });
310
+ renderItem(book.json(), isJson());
311
+ }
312
+ catch (err) {
313
+ console.error('Error creating book:', err);
314
+ process.exit(1);
315
+ }
316
+ }));
317
+ bookCommand
318
+ .command('update <bookId>')
319
+ .description('Update a book')
320
+ .option('--name <name>', 'Book name')
321
+ .option('--fraction-digits <digits>', 'Number of decimal places (0-8)', parseInt)
322
+ .option('--date-pattern <pattern>', 'Date format pattern (dd/MM/yyyy, MM/dd/yyyy, or yyyy/MM/dd)')
323
+ .option('--decimal-separator <separator>', 'Decimal separator (DOT or COMMA)')
324
+ .option('--time-zone <timezone>', 'IANA time zone (e.g. America/New_York, UTC)')
325
+ .option('--lock-date <date>', 'Lock date in ISO format (yyyy-MM-dd)')
326
+ .option('--closing-date <date>', 'Closing date in ISO format (yyyy-MM-dd)')
327
+ .option('--period <period>', 'Period (MONTH, QUARTER, or YEAR)')
328
+ .option('-p, --property <key=value>', 'Set a property (repeatable, empty value deletes)', collectProperty)
329
+ .action((bookId, options) => __awaiter(void 0, void 0, void 0, function* () {
330
+ try {
331
+ setupBkper();
332
+ const book = yield updateBook(bookId, {
333
+ name: options.name,
334
+ fractionDigits: options.fractionDigits,
335
+ datePattern: options.datePattern,
336
+ decimalSeparator: options.decimalSeparator,
337
+ timeZone: options.timeZone,
338
+ lockDate: options.lockDate,
339
+ closingDate: options.closingDate,
340
+ period: options.period,
341
+ property: options.property,
342
+ });
343
+ renderItem(book.json(), isJson());
344
+ }
345
+ catch (err) {
346
+ console.error('Error updating book:', err);
347
+ process.exit(1);
348
+ }
349
+ }));
350
+ // 'account' command group
351
+ const accountCommand = program.command('account').description('Manage Accounts');
352
+ accountCommand
353
+ .command('list')
354
+ .description('List all accounts in a book')
355
+ .requiredOption('-b, --book <bookId>', 'Book ID')
356
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
357
+ try {
358
+ setupBkper();
359
+ const bookId = options.book;
360
+ const accounts = yield listAccounts(bookId);
361
+ if (isJson()) {
362
+ console.log(JSON.stringify(accounts.map(a => a.json()), null, 2));
363
+ }
364
+ else {
365
+ const matrix = yield new AccountsDataTableBuilder(accounts)
366
+ .ids(true)
367
+ .groups(true)
368
+ .build();
369
+ renderTable(matrix, false);
370
+ }
371
+ }
372
+ catch (err) {
373
+ console.error('Error listing accounts:', err);
374
+ process.exit(1);
375
+ }
376
+ }));
377
+ accountCommand
378
+ .command('get <idOrName>')
379
+ .description('Get an account by ID or name')
380
+ .requiredOption('-b, --book <bookId>', 'Book ID')
381
+ .action((idOrName, options) => __awaiter(void 0, void 0, void 0, function* () {
382
+ try {
383
+ setupBkper();
384
+ const bookId = options.book;
385
+ const account = yield getAccount(bookId, idOrName);
386
+ renderItem(account.json(), isJson());
387
+ }
388
+ catch (err) {
389
+ console.error('Error getting account:', err);
390
+ process.exit(1);
391
+ }
392
+ }));
393
+ accountCommand
394
+ .command('create')
395
+ .description('Create a new account')
396
+ .requiredOption('-b, --book <bookId>', 'Book ID')
397
+ .requiredOption('--name <name>', 'Account name')
398
+ .option('--type <type>', 'Account type (ASSET, LIABILITY, INCOMING, OUTGOING)')
399
+ .option('--description <description>', 'Account description')
400
+ .option('--groups <groups>', 'Comma-separated group names')
401
+ .option('-p, --property <key=value>', 'Set a property (repeatable)', collectProperty)
402
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
403
+ try {
404
+ setupBkper();
405
+ const bookId = options.book;
406
+ const account = yield createAccount(bookId, {
407
+ name: options.name,
408
+ type: options.type,
409
+ description: options.description,
410
+ groups: options.groups
411
+ ? options.groups.split(',').map((g) => g.trim())
412
+ : undefined,
413
+ property: options.property,
414
+ });
415
+ renderItem(account.json(), isJson());
416
+ }
417
+ catch (err) {
418
+ console.error('Error creating account:', err);
419
+ process.exit(1);
420
+ }
421
+ }));
422
+ accountCommand
423
+ .command('update <idOrName>')
424
+ .description('Update an account')
425
+ .requiredOption('-b, --book <bookId>', 'Book ID')
426
+ .option('--name <name>', 'Account name')
427
+ .option('--type <type>', 'Account type (ASSET, LIABILITY, INCOMING, OUTGOING)')
428
+ .option('--archived <archived>', 'Archive status (true/false)')
429
+ .option('-p, --property <key=value>', 'Set a property (repeatable)', collectProperty)
430
+ .action((idOrName, options) => __awaiter(void 0, void 0, void 0, function* () {
431
+ try {
432
+ setupBkper();
433
+ const bookId = options.book;
434
+ const account = yield updateAccount(bookId, idOrName, {
435
+ name: options.name,
436
+ type: options.type,
437
+ archived: options.archived !== undefined ? options.archived === 'true' : undefined,
438
+ property: options.property,
439
+ });
440
+ renderItem(account.json(), isJson());
441
+ }
442
+ catch (err) {
443
+ console.error('Error updating account:', err);
444
+ process.exit(1);
445
+ }
446
+ }));
447
+ accountCommand
448
+ .command('delete <idOrName>')
449
+ .description('Delete an account')
450
+ .requiredOption('-b, --book <bookId>', 'Book ID')
451
+ .action((idOrName, options) => __awaiter(void 0, void 0, void 0, function* () {
452
+ try {
453
+ setupBkper();
454
+ const bookId = options.book;
455
+ const account = yield deleteAccount(bookId, idOrName);
456
+ renderItem(account.json(), isJson());
457
+ }
458
+ catch (err) {
459
+ console.error('Error deleting account:', err);
460
+ process.exit(1);
461
+ }
462
+ }));
463
+ // 'group' command group
464
+ const groupCommand = program.command('group').description('Manage Groups');
465
+ groupCommand
466
+ .command('list')
467
+ .description('List all groups in a book')
468
+ .requiredOption('-b, --book <bookId>', 'Book ID')
469
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
77
470
  try {
78
471
  setupBkper();
79
- const app = yield updateApp();
80
- console.log(`Updated ${app.getId()} successfully.`);
472
+ const bookId = options.book;
473
+ const groups = yield listGroups(bookId);
474
+ if (isJson()) {
475
+ console.log(JSON.stringify(groups.map(g => g.json()), null, 2));
476
+ }
477
+ else {
478
+ const matrix = new GroupsDataTableBuilder(groups).ids(true).tree(true).build();
479
+ renderTable(matrix, false);
480
+ }
481
+ }
482
+ catch (err) {
483
+ console.error('Error listing groups:', err);
484
+ process.exit(1);
485
+ }
486
+ }));
487
+ groupCommand
488
+ .command('get <idOrName>')
489
+ .description('Get a group by ID or name')
490
+ .requiredOption('-b, --book <bookId>', 'Book ID')
491
+ .action((idOrName, options) => __awaiter(void 0, void 0, void 0, function* () {
492
+ try {
493
+ setupBkper();
494
+ const bookId = options.book;
495
+ const group = yield getGroup(bookId, idOrName);
496
+ renderItem(group.json(), isJson());
497
+ }
498
+ catch (err) {
499
+ console.error('Error getting group:', err);
500
+ process.exit(1);
501
+ }
502
+ }));
503
+ groupCommand
504
+ .command('create')
505
+ .description('Create a new group')
506
+ .requiredOption('-b, --book <bookId>', 'Book ID')
507
+ .requiredOption('--name <name>', 'Group name')
508
+ .option('--parent <parent>', 'Parent group name or ID')
509
+ .option('--hidden', 'Hide the group')
510
+ .option('-p, --property <key=value>', 'Set a property (repeatable)', collectProperty)
511
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
512
+ try {
513
+ setupBkper();
514
+ const bookId = options.book;
515
+ const group = yield createGroup(bookId, {
516
+ name: options.name,
517
+ parent: options.parent,
518
+ hidden: options.hidden,
519
+ property: options.property,
520
+ });
521
+ renderItem(group.json(), isJson());
522
+ }
523
+ catch (err) {
524
+ console.error('Error creating group:', err);
525
+ process.exit(1);
526
+ }
527
+ }));
528
+ groupCommand
529
+ .command('update <idOrName>')
530
+ .description('Update a group')
531
+ .requiredOption('-b, --book <bookId>', 'Book ID')
532
+ .option('--name <name>', 'Group name')
533
+ .option('--hidden <hidden>', 'Hide status (true/false)')
534
+ .option('-p, --property <key=value>', 'Set a property (repeatable)', collectProperty)
535
+ .action((idOrName, options) => __awaiter(void 0, void 0, void 0, function* () {
536
+ try {
537
+ setupBkper();
538
+ const bookId = options.book;
539
+ const group = yield updateGroup(bookId, idOrName, {
540
+ name: options.name,
541
+ hidden: options.hidden !== undefined ? options.hidden === 'true' : undefined,
542
+ property: options.property,
543
+ });
544
+ renderItem(group.json(), isJson());
545
+ }
546
+ catch (err) {
547
+ console.error('Error updating group:', err);
548
+ process.exit(1);
549
+ }
550
+ }));
551
+ groupCommand
552
+ .command('delete <idOrName>')
553
+ .description('Delete a group')
554
+ .requiredOption('-b, --book <bookId>', 'Book ID')
555
+ .action((idOrName, options) => __awaiter(void 0, void 0, void 0, function* () {
556
+ try {
557
+ setupBkper();
558
+ const bookId = options.book;
559
+ const group = yield deleteGroup(bookId, idOrName);
560
+ renderItem(group.json(), isJson());
561
+ }
562
+ catch (err) {
563
+ console.error('Error deleting group:', err);
564
+ process.exit(1);
565
+ }
566
+ }));
567
+ // 'transaction' command group
568
+ const transactionCommand = program.command('transaction').description('Manage Transactions');
569
+ transactionCommand
570
+ .command('list')
571
+ .description('List transactions in a book')
572
+ .requiredOption('-b, --book <bookId>', 'Book ID')
573
+ .requiredOption('-q, --query <query>', 'Search query')
574
+ .option('-l, --limit <limit>', 'Maximum number of results (1-1000)', parseInt)
575
+ .option('-c, --cursor <cursor>', 'Pagination cursor')
576
+ .option('-p, --properties', 'Include custom properties')
577
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
578
+ try {
579
+ setupBkper();
580
+ const bookId = options.book;
581
+ const result = yield listTransactions(bookId, {
582
+ query: options.query,
583
+ limit: options.limit,
584
+ cursor: options.cursor,
585
+ });
586
+ if (isJson()) {
587
+ console.log(JSON.stringify({
588
+ items: result.items.map(tx => tx.json()),
589
+ cursor: result.cursor,
590
+ }, null, 2));
591
+ }
592
+ else {
593
+ const builder = result.book
594
+ .createTransactionsDataTable(result.items, result.account)
595
+ .ids(true)
596
+ .formatDates(true)
597
+ .formatValues(true)
598
+ .recordedAt(false);
599
+ if (options.properties) {
600
+ builder.properties(true);
601
+ }
602
+ const matrix = yield builder.build();
603
+ renderTable(matrix, false);
604
+ if (result.cursor) {
605
+ console.log(`\nNext cursor: ${result.cursor}`);
606
+ }
607
+ }
608
+ }
609
+ catch (err) {
610
+ console.error('Error listing transactions:', err);
611
+ process.exit(1);
612
+ }
613
+ }));
614
+ transactionCommand
615
+ .command('create')
616
+ .description('Create a transaction')
617
+ .requiredOption('-b, --book <bookId>', 'Book ID')
618
+ .requiredOption('--date <date>', 'Transaction date')
619
+ .requiredOption('--amount <amount>', 'Transaction amount')
620
+ .option('--description <description>', 'Transaction description')
621
+ .option('--from <from>', 'Credit account (source)')
622
+ .option('--to <to>', 'Debit account (destination)')
623
+ .option('--url <url>', 'URL (repeatable)', collectProperty)
624
+ .option('--remote-id <remoteId>', 'Remote ID (repeatable)', collectProperty)
625
+ .option('-p, --property <key=value>', 'Set a property (repeatable, empty value deletes)', collectProperty)
626
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
627
+ try {
628
+ setupBkper();
629
+ const bookId = options.book;
630
+ const transaction = yield createTransaction(bookId, {
631
+ date: options.date,
632
+ amount: options.amount,
633
+ description: options.description,
634
+ from: options.from,
635
+ to: options.to,
636
+ url: options.url,
637
+ remoteId: options.remoteId,
638
+ property: options.property,
639
+ });
640
+ renderItem(transaction.json(), isJson());
641
+ }
642
+ catch (err) {
643
+ console.error('Error creating transaction:', err);
644
+ process.exit(1);
645
+ }
646
+ }));
647
+ transactionCommand
648
+ .command('post <transactionId>')
649
+ .description('Post a transaction')
650
+ .requiredOption('-b, --book <bookId>', 'Book ID')
651
+ .action((transactionId, options) => __awaiter(void 0, void 0, void 0, function* () {
652
+ try {
653
+ setupBkper();
654
+ const bookId = options.book;
655
+ const transaction = yield postTransaction(bookId, transactionId);
656
+ renderItem(transaction.json(), isJson());
81
657
  }
82
658
  catch (err) {
83
- console.error("Error updating app:", err);
659
+ console.error('Error posting transaction:', err);
84
660
  process.exit(1);
85
661
  }
86
662
  }));
87
- const mcpCommand = program.command("mcp").description("Bkper MCP server commands");
88
- mcpCommand
89
- .command("start")
90
- .description("Start Bkper MCP server")
663
+ transactionCommand
664
+ .command('update <transactionId>')
665
+ .description('Update a transaction')
666
+ .requiredOption('-b, --book <bookId>', 'Book ID')
667
+ .option('--date <date>', 'Transaction date')
668
+ .option('--amount <amount>', 'Transaction amount')
669
+ .option('--description <description>', 'Transaction description')
670
+ .option('--from <from>', 'Credit account (source)')
671
+ .option('--to <to>', 'Debit account (destination)')
672
+ .option('--url <url>', 'URL (repeatable, replaces all)', collectProperty)
673
+ .option('-p, --property <key=value>', 'Set a property (repeatable, empty value deletes)', collectProperty)
674
+ .action((transactionId, options) => __awaiter(void 0, void 0, void 0, function* () {
675
+ try {
676
+ setupBkper();
677
+ const bookId = options.book;
678
+ const transaction = yield updateTransaction(bookId, transactionId, {
679
+ date: options.date,
680
+ amount: options.amount,
681
+ description: options.description,
682
+ from: options.from,
683
+ to: options.to,
684
+ url: options.url,
685
+ property: options.property,
686
+ });
687
+ renderItem(transaction.json(), isJson());
688
+ }
689
+ catch (err) {
690
+ console.error('Error updating transaction:', err);
691
+ process.exit(1);
692
+ }
693
+ }));
694
+ transactionCommand
695
+ .command('check <transactionId>')
696
+ .description('Check a transaction')
697
+ .requiredOption('-b, --book <bookId>', 'Book ID')
698
+ .action((transactionId, options) => __awaiter(void 0, void 0, void 0, function* () {
699
+ try {
700
+ setupBkper();
701
+ const bookId = options.book;
702
+ const transaction = yield checkTransaction(bookId, transactionId);
703
+ renderItem(transaction.json(), isJson());
704
+ }
705
+ catch (err) {
706
+ console.error('Error checking transaction:', err);
707
+ process.exit(1);
708
+ }
709
+ }));
710
+ transactionCommand
711
+ .command('trash <transactionId>')
712
+ .description('Trash a transaction')
713
+ .requiredOption('-b, --book <bookId>', 'Book ID')
714
+ .action((transactionId, options) => __awaiter(void 0, void 0, void 0, function* () {
715
+ try {
716
+ setupBkper();
717
+ const bookId = options.book;
718
+ const transaction = yield trashTransaction(bookId, transactionId);
719
+ renderItem(transaction.json(), isJson());
720
+ }
721
+ catch (err) {
722
+ console.error('Error trashing transaction:', err);
723
+ process.exit(1);
724
+ }
725
+ }));
726
+ transactionCommand
727
+ .command('merge <transactionId1> <transactionId2>')
728
+ .description('Merge two transactions')
729
+ .requiredOption('-b, --book <bookId>', 'Book ID')
730
+ .action((transactionId1, transactionId2, options) => __awaiter(void 0, void 0, void 0, function* () {
731
+ try {
732
+ setupBkper();
733
+ const bookId = options.book;
734
+ const result = yield mergeTransactions(bookId, transactionId1, transactionId2);
735
+ if (isJson()) {
736
+ console.log(JSON.stringify({
737
+ mergedTransaction: result.mergedTransaction.json(),
738
+ revertedTransactionId: result.revertedTransactionId,
739
+ auditRecord: result.auditRecord,
740
+ }, null, 2));
741
+ }
742
+ else {
743
+ renderItem(result.mergedTransaction.json(), false);
744
+ }
745
+ }
746
+ catch (err) {
747
+ console.error('Error merging transactions:', err);
748
+ process.exit(1);
749
+ }
750
+ }));
751
+ // 'balance' command group
752
+ const balanceCommand = program.command('balance').description('Manage Balances');
753
+ balanceCommand
754
+ .command('get')
755
+ .description('Get balances report')
756
+ .requiredOption('-b, --book <bookId>', 'Book ID')
757
+ .requiredOption('-q, --query <query>', 'Balances query')
758
+ .option('--expanded <level>', 'Expand groups to specified depth (0+)', parseInt)
759
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
760
+ try {
761
+ setupBkper();
762
+ const bookId = options.book;
763
+ const matrix = yield getBalancesMatrix(bookId, {
764
+ query: options.query,
765
+ expanded: options.expanded,
766
+ });
767
+ renderTable(matrix, isJson());
768
+ }
769
+ catch (err) {
770
+ console.error('Error getting balances:', err);
771
+ process.exit(1);
772
+ }
773
+ }));
774
+ // 'collection' command group
775
+ const collectionCommand = program.command('collection').description('Manage Collections');
776
+ collectionCommand
777
+ .command('list')
778
+ .description('List all collections')
91
779
  .action(() => __awaiter(void 0, void 0, void 0, function* () {
92
780
  try {
93
- // Import and start the MCP server directly
94
- const { BkperMcpServer } = yield import("./mcp/server.js");
95
- const server = new BkperMcpServer();
96
- yield server.run();
781
+ setupBkper();
782
+ const collections = yield listCollections();
783
+ if (isJson()) {
784
+ console.log(JSON.stringify(collections.map(c => c.json()), null, 2));
785
+ }
786
+ else {
787
+ if (collections.length === 0) {
788
+ console.log('No collections found.');
789
+ return;
790
+ }
791
+ const matrix = [['ID', 'Name', 'Books']];
792
+ for (const col of collections) {
793
+ const books = col.getBooks();
794
+ matrix.push([col.getId() || '', col.getName() || '', books.length.toString()]);
795
+ }
796
+ renderTable(matrix, false);
797
+ }
798
+ }
799
+ catch (err) {
800
+ console.error('Error listing collections:', err);
801
+ process.exit(1);
802
+ }
803
+ }));
804
+ collectionCommand
805
+ .command('get <collectionId>')
806
+ .description('Get a collection by ID')
807
+ .action((collectionId) => __awaiter(void 0, void 0, void 0, function* () {
808
+ try {
809
+ setupBkper();
810
+ const collection = yield getCollection(collectionId);
811
+ renderItem(collection.json(), isJson());
812
+ }
813
+ catch (err) {
814
+ console.error('Error getting collection:', err);
815
+ process.exit(1);
816
+ }
817
+ }));
818
+ collectionCommand
819
+ .command('create')
820
+ .description('Create a new collection')
821
+ .requiredOption('--name <name>', 'Collection name')
822
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
823
+ try {
824
+ setupBkper();
825
+ const collection = yield createCollection({ name: options.name });
826
+ renderItem(collection.json(), isJson());
827
+ }
828
+ catch (err) {
829
+ console.error('Error creating collection:', err);
830
+ process.exit(1);
831
+ }
832
+ }));
833
+ collectionCommand
834
+ .command('update <collectionId>')
835
+ .description('Update a collection')
836
+ .option('--name <name>', 'Collection name')
837
+ .action((collectionId, options) => __awaiter(void 0, void 0, void 0, function* () {
838
+ try {
839
+ setupBkper();
840
+ const collection = yield updateCollection(collectionId, {
841
+ name: options.name,
842
+ });
843
+ renderItem(collection.json(), isJson());
844
+ }
845
+ catch (err) {
846
+ console.error('Error updating collection:', err);
847
+ process.exit(1);
848
+ }
849
+ }));
850
+ collectionCommand
851
+ .command('delete <collectionId>')
852
+ .description('Delete a collection')
853
+ .action((collectionId) => __awaiter(void 0, void 0, void 0, function* () {
854
+ try {
855
+ setupBkper();
856
+ yield deleteCollection(collectionId);
857
+ console.log(`Collection ${collectionId} deleted.`);
858
+ }
859
+ catch (err) {
860
+ console.error('Error deleting collection:', err);
861
+ process.exit(1);
862
+ }
863
+ }));
864
+ function collectBook(value, previous) {
865
+ return previous ? [...previous, value] : [value];
866
+ }
867
+ collectionCommand
868
+ .command('add-book <collectionId>')
869
+ .description('Add books to a collection')
870
+ .requiredOption('-b, --book <bookId>', 'Book ID (repeatable)', collectBook)
871
+ .action((collectionId, options) => __awaiter(void 0, void 0, void 0, function* () {
872
+ try {
873
+ setupBkper();
874
+ const books = yield addBookToCollection(collectionId, options.book);
875
+ if (isJson()) {
876
+ console.log(JSON.stringify(books.map(b => b.json()), null, 2));
877
+ }
878
+ else {
879
+ console.log(`Added ${options.book.length} book(s) to collection ${collectionId}.`);
880
+ }
881
+ }
882
+ catch (err) {
883
+ console.error('Error adding books to collection:', err);
884
+ process.exit(1);
885
+ }
886
+ }));
887
+ collectionCommand
888
+ .command('remove-book <collectionId>')
889
+ .description('Remove books from a collection')
890
+ .requiredOption('-b, --book <bookId>', 'Book ID (repeatable)', collectBook)
891
+ .action((collectionId, options) => __awaiter(void 0, void 0, void 0, function* () {
892
+ try {
893
+ setupBkper();
894
+ const books = yield removeBookFromCollection(collectionId, options.book);
895
+ if (isJson()) {
896
+ console.log(JSON.stringify(books.map(b => b.json()), null, 2));
897
+ }
898
+ else {
899
+ console.log(`Removed ${options.book.length} book(s) from collection ${collectionId}.`);
900
+ }
97
901
  }
98
902
  catch (err) {
99
- console.error("Error starting MCP server:", err);
903
+ console.error('Error removing books from collection:', err);
100
904
  process.exit(1);
101
905
  }
102
906
  }));