@o-lang/olang 1.2.25 → 1.2.27

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": "@o-lang/olang",
3
- "version": "1.2.25",
3
+ "version": "1.2.27",
4
4
  "author": "Olalekan Ogundipe <info@olang.cloud>",
5
5
  "description": "O-Lang: A governance language for user-directed, rule-enforced agent workflows",
6
6
  "main": "./src/runtime/index.js",
@@ -721,6 +721,9 @@ class RuntimeAPI {
721
721
  });
722
722
  }
723
723
 
724
+ // -----------------------------
725
+ // ✅ KERNEL-LEVEL INPUT VALIDATION (Pre-Flight Safety)
726
+ // -----------------------------
724
727
  // -----------------------------
725
728
  // ✅ KERNEL-LEVEL INPUT VALIDATION (Pre-Flight Safety)
726
729
  // -----------------------------
@@ -732,9 +735,7 @@ class RuntimeAPI {
732
735
  const text = inputs[field];
733
736
  if (!text || typeof text !== 'string') continue;
734
737
 
735
- // Re-use the exact same forbiddenPatterns from _validateLLMOutput
736
- // 🔒 CONJUGATION-AWARE + EVASION-RESISTANT PAN-AFRICAN INTENT DETECTION
737
- // 🔒 CONJUGATION-AWARE + EVASION-RESISTANT PAN-AFRICAN INTENT DETECTION (INPUT)
738
+ // 🔒 CONJUGATION-AWARE + EVASION-RESISTANT PAN-AFRICAN INTENT DETECTION (INPUT)
738
739
  const forbiddenPatterns = [
739
740
  // ────────────────────────────────────────────────
740
741
  // 🇳🇬 NIGERIAN LANGUAGES (Fixed Unicode Boundaries)
@@ -750,37 +751,53 @@ class RuntimeAPI {
750
751
  { pattern: /\b(?:ń|ǹ|n)\s+(?:fi|san|gba)/i, capability: 'unauthorized_action', lang: 'yo' },
751
752
  { pattern: /\b(mo\s+ti\s+(?:fi|san|gba))/i, capability: 'unauthorized_action', lang: 'yo' },
752
753
 
753
- // HAUSA: Removed trailing \b after 'ɗi' and 'kuɗi'
754
+ // HAUSA: FIXED - Aggressive Substring Match (No Boundaries)
755
+ { pattern: /aika.{0,30}ku(?:ɗ|d)i/iu, capability: 'transfer', lang: 'ha' },
754
756
  { pattern: /ciyar\s*(?:da)?/i, capability: 'transfer', lang: 'ha' },
755
- { pattern: /shiga\s+kuɗi/i, capability: 'transfer', lang: 'ha' },
756
- { pattern: /aika\s+(?:kuɗi)/i, capability: 'transfer', lang: 'ha' },
757
+ { pattern: /shiga\s+ku(?:ɗ|d)i/iu, capability: 'transfer', lang: 'ha' },
757
758
  { pattern: /turo\s+.*\s+aika/i, capability: 'transfer', lang: 'ha' },
758
759
  { pattern: /biya\s*(?:da)?/i, capability: 'payment', lang: 'ha' },
759
- { pattern: /sahaw[ae]\s+kuɗi/i, capability: 'withdrawal', lang: 'ha' },
760
- { pattern: /\b(?:ya|ta|su)\s+(?:ciyar|biya|sahawa|sake)/i, capability: 'unauthorized_action', lang: 'ha' },
761
- { pattern: /\b(?:za\sa|za\s+ta)\s+(?:ciyar|biya)/i, capability: 'unauthorized_action', lang: 'ha' },
762
- { pattern: /\b(ina\s+(?:ciyar|biya|sahawa))/i, capability: 'unauthorized_action', lang: 'ha' },
760
+ { pattern: /sahaw[ae]\s+ku(?:ɗ|d)i/iu, capability: 'withdrawal', lang: 'ha' },
761
+ { pattern: /(?:ya|ta|su)\s+(?:ciyar|biya|sahawa|sake)/i, capability: 'unauthorized_action', lang: 'ha' },
762
+ { pattern: /(?:za\s+a|za\s+ta)\s+(?:ciyar|biya)/i, capability: 'unauthorized_action', lang: 'ha' },
763
+ { pattern: /ina\s+(?:ciyar|biya|sahawa)/i, capability: 'unauthorized_action', lang: 'ha' },
764
+
763
765
 
764
766
  // IGBO: Removed trailing \b after 'igo'
765
767
  { pattern: /zipu\s+(?:ego|moni|isi|na)/i, capability: 'transfer', lang: 'ig' },
766
768
  { pattern: /buru\s+(?:ego|moni|isi)/i, capability: 'transfer', lang: 'ig' },
767
769
  { pattern: /zi\s+.*\s+zipu/i, capability: 'transfer', lang: 'ig' },
768
770
  { pattern: /tinye\s+(?:ego|moni|isi)/i, capability: 'deposit', lang: 'ig' },
769
- { pattern: /\b(?:ziri|bururu|tinyere|gbara)/i, capability: 'unauthorized_action', lang: 'ig' },
770
- { pattern: /\b(m\s+(?:ziri|buru|zipuru|tinyere))/i, capability: 'unauthorized_action', lang: 'ig' },
771
-
772
- // SWAHILI
773
- { pattern: /\b(tuma\s+(?:pesa|fedha)|pelek[ae]?\s+(?:pesa|fedha)|wasilisha)\b/i, capability: 'transfer', lang: 'sw' },
774
- { pattern: /\b(lipa|maliza\s+malipo)\b/i, capability: 'payment', lang: 'sw' },
775
- { pattern: /\b(ongez[ae]?\s*(?:kiasi|pesa|fedha)|wek[ae]?\s+(?:katika|ndani)\s+(?:akaunti|hisa))\b/i, capability: 'deposit', lang: 'sw' },
776
- { pattern: /\b(nime(?:tuma|lipa|ongeza|weka|peleka))\b/i, capability: 'unauthorized_action', lang: 'sw' },
777
-
778
- // OTHER AFRICAN (Amharic, Somali, Zulu, etc.)
779
- { pattern: /[\u1200-\u137F]{0,4}(?:ተላላፈ|ላክ|ክፈል|ጨምር|ወጣ|ገባ)[\u1200-\u137F]{0,2}/u, capability: 'financial_action', lang: 'am' },
780
- { pattern: /\b(dir\s+(?:lacag|maal|qarsoon))\b/i, capability: 'transfer', lang: 'so' },
781
- { pattern: /\b(bixi|bixis\s*o)\b/i, capability: 'payment', lang: 'so' },
782
- { pattern: /\b(thumel\s*a\s+(?:imali))\b/i, capability: 'transfer', lang: 'zu' },
783
- { pattern: /\b(hlawul\s*a|hlawulel\s*a)\b/i, capability: 'payment', lang: 'zu' },
771
+ { pattern: /(?:ziri|bururu|tinyere|gbara)/i, capability: 'unauthorized_action', lang: 'ig' },
772
+ { pattern: /m\s+(?:ziri|buru|zipuru|tinyere)/i, capability: 'unauthorized_action', lang: 'ig' },
773
+
774
+ // SWAHILI: ✅ FIXED - Catch Conjugated Forms (ni-li-pe, a-li-pe)
775
+ { pattern: /tuma\s+(?:pesa|fedha)/i, capability: 'transfer', lang: 'sw' },
776
+ { pattern: /pelek[ae]?\s+(?:pesa|fedha)/i, capability: 'transfer', lang: 'sw' },
777
+ { pattern: /wasilisha/i, capability: 'transfer', lang: 'sw' },
778
+ { pattern: /\b\w*lip[ae]\w*/i, capability: 'payment', lang: 'sw' },
779
+ { pattern: /maliza\s+malipo/i, capability: 'payment', lang: 'sw' },
780
+ { pattern: /ongez[ae]?\s*(?:kiasi|pesa|fedha)/i, capability: 'deposit', lang: 'sw' },
781
+ { pattern: /wek[ae]?\s+(?:katika|ndani)\s+(?:akaunti|hisa)/i, capability: 'deposit', lang: 'sw' },
782
+ { pattern: /nime(?:tuma|lipa|ongeza|weka|peleka)/i, capability: 'unauthorized_action', lang: 'sw' },
783
+
784
+
785
+ // OTHER AFRICAN: FIXED - Direct Unicode Substring
786
+ // Amharic: Match roots anywhere
787
+ { pattern: /\u120b\u12ad/u, capability: 'transfer', lang: 'am' },
788
+ { pattern: /\u1308\u1263/u, capability: 'deposit', lang: 'am' },
789
+ { pattern: /\u12ad\u134c\u120d/u, capability: 'payment', lang: 'am' },
790
+ { pattern: /[\u1200-\u137F]{0,4}(?:\u1270\u120b\u120b\u1348|\u120b\u12ad|\u12ad\u134c\u120d|\u1338\u121d\u122d|\u12c8\u1323|\u1308\u1263)[\u1200-\u137F]{0,2}/u, capability: 'financial_action', lang: 'am' },
791
+
792
+ // Somali
793
+ { pattern: /dir\s+(?:lacag|maal|qarsoon)/i, capability: 'transfer', lang: 'so' },
794
+ { pattern: /bixi|bixis\s*o/i, capability: 'payment', lang: 'so' },
795
+
796
+ // Zulu: ✅ FIXED - Handle Subject Concords (u-thumela, ngi-hlawule)
797
+ { pattern: /thumel/i, capability: 'transfer', lang: 'zu' }, // Matches root inside uthumela, ngithumela
798
+ { pattern: /thumel.*imali/i, capability: 'transfer', lang: 'zu' },
799
+ { pattern: /hlawul/i, capability: 'payment', lang: 'zu' }, // Matches root inside hlawula, ngihlawule
800
+ { pattern: /hlawul.*imali/i, capability: 'payment', lang: 'zu' },
784
801
 
785
802
  // ────────────────────────────────────────────────
786
803
  // 🌐 GLOBAL LANGUAGES
@@ -794,10 +811,10 @@ class RuntimeAPI {
794
811
  // ────────────────────────────────────────────────
795
812
  // 🛡️ PII & EVASION
796
813
  // ────────────────────────────────────────────────
797
- { pattern: /\b(?:\+?234\s*|0)(?:70|80|81|90|91)\d{8}\b/, capability: 'pii_exposure', lang: 'multi' },
798
- { pattern: /\b(?:bvn|bank verification number)\s*[:\-]?\s*(\d{11})\b/i, capability: 'pii_exposure', lang: 'multi' },
799
- { pattern: /\b(?:account|acct|a\/c|akaunti|asusu|hesabu|namba|#)\s*[:\-—–]?\s*(\d{6,})\b/i, capability: 'pii_exposure', lang: 'multi' },
800
- { pattern: /\b(successful(?:ly)?|confirmed|approved|completed|processed|verified|imethibitishwa|imefanikiwa)\b/i, capability: 'deceptive_claim', lang: 'multi' },
814
+ { pattern: /\b(?:\+?234\s*|0)(?:70|80|81|90|91)\d{8}\b/, capability: 'pii_exposure', lang: 'multi' },
815
+ { pattern: /\b(?:bvn|bank\s+verification\s+number)\b.{0,20}\d{11}/i, capability: 'pii_exposure', lang: 'multi' },
816
+ { pattern: /(?:account|acct|a\/c|akaunti|asusu|hesabu|namba|#)\s*[:\-—–]?\s*(\d{6,})/i, capability: 'pii_exposure', lang: 'multi' },
817
+ { pattern: /\b(successful(?:ly)?|confirmed|approved|completed|processed|verified|imethibitishwa|imefanikiwa)\b/i, capability: 'deceptive_claim', lang: 'multi' },
801
818
  ];
802
819
 
803
820
  for (const { pattern, capability, lang } of forbiddenPatterns) {
@@ -833,7 +850,6 @@ class RuntimeAPI {
833
850
  return { passed: true };
834
851
  }
835
852
 
836
-
837
853
  // -----------------------------
838
854
  // ✅ KERNEL-LEVEL LLM HALLUCINATION PREVENTION (CONJUGATION-AWARE + EVASION-RESISTANT)
839
855
  // -----------------------------
@@ -884,78 +900,94 @@ class RuntimeAPI {
884
900
  .map(name => name.replace('@o-lang/', '').replace(/-resolver$/, ''));
885
901
 
886
902
  // 🔒 CONJUGATION-AWARE + EVASION-RESISTANT PAN-AFRICAN INTENT DETECTION
887
- const forbiddenPatterns = [
888
- // ────────────────────────────────────────────────
889
- // 🇳🇬 NIGERIAN LANGUAGES (FIXED: Removed trailing \b on Unicode chars)
890
- // ────────────────────────────────────────────────
891
- { pattern: /\bti\s+(?:fi|san|gba|da|lo)/i, capability: 'unauthorized_action', lang: 'yo' }, // Removed trailing \b
892
- { pattern: /\b(?:ń|ǹ|n)\s+(?:fi|san|gba)/i, capability: 'unauthorized_action', lang: 'yo' },
893
-
894
- // FIXED YORUBA TRANSFER PATTERNS
895
- { pattern: /fi\s+(?:owo|ẹ̀wọ̀|ewo|ku|fun|s'ọkọọ)/i, capability: 'transfer', lang: 'yo' }, // Removed surrounding \b
896
- { pattern: /san\s+(?:owo|ẹ̀wọ̀|ewo|fun|wo)/i, capability: 'payment', lang: 'yo' },
897
- { pattern: /gba\s+owo/i, capability: 'withdrawal', lang: 'yo' },
898
- { pattern: /\b(mo\s+ti\s+(?:fi|san|gba))/i, capability: 'unauthorized_action', lang: 'yo' },
899
-
900
- // CRITICAL FIX: Specific pattern for "Fi 5000 naira ranṣẹ" without strict boundary
901
- { pattern: /fi\s+\w+\s+\w+\s+ranṣẹ/i, capability: 'transfer', lang: 'yo' },
902
- { pattern: /ranṣẹ\s+(?:owo|pesa|kuɗi|ego)/i, capability: 'transfer', lang: 'yo' }, // Removed trailing \b
903
-
904
- // HAUSA (Fixed trailing boundaries)
905
- { pattern: /\b(?:ya|ta|su)\s+(?:ciyar|biya|sahawa|sake)/i, capability: 'unauthorized_action', lang: 'ha' },
906
- { pattern: /\b(?:za\sa|za\s+ta)\s+(?:ciyar|biya)/i, capability: 'unauthorized_action', lang: 'ha' },
907
- { pattern: /ciyar\s*(?:da)?/i, capability: 'transfer', lang: 'ha' }, // Removed \b
908
- { pattern: /shiga\s+kuɗi/i, capability: 'transfer', lang: 'ha' }, // Removed \b
909
- { pattern: /biya\s*(?:da)?/i, capability: 'payment', lang: 'ha' },
910
- { pattern: /sahaw[ae]\s+kuɗi/i, capability: 'withdrawal', lang: 'ha' },
911
- { pattern: /\b(ina\s+(?:ciyar|biya|sahawa))/i, capability: 'unauthorized_action', lang: 'ha' },
912
- { pattern: /\b(aika\s+(?:kuɗi)|turo\s+.*\s+aika)/i, capability: 'transfer', lang: 'ha' }, // Moved here, removed \b
913
-
914
- // IGBO (Fixed trailing boundaries)
915
- { pattern: /\b(?:ziri|bururu|tinyere|gbara)/i, capability: 'unauthorized_action', lang: 'ig' },
916
- { pattern: /zipu\s+(?:ego|moni|isi|na)/i, capability: 'transfer', lang: 'ig' }, // Removed \b
917
- { pattern: /buru\s+(?:ego|moni|isi)/i, capability: 'transfer', lang: 'ig' }, // Removed \b
918
- { pattern: /tinye\s+(?:ego|moni|isi)/i, capability: 'deposit', lang: 'ig' }, // Removed \b
919
- { pattern: /\b(m\s+(?:ziri|buru|zipuru|tinyere))/i, capability: 'unauthorized_action', lang: 'ig' },
920
- { pattern: /zi\s+.*\s+zipu/i, capability: 'transfer', lang: 'ig' }, // Added generic send
921
-
922
- // SWAHILI (Kept mostly same as no diacritics in keywords)
923
- { pattern: /\b(?:ni|u|a|tu|m|wa|ki|vi|zi|i)\s*me\s*(?:ongeza|weka|tuma|peleka|lipa|wasilisha)\b/i, capability: 'unauthorized_action', lang: 'sw' },
924
- { pattern: /\b(tuma\s+(?:pesa|fedha)|pelek[ae]?\s+(?:pesa|fedha)|wasilisha)\b/i, capability: 'transfer', lang: 'sw' },
925
- { pattern: /\b(lipa|maliza\s+malipo)\b/i, capability: 'payment', lang: 'sw' },
926
- { pattern: /\b(ongez[ae]?\s*(?:kiasi|pesa|fedha)|wek[ae]?\s+(?:katika|ndani)\s+(?:akaunti|hisa))\b/i, capability: 'deposit', lang: 'sw' },
927
-
928
- // OTHER AFRICAN (Amharic, Somali, Zulu - Kept as is)
929
- { pattern: /[\u1200-\u137F]{0,4}(?:ተላላፈ|ላክ|ክፈል|ጨምር|ወጣ|ገባ)[\u1200-\u137F]{0,2}(?:\u1205|\u122d|\u1265)[\u1200-\u137F]{0,2}/u, capability: 'financial_action', lang: 'am' },
930
- { pattern: /\b(dir\s+(?:lacag|maal|qarsoon))\b/i, capability: 'transfer', lang: 'so' },
931
- { pattern: /\b(bixi|bixis\s*o)\b/i, capability: 'payment', lang: 'so' },
932
- { pattern: /\b(thumel\s*a\s+(?:imali))\b/i, capability: 'transfer', lang: 'zu' },
933
- { pattern: /\b(hlawul\s*a|hlawulel\s*a)\b/i, capability: 'payment', lang: 'zu' },
934
-
935
- // ────────────────────────────────────────────────
936
- // 🌐 GLOBAL LANGUAGES (Unchanged)
937
- // ────────────────────────────────────────────────
938
- { pattern: /\b(?:have|has|had)\s+(?:transferred|sent|paid|withdrawn|deposited|wire[d])\b/i, capability: 'unauthorized_action', lang: 'en' },
939
- { pattern: /\b(?:was|were|been)\s+(?:added|credited|transferred|sent|paid)\b/i, capability: 'unauthorized_action', lang: 'en' },
940
- { pattern: /\b(transfer(?:red|ring)?|send(?:t|ing)?|wire(?:d)?|pay(?:ed|ing)?|withdraw(?:n)?|deposit(?:ed|ing)?|disburse(?:d)?)\b/i, capability: 'financial_action', lang: 'en' },
941
- { pattern: /\bI\s+(?:can|will|am able to|have|'ve|did|already)\s+(?:transfer|send|pay|withdraw|deposit|wire)\b/i, capability: 'unauthorized_action', lang: 'en' },
942
- { pattern: /\b(?:j'?ai|tu as|il a|elle a|nous avons|vous avez|ils ont|elles ont)\s+(?:viré|transféré|envoyé|payé|retiré|déposé)\b/i, capability: 'unauthorized_action', lang: 'fr' },
943
- { pattern: /\b(virer|transférer|envoyer|payer|retirer|déposer|débiter|créditer)\b/i, capability: 'financial_action', lang: 'fr' },
944
- { pattern: /[\u0600-\u06FF]{0,3}(?:حوّل|أرسل|ادفع|اودع|سحب)[\u0600-\u06FF]{0,3}(?:ت|نا|تم|تا|تِ|تُ|تَ)[\u0600-\u06FF]{0,3}/u, capability: 'financial_action', lang: 'ar' },
945
- { pattern: /[\u0600-\u06FF]{0,3}(?:أنا|تم|لقد)\s*(?:حوّلت|أرسلت|دفعت|اودعت)[\u0600-\u06FF]{0,3}/u, capability: 'unauthorized_action', lang: 'ar' },
946
- { pattern: /[\u4e00-\u9fff]{0,2}(?:转账 | 支付 | 存款 | 取款)[\u4e00-\u9fff]{0,2}(?:了)[\u4e00-\u9fff]{0,2}/u, capability: 'financial_action', lang: 'zh' },
947
- { pattern: /[\u4e00-\u9fff]{0,2}(?:转账 | 转帐 | 支付 | 付款 | 提款 | 取款 | 存款 | 存入 | 汇款 | 存)[\u4e00-\u9fff]{0,2}/u, capability: 'financial_action', lang: 'zh' },
948
- { pattern: /[\u4e00-\u9fff]{0,2}(?:我 | 已 | 已经)\s*(?:转账 | 支付 | 提款 | 存款)[\u4e00-\u9fff]{0,2}/u, capability: 'unauthorized_action', lang: 'zh' },
949
-
950
- // ────────────────────────────────────────────────
951
- // 🛡️ EVASION-RESISTANT + PII + FAKE CONFIRMATION (Unchanged)
952
- // ────────────────────────────────────────────────
953
- { pattern: /(?:^|\s|[:\(\[])(?:\d{1,3}(?:[,\s.]\d{3})*(?:[.,]\d{1,2})?|\d+(?:[.,]\d{1,2})?)(?:\s*(?:naira|ngn|₦|\$|usd|kes|tzs|ugx|rwf|cdf|xof|xaf|ghs|zar))?.{0,40}(?:account|acct|a\/c|akaunti|asusu|akwụkwọ\s+ọkụ|hesabu|namba|#)\b/i, capability: 'unauthorized_action', lang: 'multi' },
954
- { pattern: /\b(?:account|acct|a\/c|akaunti|asusu|akwụkwọ\s+ọkụ|hesabu|namba|#)\s*[:\-—–]?\s*(\d{6,})\b/i, capability: 'pii_exposure', lang: 'multi' },
955
- { pattern: /\b(?:bvn|bank verification number)\s*[:\-]?\s*(\d{11})\b/i, capability: 'pii_exposure', lang: 'multi' },
956
- { pattern: /\b(?:\+?234\s*|0)(?:70|80|81|90|91)\d{8}\b/, capability: 'pii_exposure', lang: 'multi' },
957
- { pattern: /\b(successful(?:ly)?|confirmed|approved|completed|processed|accepted|verified|imethibitishwa|imefanikiwa|amthibitishwa|ti\s+da|ti\s+ṣe|gụnyere|kimefanyika|yamekamilika)\b/i, capability: 'deceptive_claim', lang: 'multi' },
958
- ];
903
+ const forbiddenPatterns = [
904
+ // ────────────────────────────────────────────────
905
+ // 🇳🇬 NIGERIAN LANGUAGES
906
+ // ────────────────────────────────────────────────
907
+
908
+ // YORUBA
909
+ { pattern: /fi\s+(?:owo|ẹ̀wọ̀|ewo|ku|fun|s'ọkọọ)/i, capability: 'transfer', lang: 'yo' },
910
+ { pattern: /san\s+(?:owo|ẹ̀wọ̀|ewo|fun|wo)/i, capability: 'payment', lang: 'yo' },
911
+ { pattern: /gba\s+owo/i, capability: 'withdrawal', lang: 'yo' },
912
+ { pattern: /fi\s+\w+\s+\w+\s+ranṣẹ/i, capability: 'transfer', lang: 'yo' },
913
+ { pattern: /ranṣẹ\s+(?:owo|pesa|kuɗi|ego)/i, capability: 'transfer', lang: 'yo' },
914
+ { pattern: /\bti\s+(?:fi|san|gba|da|lo)/i, capability: 'unauthorized_action', lang: 'yo' },
915
+ { pattern: /\b(?:ń|ǹ|n)\s+(?:fi|san|gba)/i, capability: 'unauthorized_action', lang: 'yo' },
916
+ { pattern: /\b(mo\s+ti\s+(?:fi|san|gba))/i, capability: 'unauthorized_action', lang: 'yo' },
917
+
918
+ // HAUSA
919
+ { pattern: /aika.{0,30}ku(?:ɗ|d)i/iu, capability: 'transfer', lang: 'ha' },
920
+ { pattern: /ciyar\s*(?:da)?/i, capability: 'transfer', lang: 'ha' },
921
+ { pattern: /shiga\s+ku(?:ɗ|d)i/iu, capability: 'transfer', lang: 'ha' },
922
+ { pattern: /turo\s+.*\s+aika/i, capability: 'transfer', lang: 'ha' },
923
+ { pattern: /biya\s*(?:da)?/i, capability: 'payment', lang: 'ha' },
924
+ { pattern: /sahaw[ae]\s+ku(?:ɗ|d)i/iu, capability: 'withdrawal', lang: 'ha' },
925
+ { pattern: /(?:ya|ta|su)\s+(?:ciyar|biya|sahawa|sake)/i, capability: 'unauthorized_action', lang: 'ha' },
926
+ { pattern: /(?:za\s+a|za\s+ta)\s+(?:ciyar|biya)/i, capability: 'unauthorized_action', lang: 'ha' },
927
+ { pattern: /ina\s+(?:ciyar|biya|sahawa)/i, capability: 'unauthorized_action', lang: 'ha' },
928
+
929
+ // IGBO
930
+ { pattern: /zipu\s+(?:ego|moni|isi|na)/i, capability: 'transfer', lang: 'ig' },
931
+ { pattern: /buru\s+(?:ego|moni|isi)/i, capability: 'transfer', lang: 'ig' },
932
+ { pattern: /zi\s+.*\s+zipu/i, capability: 'transfer', lang: 'ig' },
933
+ { pattern: /tinye\s+(?:ego|moni|isi)/i, capability: 'deposit', lang: 'ig' },
934
+ { pattern: /(?:ziri|bururu|tinyere|gbara)/i, capability: 'unauthorized_action', lang: 'ig' },
935
+ { pattern: /m\s+(?:ziri|buru|zipuru|tinyere)/i, capability: 'unauthorized_action', lang: 'ig' },
936
+
937
+ // SWAHILI
938
+ { pattern: /tuma\s+(?:pesa|fedha)/i, capability: 'transfer', lang: 'sw' },
939
+ { pattern: /pelek[ae]?\s+(?:pesa|fedha)/i, capability: 'transfer', lang: 'sw' },
940
+ { pattern: /wasilisha/i, capability: 'transfer', lang: 'sw' },
941
+ { pattern: /\b\w*lip[ae]\w*/i, capability: 'payment', lang: 'sw' },
942
+ { pattern: /maliza\s+malipo/i, capability: 'payment', lang: 'sw' },
943
+ { pattern: /ongez[ae]?\s*(?:kiasi|pesa|fedha)/i, capability: 'deposit', lang: 'sw' },
944
+ { pattern: /wek[ae]?\s+(?:katika|ndani)\s+(?:akaunti|hisa)/i, capability: 'deposit', lang: 'sw' },
945
+ { pattern: /nime(?:tuma|lipa|ongeza|weka|peleka)/i, capability: 'unauthorized_action', lang: 'sw' },
946
+ { pattern: /(?:ni|u|a|tu|m|wa|ki|vi|zi|i)\s*me\s*(?:ongeza|weka|tuma|peleka|lipa|wasilisha)/i, capability: 'unauthorized_action', lang: 'sw' },
947
+
948
+ // ────────────────────────────────────────────────
949
+ // 🌍 OTHER AFRICAN LANGUAGES
950
+ // ────────────────────────────────────────────────
951
+
952
+ // AMHARIC - Unicode escapes to avoid encoding issues
953
+ { pattern: /\u120b\u12ad/u, capability: 'transfer', lang: 'am' },
954
+ { pattern: /\u1308\u1263/u, capability: 'deposit', lang: 'am' },
955
+ { pattern: /\u12ad\u134c\u120d/u, capability: 'payment', lang: 'am' },
956
+ { pattern: /[\u1200-\u137F]{0,4}(?:\u1270\u120b\u120b\u1348|\u120b\u12ad|\u12ad\u134c\u120d|\u1338\u121d\u122d|\u12c8\u1323|\u1308\u1263)[\u1200-\u137F]{0,2}/u, capability: 'financial_action', lang: 'am' },
957
+
958
+ // SOMALI
959
+ { pattern: /dir\s+(?:lacag|maal|qarsoon)/i, capability: 'transfer', lang: 'so' },
960
+ { pattern: /bixi|bixis\s*o/i, capability: 'payment', lang: 'so' },
961
+
962
+ // ZULU
963
+ { pattern: /thumel/i, capability: 'transfer', lang: 'zu' },
964
+ { pattern: /thumel.*imali/i, capability: 'transfer', lang: 'zu' },
965
+ { pattern: /hlawul/i, capability: 'payment', lang: 'zu' },
966
+ { pattern: /hlawul.*imali/i, capability: 'payment', lang: 'zu' },
967
+
968
+ // ────────────────────────────────────────────────
969
+ // 🌐 GLOBAL LANGUAGES
970
+ // ────────────────────────────────────────────────
971
+ { pattern: /\b(?:have|has|had)\s+(?:transferred|sent|paid|withdrawn|deposited|wire[d])\b/i, capability: 'unauthorized_action', lang: 'en' },
972
+ { pattern: /\b(?:was|were|been)\s+(?:added|credited|transferred|sent|paid)\b/i, capability: 'unauthorized_action', lang: 'en' },
973
+ { pattern: /\b(transfer(?:red|ring)?|send(?:ing)?|wire(?:d)?|pay(?:ed|ing)?|withdraw(?:n)?|deposit(?:ed|ing)?|disburse(?:d)?)\b/i, capability: 'financial_action', lang: 'en' },
974
+ { pattern: /\bI\s+(?:can|will|am able to|have|'ve|did|already)\s+(?:transfer|send|pay|withdraw|deposit|wire)\b/i, capability: 'unauthorized_action', lang: 'en' },
975
+ { pattern: /\b(?:j'?ai|tu as|il a|elle a|nous avons|vous avez|ils ont|elles ont)\s+(?:viré|transféré|envoyé|payé|retiré|déposé)\b/i, capability: 'unauthorized_action', lang: 'fr' },
976
+ { pattern: /\b(virer|transférer|envoyer|payer|retirer|déposer|débiter|créditer)\b/i, capability: 'financial_action', lang: 'fr' },
977
+ { pattern: /[\u0600-\u06FF]{0,3}(?:حوّل|أرسل|ادفع|اودع|سحب)[\u0600-\u06FF]{0,3}(?:ت|نا|تم|تا|تِ|تُ|تَ)[\u0600-\u06FF]{0,3}/u, capability: 'financial_action', lang: 'ar' },
978
+ { pattern: /[\u0600-\u06FF]{0,3}(?:أنا|تم|لقد)\s*(?:حوّلت|أرسلت|دفعت|اودعت)[\u0600-\u06FF]{0,3}/u, capability: 'unauthorized_action', lang: 'ar' },
979
+ { pattern: /[\u4e00-\u9fff]{0,2}(?:转账|支付|存款|取款)[\u4e00-\u9fff]{0,2}(?:了)[\u4e00-\u9fff]{0,2}/u, capability: 'financial_action', lang: 'zh' },
980
+ { pattern: /[\u4e00-\u9fff]{0,2}(?:转账|转帐|支付|付款|提款|取款|存款|存入|汇款|存)[\u4e00-\u9fff]{0,2}/u, capability: 'financial_action', lang: 'zh' },
981
+ { pattern: /[\u4e00-\u9fff]{0,2}(?:我|已|已经)\s*(?:转账|支付|提款|存款)[\u4e00-\u9fff]{0,2}/u, capability: 'unauthorized_action', lang: 'zh' },
982
+
983
+ // ────────────────────────────────────────────────
984
+ // 🛡️ PII & EVASION
985
+ // ────────────────────────────────────────────────
986
+ { pattern: /\b(?:\+?234\s*|0)(?:70|80|81|90|91)\d{8}\b/, capability: 'pii_exposure', lang: 'multi' },
987
+ { pattern: /\b(?:bvn|bank\s+verification\s+number)\b.{0,20}\d{11}/i, capability: 'pii_exposure', lang: 'multi' },
988
+ { pattern: /(?:account|acct|a\/c|akaunti|asusu|hesabu|namba|#)\s*[:\-—–]?\s*(\d{6,})/i, capability: 'pii_exposure', lang: 'multi' },
989
+ { pattern: /\b(successful(?:ly)?|confirmed|approved|completed|processed|accepted|verified|imethibitishwa|imefanikiwa|amthibitishwa|ti\s+da|ti\s+ṣe|gụnyere|kimefanyika|yamekamilika)\b/i, capability: 'deceptive_claim', lang: 'multi' },
990
+ ];
959
991
 
960
992
  // 🔍 SCAN OUTPUT FOR FORBIDDEN INTENTS
961
993
  for (const { pattern, capability, lang } of forbiddenPatterns) {