@polycode-projects/the-mechanical-code-talker 2.11.1 → 2.11.3

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@polycode-projects/the-mechanical-code-talker",
3
- "version": "2.11.1",
3
+ "version": "2.11.3",
4
4
  "private": false,
5
5
  "type": "module",
6
6
  "description": "The Mechanical Code Talker (tmct) — a tolerant, offline, $0 chat surface that guides you toward precision queries about a software repository. ELIZA/PARRY-style but domain-obsessed with code. No model calls; no codebase index of its own.",
@@ -3163,6 +3163,14 @@ async function unknownAdjectiveFallback(payload, { memoryDir, sessionId, lexicon
3163
3163
  if (!m) return null;
3164
3164
  const [, det, subjectRaw, verb, objectRaw] = m;
3165
3165
  if (PLACE_ADVERB_OBJECT_RE.test(objectRaw)) return null; // a place adverb is never a property
3166
+ // An ARTICLED complement ("a dog is a mammal") is a noun-phrase kind claim,
3167
+ // never an adjective property — but UNKNOWN_SUBJECT_RE strips the object's
3168
+ // article before capture, so objectRaw alone can't show the difference from
3169
+ // "the cache is bespoke". Without this re-check, a fact-grounded subject
3170
+ // silently minted the kind claim as an mgx:hasProperty garble that the isa
3171
+ // read-back then denied. Declining here lands on the honest teach-miss,
3172
+ // whose nudge already names the storable form ("every dog is a mammal").
3173
+ if (/\s+(?:is|are)\s+an?\s+[\w-]+[.!?]*\s*$/i.test(String(payload).trim())) return null;
3166
3174
  const { loadLexicon, lookupNoun, lookupAdjective, classify } = await import("../domain/grammar/lexicon.mjs");
3167
3175
  const lex = lexicon || loadLexicon();
3168
3176
  // Y already a known NOUN or a fact-grounded CLASS term — a genuine class-
@@ -6826,7 +6834,7 @@ const FACT_ANSWER_CAP = 32;
6826
6834
  * RELATION_WHO_ASK_RE's required leading "is/are/was/were" (those two live in
6827
6835
  * the separate factReadBack, only ever reached via `factAnswer(...) ??
6828
6836
  * factReadBack(...)` — never both). */
6829
- const CAN_ASK_RE = /^(?:can|could)\s+(?:an?\s+)?([\w'-]+(?:\s+[\w'-]+)*?)\s+([a-z]+)[?.!\s]*$/i;
6837
+ const CAN_ASK_RE = /^(?:can|could)\s+(all\s+|every\s+)?(?:an?\s+)?([\w'-]+(?:\s+[\w'-]+)*?)\s+([a-z]+)[?.!\s]*$/i;
6830
6838
  const DOES_HAVE_ASK_RE = /^(?:does|do)\s+(?:an?\s+|the\s+)?(.+?)\s+have\s+(?:an?\s+|the\s+)?(.+?)[?.!\s]*$/i;
6831
6839
  const WHAT_CAN_DO_RE = /^what\s+can\s+(?:an?\s+)?(.+?)\s+do[?.!\s]*$/i;
6832
6840
  const WHAT_HAS_RE = /^what\s+has\s+(?:an?\s+)?(.+?)[?.!\s]*$/i;
@@ -7584,14 +7592,24 @@ async function factAnswerReaders(memoryDir, query, envelope, miss, biasByBundle
7584
7592
  const can = positiveQuestionSurface(q).match(CAN_ASK_RE);
7585
7593
  if (can) {
7586
7594
  const facts = await factRows(memoryDir, cache);
7587
- const reply = capabilityReply(can[1], can[2], facts);
7595
+ const canUniversal = can[1];
7596
+ const reply = capabilityReply(can[2], can[3], facts);
7597
+ // Quantified ("can all/every X ..."): the stored facts are generic, and a
7598
+ // bare "yes" would claim universality the memory can't support — the same
7599
+ // hedge the do-support surface applies, echoing the quantifier as typed.
7600
+ if (reply && canUniversal) {
7601
+ return {
7602
+ text: `I can't speak for ${canUniversal.trim()} ${can[2]} — what I remember is generic, not universal. ${reply.text}.`,
7603
+ replace: true,
7604
+ };
7605
+ }
7588
7606
  if (reply) return reply;
7589
7607
  // A KNOWN subject with capability facts, none matching: an honest,
7590
7608
  // specific miss citing what it CAN do — the same closer the is-a ladder
7591
7609
  // answers with, instead of the misleading structural parse wall. An
7592
7610
  // unknown subject still declines. Never a guessed "no": absence of a
7593
7611
  // capableOf fact proves nothing.
7594
- const subj = factTermVariants(normFactTerm, can[1]);
7612
+ const subj = factTermVariants(normFactTerm, can[2]);
7595
7613
  const knownCan = facts.filter((f) => f.predicate === "mgx:capableOf" && subj.has(f.subject));
7596
7614
  if (knownCan.length) {
7597
7615
  const shown = knownCan.slice(0, 3).map(renderFactLine).join("; ");
@@ -7599,14 +7617,14 @@ async function factAnswerReaders(memoryDir, query, envelope, miss, biasByBundle
7599
7617
  // not as the user typed it — 'teach me: "a birds can swim"' is a
7600
7618
  // garbled hint that can't round-trip.
7601
7619
  return {
7602
- text: `I can't confirm that — nothing I remember says ${can[1]} can ${can[2]}. I do know: ${shown}. If it's true, teach me: "a ${knownCan[0].subject} can ${can[2]}".`,
7620
+ text: `I can't confirm that — nothing I remember says ${can[2]} can ${can[3]}. I do know: ${shown}. If it's true, teach me: "a ${knownCan[0].subject} can ${can[3]}".`,
7603
7621
  replace: true,
7604
7622
  miss: true,
7605
7623
  };
7606
7624
  }
7607
7625
  // nothing about the subject at all — report the class base rate, and answer
7608
7626
  // neither yes nor no
7609
- return capabilityBaseRateReply(can[1], can[2], facts);
7627
+ return capabilityBaseRateReply(can[2], can[3], facts);
7610
7628
  }
7611
7629
 
7612
7630
  // (b2b) "does a dog have a tail" — yes iff a remembered possession fact
@@ -7685,8 +7703,10 @@ async function factAnswerReaders(memoryDir, query, envelope, miss, biasByBundle
7685
7703
  // penguin fly" can never disagree in one session
7686
7704
  const reply = capabilityReply(doAsk[2], doAsk[3], facts);
7687
7705
  if (reply && universal) {
7706
+ // Echo the quantifier as typed ("every dog", "all dogs") — "all dog"
7707
+ // for a singular every-question is a garbled echo.
7688
7708
  return {
7689
- text: `I can't speak for all ${doAsk[2]} — what I remember is generic, not universal. ${reply.text}.`,
7709
+ text: `I can't speak for ${doAsk[1].trim()} ${doAsk[2]} — what I remember is generic, not universal. ${reply.text}.`,
7690
7710
  replace: true,
7691
7711
  };
7692
7712
  }