securemark 0.299.4 → 0.300.0

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 (231) hide show
  1. package/CHANGELOG.md +4 -0
  2. package/design.md +0 -6
  3. package/dist/index.js +2749 -1979
  4. package/index.d.ts +2 -1
  5. package/markdown.d.ts +209 -183
  6. package/package.json +1 -1
  7. package/src/api/bind.test.ts +0 -22
  8. package/src/api/bind.ts +15 -10
  9. package/src/api/header.ts +8 -5
  10. package/src/api/parse.test.ts +118 -122
  11. package/src/api/parse.ts +13 -31
  12. package/src/api/run.ts +6 -0
  13. package/src/api.ts +1 -0
  14. package/src/combinator/control/inits.ts +26 -0
  15. package/src/combinator/control/sequence.test.ts +38 -0
  16. package/src/combinator/control/sequence.ts +17 -0
  17. package/src/combinator/control/some.test.ts +41 -0
  18. package/src/combinator/{data/parser → control}/some.ts +39 -26
  19. package/src/combinator/control/state.ts +42 -0
  20. package/src/combinator/control/subsequence.test.ts +47 -0
  21. package/src/combinator/control/subsequence.ts +16 -0
  22. package/src/combinator/control/tails.ts +8 -0
  23. package/src/combinator/control/union.test.ts +37 -0
  24. package/src/combinator/control/union.ts +18 -0
  25. package/src/combinator/{data/delimiter.ts → delimiter.ts} +40 -60
  26. package/src/combinator/effect/backtrack.ts +64 -0
  27. package/src/combinator/effect/clock.ts +10 -0
  28. package/src/combinator/effect/precedence.ts +50 -0
  29. package/src/combinator/effect/recursion.ts +30 -0
  30. package/src/combinator/effect/scope.ts +100 -0
  31. package/src/combinator/effect/state.ts +72 -0
  32. package/src/combinator/{data/list → parser}/list.ts +35 -10
  33. package/src/combinator/parser.ts +293 -0
  34. package/src/combinator/process/bind.ts +34 -0
  35. package/src/combinator/process/block.test.ts +20 -0
  36. package/src/combinator/process/block.ts +33 -0
  37. package/src/combinator/process/clear.ts +16 -0
  38. package/src/combinator/process/contract.ts +35 -0
  39. package/src/combinator/process/duplicate.ts +7 -0
  40. package/src/combinator/process/error.ts +13 -0
  41. package/src/combinator/{control/manipulation → process}/fallback.ts +3 -3
  42. package/src/combinator/process/fence.ts +59 -0
  43. package/src/combinator/process/fmap.ts +10 -0
  44. package/src/combinator/process/indent.test.ts +31 -0
  45. package/src/combinator/process/indent.ts +51 -0
  46. package/src/combinator/process/lazy.ts +8 -0
  47. package/src/combinator/process/line.test.ts +21 -0
  48. package/src/combinator/process/line.ts +55 -0
  49. package/src/combinator/process/match.ts +37 -0
  50. package/src/combinator/process/reverse.ts +7 -0
  51. package/src/combinator/process/scope.ts +102 -0
  52. package/src/combinator/process/surround.ts +271 -0
  53. package/src/combinator.ts +28 -24
  54. package/src/debug.test.ts +11 -8
  55. package/src/parser/autolink.test.ts +17 -18
  56. package/src/parser/block/blockquote.test.ts +78 -79
  57. package/src/parser/block/blockquote.ts +32 -25
  58. package/src/parser/block/codeblock.test.ts +56 -57
  59. package/src/parser/block/codeblock.ts +44 -26
  60. package/src/parser/block/dlist.test.ts +56 -57
  61. package/src/parser/block/dlist.ts +5 -5
  62. package/src/parser/block/extension/aside.test.ts +8 -9
  63. package/src/parser/block/extension/aside.ts +76 -47
  64. package/src/parser/block/extension/example.test.ts +18 -19
  65. package/src/parser/block/extension/example.ts +88 -48
  66. package/src/parser/block/extension/fig.test.ts +37 -36
  67. package/src/parser/block/extension/fig.ts +20 -25
  68. package/src/parser/block/extension/figbase.test.ts +18 -19
  69. package/src/parser/block/extension/figbase.ts +3 -3
  70. package/src/parser/block/extension/figure.test.ts +62 -63
  71. package/src/parser/block/extension/figure.ts +23 -21
  72. package/src/parser/block/extension/message.test.ts +13 -14
  73. package/src/parser/block/extension/message.ts +52 -39
  74. package/src/parser/block/extension/placeholder.test.ts +13 -13
  75. package/src/parser/block/extension/placeholder.ts +23 -21
  76. package/src/parser/block/extension/table.test.ts +70 -71
  77. package/src/parser/block/extension/table.ts +43 -31
  78. package/src/parser/block/extension.test.ts +24 -24
  79. package/src/parser/block/extension.ts +3 -3
  80. package/src/parser/block/heading.test.ts +58 -59
  81. package/src/parser/block/heading.ts +19 -18
  82. package/src/parser/block/ilist.test.ts +8 -8
  83. package/src/parser/block/ilist.ts +9 -7
  84. package/src/parser/block/mathblock.test.ts +31 -32
  85. package/src/parser/block/mathblock.ts +24 -23
  86. package/src/parser/block/mediablock.ts +7 -7
  87. package/src/parser/block/olist.test.ts +102 -103
  88. package/src/parser/block/olist.ts +11 -12
  89. package/src/parser/block/pagebreak.test.ts +15 -16
  90. package/src/parser/block/pagebreak.ts +5 -5
  91. package/src/parser/block/paragraph.test.ts +57 -58
  92. package/src/parser/block/paragraph.ts +1 -1
  93. package/src/parser/block/reply/cite.test.ts +39 -40
  94. package/src/parser/block/reply/cite.ts +5 -5
  95. package/src/parser/block/reply/quote.test.ts +50 -51
  96. package/src/parser/block/reply/quote.ts +8 -7
  97. package/src/parser/block/reply.test.ts +19 -20
  98. package/src/parser/block/reply.ts +2 -2
  99. package/src/parser/block/sidefence.test.ts +41 -48
  100. package/src/parser/block/sidefence.ts +17 -11
  101. package/src/parser/block/table.test.ts +48 -49
  102. package/src/parser/block/table.ts +10 -9
  103. package/src/parser/block/ulist.test.ts +52 -53
  104. package/src/parser/block/ulist.ts +9 -8
  105. package/src/parser/block.ts +63 -51
  106. package/src/parser/context.ts +35 -32
  107. package/src/parser/document.ts +48 -0
  108. package/src/parser/header.test.ts +19 -20
  109. package/src/parser/header.ts +31 -25
  110. package/src/parser/inline/annotation.test.ts +49 -50
  111. package/src/parser/inline/annotation.ts +14 -16
  112. package/src/parser/inline/autolink/account.test.ts +32 -33
  113. package/src/parser/inline/autolink/account.ts +18 -19
  114. package/src/parser/inline/autolink/anchor.test.ts +21 -22
  115. package/src/parser/inline/autolink/anchor.ts +7 -8
  116. package/src/parser/inline/autolink/channel.test.ts +14 -15
  117. package/src/parser/inline/autolink/email.test.ts +36 -37
  118. package/src/parser/inline/autolink/email.ts +6 -6
  119. package/src/parser/inline/autolink/hashnum.test.ts +32 -33
  120. package/src/parser/inline/autolink/hashnum.ts +7 -8
  121. package/src/parser/inline/autolink/hashtag.test.ts +59 -60
  122. package/src/parser/inline/autolink/hashtag.ts +8 -9
  123. package/src/parser/inline/autolink/url.test.ts +75 -76
  124. package/src/parser/inline/autolink/url.ts +13 -14
  125. package/src/parser/inline/autolink.ts +24 -11
  126. package/src/parser/inline/bracket.test.ts +73 -74
  127. package/src/parser/inline/bracket.ts +88 -63
  128. package/src/parser/inline/code.test.ts +30 -31
  129. package/src/parser/inline/code.ts +6 -6
  130. package/src/parser/inline/deletion.test.ts +27 -28
  131. package/src/parser/inline/deletion.ts +5 -5
  132. package/src/parser/inline/emphasis.test.ts +39 -40
  133. package/src/parser/inline/emphasis.ts +5 -5
  134. package/src/parser/inline/emstrong.test.ts +101 -102
  135. package/src/parser/inline/emstrong.ts +103 -85
  136. package/src/parser/inline/extension/index.test.ts +91 -92
  137. package/src/parser/inline/extension/index.ts +17 -13
  138. package/src/parser/inline/extension/indexee.ts +4 -4
  139. package/src/parser/inline/extension/indexer.test.ts +23 -24
  140. package/src/parser/inline/extension/indexer.ts +6 -5
  141. package/src/parser/inline/extension/label.test.ts +32 -33
  142. package/src/parser/inline/extension/label.ts +14 -5
  143. package/src/parser/inline/extension/placeholder.test.ts +42 -43
  144. package/src/parser/inline/extension/placeholder.ts +8 -9
  145. package/src/parser/inline/html.test.ts +109 -109
  146. package/src/parser/inline/html.ts +27 -27
  147. package/src/parser/inline/htmlentity.test.ts +37 -38
  148. package/src/parser/inline/htmlentity.ts +6 -7
  149. package/src/parser/inline/insertion.test.ts +27 -28
  150. package/src/parser/inline/insertion.ts +5 -5
  151. package/src/parser/inline/italic.test.ts +55 -56
  152. package/src/parser/inline/italic.ts +5 -5
  153. package/src/parser/inline/link.test.ts +186 -187
  154. package/src/parser/inline/link.ts +29 -30
  155. package/src/parser/inline/mark.test.ts +31 -32
  156. package/src/parser/inline/mark.ts +6 -6
  157. package/src/parser/inline/math.test.ts +140 -141
  158. package/src/parser/inline/math.ts +6 -7
  159. package/src/parser/inline/media.test.ts +92 -93
  160. package/src/parser/inline/media.ts +31 -37
  161. package/src/parser/inline/reference.test.ts +111 -112
  162. package/src/parser/inline/reference.ts +61 -32
  163. package/src/parser/inline/remark.test.ts +49 -50
  164. package/src/parser/inline/remark.ts +13 -13
  165. package/src/parser/inline/ruby.test.ts +49 -50
  166. package/src/parser/inline/ruby.ts +60 -49
  167. package/src/parser/inline/shortmedia.test.ts +9 -10
  168. package/src/parser/inline/shortmedia.ts +11 -9
  169. package/src/parser/inline/strong.test.ts +36 -37
  170. package/src/parser/inline/strong.ts +5 -5
  171. package/src/parser/inline/template.test.ts +22 -23
  172. package/src/parser/inline/template.ts +13 -16
  173. package/src/parser/inline.test.ts +225 -226
  174. package/src/parser/inline.ts +68 -34
  175. package/src/parser/parser.ts +51 -0
  176. package/src/parser/repeat.ts +118 -91
  177. package/src/parser/segment.test.ts +0 -11
  178. package/src/parser/segment.ts +25 -28
  179. package/src/parser/source/escapable.test.ts +23 -24
  180. package/src/parser/source/escapable.ts +20 -20
  181. package/src/parser/source/line.test.ts +17 -18
  182. package/src/parser/source/line.ts +19 -24
  183. package/src/parser/source/str.ts +17 -10
  184. package/src/parser/source/text.test.ts +88 -89
  185. package/src/parser/source/text.ts +19 -20
  186. package/src/parser/source/unescapable.test.ts +23 -24
  187. package/src/parser/source/unescapable.ts +16 -16
  188. package/src/parser/util.ts +1 -1
  189. package/src/parser/visibility.ts +35 -14
  190. package/src/processor/figure.test.ts +20 -20
  191. package/src/processor/figure.ts +18 -10
  192. package/src/processor/note.test.ts +13 -13
  193. package/src/processor/note.ts +4 -2
  194. package/src/renderer/render/media/pdf.ts +2 -2
  195. package/src/renderer/render/media/twitter.ts +2 -2
  196. package/src/renderer/render/media.test.ts +12 -12
  197. package/src/renderer/render.test.ts +11 -11
  198. package/src/util/info.test.ts +2 -2
  199. package/src/util/quote.test.ts +3 -3
  200. package/src/util/quote.ts +6 -5
  201. package/src/util/toc.test.ts +12 -12
  202. package/src/combinator/control/constraint/block.test.ts +0 -20
  203. package/src/combinator/control/constraint/block.ts +0 -28
  204. package/src/combinator/control/constraint/contract.ts +0 -27
  205. package/src/combinator/control/constraint/line.test.ts +0 -21
  206. package/src/combinator/control/constraint/line.ts +0 -42
  207. package/src/combinator/control/manipulation/clear.ts +0 -5
  208. package/src/combinator/control/manipulation/convert.ts +0 -22
  209. package/src/combinator/control/manipulation/duplicate.ts +0 -7
  210. package/src/combinator/control/manipulation/fence.ts +0 -54
  211. package/src/combinator/control/manipulation/indent.test.ts +0 -31
  212. package/src/combinator/control/manipulation/indent.ts +0 -39
  213. package/src/combinator/control/manipulation/lazy.ts +0 -8
  214. package/src/combinator/control/manipulation/match.ts +0 -27
  215. package/src/combinator/control/manipulation/recovery.ts +0 -18
  216. package/src/combinator/control/manipulation/reverse.ts +0 -8
  217. package/src/combinator/control/manipulation/scope.ts +0 -61
  218. package/src/combinator/control/manipulation/surround.ts +0 -223
  219. package/src/combinator/control/monad/bind.ts +0 -26
  220. package/src/combinator/control/monad/fmap.ts +0 -10
  221. package/src/combinator/data/parser/context.ts +0 -96
  222. package/src/combinator/data/parser/inits.ts +0 -20
  223. package/src/combinator/data/parser/sequence.test.ts +0 -33
  224. package/src/combinator/data/parser/sequence.ts +0 -20
  225. package/src/combinator/data/parser/some.test.ts +0 -37
  226. package/src/combinator/data/parser/subsequence.test.ts +0 -41
  227. package/src/combinator/data/parser/subsequence.ts +0 -13
  228. package/src/combinator/data/parser/tails.ts +0 -8
  229. package/src/combinator/data/parser/union.test.ts +0 -33
  230. package/src/combinator/data/parser/union.ts +0 -18
  231. package/src/combinator/data/parser.ts +0 -144
@@ -1,223 +0,0 @@
1
- import { Parser, Result, List, Node, Context, failsafe } from '../../data/parser';
2
- import { tester } from '../../data/delimiter';
3
-
4
- export function surround<P extends Parser, S = string>(
5
- opener: string | RegExp | Parser<S, Parser.Context<P>>,
6
- parser: Parser.IntermediateParser<P>,
7
- closer: string | RegExp | Parser<S, Parser.Context<P>>,
8
- optional?: false,
9
- backtracks?: readonly number[],
10
- f?: (rss: [List<Node<S>>, List<Node<Parser.SubNode<P>>>, List<Node<S>>], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
11
- g?: (rss: [List<Node<S>>, List<Node<Parser.SubNode<P>>> | undefined], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
12
- ): P;
13
- export function surround<P extends Parser, S = string>(
14
- opener: string | RegExp | Parser<S, Parser.Context<P>>,
15
- parser: Parser.IntermediateParser<P>,
16
- closer: string | RegExp | Parser<S, Parser.Context<P>>,
17
- optional?: boolean,
18
- backtracks?: readonly number[],
19
- f?: (rss: [List<Node<S>>, List<Node<Parser.SubNode<P>>> | undefined, List<Node<S>>], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
20
- g?: (rss: [List<Node<S>>, List<Node<Parser.SubNode<P>>> | undefined], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
21
- ): P;
22
- export function surround<P extends Parser, S = string>(
23
- opener: string | RegExp | Parser<S, Parser.Context<P>>,
24
- parser: P,
25
- closer: string | RegExp | Parser<S, Parser.Context<P>>,
26
- optional?: false,
27
- backtracks?: readonly number[],
28
- f?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>>, List<Node<S>>], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
29
- g?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>> | undefined], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
30
- ): P;
31
- export function surround<P extends Parser, S = string>(
32
- opener: string | RegExp | Parser<S, Parser.Context<P>>,
33
- parser: P,
34
- closer: string | RegExp | Parser<S, Parser.Context<P>>,
35
- optional?: boolean,
36
- backtracks?: readonly number[],
37
- f?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>> | undefined, List<Node<S>>], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
38
- g?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>> | undefined], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
39
- ): P;
40
- export function surround<P extends Parser<string>, S = string>(
41
- opener: string | RegExp | Parser<S, Parser.Context<P>>,
42
- parser: string | RegExp | P,
43
- closer: string | RegExp | Parser<S, Parser.Context<P>>,
44
- optional?: false,
45
- backtracks?: readonly number[],
46
- f?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>>, List<Node<S>>], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
47
- g?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>> | undefined], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
48
- ): P;
49
- export function surround<P extends Parser<string>, S = string>(
50
- opener: string | RegExp | Parser<S, Parser.Context<P>>,
51
- parser: string | RegExp | P,
52
- closer: string | RegExp | Parser<S, Parser.Context<P>>,
53
- optional?: boolean,
54
- backtracks?: readonly number[],
55
- f?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>> | undefined, List<Node<S>>], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
56
- g?: (rss: [List<Node<S>>, List<Node<Parser.Node<P>>> | undefined], context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>,
57
- ): P;
58
- export function surround<N>(
59
- opener: string | RegExp | Parser<N>,
60
- parser: string | RegExp | Parser<N>,
61
- closer: string | RegExp | Parser<N>,
62
- optional: boolean = false,
63
- backtracks: readonly number[] = [],
64
- f?: (rss: [List<Node<N>>, List<Node<N>>, List<Node<N>>], context: Context) => Result<N>,
65
- g?: (rss: [List<Node<N>>, List<Node<N>> | undefined], context: Context) => Result<N>,
66
- ): Parser<N> {
67
- switch (typeof opener) {
68
- case 'string':
69
- case 'object':
70
- opener = tester(opener, true);
71
- }
72
- assert(opener);
73
- switch (typeof parser) {
74
- case 'string':
75
- case 'object':
76
- parser = tester(parser, true);
77
- }
78
- assert(parser);
79
- switch (typeof closer) {
80
- case 'string':
81
- case 'object':
82
- closer = tester(closer, true);
83
- }
84
- assert(closer);
85
- const [blen, rbs, wbs] = reduce(backtracks);
86
- return failsafe(input => {
87
- const context = input;
88
- const { source, position } = context;
89
- if (position === source.length) return;
90
- const { linebreak } = context;
91
- context.linebreak = 0;
92
- const nodesO = opener(input);
93
- if (nodesO === undefined) {
94
- return void revert(context, linebreak);
95
- }
96
- if (rbs && isBacktrack(context, rbs, position, blen)) {
97
- return void revert(context, linebreak);
98
- }
99
- const nodesM = context.position < source.length ? parser(input) : undefined;
100
- context.range = context.position - position;
101
- if (nodesM === undefined && !optional) {
102
- wbs && setBacktrack(context, wbs, position);
103
- const result = g?.([nodesO, nodesM], context);
104
- return result || void revert(context, linebreak);
105
- }
106
- const nodesC = optional || nodesM ? closer(input) : undefined;
107
- context.range = context.position - position;
108
- if (nodesC === undefined) {
109
- wbs && setBacktrack(context, wbs, position);
110
- const result = g?.([nodesO, nodesM], context);
111
- return result || void revert(context, linebreak);
112
- }
113
- if (context.position === position) {
114
- return void revert(context, linebreak);
115
- }
116
- context.range = context.position - position;
117
- const result = f
118
- ? f([nodesO, nodesM!, nodesC], context)
119
- : nodesM
120
- ? nodesO.import(nodesM).import(nodesC)
121
- : nodesO.import(nodesC);
122
- if (result) {
123
- context.linebreak ||= linebreak;
124
- }
125
- return result || void revert(context, linebreak);
126
- });
127
- }
128
- export function open<P extends Parser>(
129
- opener: string | RegExp | Parser<Parser.Node<P>, Parser.Context<P>>,
130
- parser: P,
131
- optional?: boolean,
132
- backtracks?: readonly number[],
133
- ): P;
134
- export function open<P extends Parser<string>>(
135
- opener: string | RegExp | Parser<Parser.Node<P>, Parser.Context<P>>,
136
- parser: string | RegExp | P,
137
- optional?: boolean,
138
- backtracks?: readonly number[],
139
- ): P;
140
- export function open<N>(
141
- opener: string | RegExp | Parser<N, Context>,
142
- parser: string | RegExp | Parser<N>,
143
- optional?: boolean,
144
- backtracks: readonly number[] = [],
145
- ): Parser<N> {
146
- return surround(opener, parser as Parser<N>, '', optional, backtracks);
147
- }
148
- export function close<P extends Parser>(
149
- parser: P,
150
- closer: string | RegExp | Parser<Parser.Node<P>, Parser.Context<P>>,
151
- optional?: boolean,
152
- backtracks?: readonly number[],
153
- ): P;
154
- export function close<P extends Parser<string>>(
155
- parser: string | RegExp | P,
156
- closer: string | RegExp | Parser<Parser.Node<P>, Parser.Context<P>>,
157
- optional?: boolean,
158
- backtracks?: readonly number[],
159
- ): P;
160
- export function close<N>(
161
- parser: string | RegExp | Parser<N>,
162
- closer: string | RegExp | Parser<N, Context>,
163
- optional?: boolean,
164
- backtracks: readonly number[] = [],
165
- ): Parser<N> {
166
- return surround('', parser as Parser<N>, closer, optional, backtracks);
167
- }
168
-
169
- const commandsize = 2;
170
- export function isBacktrack(
171
- context: Context,
172
- backtrack: number,
173
- position: number = context.position,
174
- length: number = 1,
175
- ): boolean {
176
- assert(1 & backtrack);
177
- assert(backtrack >>> commandsize);
178
- assert(0 < length && length < 3);
179
- const { backtracks, offset } = context;
180
- for (let i = 0; i < length; ++i) {
181
- if (backtracks[position + i + offset] & backtrack >>> commandsize) return true;
182
- }
183
- return false;
184
- }
185
- export function setBacktrack(
186
- context: Context,
187
- backtrack: number,
188
- position: number,
189
- length: number = 1,
190
- ): void {
191
- // バックトラックの可能性がなく記録不要の場合もあるが判別が面倒なので省略
192
- assert(2 & backtrack);
193
- assert(backtrack >>> commandsize);
194
- assert(0 < length && length < 3);
195
- const { backtracks, offset } = context;
196
- for (let i = 0; i < length; ++i) {
197
- backtracks[position + i + offset] |= backtrack >>> commandsize;
198
- }
199
- }
200
- function reduce(backtracks: readonly number[]): readonly [number, number, number] {
201
- let len = 1;
202
- let rbs = 0;
203
- let wbs = 0;
204
- for (const backtrack of backtracks) {
205
- if (backtrack >>> commandsize === 0) {
206
- len = backtrack;
207
- assert(len > 0);
208
- continue;
209
- }
210
- assert(backtrack >>> commandsize);
211
- if (1 & backtrack) {
212
- rbs |= backtrack;
213
- }
214
- if (2 & backtrack) {
215
- wbs |= backtrack;
216
- }
217
- }
218
- return [len, rbs, wbs];
219
- }
220
-
221
- function revert(context: Context, linebreak: number): void {
222
- context.linebreak = linebreak;
223
- }
@@ -1,26 +0,0 @@
1
- import { Parser, Result, List, Node, Context } from '../../data/parser';
2
-
3
- export function bind<P extends Parser>(parser: Parser.IntermediateParser<P>, f: (nodes: List<Node<Parser.SubNode<P>>>, context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>): P;
4
- export function bind<P extends Parser>(parser: P, f: (nodes: List<Node<Parser.Node<P>>>, context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>): P;
5
- export function bind<N, P extends Parser>(parser: Parser<N, Parser.Context<P>, Parser.SubParsers<P>>, f: (nodes: List<Node<N>>, context: Parser.Context<P>) => Result<Parser.Node<P>, Parser.Context<P>, Parser.SubParsers<P>>): P;
6
- export function bind<U, P extends Parser>(parser: P, f: (nodes: List<Node<Parser.Node<P>>>, context: Parser.Context<P>) => Result<U, Parser.Context<P>, Parser.SubParsers<P>>): Parser<U, Parser.Context<P>, Parser.SubParsers<P>>;
7
- export function bind<N, U>(parser: Parser<N>, f: (nodes: List<Node<N>>, context: Context) => Result<U>): Parser<U> {
8
- assert(parser);
9
- return input => {
10
- const context = input;
11
- const { source, position } = context;
12
- if (position === source.length) return;
13
- const res1 = parser(input);
14
- if (res1 === undefined) {
15
- context.position = position;
16
- return;
17
- }
18
- context.range = context.position - position;
19
- const res2 = f(res1, context);
20
- if (res2 === undefined) {
21
- context.position = position;
22
- return;
23
- }
24
- return res2;
25
- };
26
- }
@@ -1,10 +0,0 @@
1
- import { Parser, List, Node, Context } from '../../data/parser';
2
- import { bind } from './bind';
3
-
4
- export function fmap<P extends Parser>(parser: Parser.IntermediateParser<P>, f: (nodes: List<Node<Parser.SubNode<P>>>, context: Parser.Context<P>) => List<Node<Parser.Node<P>>>): P;
5
- export function fmap<P extends Parser>(parser: P, f: (nodes: List<Node<Parser.Node<P>>>, context: Parser.Context<P>) => List<Node<Parser.Node<P>>>): P;
6
- export function fmap<N, P extends Parser>(parser: Parser<N, Parser.Context<P>, Parser.SubParsers<P>>, f: (nodes: List<Node<N>>, context: Parser.Context<P>) => List<Node<Parser.Node<P>>>): P;
7
- export function fmap<U, P extends Parser>(parser: P, f: (nodes: List<Node<Parser.Node<P>>>, context: Parser.Context<P>) => List<Node<U>>): Parser<U, Parser.Context<P>, Parser.SubParsers<P>>;
8
- export function fmap<N, U>(parser: Parser<N>, f: (nodes: List<Node<N>>, context: Context) => List<Node<U>>): Parser<U> {
9
- return bind(parser, (nodes, context) => f(nodes, context));
10
- }
@@ -1,96 +0,0 @@
1
- import { Parser, Context } from '../../data/parser';
2
- import { min } from 'spica/alias';
3
-
4
- export function creation<P extends Parser>(cost: number, parser: P): P;
5
- export function creation(cost: number, parser: Parser): Parser {
6
- assert(cost >= 0);
7
- return input => {
8
- const context = input;
9
- const result = parser(input);
10
- if (result === undefined) return;
11
- spend(context, cost);
12
- return result;
13
- };
14
- }
15
- export function spend(context: Context, cost: number): void {
16
- const resources = context.resources ?? { clock: cost || 1, recursions: [1] };
17
- if (resources.clock < cost) throw new Error('Too many creations');
18
- resources.clock -= cost;
19
- }
20
-
21
- export function recursion<P extends Parser>(index: number, parser: P): P;
22
- export function recursion(index: number, parser: Parser): Parser {
23
- assert(index >= 0);
24
- return input => {
25
- const context = input;
26
- const resources = context.resources ?? { clock: 1, recursions: [1] };
27
- const { recursions } = resources;
28
- recur(recursions, index, 1);
29
- const result = parser(input);
30
- recur(recursions, index, -1);
31
- return result;
32
- };
33
- }
34
- export function recur(recursions: number[], index: number, size: number, force: boolean = false): void {
35
- index = min(index, recursions.length && recursions.length - 1);
36
- if (recursions[index] < size - +force) throw new Error('Too much recursion');
37
- recursions[index] -= size;
38
- }
39
-
40
- export function precedence<P extends Parser>(precedence: number, parser: P): P;
41
- export function precedence<N>(precedence: number, parser: Parser<N>): Parser<N> {
42
- assert(precedence >= 0);
43
- return input => {
44
- const context = input;
45
- const { delimiters, precedence: p } = context;
46
- const shift = delimiters && precedence > p;
47
- context.precedence = precedence;
48
- // デリミタはシフト後に設定しなければならない
49
- shift && delimiters.shift(precedence);
50
- const result = parser(input);
51
- shift && delimiters.unshift();
52
- context.precedence = p;
53
- return result;
54
- };
55
- }
56
-
57
- export function state<P extends Parser>(state: number, parser: P): P;
58
- export function state<P extends Parser>(state: number, positive: boolean, parser: P): P;
59
- export function state<N>(state: number, positive: boolean | Parser<N>, parser?: Parser<N>): Parser<N> {
60
- if (typeof positive === 'function') {
61
- parser = positive;
62
- positive = true;
63
- }
64
- assert(state);
65
- assert(parser = parser!);
66
- return input => {
67
- const context = input;
68
- const s = context.state ?? 0;
69
- context.state = positive
70
- ? s | state
71
- : s & ~state;
72
- const result = parser(input);
73
- context.state = s;
74
- return result;
75
- };
76
- }
77
-
78
- export function constraint<P extends Parser>(state: number, parser: P): P;
79
- //export function constraint<P extends Parser>(state: number, positive: boolean, parser: P): P;
80
- export function constraint<N>(state: number, positive: boolean | Parser<N>, parser?: Parser<N>): Parser<N> {
81
- if (typeof positive === 'function') {
82
- parser = positive;
83
- positive = false;
84
- }
85
- assert(state);
86
- assert(parser = parser!);
87
- return input => {
88
- const context = input;
89
- const s = positive
90
- ? state & context.state
91
- : state & ~context.state;
92
- return s === state
93
- ? parser(input)
94
- : undefined;
95
- };
96
- }
@@ -1,20 +0,0 @@
1
- import { Parser, List, Node, Context } from '../parser';
2
-
3
- export function inits<P extends Parser>(parsers: Parser.SubParsers<P>, delimitation?: boolean): Parser.SubNode<P> extends Parser.Node<P> ? P : Parser<Parser.SubNode<P>, Parser.Context<P>, Parser.SubParsers<P>>;
4
- export function inits<N, D extends Parser<N>[]>(parsers: D, delimitation = false): Parser<N, Context, D> {
5
- assert(parsers.every(f => f));
6
- if (parsers.length === 1) return parsers[0];
7
- return input => {
8
- const context = input;
9
- const { source } = context;
10
- let nodes: List<Node<N>> | undefined;
11
- for (let len = parsers.length, i = 0; i < len; ++i) {
12
- if (context.position === source.length) break;
13
- if (delimitation && context.delimiters.test(input)) break;
14
- const result = parsers[i](input);
15
- if (result === undefined) break;
16
- nodes = nodes?.import(result) ?? result;
17
- }
18
- return nodes;
19
- };
20
- }
@@ -1,33 +0,0 @@
1
- import { Parser, List, Node, Context, input } from '../parser';
2
- import { sequence } from './sequence';
3
- import { inspect } from '../../../debug.test';
4
-
5
- describe('Unit: combinator/data/parser/sequence', () => {
6
- describe('sequence', () => {
7
- const a: Parser<string> = context => {
8
- return context.source[context.position] === 'a'
9
- ? void ++context.position || new List([new Node('A')])
10
- : undefined;
11
- };
12
- const b: Parser<string> = context => {
13
- return context.source[context.position] === 'b'
14
- ? void ++context.position || new List([new Node('B')])
15
- : undefined;
16
- };
17
- const ab = sequence<Parser<string, Context, [typeof a, typeof b]>>([a, b]);
18
-
19
- it('basic', () => {
20
- const parser = ab;
21
- assert.deepStrictEqual(inspect(parser, input('', new Context())), undefined);
22
- assert.deepStrictEqual(inspect(parser, input('a', new Context())), undefined);
23
- assert.deepStrictEqual(inspect(parser, input('b', new Context())), undefined);
24
- assert.deepStrictEqual(inspect(parser, input('ab', new Context())), [['A', 'B'], '']);
25
- assert.deepStrictEqual(inspect(parser, input('ba', new Context())), undefined);
26
- assert.deepStrictEqual(inspect(parser, input('aab', new Context())), undefined);
27
- assert.deepStrictEqual(inspect(parser, input('abb', new Context())), [['A', 'B'], 'b']);
28
- assert.deepStrictEqual(inspect(parser, input('bba', new Context())), undefined);
29
- });
30
-
31
- });
32
-
33
- });
@@ -1,20 +0,0 @@
1
- import { Parser, List, Node, Context, failsafe } from '../parser';
2
-
3
- export function sequence<P extends Parser>(parsers: Parser.SubParsers<P>, delimitation?: boolean): Parser.SubNode<P> extends Parser.Node<P> ? P : Parser<Parser.SubNode<P>, Parser.Context<P>, Parser.SubParsers<P>>;
4
- export function sequence<N, D extends Parser<N>[]>(parsers: D, delimitation = false): Parser<N, Context, D> {
5
- assert(parsers.every(f => f));
6
- if (parsers.length === 1) return parsers[0];
7
- return failsafe(input => {
8
- const context = input;
9
- const { source } = context;
10
- let nodes: List<Node<N>> | undefined;
11
- for (let len = parsers.length, i = 0; i < len; ++i) {
12
- if (context.position === source.length) return;
13
- if (delimitation && context.delimiters.test(input)) return;
14
- const result = parsers[i](input);
15
- if (result === undefined) return;
16
- nodes = nodes?.import(result) ?? result;
17
- }
18
- return nodes;
19
- });
20
- }
@@ -1,37 +0,0 @@
1
- import { Parser, List, Node, Context, input } from '../parser';
2
- import { union } from './union';
3
- import { some } from './some';
4
- import { inspect } from '../../../debug.test';
5
-
6
- describe('Unit: combinator/data/parser/some', () => {
7
- describe('some', () => {
8
- const a: Parser<string> = context => {
9
- return context.source[context.position] === 'a'
10
- ? void ++context.position || new List([new Node('A')])
11
- : undefined;
12
- };
13
- const b: Parser<string> = context => {
14
- return context.source[context.position] === 'b'
15
- ? void ++context.position || new List([new Node('B')])
16
- : undefined;
17
- };
18
- const ab = union<Parser<string, Context, [typeof a, typeof b]>>([a, b]);
19
-
20
- it('basic', () => {
21
- const parser = some(ab, /aaa/y);
22
- assert.deepStrictEqual(inspect(parser, input('', new Context())), undefined);
23
- assert.deepStrictEqual(inspect(parser, input('a', new Context())), [['A'], '']);
24
- assert.deepStrictEqual(inspect(parser, input('b', new Context())), [['B'], '']);
25
- assert.deepStrictEqual(inspect(parser, input('ab', new Context())), [['A', 'B'], '']);
26
- assert.deepStrictEqual(inspect(parser, input('ba', new Context())), [['B', 'A'], '']);
27
- assert.deepStrictEqual(inspect(parser, input('aab', new Context())), [['A', 'A', 'B'], '']);
28
- assert.deepStrictEqual(inspect(parser, input('bba', new Context())), [['B', 'B', 'A'], '']);
29
- assert.deepStrictEqual(inspect(parser, input('aaa', new Context())), undefined);
30
- assert.deepStrictEqual(inspect(parser, input('bbb', new Context())), [['B', 'B', 'B'], '']);
31
- assert.deepStrictEqual(inspect(parser, input('aaab', new Context())), undefined);
32
- assert.deepStrictEqual(inspect(parser, input('baaa', new Context())), [['B'], 'aaa']);
33
- });
34
-
35
- });
36
-
37
- });
@@ -1,41 +0,0 @@
1
- import { Parser, List, Node, Context, input } from '../parser';
2
- import { subsequence } from './subsequence';
3
- import { inspect } from '../../../debug.test';
4
-
5
- describe('Unit: combinator/data/parser/subsequence', () => {
6
- describe('subsequence', () => {
7
- const a: Parser<string> = context => {
8
- return context.source[context.position] === 'a'
9
- ? void ++context.position || new List([new Node('A')])
10
- : undefined;
11
- };
12
- const b: Parser<string> = context => {
13
- return context.source[context.position] === 'b'
14
- ? void ++context.position || new List([new Node('B')])
15
- : undefined;
16
- };
17
- const c: Parser<string> = context => {
18
- return context.source[context.position] === 'c'
19
- ? void ++context.position || new List([new Node('C')])
20
- : undefined;
21
- };
22
- const abc = subsequence<Parser<string, Context, [typeof a, typeof b, typeof c]>>([a, b, c]);
23
-
24
- it('basic', () => {
25
- const parser = abc;
26
- assert.deepStrictEqual(inspect(parser, input('', new Context())), undefined);
27
- assert.deepStrictEqual(inspect(parser, input('a', new Context())), [['A'], '']);
28
- assert.deepStrictEqual(inspect(parser, input('b', new Context())), [['B'], '']);
29
- assert.deepStrictEqual(inspect(parser, input('c', new Context())), [['C'], '']);
30
- assert.deepStrictEqual(inspect(parser, input('ab', new Context())), [['A', 'B'], '']);
31
- assert.deepStrictEqual(inspect(parser, input('ba', new Context())), [['B'], 'a']);
32
- assert.deepStrictEqual(inspect(parser, input('aab', new Context())), [['A'], 'ab']);
33
- assert.deepStrictEqual(inspect(parser, input('abb', new Context())), [['A', 'B'], 'b']);
34
- assert.deepStrictEqual(inspect(parser, input('bba', new Context())), [['B'], 'ba']);
35
- assert.deepStrictEqual(inspect(parser, input('ac', new Context())), [['A', 'C'], '']);
36
- assert.deepStrictEqual(inspect(parser, input('bc', new Context())), [['B', 'C'], '']);
37
- });
38
-
39
- });
40
-
41
- });
@@ -1,13 +0,0 @@
1
- import { Parser, Context } from '../parser';
2
- import { union } from './union';
3
- import { inits } from './inits';
4
-
5
- export function subsequence<P extends Parser>(parsers: Parser.SubParsers<P>, delimitation?: boolean): Parser.SubNode<P> extends Parser.Node<P> ? P : Parser<Parser.SubNode<P>, Parser.Context<P>, Parser.SubParsers<P>>;
6
- export function subsequence<N, D extends Parser<N>[]>(parsers: D, delimitation = false): Parser<N, Context, D> {
7
- assert(parsers.every(f => f));
8
- return union(
9
- parsers.map((_, i) =>
10
- i + 1 < parsers.length
11
- ? inits([parsers[i], subsequence(parsers.slice(i + 1), delimitation)], delimitation)
12
- : parsers[i]) as D);
13
- }
@@ -1,8 +0,0 @@
1
- import { Parser, Context } from '../parser';
2
- import { union } from './union';
3
- import { sequence } from './sequence';
4
-
5
- export function tails<P extends Parser>(parsers: Parser.SubParsers<P>, delimitation?: boolean): Parser.SubNode<P> extends Parser.Node<P> ? P : Parser<Parser.SubNode<P>, Parser.Context<P>, Parser.SubParsers<P>>;
6
- export function tails<N, D extends Parser<N>[]>(parsers: D, delimitation?: boolean): Parser<N, Context, D> {
7
- return union(parsers.map((_, i) => sequence(parsers.slice(i), delimitation)) as D);
8
- }
@@ -1,33 +0,0 @@
1
- import { Parser, List, Node, Context, input } from '../parser';
2
- import { union } from './union';
3
- import { inspect } from '../../../debug.test';
4
-
5
- describe('Unit: combinator/data/parser/union', () => {
6
- describe('union', () => {
7
- const a: Parser<string> = context => {
8
- return context.source[context.position] === 'a'
9
- ? void ++context.position || new List([new Node('A')])
10
- : undefined;
11
- };
12
- const b: Parser<string> = context => {
13
- return context.source[context.position] === 'b'
14
- ? void ++context.position || new List([new Node('B')])
15
- : undefined;
16
- };
17
- const ab = union<Parser<string, Context, [typeof a, typeof b]>>([a, b]);
18
-
19
- it('basic', () => {
20
- const parser = ab;
21
- assert.deepStrictEqual(inspect(parser, input('', new Context())), undefined);
22
- assert.deepStrictEqual(inspect(parser, input('a', new Context())), [['A'], '']);
23
- assert.deepStrictEqual(inspect(parser, input('b', new Context())), [['B'], '']);
24
- assert.deepStrictEqual(inspect(parser, input('ab', new Context())), [['A'], 'b']);
25
- assert.deepStrictEqual(inspect(parser, input('ba', new Context())), [['B'], 'a']);
26
- assert.deepStrictEqual(inspect(parser, input('aab', new Context())), [['A'], 'ab']);
27
- assert.deepStrictEqual(inspect(parser, input('abb', new Context())), [['A'], 'bb']);
28
- assert.deepStrictEqual(inspect(parser, input('bba', new Context())), [['B'], 'ba']);
29
- });
30
-
31
- });
32
-
33
- });
@@ -1,18 +0,0 @@
1
- import { Parser, Context } from '../parser';
2
-
3
- export function union<P extends Parser>(parsers: Parser.SubParsers<P>): Parser.SubNode<P> extends Parser.Node<P> ? P : Parser<Parser.SubNode<P>, Parser.Context<P>, Parser.SubParsers<P>>;
4
- export function union<N, D extends Parser<N>[]>(parsers: D): Parser<N, Context, D> {
5
- assert(parsers.every(f => f));
6
- switch (parsers.length) {
7
- case 0:
8
- return () => undefined;
9
- case 1:
10
- return parsers[0];
11
- default:
12
- return eval([
13
- '(', parsers.map((_, i) => `parser${i},`).join(''), ') =>',
14
- 'input =>',
15
- parsers.map((_, i) => `|| parser${i}(input)`).join('').slice(2),
16
- ].join(''))(...parsers);
17
- }
18
- }