naider 1.24.4 → 2.0.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/README.md +28 -83
- package/SPEC.naide +8 -6
- package/bin/naide.js +42 -103
- package/bin/postinstall.js +5 -15
- package/examples/model.naide +1 -1
- package/lsp/server.js +1 -2
- package/mcp/server.js +2 -2
- package/package.json +2 -4
- package/src/gen.js +975 -273
- package/src/generator.js +5 -1
- package/src/index.js +34 -14
- package/src/parser.js +15 -14
- package/src/typechecker.js +60 -13
- package/vscode-naide/README.md +4 -6
- package/vscode-naide/extension.js +1 -2
- package/vscode-naide/package-lock.json +2 -2
- package/vscode-naide/package.json +3 -15
- package/SPEC-X.nx +0 -276
- package/assets/nx.ico +0 -0
- package/assets/nx_check.png +0 -0
- package/examples/ai-app.nx +0 -21
- package/examples/async.nx +0 -40
- package/examples/crud.nx +0 -64
- package/examples/fullapp.nx +0 -74
- package/examples/hello.nx +0 -29
- package/examples/server.nx +0 -27
- package/examples/sql-app.nx +0 -23
- package/examples/todo-api.nx +0 -31
- package/src/preprocess.js +0 -308
- package/vscode-naide/language-configuration-nx.json +0 -32
- package/vscode-naide/naide-lang-1.1.0.vsix +0 -0
- package/vscode-naide/syntaxes/naidex.tmLanguage.json +0 -287
package/SPEC-X.nx
DELETED
|
@@ -1,276 +0,0 @@
|
|
|
1
|
-
-- ============================================
|
|
2
|
-
-- NAIDE-X Language Specification
|
|
3
|
-
-- ~80% fewer tokens than JavaScript
|
|
4
|
-
-- AI-only readability. Maximum generation speed.
|
|
5
|
-
-- ============================================
|
|
6
|
-
-- Rule: first char of line = intent
|
|
7
|
-
-- > return ? if | elif : else
|
|
8
|
-
-- @ loop * while ! try !! catch !!! ensure
|
|
9
|
-
-- $ server ^ model < import % match X patch
|
|
10
|
-
-- f func ~f async + export
|
|
11
|
-
-- s:i:n:b:l:m:a: typed vars
|
|
12
|
-
-- ~ await ~~ await.all
|
|
13
|
-
-- ============================================
|
|
14
|
-
|
|
15
|
-
-- Types: s=str i=int n=num b=bool l=list m=map a=any
|
|
16
|
-
s:name="hello"
|
|
17
|
-
i:count=42
|
|
18
|
-
n:price=9.99
|
|
19
|
-
b:active=true
|
|
20
|
-
l:items=[1,2,3]
|
|
21
|
-
m:cfg={host:"localhost",port:3000}
|
|
22
|
-
a:data=null
|
|
23
|
-
|
|
24
|
-
-- Mutable: ~ prefix
|
|
25
|
-
~i:counter=0
|
|
26
|
-
~s:label="init"
|
|
27
|
-
|
|
28
|
-
-- String interpolation: "{expr}" (double quotes)
|
|
29
|
-
s:greet="Hello {name}, count is {count}"
|
|
30
|
-
|
|
31
|
-
-- Functions: f name(TYPE:param,...)RETTYPE
|
|
32
|
-
f add(i:a,i:b)i
|
|
33
|
-
>a+b
|
|
34
|
-
|
|
35
|
-
f sayHi(s:who)
|
|
36
|
-
log"Hi {who}"
|
|
37
|
-
|
|
38
|
-
f greet2(s:name,s:prefix="Hello")
|
|
39
|
-
log"{prefix}, {name}!"
|
|
40
|
-
|
|
41
|
-
-- Async: ~f
|
|
42
|
-
~f fetchUser(s:id)m
|
|
43
|
-
a:res=~fetch("/api/users/{id}")
|
|
44
|
-
a:data=~res.json()
|
|
45
|
-
>data
|
|
46
|
-
|
|
47
|
-
-- Return: >
|
|
48
|
-
-- Return with status: >.s CODE BODY
|
|
49
|
-
|
|
50
|
-
-- If/elif/else: ? | :
|
|
51
|
-
?count>10
|
|
52
|
-
log"many"
|
|
53
|
-
|count>5
|
|
54
|
-
log"some"
|
|
55
|
-
:
|
|
56
|
-
log"few"
|
|
57
|
-
|
|
58
|
-
-- Inline ternary (same as NAIDE v1)
|
|
59
|
-
-- s:size=if count>10 then "big" else "small"
|
|
60
|
-
|
|
61
|
-
-- Each: @var<collection
|
|
62
|
-
@item<items
|
|
63
|
-
log item
|
|
64
|
-
|
|
65
|
-
-- Each with key: @key,val<collection
|
|
66
|
-
@k,v<cfg
|
|
67
|
-
log"{k}: {v}"
|
|
68
|
-
|
|
69
|
-
-- For range: @var<start..end
|
|
70
|
-
@i<0..10
|
|
71
|
-
log i
|
|
72
|
-
|
|
73
|
-
-- While: *condition
|
|
74
|
-
*active
|
|
75
|
-
log"running"
|
|
76
|
-
active=false
|
|
77
|
-
|
|
78
|
-
-- Match: %value
|
|
79
|
-
s:status="ok"
|
|
80
|
-
%status
|
|
81
|
-
"ok": log "success"
|
|
82
|
-
"error": log "failed"
|
|
83
|
-
_: log "unknown"
|
|
84
|
-
|
|
85
|
-
-- Try/catch/ensure: ! / !!var / !!!
|
|
86
|
-
~f safe(s:url)m
|
|
87
|
-
!
|
|
88
|
-
a:data=~fetch(url)
|
|
89
|
-
>{ok:true,data:data}
|
|
90
|
-
!!e
|
|
91
|
-
log.e"fail: {e.message}"
|
|
92
|
-
>{ok:false,error:e.message}
|
|
93
|
-
!!!
|
|
94
|
-
log"request done"
|
|
95
|
-
|
|
96
|
-
-- typeof / instanceof
|
|
97
|
-
?typeof x=="string"
|
|
98
|
-
log"is string"
|
|
99
|
-
?err instanceof TypeError
|
|
100
|
-
log"type error"
|
|
101
|
-
|
|
102
|
-
-- Pipe: |> (same)
|
|
103
|
-
l:result=[1,2,3,4,5]
|
|
104
|
-
|>filter((x)=>x>2)
|
|
105
|
-
|>map((x)=>x*10)
|
|
106
|
-
|
|
107
|
-
-- Model: ^Name
|
|
108
|
-
^User
|
|
109
|
-
s:name
|
|
110
|
-
s:email
|
|
111
|
-
i:age=0
|
|
112
|
-
f greet()s
|
|
113
|
-
>"Hi, I'm {self.name}"
|
|
114
|
-
~f save()
|
|
115
|
-
log"Saving {self.name}..."
|
|
116
|
-
|
|
117
|
-
-- Inheritance: ^Child<Parent
|
|
118
|
-
^Admin<User
|
|
119
|
-
s:role="admin"
|
|
120
|
-
f perms()l
|
|
121
|
-
>["read","write","delete"]
|
|
122
|
-
|
|
123
|
-
-- DB persistence: db "path/"
|
|
124
|
-
db "data/"
|
|
125
|
-
|
|
126
|
-
-- SQL database: db.sql "driver" "connection"
|
|
127
|
-
-- db.sql "sqlite" "app.db"
|
|
128
|
-
-- db.sql "postgres" "postgresql://localhost/mydb"
|
|
129
|
-
|
|
130
|
-
-- Environment variables
|
|
131
|
-
env:
|
|
132
|
-
PORT int default(3000)
|
|
133
|
-
JWT_SECRET str required
|
|
134
|
-
|
|
135
|
-
-- Schema: types + modifiers
|
|
136
|
-
schema User:
|
|
137
|
-
id auto
|
|
138
|
-
name str required min(2) max(50)
|
|
139
|
-
email str required email unique
|
|
140
|
-
role enum("admin","user") default("user")
|
|
141
|
-
joined timestamp auto
|
|
142
|
-
|
|
143
|
-
-- Server with high-level features
|
|
144
|
-
$app:PORT
|
|
145
|
-
cors "*"
|
|
146
|
-
auth JWT_SECRET:
|
|
147
|
-
protect "/api/*"
|
|
148
|
-
public "/api/auth/*"
|
|
149
|
-
limit "/api/*" 100 "1m"
|
|
150
|
-
static "/public"
|
|
151
|
-
crud "/api/users" User
|
|
152
|
-
cookie
|
|
153
|
-
session JWT_SECRET
|
|
154
|
-
cache "/api/*" "5m"
|
|
155
|
-
view "./views"
|
|
156
|
-
sse "/events"
|
|
157
|
-
upload "/api/upload" "avatar" (req,res):
|
|
158
|
-
>{file:req.file.filename}
|
|
159
|
-
-- Route middleware: [mid1, mid2]
|
|
160
|
-
G"/admin"[authCheck](req,res)
|
|
161
|
-
>{admin:true}
|
|
162
|
-
P"/api/secure"[auth,logger](req,res)
|
|
163
|
-
>req.body
|
|
164
|
-
group "/api/v1":
|
|
165
|
-
G"/status"
|
|
166
|
-
>{version:"1.0"}
|
|
167
|
-
G"/"
|
|
168
|
-
>.h "<h1>Welcome</h1>"
|
|
169
|
-
P"/api/auth/register"(req,res)
|
|
170
|
-
s:hashed=hash(req.body.password)
|
|
171
|
-
user=UserStore.create({...req.body,password:hashed})
|
|
172
|
-
token=auth.sign({id:user.id})
|
|
173
|
-
>{token,user}
|
|
174
|
-
P"/api/auth/login"(req,res)
|
|
175
|
-
user=UserStore.where({email:req.body.email})[0]
|
|
176
|
-
?not user
|
|
177
|
-
>.s 401 {error:"Invalid credentials"}
|
|
178
|
-
?not verify(req.body.password,user.password)
|
|
179
|
-
>.s 401 {error:"Invalid credentials"}
|
|
180
|
-
token=sign({id:user.id})
|
|
181
|
-
>{token}
|
|
182
|
-
ws "/chat":
|
|
183
|
-
on "connect":
|
|
184
|
-
send({type:"welcome"})
|
|
185
|
-
on "message" (data):
|
|
186
|
-
broadcast(data)
|
|
187
|
-
|
|
188
|
-
-- Error handler
|
|
189
|
-
error (err, req, res):
|
|
190
|
-
log.e err.message
|
|
191
|
-
>.s 500 {error:"Internal error"}
|
|
192
|
-
|
|
193
|
-
-- HTTP client (auto-imported)
|
|
194
|
-
-- api.get(url) api.post(url,body) api.put(url,body) api.del(url) api.raw(url,opts)
|
|
195
|
-
|
|
196
|
-
-- Return helpers
|
|
197
|
-
-- >expr → JSON
|
|
198
|
-
-- >.s CODE expr → status code
|
|
199
|
-
-- >.r "/path" → redirect
|
|
200
|
-
-- >.h "<html>" → HTML
|
|
201
|
-
-- >.t "text" → plain text
|
|
202
|
-
-- >.f "/file" → send file
|
|
203
|
-
-- >.d "/file" → download
|
|
204
|
-
-- >.v "tmpl" {} → render template
|
|
205
|
-
|
|
206
|
-
-- Built-in functions (auto-imported)
|
|
207
|
-
-- uuid() → UUID
|
|
208
|
-
-- hash("password") → scrypt hash
|
|
209
|
-
-- verify("pw",hashed) → verify
|
|
210
|
-
-- sign({id:1}) → JWT (uses auth secret)
|
|
211
|
-
-- sign({id:1},"secret") → JWT (explicit)
|
|
212
|
-
|
|
213
|
-
-- Validate: auto-validate POST/PUT/PATCH bodies
|
|
214
|
-
-- validate "/api/users" User
|
|
215
|
-
|
|
216
|
-
-- Test (node:test)
|
|
217
|
-
test "math":
|
|
218
|
-
assert 1+1==2
|
|
219
|
-
assert 2*3==6
|
|
220
|
-
|
|
221
|
-
-- Queue (async job queue)
|
|
222
|
-
queue jobs:
|
|
223
|
-
job "notify" (data):
|
|
224
|
-
log data.msg
|
|
225
|
-
|
|
226
|
-
-- OpenAPI: auto-generate spec from schemas
|
|
227
|
-
-- openapi "/docs"
|
|
228
|
-
|
|
229
|
-
-- AI / LLM integration (auto-imported, zero-dep)
|
|
230
|
-
-- s:answer=~ai.ask("Explain NAIDE")
|
|
231
|
-
-- m:result=~ai.json("List 3 colors",{colors:["string"]})
|
|
232
|
-
-- s:reply=~ai.chat(msgs)
|
|
233
|
-
-- s:a=~ai.ask("hi",{model:"gpt-4o",maxTokens:100})
|
|
234
|
-
-- Streaming: ~f main(): @chunk<~ai.stream("poem") ...
|
|
235
|
-
-- Embed: l:vec=~ai.embed("hello")
|
|
236
|
-
-- Similarity: n:score=ai.similarity(a,b)
|
|
237
|
-
|
|
238
|
-
-- Prompt template
|
|
239
|
-
-- prompt summarize {lang:"en"}:
|
|
240
|
-
-- "Summarize in {lang}: {text}"
|
|
241
|
-
|
|
242
|
-
-- Inter-file import (.naide/.nx → .mjs auto-rewrite)
|
|
243
|
-
-- <{handler}"./routes.naide"
|
|
244
|
-
|
|
245
|
-
-- Scheduled tasks
|
|
246
|
-
every "5m":
|
|
247
|
-
log"cleanup"
|
|
248
|
-
|
|
249
|
-
-- Event watch
|
|
250
|
-
watch User.create (event):
|
|
251
|
-
log"new: {event.data.name}"
|
|
252
|
-
|
|
253
|
-
-- Import: <module or <{names}"module"
|
|
254
|
-
-- <express
|
|
255
|
-
-- <{readFile,writeFile}"fs/promises"
|
|
256
|
-
|
|
257
|
-
-- Export: + prefix
|
|
258
|
-
+f helper()s
|
|
259
|
-
>"exported"
|
|
260
|
-
+s:VER="1.0.0"
|
|
261
|
-
|
|
262
|
-
-- Log: log, log.e, log.w, log.i, log.d
|
|
263
|
-
log"info"
|
|
264
|
-
log.e"error"
|
|
265
|
-
log.w"warning"
|
|
266
|
-
log.i"info level"
|
|
267
|
-
log.d"debug level"
|
|
268
|
-
|
|
269
|
-
-- Null safe: ?. and ?? (same)
|
|
270
|
-
a:val=data?.nested?.value??"default"
|
|
271
|
-
|
|
272
|
-
-- Await all: ~~[expr1,expr2]
|
|
273
|
-
|
|
274
|
-
-- Spread: ...
|
|
275
|
-
l:combined=[...items,4,5,6]
|
|
276
|
-
m:merged={...cfg,debug:true}
|
package/assets/nx.ico
DELETED
|
Binary file
|
package/assets/nx_check.png
DELETED
|
Binary file
|
package/examples/ai-app.nx
DELETED
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
-- AI-powered API (NAIDE-X)
|
|
2
|
-
-- Set AI_KEY or OPENAI_API_KEY env var
|
|
3
|
-
|
|
4
|
-
$app:3000
|
|
5
|
-
cors "*"
|
|
6
|
-
|
|
7
|
-
P"/api/ask"(req,res)
|
|
8
|
-
s:answer=~ai.ask(req.body.prompt)
|
|
9
|
-
>{answer}
|
|
10
|
-
|
|
11
|
-
P"/api/summarize"(req,res)
|
|
12
|
-
s:summary=~ai.ask("Summarize: {req.body.text}")
|
|
13
|
-
>{summary}
|
|
14
|
-
|
|
15
|
-
P"/api/extract"(req,res)
|
|
16
|
-
m:data=~ai.json("Extract name, email, phone: {req.body.text}",{name:"string",email:"string",phone:"string"})
|
|
17
|
-
>data
|
|
18
|
-
|
|
19
|
-
P"/api/chat"(req,res)
|
|
20
|
-
s:reply=~ai.chat(req.body.messages)
|
|
21
|
-
>{reply}
|
package/examples/async.nx
DELETED
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
-- NAIDE-X async/await
|
|
2
|
-
|
|
3
|
-
~f fetchData(s:url)a
|
|
4
|
-
a:res=~fetch(url)
|
|
5
|
-
a:data=~res.json()
|
|
6
|
-
>data
|
|
7
|
-
|
|
8
|
-
~f getTopUsers()l
|
|
9
|
-
a:data=~fetchData("https://jsonplaceholder.typicode.com/users")
|
|
10
|
-
l:result=data
|
|
11
|
-
|>filter((u)=>u.name.length>5)
|
|
12
|
-
|>map((u)=>({name:u.name,email:u.email}))
|
|
13
|
-
>result
|
|
14
|
-
|
|
15
|
-
~f safeFetch(s:url)m
|
|
16
|
-
!
|
|
17
|
-
a:data=~fetchData(url)
|
|
18
|
-
>{ok:true,data:data}
|
|
19
|
-
!!e
|
|
20
|
-
log.e"Fetch failed: {e.message}"
|
|
21
|
-
>{ok:false,error:e.message}
|
|
22
|
-
|
|
23
|
-
~f loadDash()m
|
|
24
|
-
l:urls=[
|
|
25
|
-
"https://jsonplaceholder.typicode.com/users",
|
|
26
|
-
"https://jsonplaceholder.typicode.com/posts",
|
|
27
|
-
"https://jsonplaceholder.typicode.com/todos"
|
|
28
|
-
]
|
|
29
|
-
l:results=~~urls.map((url)=>fetchData(url))
|
|
30
|
-
>{users:results[0],posts:results[1],todos:results[2]}
|
|
31
|
-
|
|
32
|
-
~f main()
|
|
33
|
-
log"Fetching data..."
|
|
34
|
-
m:dash=~safeFetch("https://jsonplaceholder.typicode.com/users")
|
|
35
|
-
?dash.ok
|
|
36
|
-
log"Got {dash.data.length} items"
|
|
37
|
-
:
|
|
38
|
-
log.e dash.error
|
|
39
|
-
|
|
40
|
-
main()
|
package/examples/crud.nx
DELETED
|
@@ -1,64 +0,0 @@
|
|
|
1
|
-
-- NAIDE-X full CRUD
|
|
2
|
-
|
|
3
|
-
^Todo
|
|
4
|
-
s:id
|
|
5
|
-
s:title
|
|
6
|
-
b:done=false
|
|
7
|
-
s:createdAt
|
|
8
|
-
|
|
9
|
-
f toggle()
|
|
10
|
-
self.done=not self.done
|
|
11
|
-
|
|
12
|
-
f toJSON()m
|
|
13
|
-
>{id:self.id,title:self.title,done:self.done,createdAt:self.createdAt}
|
|
14
|
-
|
|
15
|
-
~l:todos=[]
|
|
16
|
-
~i:nextId=1
|
|
17
|
-
|
|
18
|
-
f findTodo(s:id)a
|
|
19
|
-
@todo<todos
|
|
20
|
-
?todo.id==id
|
|
21
|
-
>todo
|
|
22
|
-
>null
|
|
23
|
-
|
|
24
|
-
f genId()s
|
|
25
|
-
s:id="todo_{nextId}"
|
|
26
|
-
nextId+=1
|
|
27
|
-
>id
|
|
28
|
-
|
|
29
|
-
$app:8080
|
|
30
|
-
|
|
31
|
-
G"/api/todos"
|
|
32
|
-
>{todos:todos,count:todos.length}
|
|
33
|
-
|
|
34
|
-
G"/api/todos/:id"(req,res)
|
|
35
|
-
a:todo=findTodo(req.params.id)
|
|
36
|
-
?todo==null
|
|
37
|
-
>.s 404 {error:"Todo not found"}
|
|
38
|
-
>todo
|
|
39
|
-
|
|
40
|
-
P"/api/todos"(req,res)
|
|
41
|
-
m:body=req.body
|
|
42
|
-
?not body.title
|
|
43
|
-
>.s 400 {error:"Title is required"}
|
|
44
|
-
m:todo={id:genId(),title:body.title,done:false,createdAt:new Date().toISOString()}
|
|
45
|
-
todos.push(todo)
|
|
46
|
-
>.s 201 todo
|
|
47
|
-
|
|
48
|
-
U"/api/todos/:id"(req,res)
|
|
49
|
-
a:todo=findTodo(req.params.id)
|
|
50
|
-
?todo==null
|
|
51
|
-
>.s 404 {error:"Todo not found"}
|
|
52
|
-
m:body=req.body
|
|
53
|
-
?body.title
|
|
54
|
-
todo.title=body.title
|
|
55
|
-
?body.done!=null
|
|
56
|
-
todo.done=body.done
|
|
57
|
-
>todo
|
|
58
|
-
|
|
59
|
-
D"/api/todos/:id"(req,res)
|
|
60
|
-
i:idx=todos.findIndex((t)=>t.id==req.params.id)
|
|
61
|
-
?idx==-1
|
|
62
|
-
>.s 404 {error:"Todo not found"}
|
|
63
|
-
todos.splice(idx,1)
|
|
64
|
-
>{status:"deleted"}
|
package/examples/fullapp.nx
DELETED
|
@@ -1,74 +0,0 @@
|
|
|
1
|
-
-- Full NAIDE-X app with all features
|
|
2
|
-
|
|
3
|
-
db "data/"
|
|
4
|
-
|
|
5
|
-
env:
|
|
6
|
-
PORT int default(3000)
|
|
7
|
-
JWT_SECRET str required
|
|
8
|
-
|
|
9
|
-
schema User:
|
|
10
|
-
id auto
|
|
11
|
-
name str required min(2) max(50)
|
|
12
|
-
email str required email
|
|
13
|
-
password str required
|
|
14
|
-
role str default("user")
|
|
15
|
-
|
|
16
|
-
schema Todo:
|
|
17
|
-
id auto
|
|
18
|
-
title str required min(1)
|
|
19
|
-
done bool default(false)
|
|
20
|
-
created timestamp auto
|
|
21
|
-
|
|
22
|
-
$app:PORT
|
|
23
|
-
cors "*"
|
|
24
|
-
cookie
|
|
25
|
-
auth JWT_SECRET:
|
|
26
|
-
protect "/api/*"
|
|
27
|
-
public "/api/auth/*"
|
|
28
|
-
limit "/api/*" 100 "1m"
|
|
29
|
-
static "/public"
|
|
30
|
-
crud "/api/users" User
|
|
31
|
-
crud "/api/todos" Todo
|
|
32
|
-
|
|
33
|
-
group "/api/v1":
|
|
34
|
-
G"/status"
|
|
35
|
-
>{version:"1.0",status:"ok"}
|
|
36
|
-
|
|
37
|
-
P"/api/auth/register"(req,res)
|
|
38
|
-
s:hashed=hash(req.body.password)
|
|
39
|
-
user=UserStore.create({name:req.body.name,email:req.body.email,password:hashed})
|
|
40
|
-
?user.error
|
|
41
|
-
>.s 400 {errors:user.error}
|
|
42
|
-
token=auth.sign({id:user.id,role:user.role})
|
|
43
|
-
>{token,user:{id:user.id,name:user.name,email:user.email}}
|
|
44
|
-
|
|
45
|
-
P"/api/auth/login"(req,res)
|
|
46
|
-
user=UserStore.where({email:req.body.email})[0]
|
|
47
|
-
?not user
|
|
48
|
-
>.s 401 {error:"Invalid credentials"}
|
|
49
|
-
?not verify(req.body.password,user.password)
|
|
50
|
-
>.s 401 {error:"Invalid credentials"}
|
|
51
|
-
token=auth.sign({id:user.id,role:user.role})
|
|
52
|
-
>{token}
|
|
53
|
-
|
|
54
|
-
G"/health"
|
|
55
|
-
>{status:"ok"}
|
|
56
|
-
|
|
57
|
-
G"/"
|
|
58
|
-
>.h "<h1>Welcome to NAIDE</h1>"
|
|
59
|
-
|
|
60
|
-
ws "/chat":
|
|
61
|
-
on "connect":
|
|
62
|
-
send({type:"welcome"})
|
|
63
|
-
on "message" (data):
|
|
64
|
-
broadcast(data)
|
|
65
|
-
|
|
66
|
-
error (err, req, res):
|
|
67
|
-
log.error err.message
|
|
68
|
-
>.s 500 {error:"Internal server error"}
|
|
69
|
-
|
|
70
|
-
every "30m":
|
|
71
|
-
log"cleanup running"
|
|
72
|
-
|
|
73
|
-
watch User.create (event):
|
|
74
|
-
log"new user: {event.data.name}"
|
package/examples/hello.nx
DELETED
|
@@ -1,29 +0,0 @@
|
|
|
1
|
-
-- NAIDE-X hello world
|
|
2
|
-
|
|
3
|
-
s:name="World"
|
|
4
|
-
i:count=3
|
|
5
|
-
|
|
6
|
-
f greet(s:who)s
|
|
7
|
-
>"Hello, {who}!"
|
|
8
|
-
|
|
9
|
-
@i<0..count
|
|
10
|
-
s:msg=greet(name)
|
|
11
|
-
log msg
|
|
12
|
-
|
|
13
|
-
?count>5
|
|
14
|
-
log"many"
|
|
15
|
-
|count>2
|
|
16
|
-
log"a few"
|
|
17
|
-
:
|
|
18
|
-
log"few"
|
|
19
|
-
|
|
20
|
-
l:items=["apple","banana","cherry"]
|
|
21
|
-
|
|
22
|
-
@fruit<items
|
|
23
|
-
log"I like {fruit}"
|
|
24
|
-
|
|
25
|
-
s:status="ok"
|
|
26
|
-
%status
|
|
27
|
-
"ok": log "All good"
|
|
28
|
-
"error": log "Something went wrong"
|
|
29
|
-
_: log "Unknown"
|
package/examples/server.nx
DELETED
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
-- NAIDE-X REST API server
|
|
2
|
-
|
|
3
|
-
$app:3000
|
|
4
|
-
|
|
5
|
-
G"/"
|
|
6
|
-
>{message:"Welcome to NAIDE-X API"}
|
|
7
|
-
|
|
8
|
-
G"/users"
|
|
9
|
-
l:users=[
|
|
10
|
-
{id:1,name:"Alice",age:30},
|
|
11
|
-
{id:2,name:"Bob",age:25}
|
|
12
|
-
]
|
|
13
|
-
>users
|
|
14
|
-
|
|
15
|
-
G"/users/:id"(req,res)
|
|
16
|
-
s:id=req.params.id
|
|
17
|
-
>{id:id,name:"User {id}"}
|
|
18
|
-
|
|
19
|
-
P"/users"(req,res)
|
|
20
|
-
m:body=req.body
|
|
21
|
-
log"Creating user: {body.name}"
|
|
22
|
-
>{status:"created",user:body}
|
|
23
|
-
|
|
24
|
-
D"/users/:id"(req,res)
|
|
25
|
-
s:id=req.params.id
|
|
26
|
-
log"Deleting user {id}"
|
|
27
|
-
>{status:"deleted",id:id}
|
package/examples/sql-app.nx
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
-- SQLite-backed API (NAIDE-X)
|
|
2
|
-
-- npm install better-sqlite3
|
|
3
|
-
|
|
4
|
-
db.sql "sqlite" "app.db"
|
|
5
|
-
|
|
6
|
-
env:
|
|
7
|
-
PORT int default(3000)
|
|
8
|
-
|
|
9
|
-
schema Task:
|
|
10
|
-
id auto
|
|
11
|
-
title str required min(1) max(200)
|
|
12
|
-
done bool default(false)
|
|
13
|
-
|
|
14
|
-
$app:PORT
|
|
15
|
-
cors "*"
|
|
16
|
-
crud "/api/tasks" Task
|
|
17
|
-
|
|
18
|
-
U"/api/tasks/:id/toggle"(req,res)
|
|
19
|
-
task=TaskStore.getById(req.params.id)
|
|
20
|
-
?not task
|
|
21
|
-
>.s 404 {error:"Not found"}
|
|
22
|
-
updated=TaskStore.update(req.params.id,{done:!task.done})
|
|
23
|
-
>updated
|
package/examples/todo-api.nx
DELETED
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
-- Todo API in NAIDE-X (~80% fewer tokens)
|
|
2
|
-
-- Run: naide examples/todo-api.nx
|
|
3
|
-
|
|
4
|
-
db "data/"
|
|
5
|
-
|
|
6
|
-
env:
|
|
7
|
-
PORT int default(3000)
|
|
8
|
-
|
|
9
|
-
schema Todo:
|
|
10
|
-
id auto
|
|
11
|
-
title str required min(1) max(200)
|
|
12
|
-
done bool default(false)
|
|
13
|
-
created timestamp auto
|
|
14
|
-
|
|
15
|
-
$app:PORT
|
|
16
|
-
cors "*"
|
|
17
|
-
cookie
|
|
18
|
-
cache "/api/todos" "30s"
|
|
19
|
-
validate "/api/todos" Todo
|
|
20
|
-
crud "/api/todos" Todo
|
|
21
|
-
openapi "/docs"
|
|
22
|
-
G"/"
|
|
23
|
-
>.h "<h1>Todo API</h1><p>GET /api/todos | /docs</p>"
|
|
24
|
-
G"/api/stats"(req,res)
|
|
25
|
-
l:all=TodoStore.all()
|
|
26
|
-
i:total=all.length
|
|
27
|
-
i:done=all.filter((t)=>t.done).length
|
|
28
|
-
>{total,done,pending:total-done}
|
|
29
|
-
error (err,req,res):
|
|
30
|
-
log.e err.message
|
|
31
|
-
>.s 500 {error:err.message}
|