slopless 0.2.23 → 0.2.25
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/dist/rules/semantic-thinness/patterns/abstract-metaphor-claim.json +83 -1
- package/dist/rules/semantic-thinness/patterns/deictic-summary.json +31 -2
- package/dist/rules/semantic-thinness/patterns/empty-quantification.json +33 -0
- package/dist/rules/semantic-thinness/patterns/empty-scene-transition.json +2 -1
- package/dist/rules/semantic-thinness/private/concrete-guards.js +2 -0
- package/dist/rules/semantic-thinness/private/pattern-data-e.js +2 -0
- package/dist/rules/semantic-thinness/private/pattern-matcher.js +28 -7
- package/dist/rules/syntactic-patterns/closers/affirmation-closers.js +13 -3
- package/dist/rules/syntactic-patterns/contrast/contrastive-aphorism.js +2 -0
- package/dist/rules/syntactic-patterns/contrast/negation-reframe.js +1 -1
- package/dist/rules/syntactic-patterns/contrast/private/action-reframe-vocabulary.js +47 -0
- package/dist/rules/syntactic-patterns/contrast/private/audience-replacement.js +267 -0
- package/dist/rules/syntactic-patterns/contrast/private/copular-reframe.js +79 -0
- package/dist/rules/syntactic-patterns/contrast/private/evidence-limitation-pair.js +307 -0
- package/dist/rules/syntactic-patterns/contrast/private/inline-semicolon-reframe.js +50 -0
- package/dist/rules/syntactic-patterns/contrast/private/inline-short-negation.js +1 -0
- package/dist/rules/syntactic-patterns/contrast/private/negation-reframe-matcher.js +78 -73
- package/dist/rules/syntactic-patterns/contrast/private/negation-reframe-parts.js +99 -31
- package/dist/rules/syntactic-patterns/contrast/private/negation-vocabulary.js +27 -0
- package/dist/rules/syntactic-patterns/contrast/private/negative-consequence.js +301 -0
- package/dist/rules/syntactic-patterns/contrast/private/negative-slop-frames.js +155 -39
- package/dist/rules/syntactic-patterns/contrast/private/policy-object.js +55 -0
- package/dist/rules/syntactic-patterns/contrast/private/reframe-classification.js +214 -0
- package/dist/rules/syntactic-patterns/contrast/private/sequence-reframes.js +9 -0
- package/dist/rules/syntactic-patterns/contrast/private/temporal-reframe.js +318 -0
- package/dist/rules/syntactic-patterns/lead-ins/generic-signposting.js +96 -102
- package/dist/rules/syntactic-patterns/lead-ins/private/component-assignment-frame.js +239 -0
- package/dist/rules/syntactic-patterns/lead-ins/private/discourse-evaluation.js +150 -4
- package/dist/rules/syntactic-patterns/lead-ins/private/evaluative-colon-frame.js +166 -0
- package/dist/rules/syntactic-patterns/lead-ins/private/reaction-frame.js +29 -0
- package/dist/rules/syntactic-patterns/lead-ins/private/relative-discourse-frame.js +119 -0
- package/package.json +1 -1
|
@@ -0,0 +1,166 @@
|
|
|
1
|
+
import { hasConcreteTechnicalToken } from "../../../../shared/matchers/concrete-evidence.js";
|
|
2
|
+
import { tokens } from "../../../../shared/matchers/prose-patterns.js";
|
|
3
|
+
import { normalizeForMatch } from "../../../../shared/text/normalize.js";
|
|
4
|
+
const SUBJECT_HEADS = new Set([
|
|
5
|
+
"answer",
|
|
6
|
+
"answers",
|
|
7
|
+
"approach",
|
|
8
|
+
"approaches",
|
|
9
|
+
"architecture",
|
|
10
|
+
"architectures",
|
|
11
|
+
"audit",
|
|
12
|
+
"audits",
|
|
13
|
+
"choice",
|
|
14
|
+
"choices",
|
|
15
|
+
"decision",
|
|
16
|
+
"decisions",
|
|
17
|
+
"design",
|
|
18
|
+
"designs",
|
|
19
|
+
"machine",
|
|
20
|
+
"machines",
|
|
21
|
+
"method",
|
|
22
|
+
"methods",
|
|
23
|
+
"model",
|
|
24
|
+
"models",
|
|
25
|
+
"pipeline",
|
|
26
|
+
"pipelines",
|
|
27
|
+
"plan",
|
|
28
|
+
"plans",
|
|
29
|
+
"platform",
|
|
30
|
+
"platforms",
|
|
31
|
+
"problem",
|
|
32
|
+
"problems",
|
|
33
|
+
"process",
|
|
34
|
+
"processes",
|
|
35
|
+
"solution",
|
|
36
|
+
"solutions",
|
|
37
|
+
"stack",
|
|
38
|
+
"stacks",
|
|
39
|
+
"strategy",
|
|
40
|
+
"strategies",
|
|
41
|
+
"setup",
|
|
42
|
+
"setups",
|
|
43
|
+
"system",
|
|
44
|
+
"systems",
|
|
45
|
+
"workflow",
|
|
46
|
+
"workflows"
|
|
47
|
+
]);
|
|
48
|
+
const EVALUATIVE_ADJECTIVES = new Set([
|
|
49
|
+
"boring",
|
|
50
|
+
"clear",
|
|
51
|
+
"complex",
|
|
52
|
+
"easy",
|
|
53
|
+
"hard",
|
|
54
|
+
"heavy",
|
|
55
|
+
"obvious",
|
|
56
|
+
"simple",
|
|
57
|
+
"straightforward"
|
|
58
|
+
]);
|
|
59
|
+
const EVALUATIVE_LINKS = new Set([
|
|
60
|
+
"are",
|
|
61
|
+
"feel",
|
|
62
|
+
"feels",
|
|
63
|
+
"is",
|
|
64
|
+
"look",
|
|
65
|
+
"looks",
|
|
66
|
+
"was",
|
|
67
|
+
"were"
|
|
68
|
+
]);
|
|
69
|
+
const QUANTITY_WORDS = new Set([
|
|
70
|
+
"one",
|
|
71
|
+
"two",
|
|
72
|
+
"three",
|
|
73
|
+
"four",
|
|
74
|
+
"five",
|
|
75
|
+
"six",
|
|
76
|
+
"seven",
|
|
77
|
+
"eight",
|
|
78
|
+
"nine",
|
|
79
|
+
"ten",
|
|
80
|
+
"dozen",
|
|
81
|
+
"hundred",
|
|
82
|
+
"thousand",
|
|
83
|
+
"million",
|
|
84
|
+
"several"
|
|
85
|
+
]);
|
|
86
|
+
const MONTHS_AND_TIMES = new Set([
|
|
87
|
+
"january",
|
|
88
|
+
"february",
|
|
89
|
+
"march",
|
|
90
|
+
"april",
|
|
91
|
+
"may",
|
|
92
|
+
"june",
|
|
93
|
+
"july",
|
|
94
|
+
"august",
|
|
95
|
+
"september",
|
|
96
|
+
"october",
|
|
97
|
+
"november",
|
|
98
|
+
"december",
|
|
99
|
+
"midnight",
|
|
100
|
+
"noon"
|
|
101
|
+
]);
|
|
102
|
+
function hasDigitOrEquationSymbol(text) {
|
|
103
|
+
for (const character of text) {
|
|
104
|
+
if ((character >= "0" && character <= "9") ||
|
|
105
|
+
["=", "<", ">", "+", "\u00d7", "\u00f7"].includes(character)) {
|
|
106
|
+
return true;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
return false;
|
|
110
|
+
}
|
|
111
|
+
function firstAsciiWord(text) {
|
|
112
|
+
let word = "";
|
|
113
|
+
for (const character of text.trimStart()) {
|
|
114
|
+
const isLetter = (character >= "A" && character <= "Z") ||
|
|
115
|
+
(character >= "a" && character <= "z");
|
|
116
|
+
const isWordContinuation = isLetter || (character >= "0" && character <= "9") || character === "-";
|
|
117
|
+
if (!isWordContinuation) {
|
|
118
|
+
break;
|
|
119
|
+
}
|
|
120
|
+
word += character;
|
|
121
|
+
}
|
|
122
|
+
return word.length > 0 ? word : undefined;
|
|
123
|
+
}
|
|
124
|
+
function isIdentifierLike(word) {
|
|
125
|
+
for (const character of word.slice(1)) {
|
|
126
|
+
if (character >= "A" && character <= "Z") {
|
|
127
|
+
return true;
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
return false;
|
|
131
|
+
}
|
|
132
|
+
function hasExcludedEvidence(text, words) {
|
|
133
|
+
const trimmed = text.trimStart();
|
|
134
|
+
const firstWord = firstAsciiWord(trimmed);
|
|
135
|
+
const startsWithNamedTechnicalSubject = firstWord !== undefined &&
|
|
136
|
+
isIdentifierLike(firstWord) &&
|
|
137
|
+
hasConcreteTechnicalToken(text);
|
|
138
|
+
return (hasDigitOrEquationSymbol(text) ||
|
|
139
|
+
trimmed.startsWith('"') ||
|
|
140
|
+
trimmed.startsWith("'") ||
|
|
141
|
+
text.includes("`") ||
|
|
142
|
+
startsWithNamedTechnicalSubject ||
|
|
143
|
+
words.some((word) => QUANTITY_WORDS.has(word) || MONTHS_AND_TIMES.has(word)));
|
|
144
|
+
}
|
|
145
|
+
export function matchEvaluativeColonFrame(text) {
|
|
146
|
+
const colonIndex = text.indexOf(":");
|
|
147
|
+
if (colonIndex < 0 || text.indexOf(":", colonIndex + 1) >= 0) {
|
|
148
|
+
return undefined;
|
|
149
|
+
}
|
|
150
|
+
const prefix = normalizeForMatch(text.slice(0, colonIndex));
|
|
151
|
+
const detail = text.slice(colonIndex + 1);
|
|
152
|
+
const prefixWords = tokens(prefix);
|
|
153
|
+
const detailWords = tokens(detail);
|
|
154
|
+
const copulaIndex = prefixWords.findIndex((word) => EVALUATIVE_LINKS.has(word));
|
|
155
|
+
if (copulaIndex < 1 ||
|
|
156
|
+
copulaIndex > 3 ||
|
|
157
|
+
prefixWords.length !== copulaIndex + 2 ||
|
|
158
|
+
!SUBJECT_HEADS.has(prefixWords[copulaIndex - 1] ?? "") ||
|
|
159
|
+
!EVALUATIVE_ADJECTIVES.has(prefixWords[copulaIndex + 1] ?? "") ||
|
|
160
|
+
detailWords.length < 2 ||
|
|
161
|
+
hasExcludedEvidence(detail, detailWords)) {
|
|
162
|
+
return undefined;
|
|
163
|
+
}
|
|
164
|
+
return prefixWords.join("-");
|
|
165
|
+
}
|
|
166
|
+
//# sourceMappingURL=evaluative-colon-frame.js.map
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
const REACTION_NOUNS = new Set(["detail", "part", "piece", "point", "thing"]);
|
|
2
|
+
const REACTION_VERBS = new Set(["got", "hit", "stuck", "surprised"]);
|
|
3
|
+
export function matchReactionFrame(words) {
|
|
4
|
+
const contracted = words[0] === "here's";
|
|
5
|
+
const start = contracted || (words[0] === "here" && words[1] === "is")
|
|
6
|
+
? contracted
|
|
7
|
+
? 1
|
|
8
|
+
: 2
|
|
9
|
+
: -1;
|
|
10
|
+
if (start < 0 ||
|
|
11
|
+
words[start] !== "the" ||
|
|
12
|
+
!REACTION_NOUNS.has(words[start + 1] ?? "") ||
|
|
13
|
+
words[start + 2] !== "that") {
|
|
14
|
+
return undefined;
|
|
15
|
+
}
|
|
16
|
+
const verb = words[start + 3];
|
|
17
|
+
const directReaction = verb !== "stuck" &&
|
|
18
|
+
REACTION_VERBS.has(verb ?? "") &&
|
|
19
|
+
["me", "us"].includes(words[start + 4] ?? "") &&
|
|
20
|
+
words.length === start + 5;
|
|
21
|
+
const stuckReaction = verb === "stuck" &&
|
|
22
|
+
words[start + 4] === "with" &&
|
|
23
|
+
["me", "us"].includes(words[start + 5] ?? "") &&
|
|
24
|
+
words.length === start + 6;
|
|
25
|
+
return directReaction || stuckReaction
|
|
26
|
+
? "here-is-the-reaction-frame"
|
|
27
|
+
: undefined;
|
|
28
|
+
}
|
|
29
|
+
//# sourceMappingURL=reaction-frame.js.map
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
import { tokens } from "../../../../shared/matchers/prose-patterns.js";
|
|
2
|
+
const DETERMINERS = new Set(["a", "an", "the", "this", "that"]);
|
|
3
|
+
const RELATIVE_FRAME_MODIFIERS = new Set([
|
|
4
|
+
"central",
|
|
5
|
+
"clearest",
|
|
6
|
+
"core",
|
|
7
|
+
"important",
|
|
8
|
+
"main",
|
|
9
|
+
"practical",
|
|
10
|
+
"real",
|
|
11
|
+
"simple",
|
|
12
|
+
"useful"
|
|
13
|
+
]);
|
|
14
|
+
const RELATIVE_HELPER_VERBS = new Set([
|
|
15
|
+
"helped",
|
|
16
|
+
"helps",
|
|
17
|
+
"mattered",
|
|
18
|
+
"matters",
|
|
19
|
+
"worked",
|
|
20
|
+
"works"
|
|
21
|
+
]);
|
|
22
|
+
const RELATIVE_USEFULNESS_ADJECTIVES = new Set([
|
|
23
|
+
"actionable",
|
|
24
|
+
"better",
|
|
25
|
+
"clear",
|
|
26
|
+
"easier",
|
|
27
|
+
"effective",
|
|
28
|
+
"helpful",
|
|
29
|
+
"practical",
|
|
30
|
+
"reliable",
|
|
31
|
+
"useful",
|
|
32
|
+
"valuable"
|
|
33
|
+
]);
|
|
34
|
+
const RELATIVE_EVALUATIONS = new Set([
|
|
35
|
+
"clear",
|
|
36
|
+
"consistent",
|
|
37
|
+
"predictable",
|
|
38
|
+
"repeatable",
|
|
39
|
+
"simple",
|
|
40
|
+
"straightforward",
|
|
41
|
+
"useful"
|
|
42
|
+
]);
|
|
43
|
+
const RELATIVE_FRAME_HEADS = new Set([
|
|
44
|
+
"answer",
|
|
45
|
+
"approach",
|
|
46
|
+
"claim",
|
|
47
|
+
"detail",
|
|
48
|
+
"evidence",
|
|
49
|
+
"factor",
|
|
50
|
+
"feature",
|
|
51
|
+
"fix",
|
|
52
|
+
"focus",
|
|
53
|
+
"idea",
|
|
54
|
+
"lesson",
|
|
55
|
+
"method",
|
|
56
|
+
"move",
|
|
57
|
+
"plan",
|
|
58
|
+
"point",
|
|
59
|
+
"process",
|
|
60
|
+
"question",
|
|
61
|
+
"result",
|
|
62
|
+
"review",
|
|
63
|
+
"rule",
|
|
64
|
+
"signal",
|
|
65
|
+
"solution",
|
|
66
|
+
"step",
|
|
67
|
+
"strategy",
|
|
68
|
+
"thing",
|
|
69
|
+
"way"
|
|
70
|
+
]);
|
|
71
|
+
function relativeFrameHeadIndex(words) {
|
|
72
|
+
if (!DETERMINERS.has(words[0] ?? "")) {
|
|
73
|
+
return -1;
|
|
74
|
+
}
|
|
75
|
+
if (RELATIVE_FRAME_HEADS.has(words[1] ?? "")) {
|
|
76
|
+
return 1;
|
|
77
|
+
}
|
|
78
|
+
return RELATIVE_FRAME_MODIFIERS.has(words[1] ?? "") &&
|
|
79
|
+
RELATIVE_FRAME_HEADS.has(words[2] ?? "")
|
|
80
|
+
? 2
|
|
81
|
+
: -1;
|
|
82
|
+
}
|
|
83
|
+
function matchRelativeHelperFrame(text, words, headIndex) {
|
|
84
|
+
const helperIndex = headIndex + 2;
|
|
85
|
+
const colonIndex = text.indexOf(":");
|
|
86
|
+
if (words[headIndex + 1] !== "that" ||
|
|
87
|
+
!RELATIVE_HELPER_VERBS.has(words[helperIndex] ?? "") ||
|
|
88
|
+
colonIndex < 0 ||
|
|
89
|
+
tokens(text.slice(0, colonIndex)).length !== helperIndex + 1) {
|
|
90
|
+
return undefined;
|
|
91
|
+
}
|
|
92
|
+
return `relative-${words[helperIndex] ?? "helps"}-frame`;
|
|
93
|
+
}
|
|
94
|
+
function matchRelativeUsefulnessFrame(words, headIndex) {
|
|
95
|
+
const makesIndex = headIndex + 2;
|
|
96
|
+
if (words[headIndex + 1] !== "that" ||
|
|
97
|
+
!["made", "makes"].includes(words[makesIndex] ?? "")) {
|
|
98
|
+
return undefined;
|
|
99
|
+
}
|
|
100
|
+
const usefulnessIndex = words.findIndex((word, index) => index > makesIndex + 1 &&
|
|
101
|
+
index <= makesIndex + 6 &&
|
|
102
|
+
RELATIVE_USEFULNESS_ADJECTIVES.has(word));
|
|
103
|
+
const evaluationIndex = usefulnessIndex + 2;
|
|
104
|
+
return usefulnessIndex > 0 &&
|
|
105
|
+
["are", "is", "was", "were"].includes(words[usefulnessIndex + 1] ?? "") &&
|
|
106
|
+
RELATIVE_EVALUATIONS.has(words[evaluationIndex] ?? "") &&
|
|
107
|
+
words.length === evaluationIndex + 1
|
|
108
|
+
? "relative-makes-useful-evaluation"
|
|
109
|
+
: undefined;
|
|
110
|
+
}
|
|
111
|
+
export function matchRelativeDiscourseFrame(text, words) {
|
|
112
|
+
const headIndex = relativeFrameHeadIndex(words);
|
|
113
|
+
if (headIndex < 0) {
|
|
114
|
+
return undefined;
|
|
115
|
+
}
|
|
116
|
+
return (matchRelativeHelperFrame(text, words, headIndex) ??
|
|
117
|
+
matchRelativeUsefulnessFrame(words, headIndex));
|
|
118
|
+
}
|
|
119
|
+
//# sourceMappingURL=relative-discourse-frame.js.map
|