force-lang 0.0.12 → 0.1.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.
- package/.eslintrc.cjs +54 -0
- package/README.md +40 -15
- package/doc/force-lang.1 +55 -36
- package/doc/force.1 +55 -36
- package/examples/cli-args.j +3 -3
- package/examples/nodejs-js-interaction.j +2 -1
- package/examples/testjs.js +2 -2
- package/examples/web_scrap.j +17 -0
- package/force +88 -88
- package/force-lang-0.1.0.tgz +0 -0
- package/package.json +17 -14
- package/src/BKlib.j +51 -0
- package/src/env.js +221 -162
- package/src/error.js +71 -59
- package/src/eval.js +454 -299
- package/src/force-lang.js +38 -34
- package/src/lib.j +17 -0
- package/src/load-file.js +62 -35
- package/src/native_lib.js +1702 -1230
- package/src/obj_utils.js +20 -18
- package/src/read.js +431 -309
- package/src/stack.js +113 -68
- package/src/token-stream.js +34 -28
- package/tests/pippo.j +1 -1
- package/tests/test-js-require.js +13 -9
- package/tests/test.j +1 -1
- package/tests/unit_tests.j +1 -1
- package/.eslintrc.js +0 -60
package/.eslintrc.cjs
ADDED
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
module.exports = {
|
|
2
|
+
root: true,
|
|
3
|
+
env: {
|
|
4
|
+
es6: true,
|
|
5
|
+
node: true,
|
|
6
|
+
},
|
|
7
|
+
parserOptions: {
|
|
8
|
+
ecmaVersion: 'latest',
|
|
9
|
+
sourceType: 'module',
|
|
10
|
+
},
|
|
11
|
+
extends: ['airbnb-base', 'prettier'],
|
|
12
|
+
plugins: ['prettier'],
|
|
13
|
+
rules: {
|
|
14
|
+
'prettier/prettier': [
|
|
15
|
+
'error',
|
|
16
|
+
{
|
|
17
|
+
printWidth: 120,
|
|
18
|
+
tabWidth: 2, // reformat to 2 eventually
|
|
19
|
+
useTabs: false, // default
|
|
20
|
+
semi: true, // default
|
|
21
|
+
singleQuote: true,
|
|
22
|
+
trailingComma: 'all',
|
|
23
|
+
bracketSpacing: true, // default
|
|
24
|
+
jsxBracketSameLine: true,
|
|
25
|
+
arrowParens: 'avoid', // default
|
|
26
|
+
},
|
|
27
|
+
],
|
|
28
|
+
indent: ['warn', 2],
|
|
29
|
+
camelcase: [0, { properties: 'never' }],
|
|
30
|
+
eqeqeq: ['error', 'always'],
|
|
31
|
+
curly: ['error', 'all'],
|
|
32
|
+
'no-prototype-builtins': 0, // refactor and enable
|
|
33
|
+
'consistent-return': 0, // refactor and enable
|
|
34
|
+
'no-param-reassign': 0, // refactor and enable
|
|
35
|
+
'no-unsafe-finally': 0, // refactor and enable
|
|
36
|
+
'no-use-before-define': 0, // refactor and enable
|
|
37
|
+
'import/no-unresolved': 0, // some linter import errors
|
|
38
|
+
'no-underscore-dangle': ['off'],
|
|
39
|
+
'no-undef': 0,
|
|
40
|
+
'class-methods-use-this': 0, // refactor and enable
|
|
41
|
+
'max-len': ['warn', 1000], // usage of SVG
|
|
42
|
+
'no-restricted-syntax': [
|
|
43
|
+
'error',
|
|
44
|
+
{
|
|
45
|
+
selector: 'LabeledStatement',
|
|
46
|
+
message: 'Labels are a form of GOTO; using them makes code confusing and hard to maintain and understand.',
|
|
47
|
+
},
|
|
48
|
+
{
|
|
49
|
+
selector: 'WithStatement',
|
|
50
|
+
message: '`with` is disallowed in strict mode because it makes code impossible to predict and optimize.',
|
|
51
|
+
},
|
|
52
|
+
],
|
|
53
|
+
},
|
|
54
|
+
};
|
package/README.md
CHANGED
|
@@ -25,7 +25,7 @@ Options:
|
|
|
25
25
|
```text
|
|
26
26
|
$ cat example.j
|
|
27
27
|
|
|
28
|
-
#!/usr/
|
|
28
|
+
#!/usr/bin/env force
|
|
29
29
|
|
|
30
30
|
2 2 + .
|
|
31
31
|
```
|
|
@@ -37,32 +37,30 @@ echo "2 2 + ."|force
|
|
|
37
37
|
|
|
38
38
|
```bash
|
|
39
39
|
$ npm i force-lang
|
|
40
|
+
|
|
41
|
+
# or
|
|
42
|
+
|
|
43
|
+
npm install git+https://github.com/elboza/force-lang#master
|
|
40
44
|
```
|
|
41
45
|
|
|
42
46
|
```javascript
|
|
43
|
-
|
|
47
|
+
import force from 'force-lang';
|
|
44
48
|
|
|
45
49
|
var x = '2 2 + .';
|
|
46
50
|
|
|
47
51
|
(async function(){
|
|
48
52
|
await force.load_lib();
|
|
49
|
-
force.exec(x);
|
|
53
|
+
await force.exec(x);
|
|
50
54
|
})();
|
|
51
55
|
```
|
|
52
|
-
or using sync functions:
|
|
53
|
-
```javascript
|
|
54
|
-
const force = require ('force-lang');
|
|
55
|
-
|
|
56
|
-
var x = '2 2 + .';
|
|
57
|
-
|
|
58
|
-
force.load_lib_sync();
|
|
59
|
-
force.exec(x);
|
|
60
|
-
```
|
|
61
56
|
## repl multiline
|
|
62
57
|
in the force-lang repl `force -i` you can input multiline by appending `\` (backslash) at the end of the current line before enter
|
|
63
58
|
|
|
64
59
|
## language constructs
|
|
65
60
|
```text
|
|
61
|
+
: word_def ... [exit] ... ;
|
|
62
|
+
\ word definition
|
|
63
|
+
\ <exit> returns from function immediately.
|
|
66
64
|
( ... ) \ lambda func
|
|
67
65
|
example: ( 1 2 + )
|
|
68
66
|
|
|
@@ -114,6 +112,7 @@ m: for maps (hash)
|
|
|
114
112
|
f: for file
|
|
115
113
|
G: for Globals
|
|
116
114
|
os: for OS env
|
|
115
|
+
xml: for xml/dom parser
|
|
117
116
|
```
|
|
118
117
|
## functions signatures
|
|
119
118
|
in the comments of the stadard lib section is described the stack consumption and the type that the function requires.
|
|
@@ -138,6 +137,7 @@ v variable name
|
|
|
138
137
|
```text
|
|
139
138
|
bye \ ( -- )
|
|
140
139
|
noop \ ( -- )
|
|
140
|
+
nop \ ( -- )
|
|
141
141
|
.s \ ( -- )
|
|
142
142
|
.e \ ( -- )
|
|
143
143
|
words \ ( -- )
|
|
@@ -146,6 +146,8 @@ emit \ ( n -- )
|
|
|
146
146
|
.? \ ( x -- )
|
|
147
147
|
! \ ( x v -- )
|
|
148
148
|
@ \ ( v -- x )
|
|
149
|
+
>r \ ( x -- )
|
|
150
|
+
r> \ ( -- x )
|
|
149
151
|
not \ ( b -- b )
|
|
150
152
|
and \ ( b -- b )
|
|
151
153
|
or \ ( b -- b )
|
|
@@ -177,13 +179,18 @@ a:@ \ ( a n -- x )
|
|
|
177
179
|
a:! \ ( a n x -- a )
|
|
178
180
|
m:@ \ ( o s -- x )
|
|
179
181
|
m:! \ ( o s x -- a )
|
|
180
|
-
a:
|
|
182
|
+
a:len \ ( a -- n )
|
|
183
|
+
a:nth \ ( a n -- x )
|
|
184
|
+
a:head \ ( a -- x )
|
|
185
|
+
a:tail \ ( a -- a )
|
|
181
186
|
a:push \ ( a x -- a )
|
|
182
187
|
a:pop \ ( a -- x )
|
|
183
188
|
m:keys \ ( o -- a )
|
|
184
189
|
m:values \ ( o -- a )
|
|
185
190
|
s:split \ ( s s -- a )
|
|
186
191
|
s:join \ ( a s -- s )
|
|
192
|
+
s:chomp \ ( s -- s )
|
|
193
|
+
s:to_num \ ( s -- n )
|
|
187
194
|
j:stringify \ ( j -- s )
|
|
188
195
|
j:parse \ ( s -- j )
|
|
189
196
|
s:@ \ ( s n -- s )
|
|
@@ -222,7 +229,23 @@ a:each \ ( a f -- )
|
|
|
222
229
|
await \ ( p -- x )
|
|
223
230
|
os:argv \ ( -- a )
|
|
224
231
|
os:parse-args \ ( -- o )
|
|
225
|
-
|
|
232
|
+
os:exec \ ( s -- s )
|
|
233
|
+
os:exec-i \ ( s -- )
|
|
234
|
+
s:format \ ( s a -- s )
|
|
235
|
+
s:len \ ( s -- n )
|
|
236
|
+
s:to_upper \ ( s -- s )
|
|
237
|
+
s:to_lower \ ( s -- s )
|
|
238
|
+
f:write \ ( s1 s2 -- ) s1=data, s2=filename
|
|
239
|
+
f:append \ ( s1 s2 -- ) s1=data, s2=filename
|
|
240
|
+
f:exists \ ( s -- b )
|
|
241
|
+
xml:loadDOM \ ( s -- f_js )
|
|
242
|
+
xml:loadXML \ ( s -- f_js )
|
|
243
|
+
xml:$ \ ( f_js -- j )
|
|
244
|
+
xml:get_text \ ( j -- s )
|
|
245
|
+
xml:get_html \ ( j -- s )
|
|
246
|
+
xml:get_attr \ ( j s -- s )
|
|
247
|
+
xml:has_class \ ( j s -- b )
|
|
248
|
+
xml:get_val \ ( j -- s )
|
|
226
249
|
```
|
|
227
250
|
## functions descriptions
|
|
228
251
|
|
|
@@ -236,11 +259,13 @@ This function throws an error object on TOS and will trigger the current `handle
|
|
|
236
259
|
you can throw a string or an object.
|
|
237
260
|
|
|
238
261
|
### G:delete \ ( s -- )
|
|
239
|
-
This function removes the latest definition of the
|
|
262
|
+
This function removes the latest definition of the word from the dictionary list restoring the previous definition if present.
|
|
240
263
|
|
|
241
264
|
### s:format \ ( s a -- s )
|
|
242
265
|
This function if an implementation of vsprintf. It takes a format string (fmt) and an args list [args] and returns a formatted string (char* vsprintf(*fmt, *args)):
|
|
243
266
|
example:
|
|
244
267
|
`"the number %d and the string %s" [22, "hey"] f:format .`
|
|
245
268
|
|
|
269
|
+
### TODO
|
|
270
|
+
other standard lib functions descriptions coming soon ...
|
|
246
271
|
|
package/doc/force-lang.1
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
.TH "
|
|
1
|
+
.TH "" "1" "January 2026" "0.1.0"
|
|
2
2
|
.SH "NAME"
|
|
3
|
-
\
|
|
3
|
+
\fB\fRForce lang
|
|
4
4
|
.SS (force\-lang)
|
|
5
5
|
.SH naming the lang
|
|
6
6
|
.P
|
|
7
7
|
Force is a modern dialect of Forth written in NodeJS and can use the NodeJS packages universe\.
|
|
8
|
+
.br
|
|
8
9
|
It is called Force because of its assonance of Forth and since the Force is the main power of the Jedi the files have \.j (or \.jedi) extension\. So Force is the Jedi programmers language !
|
|
9
10
|
.SH using Force as standalone interpreter
|
|
10
|
-
.P
|
|
11
11
|
.RS 2
|
|
12
12
|
.nf
|
|
13
13
|
$ npm install force\-lang \-g
|
|
@@ -25,75 +25,62 @@ Options:
|
|
|
25
25
|
.fi
|
|
26
26
|
.RE
|
|
27
27
|
.SH using Force in script
|
|
28
|
-
.P
|
|
29
28
|
.RS 2
|
|
30
29
|
.nf
|
|
31
30
|
$ cat example\.j
|
|
32
31
|
|
|
33
|
-
#!/usr/
|
|
32
|
+
#!/usr/bin/env force
|
|
34
33
|
|
|
35
34
|
2 2 + \.
|
|
36
35
|
.fi
|
|
37
36
|
.RE
|
|
38
37
|
.SH using force in shell
|
|
39
|
-
.P
|
|
40
38
|
.RS 2
|
|
41
39
|
.nf
|
|
42
40
|
echo "2 2 + \."|force
|
|
43
41
|
.fi
|
|
44
42
|
.RE
|
|
45
43
|
.SH using Force as node module
|
|
46
|
-
.P
|
|
47
44
|
.RS 2
|
|
48
45
|
.nf
|
|
49
46
|
$ npm i force\-lang
|
|
47
|
+
|
|
48
|
+
# or
|
|
49
|
+
|
|
50
|
+
npm install git+https://github\.com/elboza/force\-lang#master
|
|
50
51
|
.fi
|
|
51
52
|
.RE
|
|
52
|
-
.P
|
|
53
53
|
.RS 2
|
|
54
54
|
.nf
|
|
55
|
-
|
|
55
|
+
import force from 'force\-lang';
|
|
56
56
|
|
|
57
57
|
var x = '2 2 + \.';
|
|
58
58
|
|
|
59
59
|
(async function(){
|
|
60
60
|
await force\.load_lib();
|
|
61
|
-
force\.exec(x);
|
|
61
|
+
await force\.exec(x);
|
|
62
62
|
})();
|
|
63
63
|
.fi
|
|
64
64
|
.RE
|
|
65
|
-
.P
|
|
66
|
-
or using sync functions:
|
|
67
|
-
.P
|
|
68
|
-
.RS 2
|
|
69
|
-
.nf
|
|
70
|
-
const force = require ('force\-lang');
|
|
71
|
-
|
|
72
|
-
var x = '2 2 + \.';
|
|
73
|
-
|
|
74
|
-
force\.load_lib_sync();
|
|
75
|
-
force\.exec(x);
|
|
76
|
-
.fi
|
|
77
|
-
.RE
|
|
78
65
|
.SH repl multiline
|
|
79
66
|
.P
|
|
80
67
|
in the force\-lang repl \fBforce \-i\fP you can input multiline by appending \fB\\\fP (backslash) at the end of the current line before enter
|
|
81
68
|
.SH language constructs
|
|
82
|
-
.P
|
|
83
69
|
.RS 2
|
|
84
70
|
.nf
|
|
71
|
+
: word_def \.\.\. [exit] \.\.\. ;
|
|
72
|
+
\\ word definition
|
|
73
|
+
\\ <exit> returns from function immediately\.
|
|
85
74
|
( \.\.\. ) \\ lambda func
|
|
86
75
|
example: ( 1 2 + )
|
|
87
76
|
|
|
88
77
|
see \.\.\. \\ see function definition
|
|
89
78
|
example: see cr
|
|
90
|
-
|
|
91
79
|
\|\.\.\. if \.\.\. else \.\.\. then
|
|
92
80
|
\\ if ( x \-\- )
|
|
93
81
|
\\ else ( \-\- )
|
|
94
82
|
\\ then ( \-\- )
|
|
95
83
|
example: T if "no" \. else "yes" \. then
|
|
96
|
-
|
|
97
84
|
\|\.\.\. begin \.\.\.while \.\.\.repeat
|
|
98
85
|
\\ begin ( \-\- )
|
|
99
86
|
\\ repeat ( \-\- )
|
|
@@ -123,9 +110,10 @@ endcase
|
|
|
123
110
|
.SH functions prefix
|
|
124
111
|
.P
|
|
125
112
|
functions name can be prefixed to give more meaningful name to the function and the type it act on\.
|
|
113
|
+
.br
|
|
126
114
|
For example \fB@\fP is applied to normal variables to get values, \fBa:@\fP applies to array, \fBm:@\fP applies to maps (hash)\.
|
|
115
|
+
.br
|
|
127
116
|
The main prefixes are:
|
|
128
|
-
.P
|
|
129
117
|
.RS 2
|
|
130
118
|
.nf
|
|
131
119
|
n: for numbers
|
|
@@ -137,12 +125,12 @@ m: for maps (hash)
|
|
|
137
125
|
f: for file
|
|
138
126
|
G: for Globals
|
|
139
127
|
os: for OS env
|
|
128
|
+
xml: for xml/dom parser
|
|
140
129
|
.fi
|
|
141
130
|
.RE
|
|
142
131
|
.SH functions signatures
|
|
143
132
|
.P
|
|
144
133
|
in the comments of the stadard lib section is described the stack consumption and the type that the function requires\.
|
|
145
|
-
.P
|
|
146
134
|
.RS 2
|
|
147
135
|
.nf
|
|
148
136
|
o object (map)
|
|
@@ -162,11 +150,11 @@ v variable name
|
|
|
162
150
|
.fi
|
|
163
151
|
.RE
|
|
164
152
|
.SH standard lib
|
|
165
|
-
.P
|
|
166
153
|
.RS 2
|
|
167
154
|
.nf
|
|
168
155
|
bye \\ ( \-\- )
|
|
169
156
|
noop \\ ( \-\- )
|
|
157
|
+
nop \\ ( \-\- )
|
|
170
158
|
\|\.s \\ ( \-\- )
|
|
171
159
|
\|\.e \\ ( \-\- )
|
|
172
160
|
words \\ ( \-\- )
|
|
@@ -175,6 +163,8 @@ emit \\ ( n \-\- )
|
|
|
175
163
|
\|\.? \\ ( x \-\- )
|
|
176
164
|
! \\ ( x v \-\- )
|
|
177
165
|
@ \\ ( v \-\- x )
|
|
166
|
+
>r \\ ( x \-\- )
|
|
167
|
+
r> \\ ( \-\- x )
|
|
178
168
|
not \\ ( b \-\- b )
|
|
179
169
|
and \\ ( b \-\- b )
|
|
180
170
|
or \\ ( b \-\- b )
|
|
@@ -206,13 +196,18 @@ a:@ \\ ( a n \-\- x )
|
|
|
206
196
|
a:! \\ ( a n x \-\- a )
|
|
207
197
|
m:@ \\ ( o s \-\- x )
|
|
208
198
|
m:! \\ ( o s x \-\- a )
|
|
209
|
-
a:
|
|
199
|
+
a:len \\ ( a \-\- n )
|
|
200
|
+
a:nth \\ ( a n \-\- x )
|
|
201
|
+
a:head \\ ( a \-\- x )
|
|
202
|
+
a:tail \\ ( a \-\- a )
|
|
210
203
|
a:push \\ ( a x \-\- a )
|
|
211
204
|
a:pop \\ ( a \-\- x )
|
|
212
205
|
m:keys \\ ( o \-\- a )
|
|
213
206
|
m:values \\ ( o \-\- a )
|
|
214
207
|
s:split \\ ( s s \-\- a )
|
|
215
208
|
s:join \\ ( a s \-\- s )
|
|
209
|
+
s:chomp \\ ( s \-\- s )
|
|
210
|
+
s:to_num \\ ( s \-\- n )
|
|
216
211
|
j:stringify \\ ( j \-\- s )
|
|
217
212
|
j:parse \\ ( s \-\- j )
|
|
218
213
|
s:@ \\ ( s n \-\- s )
|
|
@@ -251,25 +246,49 @@ a:each \\ ( a f \-\- )
|
|
|
251
246
|
await \\ ( p \-\- x )
|
|
252
247
|
os:argv \\ ( \-\- a )
|
|
253
248
|
os:parse\-args \\ ( \-\- o )
|
|
254
|
-
|
|
249
|
+
os:exec \\ ( s \-\- s )
|
|
250
|
+
os:exec\-i \\ ( s \-\- )
|
|
251
|
+
s:format \\ ( s a \-\- s )
|
|
252
|
+
s:len \\ ( s \-\- n )
|
|
253
|
+
s:to_upper \\ ( s \-\- s )
|
|
254
|
+
s:to_lower \\ ( s \-\- s )
|
|
255
|
+
f:write \\ ( s1 s2 \-\- ) s1=data, s2=filename
|
|
256
|
+
f:append \\ ( s1 s2 \-\- ) s1=data, s2=filename
|
|
257
|
+
f:exists \\ ( s \-\- b )
|
|
258
|
+
xml:loadDOM \\ ( s \-\- f_js )
|
|
259
|
+
xml:loadXML \\ ( s \-\- f_js )
|
|
260
|
+
xml:$ \\ ( f_js \-\- j )
|
|
261
|
+
xml:get_text \\ ( j \-\- s )
|
|
262
|
+
xml:get_html \\ ( j \-\- s )
|
|
263
|
+
xml:get_attr \\ ( j s \-\- s )
|
|
264
|
+
xml:has_class \\ ( j s \-\- b )
|
|
265
|
+
xml:get_val \\ ( j \-\- s )
|
|
255
266
|
.fi
|
|
256
267
|
.RE
|
|
257
268
|
.SH functions descriptions
|
|
258
269
|
.SS handle \\ ( e \-\- )
|
|
259
270
|
.P
|
|
260
271
|
This function is called every time there is an error object on top of the stack\.
|
|
261
|
-
|
|
272
|
+
.br
|
|
273
|
+
You can override this function with you own to provide a custom error handling\. This can be permanent or temporary (by deleting the latest definition with \fB'handle' G:delete\fP)\.
|
|
274
|
+
.br
|
|
262
275
|
The first thing that your custom handler function should do is to remove the error object from the TOS\. This can be done by eighter removing it (\fBdrop\fP or print \fB\|\.\fP) or by adding another item on top of it (in case you want to preserve it for future use)\.
|
|
263
276
|
.SS throw \\ ( s \-\- ) or ( o \-\- )
|
|
264
277
|
.P
|
|
265
278
|
This function throws an error object on TOS and will trigger the current \fBhandle\fP function\.
|
|
279
|
+
.br
|
|
266
280
|
you can throw a string or an object\.
|
|
267
281
|
.SS G:delete \\ ( s \-\- )
|
|
268
282
|
.P
|
|
269
|
-
This function removes the latest definition of the
|
|
283
|
+
This function removes the latest definition of the word from the dictionary list restoring the previous definition if present\.
|
|
270
284
|
.SS s:format \\ ( s a \-\- s )
|
|
271
285
|
.P
|
|
272
|
-
This function if an implementation of vsprintf\. It takes a format string (fmt) and an args list [args] and returns a formatted string (char
|
|
273
|
-
|
|
274
|
-
|
|
286
|
+
This function if an implementation of vsprintf\. It takes a format string (fmt) and an args list [args] and returns a formatted string (char* vsprintf(*fmt, *args)):
|
|
287
|
+
.br
|
|
288
|
+
example:
|
|
289
|
+
.br
|
|
290
|
+
\fB"the number %d and the string %s" [22, "hey"] f:format \.\fP
|
|
291
|
+
.SS TODO
|
|
292
|
+
.P
|
|
293
|
+
other standard lib functions descriptions coming soon \.\.\.
|
|
275
294
|
|
package/doc/force.1
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
.TH "
|
|
1
|
+
.TH "" "1" "January 2026" "0.1.0"
|
|
2
2
|
.SH "NAME"
|
|
3
|
-
\
|
|
3
|
+
\fB\fRForce lang
|
|
4
4
|
.SS (force\-lang)
|
|
5
5
|
.SH naming the lang
|
|
6
6
|
.P
|
|
7
7
|
Force is a modern dialect of Forth written in NodeJS and can use the NodeJS packages universe\.
|
|
8
|
+
.br
|
|
8
9
|
It is called Force because of its assonance of Forth and since the Force is the main power of the Jedi the files have \.j (or \.jedi) extension\. So Force is the Jedi programmers language !
|
|
9
10
|
.SH using Force as standalone interpreter
|
|
10
|
-
.P
|
|
11
11
|
.RS 2
|
|
12
12
|
.nf
|
|
13
13
|
$ npm install force\-lang \-g
|
|
@@ -25,75 +25,62 @@ Options:
|
|
|
25
25
|
.fi
|
|
26
26
|
.RE
|
|
27
27
|
.SH using Force in script
|
|
28
|
-
.P
|
|
29
28
|
.RS 2
|
|
30
29
|
.nf
|
|
31
30
|
$ cat example\.j
|
|
32
31
|
|
|
33
|
-
#!/usr/
|
|
32
|
+
#!/usr/bin/env force
|
|
34
33
|
|
|
35
34
|
2 2 + \.
|
|
36
35
|
.fi
|
|
37
36
|
.RE
|
|
38
37
|
.SH using force in shell
|
|
39
|
-
.P
|
|
40
38
|
.RS 2
|
|
41
39
|
.nf
|
|
42
40
|
echo "2 2 + \."|force
|
|
43
41
|
.fi
|
|
44
42
|
.RE
|
|
45
43
|
.SH using Force as node module
|
|
46
|
-
.P
|
|
47
44
|
.RS 2
|
|
48
45
|
.nf
|
|
49
46
|
$ npm i force\-lang
|
|
47
|
+
|
|
48
|
+
# or
|
|
49
|
+
|
|
50
|
+
npm install git+https://github\.com/elboza/force\-lang#master
|
|
50
51
|
.fi
|
|
51
52
|
.RE
|
|
52
|
-
.P
|
|
53
53
|
.RS 2
|
|
54
54
|
.nf
|
|
55
|
-
|
|
55
|
+
import force from 'force\-lang';
|
|
56
56
|
|
|
57
57
|
var x = '2 2 + \.';
|
|
58
58
|
|
|
59
59
|
(async function(){
|
|
60
60
|
await force\.load_lib();
|
|
61
|
-
force\.exec(x);
|
|
61
|
+
await force\.exec(x);
|
|
62
62
|
})();
|
|
63
63
|
.fi
|
|
64
64
|
.RE
|
|
65
|
-
.P
|
|
66
|
-
or using sync functions:
|
|
67
|
-
.P
|
|
68
|
-
.RS 2
|
|
69
|
-
.nf
|
|
70
|
-
const force = require ('force\-lang');
|
|
71
|
-
|
|
72
|
-
var x = '2 2 + \.';
|
|
73
|
-
|
|
74
|
-
force\.load_lib_sync();
|
|
75
|
-
force\.exec(x);
|
|
76
|
-
.fi
|
|
77
|
-
.RE
|
|
78
65
|
.SH repl multiline
|
|
79
66
|
.P
|
|
80
67
|
in the force\-lang repl \fBforce \-i\fP you can input multiline by appending \fB\\\fP (backslash) at the end of the current line before enter
|
|
81
68
|
.SH language constructs
|
|
82
|
-
.P
|
|
83
69
|
.RS 2
|
|
84
70
|
.nf
|
|
71
|
+
: word_def \.\.\. [exit] \.\.\. ;
|
|
72
|
+
\\ word definition
|
|
73
|
+
\\ <exit> returns from function immediately\.
|
|
85
74
|
( \.\.\. ) \\ lambda func
|
|
86
75
|
example: ( 1 2 + )
|
|
87
76
|
|
|
88
77
|
see \.\.\. \\ see function definition
|
|
89
78
|
example: see cr
|
|
90
|
-
|
|
91
79
|
\|\.\.\. if \.\.\. else \.\.\. then
|
|
92
80
|
\\ if ( x \-\- )
|
|
93
81
|
\\ else ( \-\- )
|
|
94
82
|
\\ then ( \-\- )
|
|
95
83
|
example: T if "no" \. else "yes" \. then
|
|
96
|
-
|
|
97
84
|
\|\.\.\. begin \.\.\.while \.\.\.repeat
|
|
98
85
|
\\ begin ( \-\- )
|
|
99
86
|
\\ repeat ( \-\- )
|
|
@@ -123,9 +110,10 @@ endcase
|
|
|
123
110
|
.SH functions prefix
|
|
124
111
|
.P
|
|
125
112
|
functions name can be prefixed to give more meaningful name to the function and the type it act on\.
|
|
113
|
+
.br
|
|
126
114
|
For example \fB@\fP is applied to normal variables to get values, \fBa:@\fP applies to array, \fBm:@\fP applies to maps (hash)\.
|
|
115
|
+
.br
|
|
127
116
|
The main prefixes are:
|
|
128
|
-
.P
|
|
129
117
|
.RS 2
|
|
130
118
|
.nf
|
|
131
119
|
n: for numbers
|
|
@@ -137,12 +125,12 @@ m: for maps (hash)
|
|
|
137
125
|
f: for file
|
|
138
126
|
G: for Globals
|
|
139
127
|
os: for OS env
|
|
128
|
+
xml: for xml/dom parser
|
|
140
129
|
.fi
|
|
141
130
|
.RE
|
|
142
131
|
.SH functions signatures
|
|
143
132
|
.P
|
|
144
133
|
in the comments of the stadard lib section is described the stack consumption and the type that the function requires\.
|
|
145
|
-
.P
|
|
146
134
|
.RS 2
|
|
147
135
|
.nf
|
|
148
136
|
o object (map)
|
|
@@ -162,11 +150,11 @@ v variable name
|
|
|
162
150
|
.fi
|
|
163
151
|
.RE
|
|
164
152
|
.SH standard lib
|
|
165
|
-
.P
|
|
166
153
|
.RS 2
|
|
167
154
|
.nf
|
|
168
155
|
bye \\ ( \-\- )
|
|
169
156
|
noop \\ ( \-\- )
|
|
157
|
+
nop \\ ( \-\- )
|
|
170
158
|
\|\.s \\ ( \-\- )
|
|
171
159
|
\|\.e \\ ( \-\- )
|
|
172
160
|
words \\ ( \-\- )
|
|
@@ -175,6 +163,8 @@ emit \\ ( n \-\- )
|
|
|
175
163
|
\|\.? \\ ( x \-\- )
|
|
176
164
|
! \\ ( x v \-\- )
|
|
177
165
|
@ \\ ( v \-\- x )
|
|
166
|
+
>r \\ ( x \-\- )
|
|
167
|
+
r> \\ ( \-\- x )
|
|
178
168
|
not \\ ( b \-\- b )
|
|
179
169
|
and \\ ( b \-\- b )
|
|
180
170
|
or \\ ( b \-\- b )
|
|
@@ -206,13 +196,18 @@ a:@ \\ ( a n \-\- x )
|
|
|
206
196
|
a:! \\ ( a n x \-\- a )
|
|
207
197
|
m:@ \\ ( o s \-\- x )
|
|
208
198
|
m:! \\ ( o s x \-\- a )
|
|
209
|
-
a:
|
|
199
|
+
a:len \\ ( a \-\- n )
|
|
200
|
+
a:nth \\ ( a n \-\- x )
|
|
201
|
+
a:head \\ ( a \-\- x )
|
|
202
|
+
a:tail \\ ( a \-\- a )
|
|
210
203
|
a:push \\ ( a x \-\- a )
|
|
211
204
|
a:pop \\ ( a \-\- x )
|
|
212
205
|
m:keys \\ ( o \-\- a )
|
|
213
206
|
m:values \\ ( o \-\- a )
|
|
214
207
|
s:split \\ ( s s \-\- a )
|
|
215
208
|
s:join \\ ( a s \-\- s )
|
|
209
|
+
s:chomp \\ ( s \-\- s )
|
|
210
|
+
s:to_num \\ ( s \-\- n )
|
|
216
211
|
j:stringify \\ ( j \-\- s )
|
|
217
212
|
j:parse \\ ( s \-\- j )
|
|
218
213
|
s:@ \\ ( s n \-\- s )
|
|
@@ -251,25 +246,49 @@ a:each \\ ( a f \-\- )
|
|
|
251
246
|
await \\ ( p \-\- x )
|
|
252
247
|
os:argv \\ ( \-\- a )
|
|
253
248
|
os:parse\-args \\ ( \-\- o )
|
|
254
|
-
|
|
249
|
+
os:exec \\ ( s \-\- s )
|
|
250
|
+
os:exec\-i \\ ( s \-\- )
|
|
251
|
+
s:format \\ ( s a \-\- s )
|
|
252
|
+
s:len \\ ( s \-\- n )
|
|
253
|
+
s:to_upper \\ ( s \-\- s )
|
|
254
|
+
s:to_lower \\ ( s \-\- s )
|
|
255
|
+
f:write \\ ( s1 s2 \-\- ) s1=data, s2=filename
|
|
256
|
+
f:append \\ ( s1 s2 \-\- ) s1=data, s2=filename
|
|
257
|
+
f:exists \\ ( s \-\- b )
|
|
258
|
+
xml:loadDOM \\ ( s \-\- f_js )
|
|
259
|
+
xml:loadXML \\ ( s \-\- f_js )
|
|
260
|
+
xml:$ \\ ( f_js \-\- j )
|
|
261
|
+
xml:get_text \\ ( j \-\- s )
|
|
262
|
+
xml:get_html \\ ( j \-\- s )
|
|
263
|
+
xml:get_attr \\ ( j s \-\- s )
|
|
264
|
+
xml:has_class \\ ( j s \-\- b )
|
|
265
|
+
xml:get_val \\ ( j \-\- s )
|
|
255
266
|
.fi
|
|
256
267
|
.RE
|
|
257
268
|
.SH functions descriptions
|
|
258
269
|
.SS handle \\ ( e \-\- )
|
|
259
270
|
.P
|
|
260
271
|
This function is called every time there is an error object on top of the stack\.
|
|
261
|
-
|
|
272
|
+
.br
|
|
273
|
+
You can override this function with you own to provide a custom error handling\. This can be permanent or temporary (by deleting the latest definition with \fB'handle' G:delete\fP)\.
|
|
274
|
+
.br
|
|
262
275
|
The first thing that your custom handler function should do is to remove the error object from the TOS\. This can be done by eighter removing it (\fBdrop\fP or print \fB\|\.\fP) or by adding another item on top of it (in case you want to preserve it for future use)\.
|
|
263
276
|
.SS throw \\ ( s \-\- ) or ( o \-\- )
|
|
264
277
|
.P
|
|
265
278
|
This function throws an error object on TOS and will trigger the current \fBhandle\fP function\.
|
|
279
|
+
.br
|
|
266
280
|
you can throw a string or an object\.
|
|
267
281
|
.SS G:delete \\ ( s \-\- )
|
|
268
282
|
.P
|
|
269
|
-
This function removes the latest definition of the
|
|
283
|
+
This function removes the latest definition of the word from the dictionary list restoring the previous definition if present\.
|
|
270
284
|
.SS s:format \\ ( s a \-\- s )
|
|
271
285
|
.P
|
|
272
|
-
This function if an implementation of vsprintf\. It takes a format string (fmt) and an args list [args] and returns a formatted string (char
|
|
273
|
-
|
|
274
|
-
|
|
286
|
+
This function if an implementation of vsprintf\. It takes a format string (fmt) and an args list [args] and returns a formatted string (char* vsprintf(*fmt, *args)):
|
|
287
|
+
.br
|
|
288
|
+
example:
|
|
289
|
+
.br
|
|
290
|
+
\fB"the number %d and the string %s" [22, "hey"] f:format \.\fP
|
|
291
|
+
.SS TODO
|
|
292
|
+
.P
|
|
293
|
+
other standard lib functions descriptions coming soon \.\.\.
|
|
275
294
|
|
package/examples/cli-args.j
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
#!/usr/
|
|
1
|
+
#!/usr/bin/env force
|
|
2
2
|
|
|
3
3
|
|
|
4
4
|
os:argv @ .
|
|
@@ -8,10 +8,10 @@ os:argv @ .
|
|
|
8
8
|
['-h','--help','n'],
|
|
9
9
|
['-k','--kkk','?']
|
|
10
10
|
]
|
|
11
|
-
os:parse-args
|
|
11
|
+
os:parse-args .s
|
|
12
12
|
|
|
13
13
|
// run with:
|
|
14
14
|
// ./cli-args.j -x 99
|
|
15
15
|
// the putput will be:
|
|
16
16
|
// ["/usr/local/bin/node","/usr/local/bin/force","./cli-args.j","-x","99"]
|
|
17
|
-
// { argv: [], xray: '99' }
|
|
17
|
+
// { argv: [], xray: '99' }
|
package/examples/testjs.js
CHANGED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
'<div id="kk" class="as">foo</div>'
|
|
2
|
+
xml:loadDOM
|
|
3
|
+
'div' xml:$
|
|
4
|
+
'as' xml:has_class
|
|
5
|
+
.
|
|
6
|
+
|
|
7
|
+
'<div id="kk" class="as">foo</div>'
|
|
8
|
+
xml:loadDOM
|
|
9
|
+
'#kk' xml:$
|
|
10
|
+
xml:get_text
|
|
11
|
+
.
|
|
12
|
+
|
|
13
|
+
'<div id="kk" class="as">foo</div>'
|
|
14
|
+
xml:loadDOM
|
|
15
|
+
'div' xml:$
|
|
16
|
+
'class' xml:get_attr
|
|
17
|
+
.
|