@cremini/skillpack 1.2.8 → 1.2.10

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 (2) hide show
  1. package/dist/cli.js +222 -106
  2. package/package.json +2 -3
package/dist/cli.js CHANGED
@@ -9,6 +9,26 @@ var __export = (target, all) => {
9
9
  __defProp(target, name, { get: all[name], enumerable: true });
10
10
  };
11
11
 
12
+ // src/job-schedule.ts
13
+ function normalizeJobCron(cron2) {
14
+ if (typeof cron2 !== "string") {
15
+ return void 0;
16
+ }
17
+ const normalized = cron2.trim();
18
+ return normalized ? normalized : void 0;
19
+ }
20
+ function hasJobSchedule(jobOrCron) {
21
+ if (typeof jobOrCron === "string" || jobOrCron == null) {
22
+ return !!normalizeJobCron(jobOrCron);
23
+ }
24
+ return !!normalizeJobCron(jobOrCron.cron);
25
+ }
26
+ var init_job_schedule = __esm({
27
+ "src/job-schedule.ts"() {
28
+ "use strict";
29
+ }
30
+ });
31
+
12
32
  // src/job-config.ts
13
33
  import fs2 from "fs";
14
34
  import path2 from "path";
@@ -27,9 +47,9 @@ function validateScheduledJobConfig(value, sourceLabel, index) {
27
47
  `Invalid job config from ${sourceLabel}: "jobs[${index}].name" is required`
28
48
  );
29
49
  }
30
- if (typeof job.cron !== "string" || !job.cron.trim()) {
50
+ if (job.cron !== void 0 && typeof job.cron !== "string") {
31
51
  throw new Error(
32
- `Invalid job config from ${sourceLabel}: "jobs[${index}].cron" is required`
52
+ `Invalid job config from ${sourceLabel}: "jobs[${index}].cron" must be a string`
33
53
  );
34
54
  }
35
55
  if (typeof job.prompt !== "string" || !job.prompt.trim()) {
@@ -87,18 +107,25 @@ function validateJobFileShape(value, sourceLabel) {
87
107
  function normalizeJobFile(jobFile) {
88
108
  return {
89
109
  jobs: jobFile.jobs.map((job) => ({
90
- name: job.name.trim(),
91
- cron: job.cron.trim(),
92
- prompt: job.prompt,
93
- notify: {
94
- adapter: job.notify.adapter.trim(),
95
- channelId: job.notify.channelId.trim()
96
- },
97
- ...job.enabled !== void 0 ? { enabled: job.enabled } : {},
98
- ...job.timezone !== void 0 ? { timezone: job.timezone.trim() } : {}
110
+ ...normalizeScheduledJobConfig(job)
99
111
  }))
100
112
  };
101
113
  }
114
+ function normalizeScheduledJobConfig(job) {
115
+ const normalizedCron = normalizeJobCron(job.cron);
116
+ const normalizedTimezone = typeof job.timezone === "string" && job.timezone.trim() ? job.timezone.trim() : void 0;
117
+ return {
118
+ name: job.name.trim(),
119
+ ...normalizedCron ? { cron: normalizedCron } : {},
120
+ prompt: job.prompt,
121
+ notify: {
122
+ adapter: job.notify.adapter.trim(),
123
+ channelId: job.notify.channelId.trim()
124
+ },
125
+ ...normalizedCron && job.enabled !== void 0 ? { enabled: job.enabled } : {},
126
+ ...normalizedCron && normalizedTimezone ? { timezone: normalizedTimezone } : {}
127
+ };
128
+ }
102
129
  function loadJobFile(workDir) {
103
130
  const filePath = getJobFilePath(workDir);
104
131
  if (!fs2.existsSync(filePath)) {
@@ -119,6 +146,7 @@ var JOB_FILE;
119
146
  var init_job_config = __esm({
120
147
  "src/job-config.ts"() {
121
148
  "use strict";
149
+ init_job_schedule();
122
150
  JOB_FILE = "job.json";
123
151
  }
124
152
  });
@@ -1402,11 +1430,15 @@ function isValidTimezone(tz) {
1402
1430
  function isValidJobName(name) {
1403
1431
  return VALID_JOB_NAME.test(name) && name.length <= 64;
1404
1432
  }
1433
+ function isRecurringJob(jobConfig) {
1434
+ return hasJobSchedule(jobConfig);
1435
+ }
1405
1436
  var VALID_JOB_NAME, SchedulerAdapter;
1406
1437
  var init_scheduler = __esm({
1407
1438
  "src/runtime/adapters/scheduler.ts"() {
1408
1439
  "use strict";
1409
1440
  init_job_config();
1441
+ init_job_schedule();
1410
1442
  VALID_JOB_NAME = /^[a-zA-Z0-9][a-zA-Z0-9_-]*$/;
1411
1443
  SchedulerAdapter = class {
1412
1444
  name = "scheduler";
@@ -1423,10 +1455,13 @@ var init_scheduler = __esm({
1423
1455
  const jobConfigs = loadJobFile(this.rootDir).jobs;
1424
1456
  let scheduledCount = 0;
1425
1457
  let disabledCount = 0;
1458
+ let oneTimeCount = 0;
1426
1459
  for (const jc of jobConfigs) {
1427
1460
  const result = this.registerJob(jc);
1428
1461
  if (result.registered) {
1429
- if (jc.enabled === false) {
1462
+ if (!isRecurringJob(jc)) {
1463
+ oneTimeCount++;
1464
+ } else if (jc.enabled === false) {
1430
1465
  disabledCount++;
1431
1466
  } else {
1432
1467
  scheduledCount++;
@@ -1436,6 +1471,7 @@ var init_scheduler = __esm({
1436
1471
  const parts = [];
1437
1472
  if (scheduledCount > 0) parts.push(`${scheduledCount} active`);
1438
1473
  if (disabledCount > 0) parts.push(`${disabledCount} disabled`);
1474
+ if (oneTimeCount > 0) parts.push(`${oneTimeCount} one-time`);
1439
1475
  if (parts.length > 0) {
1440
1476
  console.log(`[SchedulerAdapter] Started with ${parts.join(", ")} job(s)`);
1441
1477
  } else {
@@ -1450,43 +1486,43 @@ var init_scheduler = __esm({
1450
1486
  * Does NOT persist – callers decide when to persist.
1451
1487
  */
1452
1488
  registerJob(jobConfig) {
1453
- if (!isValidJobName(jobConfig.name)) {
1454
- const msg = `[Scheduler] Invalid job name "${jobConfig.name}": must match ${VALID_JOB_NAME} and be \u226464 chars`;
1489
+ const normalizedConfig = normalizeScheduledJobConfig(jobConfig);
1490
+ const normalizedCron = normalizeJobCron(normalizedConfig.cron);
1491
+ if (!isValidJobName(normalizedConfig.name)) {
1492
+ const msg = `[Scheduler] Invalid job name "${normalizedConfig.name}": must match ${VALID_JOB_NAME} and be \u226464 chars`;
1455
1493
  console.error(msg);
1456
1494
  return { registered: false, message: msg };
1457
1495
  }
1458
- if (!cron.validate(jobConfig.cron)) {
1459
- const msg = `[Scheduler] Invalid cron expression for job "${jobConfig.name}": ${jobConfig.cron}`;
1460
- console.error(msg);
1461
- return { registered: false, message: msg };
1462
- }
1463
- if (jobConfig.timezone && !isValidTimezone(jobConfig.timezone)) {
1464
- const msg = `[Scheduler] Invalid timezone for job "${jobConfig.name}": ${jobConfig.timezone}`;
1465
- console.error(msg);
1466
- return { registered: false, message: msg };
1496
+ if (normalizedCron) {
1497
+ if (!cron.validate(normalizedCron)) {
1498
+ const msg = `[Scheduler] Invalid cron expression for job "${normalizedConfig.name}": ${normalizedCron}`;
1499
+ console.error(msg);
1500
+ return { registered: false, message: msg };
1501
+ }
1502
+ if (normalizedConfig.timezone && !isValidTimezone(normalizedConfig.timezone)) {
1503
+ const msg = `[Scheduler] Invalid timezone for job "${normalizedConfig.name}": ${normalizedConfig.timezone}`;
1504
+ console.error(msg);
1505
+ return { registered: false, message: msg };
1506
+ }
1467
1507
  }
1468
- this.removeFromMap(jobConfig.name);
1508
+ this.removeFromMap(normalizedConfig.name);
1469
1509
  let task = null;
1470
- if (jobConfig.enabled !== false) {
1471
- task = cron.schedule(
1472
- jobConfig.cron,
1473
- () => {
1474
- void this.runJob(jobConfig);
1475
- },
1476
- {
1477
- timezone: jobConfig.timezone
1478
- }
1510
+ if (normalizedCron && normalizedConfig.enabled !== false) {
1511
+ task = this.createCronTask(normalizedConfig);
1512
+ console.log(
1513
+ `[Scheduler] Job "${normalizedConfig.name}" scheduled: ${normalizedCron}${normalizedConfig.timezone ? ` (${normalizedConfig.timezone})` : ""}`
1479
1514
  );
1515
+ } else if (normalizedCron) {
1480
1516
  console.log(
1481
- `[Scheduler] Job "${jobConfig.name}" scheduled: ${jobConfig.cron}${jobConfig.timezone ? ` (${jobConfig.timezone})` : ""}`
1517
+ `[Scheduler] Job "${normalizedConfig.name}" registered (disabled)`
1482
1518
  );
1483
1519
  } else {
1484
1520
  console.log(
1485
- `[Scheduler] Job "${jobConfig.name}" registered (disabled)`
1521
+ `[Scheduler] Job "${normalizedConfig.name}" registered as one-time (manual trigger only)`
1486
1522
  );
1487
1523
  }
1488
- this.jobs.set(jobConfig.name, {
1489
- config: jobConfig,
1524
+ this.jobs.set(normalizedConfig.name, {
1525
+ config: normalizedConfig,
1490
1526
  task,
1491
1527
  running: false,
1492
1528
  notifyFailed: false
@@ -1599,10 +1635,11 @@ var init_scheduler = __esm({
1599
1635
  return { success: false, message: result.message };
1600
1636
  }
1601
1637
  this.persistJobs();
1602
- const enabled = jobConfig.enabled !== false;
1638
+ const recurring = isRecurringJob(jobConfig);
1639
+ const enabled = recurring ? jobConfig.enabled !== false : true;
1603
1640
  return {
1604
1641
  success: true,
1605
- message: enabled ? `Job "${jobConfig.name}" created and scheduled.` : `Job "${jobConfig.name}" created (disabled).`
1642
+ message: recurring ? enabled ? `Job "${jobConfig.name}" created and scheduled.` : `Job "${jobConfig.name}" created (disabled).` : `Job "${jobConfig.name}" created as a one-time task.`
1606
1643
  };
1607
1644
  }
1608
1645
  /**
@@ -1647,17 +1684,15 @@ var init_scheduler = __esm({
1647
1684
  if (!job) {
1648
1685
  return { success: false, message: `Job "${name}" not found.` };
1649
1686
  }
1687
+ if (!isRecurringJob(job.config)) {
1688
+ return {
1689
+ success: false,
1690
+ message: `Job "${name}" does not have a schedule and cannot be enabled or disabled.`
1691
+ };
1692
+ }
1650
1693
  job.config.enabled = enabled;
1651
1694
  if (enabled && !job.task) {
1652
- job.task = cron.schedule(
1653
- job.config.cron,
1654
- () => {
1655
- void this.runJob(job.config);
1656
- },
1657
- {
1658
- timezone: job.config.timezone
1659
- }
1660
- );
1695
+ job.task = this.createCronTask(job.config);
1661
1696
  } else if (enabled && job.task) {
1662
1697
  job.task.start();
1663
1698
  } else if (!enabled && job.task) {
@@ -1703,13 +1738,13 @@ var init_scheduler = __esm({
1703
1738
  for (const [, job] of this.jobs) {
1704
1739
  result.push({
1705
1740
  name: job.config.name,
1706
- cron: job.config.cron,
1741
+ ...job.config.cron ? { cron: job.config.cron } : {},
1707
1742
  prompt: job.config.prompt,
1708
1743
  notify: job.config.notify,
1709
- enabled: job.config.enabled !== false,
1710
- timezone: job.config.timezone,
1711
- lastRunAt: job.lastRunAt,
1712
- lastError: job.lastError,
1744
+ enabled: isRecurringJob(job.config) ? job.config.enabled !== false : true,
1745
+ ...job.config.timezone ? { timezone: job.config.timezone } : {},
1746
+ ...job.lastRunAt ? { lastRunAt: job.lastRunAt } : {},
1747
+ ...job.lastError ? { lastError: job.lastError } : {},
1713
1748
  running: job.running,
1714
1749
  notifyFailed: job.notifyFailed
1715
1750
  });
@@ -1749,6 +1784,21 @@ var init_scheduler = __esm({
1749
1784
  this.jobs.clear();
1750
1785
  console.log("[SchedulerAdapter] All jobs stopped.");
1751
1786
  }
1787
+ createCronTask(jobConfig) {
1788
+ const cronExpr = normalizeJobCron(jobConfig.cron);
1789
+ if (!cronExpr) {
1790
+ throw new Error(`Job "${jobConfig.name}" does not have a valid cron expression`);
1791
+ }
1792
+ return cron.schedule(
1793
+ cronExpr,
1794
+ () => {
1795
+ void this.runJob(jobConfig);
1796
+ },
1797
+ {
1798
+ timezone: jobConfig.timezone
1799
+ }
1800
+ );
1801
+ }
1752
1802
  };
1753
1803
  }
1754
1804
  });
@@ -2694,7 +2744,7 @@ var ResultsQueryService = class {
2694
2744
  constructor(resultStore) {
2695
2745
  this.resultStore = resultStore;
2696
2746
  }
2697
- listRecentArtifacts(options = {}) {
2747
+ async listRecentArtifacts(options = {}) {
2698
2748
  return this.resultStore.listRecentArtifacts({
2699
2749
  channelId: options.channelId,
2700
2750
  limit: clampLimit(options.limit, 100, 500),
@@ -2865,7 +2915,7 @@ var ArtifactPersistenceService = class {
2865
2915
  this.snapshotService = snapshotService;
2866
2916
  this.resultStore = resultStore;
2867
2917
  }
2868
- saveArtifacts(input) {
2918
+ async saveArtifacts(input) {
2869
2919
  const declaredAt = (/* @__PURE__ */ new Date()).toISOString();
2870
2920
  const snapshots = this.snapshotService.createSnapshots(
2871
2921
  input.runId,
@@ -2873,7 +2923,7 @@ var ArtifactPersistenceService = class {
2873
2923
  declaredAt
2874
2924
  );
2875
2925
  try {
2876
- this.resultStore.insertArtifacts({
2926
+ await this.resultStore.insertArtifacts({
2877
2927
  runId: input.runId,
2878
2928
  channelId: input.channelId,
2879
2929
  artifacts: snapshots
@@ -2892,7 +2942,7 @@ var ArtifactPersistenceService = class {
2892
2942
  import fs10 from "fs";
2893
2943
  import path10 from "path";
2894
2944
  import { randomUUID as randomUUID2 } from "crypto";
2895
- import Database from "better-sqlite3";
2945
+ import sqlite3 from "sqlite3";
2896
2946
  function mapArtifactRow(row) {
2897
2947
  return {
2898
2948
  artifactId: row.artifact_id,
@@ -2909,16 +2959,17 @@ function mapArtifactRow(row) {
2909
2959
  };
2910
2960
  }
2911
2961
  var ResultStore = class {
2912
- db;
2962
+ db = null;
2963
+ ready;
2913
2964
  constructor(rootDir) {
2914
2965
  const dataDir = path10.resolve(rootDir, "data");
2915
2966
  fs10.mkdirSync(dataDir, { recursive: true });
2916
- this.db = new Database(path10.join(dataDir, "result.db"));
2917
- this.db.pragma("journal_mode = WAL");
2918
- this.initialize();
2967
+ this.ready = this.initialize(path10.join(dataDir, "result-v2.db"));
2919
2968
  }
2920
- initialize() {
2921
- this.db.exec(`
2969
+ async initialize(databasePath) {
2970
+ this.db = await openDatabase(databasePath);
2971
+ await this.exec("PRAGMA journal_mode = WAL");
2972
+ await this.exec(`
2922
2973
  CREATE TABLE IF NOT EXISTS artifacts (
2923
2974
  artifact_id TEXT PRIMARY KEY,
2924
2975
  run_id TEXT NOT NULL,
@@ -2937,11 +2988,12 @@ var ResultStore = class {
2937
2988
  ON artifacts(channel_id, declared_at DESC);
2938
2989
  `);
2939
2990
  }
2940
- insertArtifacts(input) {
2991
+ async insertArtifacts(input) {
2992
+ await this.ready;
2941
2993
  if (input.artifacts.length === 0) {
2942
2994
  return;
2943
2995
  }
2944
- const insertArtifact = this.db.prepare(`
2996
+ const insertArtifact = `
2945
2997
  INSERT INTO artifacts (
2946
2998
  artifact_id,
2947
2999
  run_id,
@@ -2955,39 +3007,44 @@ var ResultStore = class {
2955
3007
  is_primary,
2956
3008
  declared_at
2957
3009
  ) VALUES (
2958
- @artifactId,
2959
- @runId,
2960
- @channelId,
2961
- @originalPath,
2962
- @snapshotPath,
2963
- @fileName,
2964
- @mimeType,
2965
- @sizeBytes,
2966
- @title,
2967
- @isPrimary,
2968
- @declaredAt
3010
+ ?,
3011
+ ?,
3012
+ ?,
3013
+ ?,
3014
+ ?,
3015
+ ?,
3016
+ ?,
3017
+ ?,
3018
+ ?,
3019
+ ?,
3020
+ ?
2969
3021
  )
2970
- `);
2971
- const transaction = this.db.transaction((payload) => {
2972
- for (const artifact of payload.artifacts) {
2973
- insertArtifact.run({
2974
- artifactId: randomUUID2(),
2975
- runId: payload.runId,
2976
- channelId: payload.channelId,
2977
- originalPath: artifact.originalPath,
2978
- snapshotPath: artifact.snapshotPath,
2979
- fileName: artifact.fileName,
2980
- mimeType: artifact.mimeType ?? null,
2981
- sizeBytes: artifact.sizeBytes,
2982
- title: artifact.title ?? null,
2983
- isPrimary: artifact.isPrimary ? 1 : 0,
2984
- declaredAt: artifact.declaredAt
2985
- });
2986
- }
2987
- });
2988
- transaction(input);
3022
+ `;
3023
+ await this.exec("BEGIN");
3024
+ try {
3025
+ for (const artifact of input.artifacts) {
3026
+ await this.run(insertArtifact, [
3027
+ randomUUID2(),
3028
+ input.runId,
3029
+ input.channelId,
3030
+ artifact.originalPath,
3031
+ artifact.snapshotPath,
3032
+ artifact.fileName,
3033
+ artifact.mimeType ?? null,
3034
+ artifact.sizeBytes,
3035
+ artifact.title ?? null,
3036
+ artifact.isPrimary ? 1 : 0,
3037
+ artifact.declaredAt
3038
+ ]);
3039
+ }
3040
+ await this.exec("COMMIT");
3041
+ } catch (error) {
3042
+ await this.rollback();
3043
+ throw error;
3044
+ }
2989
3045
  }
2990
- listRecentArtifacts(options = {}) {
3046
+ async listRecentArtifacts(options = {}) {
3047
+ await this.ready;
2991
3048
  const limit = options.limit ?? 100;
2992
3049
  const offset = options.offset ?? 0;
2993
3050
  const conditions = [];
@@ -2997,16 +3054,75 @@ var ResultStore = class {
2997
3054
  params.push(options.channelId);
2998
3055
  }
2999
3056
  const whereClause = conditions.length > 0 ? `WHERE ${conditions.join(" AND ")}` : "";
3000
- const rows = this.db.prepare(`
3057
+ const rows = await this.all(`
3001
3058
  SELECT *
3002
3059
  FROM artifacts
3003
3060
  ${whereClause}
3004
3061
  ORDER BY declared_at DESC, rowid DESC
3005
3062
  LIMIT ? OFFSET ?
3006
- `).all(...params, limit, offset);
3063
+ `, [...params, limit, offset]);
3007
3064
  return rows.map(mapArtifactRow);
3008
3065
  }
3066
+ getDatabase() {
3067
+ if (!this.db) {
3068
+ throw new Error("Result store database is not ready");
3069
+ }
3070
+ return this.db;
3071
+ }
3072
+ exec(sql) {
3073
+ const db = this.getDatabase();
3074
+ return new Promise((resolve, reject) => {
3075
+ db.exec(sql, (error) => {
3076
+ if (error) {
3077
+ reject(error);
3078
+ return;
3079
+ }
3080
+ resolve();
3081
+ });
3082
+ });
3083
+ }
3084
+ run(sql, params = []) {
3085
+ const db = this.getDatabase();
3086
+ return new Promise((resolve, reject) => {
3087
+ db.run(sql, params, (error) => {
3088
+ if (error) {
3089
+ reject(error);
3090
+ return;
3091
+ }
3092
+ resolve();
3093
+ });
3094
+ });
3095
+ }
3096
+ all(sql, params = []) {
3097
+ const db = this.getDatabase();
3098
+ return new Promise((resolve, reject) => {
3099
+ db.all(sql, params, (error, rows) => {
3100
+ if (error) {
3101
+ reject(error);
3102
+ return;
3103
+ }
3104
+ resolve(rows);
3105
+ });
3106
+ });
3107
+ }
3108
+ async rollback() {
3109
+ try {
3110
+ await this.exec("ROLLBACK");
3111
+ } catch {
3112
+ }
3113
+ }
3009
3114
  };
3115
+ function openDatabase(databasePath) {
3116
+ return new Promise((resolve, reject) => {
3117
+ const db = new sqlite3.Database(databasePath, (error) => {
3118
+ if (error) {
3119
+ reject(error);
3120
+ return;
3121
+ }
3122
+ resolve(db);
3123
+ });
3124
+ });
3125
+ }
3010
3126
 
3011
3127
  // src/runtime/artifacts/save-artifacts-tool.ts
3012
3128
  import { Type } from "@sinclair/typebox";
@@ -4495,12 +4611,12 @@ var WebAdapter = class {
4495
4611
  )
4496
4612
  );
4497
4613
  });
4498
- app.get("/api/results/artifacts", (req, res) => {
4614
+ app.get("/api/results/artifacts", async (req, res) => {
4499
4615
  if (!resultsQueryService) {
4500
4616
  res.status(503).json({ error: "Results query service is not available" });
4501
4617
  return;
4502
4618
  }
4503
- res.json(resultsQueryService.listRecentArtifacts({
4619
+ res.json(await resultsQueryService.listRecentArtifacts({
4504
4620
  channelId: typeof req.query.channelId === "string" ? req.query.channelId : void 0,
4505
4621
  limit: parsePositiveInt(req.query.limit, 100),
4506
4622
  offset: parsePositiveInt(req.query.offset, 0)
@@ -4549,20 +4665,20 @@ var WebAdapter = class {
4549
4665
  return;
4550
4666
  }
4551
4667
  const { name, cron: cronExpr, prompt, notify, enabled, timezone } = req.body;
4552
- if (!name || !cronExpr || !prompt || !notify?.adapter || !notify?.channelId) {
4668
+ if (!name || !prompt || !notify?.adapter || !notify?.channelId) {
4553
4669
  res.status(400).json({
4554
4670
  success: false,
4555
- message: "Required fields: name, cron, prompt, notify.adapter, notify.channelId"
4671
+ message: "Required fields: name, prompt, notify.adapter, notify.channelId"
4556
4672
  });
4557
4673
  return;
4558
4674
  }
4559
4675
  const result = scheduler.addJob({
4560
4676
  name,
4561
- cron: cronExpr,
4677
+ ...typeof cronExpr === "string" ? { cron: cronExpr } : {},
4562
4678
  prompt,
4563
4679
  notify,
4564
- enabled: enabled !== false,
4565
- timezone
4680
+ ...typeof enabled === "boolean" ? { enabled } : {},
4681
+ ...typeof timezone === "string" ? { timezone } : {}
4566
4682
  });
4567
4683
  res.json(result);
4568
4684
  });
@@ -4819,7 +4935,7 @@ var IpcAdapter = class {
4819
4935
  this.replyError(request.id, "Results query service is not available");
4820
4936
  return;
4821
4937
  }
4822
- this.reply(request.id, this.resultsQueryService.listRecentArtifacts({
4938
+ this.reply(request.id, await this.resultsQueryService.listRecentArtifacts({
4823
4939
  channelId: request.channelId,
4824
4940
  limit: request.limit,
4825
4941
  offset: request.offset
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cremini/skillpack",
3
- "version": "1.2.8",
3
+ "version": "1.2.10",
4
4
  "description": "Pack AI Skills into Local Agents",
5
5
  "type": "module",
6
6
  "repository": {
@@ -49,18 +49,17 @@
49
49
  "@slack/bolt": "^4.6.0",
50
50
  "ajv": "^8.17.1",
51
51
  "archiver": "^7.0.1",
52
- "better-sqlite3": "^11.10.0",
53
52
  "chalk": "^5.6.2",
54
53
  "commander": "^14.0.3",
55
54
  "express": "^5.1.0",
56
55
  "inquirer": "^13.3.0",
57
56
  "node-cron": "^4.2.1",
58
57
  "node-telegram-bot-api": "^0.66.0",
58
+ "sqlite3": "^5.1.7",
59
59
  "ws": "^8.19.0"
60
60
  },
61
61
  "devDependencies": {
62
62
  "@types/archiver": "^7.0.0",
63
- "@types/better-sqlite3": "^7.6.13",
64
63
  "@types/express": "^5.0.0",
65
64
  "@types/inquirer": "^9.0.9",
66
65
  "@types/node": "^25.5.0",