terminal-smart-cli 0.97.22 → 0.97.24

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/lib/meta.js +17 -1
  2. package/package.json +1 -1
package/lib/meta.js CHANGED
@@ -9,6 +9,7 @@
9
9
  const fs = require('fs');
10
10
  const path = require('path');
11
11
  const cp = require('child_process');
12
+ const crypto = require('crypto');
12
13
  const compactor = require('./compactor');
13
14
  const { api, ApiError } = require('./api');
14
15
  const keyring = require('./keyring');
@@ -62,6 +63,9 @@ function artifactForMetaItem(item, st, dir = '') {
62
63
  if (fs.existsSync(path.join(dir, 'test', 'integration.test.js'))) return 'test/integration.test.js';
63
64
  if (fs.existsSync(path.join(dir, 'test', 'core.test.js'))) return 'test/core.test.js';
64
65
  }
66
+ // Canvas games render character poses and animation in JavaScript. A
67
+ // generic "visual" word must not redirect gameplay animation to CSS.
68
+ if (/anima[çc][aã]o|pose|personagem|movimento|dire[çc][aã]o|npc|miss[aã]o|invent[aá]rio|inimigo|drop|salvar|carregar/.test(d)) return 'src/game.js';
65
69
  if (/visual|cen[aá]rio|ilumina|hud|estilo|profundidade/.test(d) && fs.existsSync(path.join(dir, 'styles.css'))) return 'styles.css';
66
70
  return 'src/game.js';
67
71
  }
@@ -71,6 +75,11 @@ function artifactForMetaItem(item, st, dir = '') {
71
75
  return `artifacts/${String(item && item.id || 'item').replace(/[^a-z0-9_-]/gi, '_')}.md`;
72
76
  }
73
77
 
78
+ function artifactHash(file) {
79
+ try { return crypto.createHash('sha256').update(fs.readFileSync(file)).digest('hex'); }
80
+ catch (_) { return null; }
81
+ }
82
+
74
83
  function normalizeMetaArtifact(relativePath, raw) {
75
84
  let text = String(raw || '').trim().replace(/^```(?:json|gdscript|markdown|md)?\s*/i, '').replace(/\s*```\s*$/i, '').trim();
76
85
  if (/\.json$/i.test(relativePath)) {
@@ -1390,6 +1399,7 @@ async function run(goal, opts = {}) {
1390
1399
  const expectedOnDisk = expectedArtifact
1391
1400
  ? (path.isAbsolute(expectedArtifact) ? expectedArtifact : path.resolve(dir, expectedArtifact))
1392
1401
  : null;
1402
+ const expectedBeforeHash = expectedOnDisk ? artifactHash(expectedOnDisk) : null;
1393
1403
  if (!item.directArtifact && (item.attempts || 0) > 0 && expectedOnDisk && !fs.existsSync(expectedOnDisk)) {
1394
1404
  item.directArtifact = true;
1395
1405
  item.directModel = item.directModel || 'glm-5.2';
@@ -1644,7 +1654,9 @@ async function run(goal, opts = {}) {
1644
1654
  }
1645
1655
 
1646
1656
  const expectedNow = String(expectedArtifact || '').replace(/\\/g, '/').toLowerCase();
1647
- const wroteExpectedNow = (out.actions || []).some(a => {
1657
+ const expectedAfterHash = expectedOnDisk ? artifactHash(expectedOnDisk) : null;
1658
+ const expectedChangedNow = !!expectedAfterHash && expectedAfterHash !== expectedBeforeHash;
1659
+ const wroteExpectedNow = expectedChangedNow || (out.actions || []).some(a => {
1648
1660
  if (!['escrever_arquivo', 'editar_arquivo'].includes(a && a.name)) return false;
1649
1661
  const target = String(a.target || '').replace(/\\/g, '/').toLowerCase();
1650
1662
  return target === expectedNow || target.endsWith('/' + expectedNow);
@@ -1686,6 +1698,10 @@ async function run(goal, opts = {}) {
1686
1698
  // (Bug real do teste MultiApps: flash-lite bloqueou itens cujos arquivos existiam no disco.)
1687
1699
  let marks = [];
1688
1700
  const written = (out.actions || []).filter(a => a.name === 'escrever_arquivo' || a.name === 'editar_arquivo').map(a => String(a.target || ''));
1701
+ // A confined command may legitimately edit the project (formatter, codemod,
1702
+ // migration script). Hash evidence ties that mutation to the exact expected
1703
+ // artifact instead of trusting the command narrative.
1704
+ if (expectedChangedNow && expectedArtifact) written.push(String(expectedArtifact));
1689
1705
  const _basename = (p) => String(p).replace(/\\/g, '/').split('/').pop().toLowerCase();
1690
1706
  const _fileHints = (txt) => (String(txt).match(/[\w.\-]+\.(kt|java|xml|gradle|json|md|txt|kts|properties|pro|png|webp|py|gd|js|ts|html|css|sh)\b/gi) || []).map(s => s.toLowerCase());
1691
1707
  const itemFiles = _fileHints(item.desc);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "terminal-smart-cli",
3
- "version": "0.97.22",
3
+ "version": "0.97.24",
4
4
  "description": "Terminal Smart no seu terminal — pergunte, analise logs por pipe e orquestre agentes de IA. Comando: ts",
5
5
  "bin": {
6
6
  "ts": "bin/ts.js"