@1kbirds/chidori 0.1.21 → 0.1.23
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/Cargo.toml +0 -1
- package/package.json +1 -1
- package/package_node/index.js +57 -23
- package/package_python/chidori.pyi +11 -9
- package/package_python/test_chidori.py +6 -5
- package/src/lib.rs +3 -2
- package/src/translations/mod.rs +2 -1
- package/src/translations/nodejs.rs +286 -771
- package/src/translations/python.rs +261 -306
- package/src/translations/rust.rs +310 -81
- package/src/translations/shared.rs +49 -0
- package/tests/nodejs/chidori.test.js +13 -26
- package/tests/nodejs/nodeHandle.test.js +6 -8
|
@@ -1,10 +1,14 @@
|
|
|
1
1
|
use std::cell::RefCell;
|
|
2
2
|
use std::collections::{HashMap, VecDeque};
|
|
3
|
+
use std::future::Future;
|
|
3
4
|
use std::marker::PhantomData;
|
|
5
|
+
use std::sync::{Arc};
|
|
6
|
+
use tokio::sync::{mpsc, Mutex};
|
|
4
7
|
use anyhow::Error;
|
|
5
8
|
use futures::StreamExt;
|
|
6
9
|
use log::{debug, info};
|
|
7
10
|
use neon::{prelude::*, types::Deferred};
|
|
11
|
+
use neon::handle::Managed;
|
|
8
12
|
use neon::result::Throw;
|
|
9
13
|
use once_cell::sync::OnceCell;
|
|
10
14
|
use tokio::runtime::Runtime;
|
|
@@ -15,7 +19,9 @@ use prompt_graph_core::proto2::execution_runtime_client::ExecutionRuntimeClient;
|
|
|
15
19
|
use prompt_graph_core::proto2::serialized_value::Val;
|
|
16
20
|
use prompt_graph_exec::tonic_runtime::run_server;
|
|
17
21
|
use neon_serde3;
|
|
22
|
+
use prost::bytes::Buf;
|
|
18
23
|
use serde::{Deserialize, Serialize};
|
|
24
|
+
use crate::translations::rust::{Chidori, CustomNodeCreateOpts, DenoCodeNodeCreateOpts, GraphBuilder, Handler, NodeHandle, PromptNodeCreateOpts, VectorMemoryNodeCreateOpts};
|
|
19
25
|
|
|
20
26
|
// Return a global tokio runtime or create one if it doesn't exist.
|
|
21
27
|
// Throws a JavaScript exception if the `Runtime` fails to create.
|
|
@@ -31,25 +37,6 @@ async fn get_client(url: String) -> Result<ExecutionRuntimeClient<tonic::transpo
|
|
|
31
37
|
}
|
|
32
38
|
|
|
33
39
|
|
|
34
|
-
async fn push_file_merge(url: &String, file_id: &String, node: Item) -> anyhow::Result<NodeHandle> {
|
|
35
|
-
let mut client = get_client(url.clone()).await?;
|
|
36
|
-
let exec_status = client.merge(RequestFileMerge {
|
|
37
|
-
id: file_id.clone(),
|
|
38
|
-
file: Some(File {
|
|
39
|
-
nodes: vec![node.clone()],
|
|
40
|
-
..Default::default()
|
|
41
|
-
}),
|
|
42
|
-
branch: 0,
|
|
43
|
-
}).await?.into_inner();
|
|
44
|
-
Ok(NodeHandle::from(
|
|
45
|
-
url.clone(),
|
|
46
|
-
file_id.clone(),
|
|
47
|
-
node,
|
|
48
|
-
exec_status
|
|
49
|
-
)?)
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
|
|
53
40
|
#[derive(Debug)]
|
|
54
41
|
pub struct SerializedValueWrapper(SerializedValue);
|
|
55
42
|
|
|
@@ -116,161 +103,69 @@ fn from_js_value<'a, C: Context<'a>>(cx: &mut C, value: Handle<JsValue>) -> Neon
|
|
|
116
103
|
cx.throw_error("Unsupported type")
|
|
117
104
|
}
|
|
118
105
|
|
|
106
|
+
macro_rules! return_or_throw_deferred {
|
|
107
|
+
($channel:expr, $deferred:expr, $m:expr) => {
|
|
108
|
+
if let Ok(result) = $m {
|
|
109
|
+
$deferred.settle_with($channel, move |mut cx| {
|
|
110
|
+
neon_serde3::to_value(&mut cx, &result)
|
|
111
|
+
.or_else(|e| cx.throw_error(e.to_string()))
|
|
112
|
+
});
|
|
113
|
+
} else {
|
|
114
|
+
$deferred.settle_with($channel, move |mut cx| {
|
|
115
|
+
cx.throw_error("Error playing")
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
};
|
|
119
|
+
}
|
|
120
|
+
|
|
119
121
|
|
|
120
122
|
// Node handle
|
|
121
123
|
#[derive(Clone)]
|
|
122
|
-
pub struct
|
|
123
|
-
|
|
124
|
-
file_id: String,
|
|
125
|
-
node: Item,
|
|
126
|
-
exec_status: ExecutionStatus,
|
|
127
|
-
indiv: CleanIndividualNode
|
|
124
|
+
pub struct NodeNodeHandle {
|
|
125
|
+
n: NodeHandle
|
|
128
126
|
}
|
|
129
127
|
|
|
130
|
-
impl
|
|
131
|
-
fn
|
|
132
|
-
|
|
133
|
-
"Example".to_string(),
|
|
134
|
-
vec![None],
|
|
135
|
-
"type O { output: String }".to_string(),
|
|
136
|
-
SourceNodeType::Code("DENO".to_string(), r#"return {"output": "hello"}"#.to_string(), false),
|
|
137
|
-
vec![],
|
|
138
|
-
);
|
|
139
|
-
let indiv = derive_for_individual_node(&node).unwrap();
|
|
140
|
-
NodeHandle {
|
|
141
|
-
url: "localhost:9800".to_string(),
|
|
142
|
-
file_id: "0".to_string(),
|
|
143
|
-
node: node,
|
|
144
|
-
exec_status: Default::default(),
|
|
145
|
-
indiv,
|
|
146
|
-
}
|
|
147
|
-
}
|
|
148
|
-
|
|
149
|
-
fn from(url: String, file_id: String, node: Item, exec_status: ExecutionStatus) -> anyhow::Result<NodeHandle> {
|
|
150
|
-
let indiv = derive_for_individual_node(&node)?;
|
|
151
|
-
Ok(NodeHandle {
|
|
152
|
-
url,
|
|
153
|
-
file_id,
|
|
154
|
-
node,
|
|
155
|
-
exec_status,
|
|
156
|
-
indiv
|
|
157
|
-
})
|
|
128
|
+
impl NodeNodeHandle {
|
|
129
|
+
fn from(n: NodeHandle) -> NodeNodeHandle {
|
|
130
|
+
NodeNodeHandle{ n }
|
|
158
131
|
}
|
|
159
132
|
}
|
|
160
133
|
|
|
161
|
-
impl Finalize for
|
|
162
|
-
|
|
134
|
+
impl Finalize for NodeNodeHandle {}
|
|
163
135
|
|
|
164
|
-
impl NodeHandle {
|
|
165
|
-
pub fn js_debug_example(mut cx: FunctionContext) -> JsResult<JsBox<RefCell<NodeHandle>>> {
|
|
166
|
-
let nh = NodeHandle::example();
|
|
167
|
-
Ok(cx.boxed(RefCell::new(nh)))
|
|
168
|
-
}
|
|
169
136
|
|
|
137
|
+
impl NodeNodeHandle {
|
|
170
138
|
fn get_name(&self) -> String {
|
|
171
|
-
self.
|
|
139
|
+
self.n.get_name()
|
|
172
140
|
}
|
|
173
141
|
|
|
174
142
|
pub fn run_when(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
175
143
|
let channel = cx.channel();
|
|
176
144
|
let (deferred, promise) = cx.promise();
|
|
177
|
-
let other_node = cx.argument::<JsBox<RefCell<NodeHandle>>>(0)?.downcast_or_throw::<JsBox<RefCell<NodeHandle>>, _>(&mut cx)?;
|
|
178
|
-
|
|
179
|
-
let self_ = cx.this()
|
|
180
|
-
.downcast_or_throw::<JsBox<RefCell<NodeHandle>>, _>(&mut cx)?;
|
|
181
|
-
|
|
182
|
-
let mut self_borrow = self_.borrow_mut();
|
|
183
|
-
let queries = &mut self_borrow.node.core.as_mut().unwrap().queries;
|
|
184
|
-
|
|
185
|
-
// Get the constructed query from the target node
|
|
186
|
-
let q = construct_query_from_output_type(
|
|
187
|
-
&other_node.borrow().get_name(),
|
|
188
|
-
&other_node.borrow().get_name(),
|
|
189
|
-
&self_.borrow().indiv.output_path
|
|
190
|
-
).unwrap();
|
|
191
|
-
|
|
192
|
-
queries.push(Query { query: Some(q)});
|
|
193
|
-
|
|
194
|
-
let url = self_.borrow().url.clone();
|
|
195
|
-
let file_id = self_.borrow().file_id.clone();
|
|
196
|
-
let node = self_.borrow().node.clone();
|
|
197
|
-
let rt = runtime(&mut cx)?;
|
|
198
|
-
rt.spawn(async move {
|
|
199
|
-
let result = push_file_merge(&url, &file_id, node).await.unwrap();
|
|
200
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
201
|
-
Ok(cx.boolean(true))
|
|
202
|
-
});
|
|
203
|
-
});
|
|
204
|
-
Ok(promise)
|
|
205
|
-
}
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
pub fn query(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
209
|
-
let (deferred, promise) = cx.promise();
|
|
210
|
-
let channel = cx.channel();
|
|
211
|
-
|
|
212
|
-
let branch = cx.argument::<JsNumber>(0)?.value(&mut cx) as u64;
|
|
213
|
-
let frame = cx.argument::<JsNumber>(1)?.value(&mut cx) as u64;
|
|
214
|
-
|
|
215
145
|
let self_ = cx.this()
|
|
216
|
-
.downcast_or_throw::<JsBox<RefCell<
|
|
217
|
-
|
|
218
|
-
let
|
|
219
|
-
let
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
let
|
|
223
|
-
|
|
224
|
-
let
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
146
|
+
.downcast_or_throw::<JsBox<RefCell<NodeNodeHandle>>, _>(&mut cx)?;
|
|
147
|
+
|
|
148
|
+
let graph_builder = cx.argument::<JsBox<NodeGraphBuilder>>(0)?;
|
|
149
|
+
let other_node_handle = cx.argument::<JsBox<RefCell<NodeNodeHandle>>>(1)?;
|
|
150
|
+
|
|
151
|
+
let mut n = &mut self_.borrow_mut().n;
|
|
152
|
+
let g = &graph_builder.g;
|
|
153
|
+
let mut graph_builder = g.blocking_lock();
|
|
154
|
+
let other_node = &other_node_handle.borrow().n;
|
|
155
|
+
let m = n.run_when(&mut graph_builder, &other_node);
|
|
156
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
157
|
+
if let Ok(result) = m {
|
|
158
|
+
Ok(cx.boolean(result))
|
|
228
159
|
} else {
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
Ok(cx.undefined())
|
|
232
|
-
});
|
|
233
|
-
panic!("Failed to connect to runtime service.");
|
|
234
|
-
};
|
|
235
|
-
let result = client.run_query(QueryAtFrame {
|
|
236
|
-
id: file_id,
|
|
237
|
-
query: Some(Query {
|
|
238
|
-
query: Some(query)
|
|
239
|
-
}),
|
|
240
|
-
frame,
|
|
241
|
-
branch,
|
|
242
|
-
}).await;
|
|
243
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
244
|
-
if let Ok(result) = result {
|
|
245
|
-
let res = result.into_inner();
|
|
246
|
-
let mut obj = cx.empty_object();
|
|
247
|
-
for value in res.values.iter() {
|
|
248
|
-
let c = value.change_value.as_ref().unwrap();
|
|
249
|
-
let k = c.path.as_ref().unwrap().address.join(":");
|
|
250
|
-
let v = c.value.as_ref().unwrap().clone();
|
|
251
|
-
let js = SerializedValueWrapper(v).to_object(&mut cx);
|
|
252
|
-
obj.set(&mut cx, k.as_str(), js?).unwrap();
|
|
253
|
-
}
|
|
254
|
-
Ok(obj)
|
|
255
|
-
} else {
|
|
256
|
-
cx.throw_error("Failed to query")
|
|
257
|
-
}
|
|
258
|
-
});
|
|
160
|
+
cx.throw_error("Error playing")
|
|
161
|
+
}
|
|
259
162
|
});
|
|
260
163
|
Ok(promise)
|
|
261
|
-
}
|
|
262
164
|
|
|
165
|
+
}
|
|
263
166
|
|
|
264
|
-
// fn
|
|
265
|
-
// let branch = cx.argument::<JsString>(0)?.value(&mut cx);
|
|
266
|
-
// let frame = cx.argument::<JsString>(1)?.value(&mut cx);
|
|
167
|
+
// pub fn query(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
267
168
|
//
|
|
268
|
-
// let channel = cx.channel();
|
|
269
|
-
//
|
|
270
|
-
// // let name = self.get_name();
|
|
271
|
-
// Ok(format!("NodeHandle(file_id={}, node={})", self.file_id, name))
|
|
272
|
-
// //
|
|
273
|
-
// // Ok(cx.undefined())
|
|
274
169
|
// }
|
|
275
170
|
}
|
|
276
171
|
|
|
@@ -305,64 +200,15 @@ fn obj_to_paths<'a, C: Context<'a>>(cx: &mut C, d: Handle<JsObject>) -> NeonResu
|
|
|
305
200
|
Ok(paths)
|
|
306
201
|
}
|
|
307
202
|
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
#[derive(serde::Serialize, serde::Deserialize)]
|
|
312
|
-
struct PromptNodeCreateOpts {
|
|
313
|
-
name: String,
|
|
314
|
-
queries: Option<Vec<String>>,
|
|
315
|
-
output_tables: Option<Vec<String>>,
|
|
316
|
-
template: String,
|
|
317
|
-
model: Option<String>
|
|
203
|
+
struct NodeChidori {
|
|
204
|
+
c: Arc<Mutex<Chidori>>
|
|
318
205
|
}
|
|
319
206
|
|
|
207
|
+
impl Finalize for NodeChidori {}
|
|
320
208
|
|
|
321
|
-
|
|
322
|
-
struct CustomNodeCreateOpts {
|
|
323
|
-
name: String,
|
|
324
|
-
queries: Option<Vec<String>>,
|
|
325
|
-
output_tables: Option<Vec<String>>,
|
|
326
|
-
output: Option<String>,
|
|
327
|
-
node_type_name: String
|
|
328
|
-
}
|
|
209
|
+
impl NodeChidori {
|
|
329
210
|
|
|
330
|
-
|
|
331
|
-
struct DenoCodeNodeCreateOpts {
|
|
332
|
-
name: String,
|
|
333
|
-
queries: Option<Vec<String>>,
|
|
334
|
-
output_tables: Option<Vec<String>>,
|
|
335
|
-
output: Option<String>,
|
|
336
|
-
code: String,
|
|
337
|
-
is_template: Option<bool>
|
|
338
|
-
}
|
|
339
|
-
|
|
340
|
-
#[derive(serde::Serialize, serde::Deserialize)]
|
|
341
|
-
struct VectorMemoryNodeCreateOpts {
|
|
342
|
-
name: String,
|
|
343
|
-
queries: Option<Vec<String>>,
|
|
344
|
-
output_tables: Option<Vec<String>>,
|
|
345
|
-
output: Option<String>,
|
|
346
|
-
template: Option<String>, // TODO: default is the contents of the query
|
|
347
|
-
action: Option<String>, // TODO: default WRITE
|
|
348
|
-
embedding_model: Option<String>, // TODO: default TEXT_EMBEDDING_ADA_002
|
|
349
|
-
db_vendor: Option<String>, // TODO: default QDRANT
|
|
350
|
-
collection_name: String,
|
|
351
|
-
}
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
struct Chidori {
|
|
355
|
-
file_id: String,
|
|
356
|
-
current_head: u64,
|
|
357
|
-
current_branch: u64,
|
|
358
|
-
url: String
|
|
359
|
-
}
|
|
360
|
-
|
|
361
|
-
impl Finalize for Chidori {}
|
|
362
|
-
|
|
363
|
-
impl Chidori {
|
|
364
|
-
|
|
365
|
-
fn js_new(mut cx: FunctionContext) -> JsResult<JsBox<Chidori>> {
|
|
211
|
+
fn js_new(mut cx: FunctionContext) -> JsResult<JsBox<NodeChidori>> {
|
|
366
212
|
let file_id = cx.argument::<JsString>(0)?.value(&mut cx);
|
|
367
213
|
let url = cx.argument::<JsString>(1)?.value(&mut cx);
|
|
368
214
|
|
|
@@ -371,55 +217,29 @@ impl Chidori {
|
|
|
371
217
|
}
|
|
372
218
|
// let api_token = cx.argument_opt(2)?.value(&mut cx);
|
|
373
219
|
debug!("Creating new Chidori instance with file_id={}, url={}, api_token={:?}", file_id, url, "".to_string());
|
|
374
|
-
Ok(cx.boxed(
|
|
375
|
-
file_id,
|
|
376
|
-
current_head: 0,
|
|
377
|
-
current_branch: 0,
|
|
378
|
-
url,
|
|
220
|
+
Ok(cx.boxed(NodeChidori {
|
|
221
|
+
c: Arc::new(Mutex::new(Chidori::new(file_id, url))),
|
|
379
222
|
}))
|
|
380
223
|
}
|
|
381
224
|
|
|
382
225
|
fn start_server(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
383
226
|
let channel = cx.channel();
|
|
384
227
|
let self_ = cx.this()
|
|
385
|
-
.downcast_or_throw::<JsBox<
|
|
228
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
386
229
|
let (deferred, promise) = cx.promise();
|
|
387
|
-
let
|
|
388
|
-
let
|
|
389
|
-
Some(v) => Some(v.downcast_or_throw(&mut cx)),
|
|
390
|
-
None => None,
|
|
391
|
-
}.map(|p: JsResult<JsString>| p.unwrap().value(&mut cx));
|
|
392
|
-
std::thread::spawn(move || {
|
|
393
|
-
let result = run_server(url_server, file_path);
|
|
394
|
-
match result {
|
|
395
|
-
Ok(_) => {
|
|
396
|
-
println!("Server exited");
|
|
397
|
-
},
|
|
398
|
-
Err(e) => {
|
|
399
|
-
println!("Error running server: {}", e);
|
|
400
|
-
},
|
|
401
|
-
}
|
|
402
|
-
});
|
|
403
|
-
|
|
404
|
-
let url = self_.url.clone();
|
|
230
|
+
let file_path = cx.argument_opt(0).map(|x| x.downcast::<JsString, _>(&mut cx).unwrap().value(&mut cx));
|
|
231
|
+
let c = Arc::clone(&self_.c);
|
|
405
232
|
let rt = runtime(&mut cx)?;
|
|
406
233
|
rt.spawn(async move {
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
});
|
|
415
|
-
break 'retry
|
|
416
|
-
},
|
|
417
|
-
Err(e) => {
|
|
418
|
-
eprintln!("Error connecting to server: {} with Error {}. Retrying...", &url, &e.to_string());
|
|
419
|
-
std::thread::sleep(std::time::Duration::from_millis(1000));
|
|
420
|
-
}
|
|
234
|
+
let mut c = c.lock().await;
|
|
235
|
+
let m = c.start_server(file_path).await;
|
|
236
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
237
|
+
if let Ok(_) = m {
|
|
238
|
+
Ok(cx.undefined())
|
|
239
|
+
} else {
|
|
240
|
+
cx.throw_error("Error playing")
|
|
421
241
|
}
|
|
422
|
-
}
|
|
242
|
+
});
|
|
423
243
|
});
|
|
424
244
|
Ok(promise)
|
|
425
245
|
}
|
|
@@ -428,73 +248,44 @@ impl Chidori {
|
|
|
428
248
|
let channel = cx.channel();
|
|
429
249
|
let (deferred, promise) = cx.promise();
|
|
430
250
|
let self_ = cx.this()
|
|
431
|
-
.downcast_or_throw::<JsBox<
|
|
251
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
432
252
|
let branch = cx.argument::<JsNumber>(0).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
433
253
|
let frame = cx.argument::<JsNumber>(1).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
434
|
-
|
|
435
|
-
let file_id = self_.file_id.clone();
|
|
436
|
-
let url = self_.url.clone();
|
|
437
|
-
|
|
254
|
+
let c = Arc::clone(&self_.c);
|
|
438
255
|
let rt = runtime(&mut cx)?;
|
|
439
256
|
rt.spawn(async move {
|
|
440
|
-
let
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
cx
|
|
445
|
-
Ok(cx.undefined())
|
|
446
|
-
});
|
|
447
|
-
panic!("Failed to connect to runtime service.");
|
|
448
|
-
};
|
|
449
|
-
let result = client.play(RequestAtFrame {
|
|
450
|
-
id: file_id,
|
|
451
|
-
frame,
|
|
452
|
-
branch,
|
|
453
|
-
}).await;
|
|
454
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
455
|
-
if let Ok(result) = result {
|
|
456
|
-
neon_serde3::to_value(&mut cx, &result.into_inner())
|
|
257
|
+
let c = c.lock().await;
|
|
258
|
+
let m = c.play(branch, frame).await;
|
|
259
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
260
|
+
if let Ok(result) = m {
|
|
261
|
+
neon_serde3::to_value(&mut cx, &result)
|
|
457
262
|
.or_else(|e| cx.throw_error(e.to_string()))
|
|
458
263
|
} else {
|
|
459
|
-
cx.throw_error("
|
|
264
|
+
cx.throw_error("Error playing")
|
|
460
265
|
}
|
|
461
266
|
});
|
|
462
267
|
});
|
|
463
268
|
Ok(promise)
|
|
269
|
+
|
|
464
270
|
}
|
|
465
271
|
|
|
466
272
|
fn pause(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
467
273
|
let channel = cx.channel();
|
|
468
274
|
let (deferred, promise) = cx.promise();
|
|
469
275
|
let self_ = cx.this()
|
|
470
|
-
.downcast_or_throw::<JsBox<
|
|
276
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
471
277
|
let frame = cx.argument::<JsNumber>(0).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
472
|
-
let
|
|
473
|
-
let url = self_.url.clone();
|
|
474
|
-
let branch = self_.current_branch.clone();
|
|
475
|
-
|
|
278
|
+
let c = Arc::clone(&self_.c);
|
|
476
279
|
let rt = runtime(&mut cx)?;
|
|
477
280
|
rt.spawn(async move {
|
|
478
|
-
let
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
cx
|
|
483
|
-
Ok(cx.undefined())
|
|
484
|
-
});
|
|
485
|
-
panic!("Failed to connect to runtime service.");
|
|
486
|
-
};
|
|
487
|
-
let result = client.pause(RequestAtFrame {
|
|
488
|
-
id: file_id,
|
|
489
|
-
frame,
|
|
490
|
-
branch,
|
|
491
|
-
}).await;
|
|
492
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
493
|
-
if let Ok(result) = result {
|
|
494
|
-
neon_serde3::to_value(&mut cx, &result.into_inner())
|
|
281
|
+
let c = c.lock().await;
|
|
282
|
+
let m = c.pause(frame).await;
|
|
283
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
284
|
+
if let Ok(result) = m {
|
|
285
|
+
neon_serde3::to_value(&mut cx, &result)
|
|
495
286
|
.or_else(|e| cx.throw_error(e.to_string()))
|
|
496
287
|
} else {
|
|
497
|
-
cx.throw_error("
|
|
288
|
+
cx.throw_error("Error playing")
|
|
498
289
|
}
|
|
499
290
|
});
|
|
500
291
|
});
|
|
@@ -505,33 +296,20 @@ impl Chidori {
|
|
|
505
296
|
let channel = cx.channel();
|
|
506
297
|
let (deferred, promise) = cx.promise();
|
|
507
298
|
let self_ = cx.this()
|
|
508
|
-
.downcast_or_throw::<JsBox<
|
|
509
|
-
let
|
|
510
|
-
let
|
|
511
|
-
let
|
|
299
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
300
|
+
let branch = cx.argument::<JsNumber>(0).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
301
|
+
let frame = cx.argument::<JsNumber>(1).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
302
|
+
let c = Arc::clone(&self_.c);
|
|
512
303
|
let rt = runtime(&mut cx)?;
|
|
513
304
|
rt.spawn(async move {
|
|
514
|
-
let
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
cx
|
|
519
|
-
Ok(cx.undefined())
|
|
520
|
-
});
|
|
521
|
-
panic!("Failed to connect to runtime service.");
|
|
522
|
-
};
|
|
523
|
-
let result = client.branch(RequestNewBranch {
|
|
524
|
-
id: file_id,
|
|
525
|
-
source_branch_id: branch,
|
|
526
|
-
diverges_at_counter: 0,
|
|
527
|
-
}).await;
|
|
528
|
-
// TODO: need to somehow handle writing to the current_branch
|
|
529
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
530
|
-
if let Ok(result) = result {
|
|
531
|
-
neon_serde3::to_value(&mut cx, &result.into_inner())
|
|
305
|
+
let c = c.lock().await;
|
|
306
|
+
let m = c.branch(branch, frame).await;
|
|
307
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
308
|
+
if let Ok(result) = m {
|
|
309
|
+
neon_serde3::to_value(&mut cx, &result)
|
|
532
310
|
.or_else(|e| cx.throw_error(e.to_string()))
|
|
533
311
|
} else {
|
|
534
|
-
cx.throw_error("
|
|
312
|
+
cx.throw_error("Error playing")
|
|
535
313
|
}
|
|
536
314
|
});
|
|
537
315
|
});
|
|
@@ -542,37 +320,22 @@ impl Chidori {
|
|
|
542
320
|
let channel = cx.channel();
|
|
543
321
|
let (deferred, promise) = cx.promise();
|
|
544
322
|
let self_ = cx.this()
|
|
545
|
-
.downcast_or_throw::<JsBox<
|
|
323
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
546
324
|
let query = cx.argument::<JsString>(0).unwrap_or(JsString::new(&mut cx, "")).value(&mut cx);
|
|
547
325
|
let branch = cx.argument::<JsNumber>(1).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
548
326
|
let frame = cx.argument::<JsNumber>(2).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
549
|
-
|
|
550
|
-
let
|
|
327
|
+
|
|
328
|
+
let c = Arc::clone(&self_.c);
|
|
551
329
|
let rt = runtime(&mut cx)?;
|
|
552
330
|
rt.spawn(async move {
|
|
553
|
-
let
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
cx
|
|
558
|
-
Ok(cx.undefined())
|
|
559
|
-
});
|
|
560
|
-
panic!("Failed to connect to runtime service.");
|
|
561
|
-
};
|
|
562
|
-
let result = client.run_query(QueryAtFrame {
|
|
563
|
-
id: file_id,
|
|
564
|
-
query: Some(Query {
|
|
565
|
-
query: Some(query)
|
|
566
|
-
}),
|
|
567
|
-
frame,
|
|
568
|
-
branch,
|
|
569
|
-
}).await;
|
|
570
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
571
|
-
if let Ok(result) = result {
|
|
572
|
-
neon_serde3::to_value(&mut cx, &result.into_inner())
|
|
331
|
+
let c = c.lock().await;
|
|
332
|
+
let m = c.query(query, branch, frame).await;
|
|
333
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
334
|
+
if let Ok(result) = m {
|
|
335
|
+
neon_serde3::to_value(&mut cx, &result)
|
|
573
336
|
.or_else(|e| cx.throw_error(e.to_string()))
|
|
574
337
|
} else {
|
|
575
|
-
cx.throw_error("
|
|
338
|
+
cx.throw_error("Error playing")
|
|
576
339
|
}
|
|
577
340
|
});
|
|
578
341
|
});
|
|
@@ -583,29 +346,18 @@ impl Chidori {
|
|
|
583
346
|
let channel = cx.channel();
|
|
584
347
|
let (deferred, promise) = cx.promise();
|
|
585
348
|
let self_ = cx.this()
|
|
586
|
-
.downcast_or_throw::<JsBox<
|
|
587
|
-
let
|
|
588
|
-
let url = self_.url.clone();
|
|
349
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
350
|
+
let c = Arc::clone(&self_.c);
|
|
589
351
|
let rt = runtime(&mut cx)?;
|
|
590
352
|
rt.spawn(async move {
|
|
591
|
-
let
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
cx
|
|
596
|
-
Ok(cx.undefined())
|
|
597
|
-
});
|
|
598
|
-
panic!("Failed to connect to runtime service.");
|
|
599
|
-
};
|
|
600
|
-
let result = client.list_branches(RequestListBranches {
|
|
601
|
-
id: file_id,
|
|
602
|
-
}).await;
|
|
603
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
604
|
-
if let Ok(result) = result {
|
|
605
|
-
neon_serde3::to_value(&mut cx, &result.into_inner())
|
|
353
|
+
let c = c.lock().await;
|
|
354
|
+
let m = c.list_branches().await;
|
|
355
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
356
|
+
if let Ok(result) = m {
|
|
357
|
+
neon_serde3::to_value(&mut cx, &result)
|
|
606
358
|
.or_else(|e| cx.throw_error(e.to_string()))
|
|
607
359
|
} else {
|
|
608
|
-
cx.throw_error("
|
|
360
|
+
cx.throw_error("Error playing")
|
|
609
361
|
}
|
|
610
362
|
});
|
|
611
363
|
});
|
|
@@ -616,82 +368,34 @@ impl Chidori {
|
|
|
616
368
|
let channel = cx.channel();
|
|
617
369
|
let (deferred, promise) = cx.promise();
|
|
618
370
|
let self_ = cx.this()
|
|
619
|
-
.downcast_or_throw::<JsBox<
|
|
620
|
-
let
|
|
621
|
-
let
|
|
622
|
-
let branch = self_.current_branch.clone();
|
|
371
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
372
|
+
let branch = cx.argument::<JsNumber>(0).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
373
|
+
let c = Arc::clone(&self_.c);
|
|
623
374
|
let rt = runtime(&mut cx)?;
|
|
624
375
|
rt.spawn(async move {
|
|
625
|
-
let
|
|
626
|
-
|
|
627
|
-
} else {
|
|
628
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
629
|
-
cx.throw_error::<&str, JsUndefined>("Failed to connect to runtime service.");
|
|
630
|
-
Ok(cx.undefined())
|
|
631
|
-
});
|
|
632
|
-
panic!("Failed to connect to runtime service.");
|
|
633
|
-
};
|
|
634
|
-
let file = if let Ok(file) = client.current_file_state(RequestOnlyId {
|
|
635
|
-
id: file_id,
|
|
636
|
-
branch
|
|
637
|
-
}).await {
|
|
638
|
-
file
|
|
639
|
-
} else {
|
|
640
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
641
|
-
cx.throw_error::<&str, JsUndefined>("Failed to get current file state.");
|
|
642
|
-
Ok(cx.undefined())
|
|
643
|
-
});
|
|
644
|
-
panic!("Failed to get current file state.");
|
|
645
|
-
};
|
|
646
|
-
let mut file = file.into_inner();
|
|
647
|
-
let mut g = CleanedDefinitionGraph::zero();
|
|
648
|
-
g.merge_file(&mut file).unwrap();
|
|
376
|
+
let c = c.lock().await;
|
|
377
|
+
let r= c.display_graph_structure(branch).await;
|
|
649
378
|
deferred.settle_with(&channel, move |mut cx| {
|
|
650
|
-
Ok(
|
|
379
|
+
if let Ok(r) = r {
|
|
380
|
+
Ok(cx.string(r))
|
|
381
|
+
} else {
|
|
382
|
+
cx.throw_error("Error displaying graph structure")
|
|
383
|
+
}
|
|
651
384
|
});
|
|
652
385
|
});
|
|
653
386
|
Ok(promise)
|
|
654
387
|
}
|
|
655
388
|
|
|
656
|
-
//
|
|
657
|
-
// // TODO: some of these register handlers instead
|
|
658
|
-
// // TODO: list registered graphs should not stream
|
|
659
|
-
// // TODO: add a message that sends the current graph state
|
|
660
|
-
//
|
|
661
|
-
|
|
662
389
|
fn list_registered_graphs(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
663
390
|
let channel = cx.channel();
|
|
664
391
|
let (deferred, promise) = cx.promise();
|
|
665
392
|
let self_ = cx.this()
|
|
666
|
-
.downcast_or_throw::<JsBox<
|
|
667
|
-
let
|
|
668
|
-
let url = self_.url.clone();
|
|
393
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
394
|
+
let c = Arc::clone(&self_.c);
|
|
669
395
|
let rt = runtime(&mut cx)?;
|
|
670
396
|
rt.spawn(async move {
|
|
671
|
-
let
|
|
672
|
-
|
|
673
|
-
} else {
|
|
674
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
675
|
-
cx.throw_error::<&str, JsUndefined>("Failed to connect to runtime service.");
|
|
676
|
-
Ok(cx.undefined())
|
|
677
|
-
});
|
|
678
|
-
panic!("Failed to connect to runtime service.");
|
|
679
|
-
};
|
|
680
|
-
let resp = if let Ok(resp) = client.list_registered_graphs(Empty {
|
|
681
|
-
}).await {
|
|
682
|
-
resp
|
|
683
|
-
} else {
|
|
684
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
685
|
-
cx.throw_error::<&str, JsUndefined>("Failed to get registered graph stream.");
|
|
686
|
-
Ok(cx.undefined())
|
|
687
|
-
});
|
|
688
|
-
panic!("Failed to get registered graph stream.");
|
|
689
|
-
};
|
|
690
|
-
let mut stream = resp.into_inner();
|
|
691
|
-
while let Some(x) = stream.next().await {
|
|
692
|
-
// callback.call(py, (x,), None);
|
|
693
|
-
info!("Registered Graph = {:?}", x);
|
|
694
|
-
};
|
|
397
|
+
let c = c.lock().await;
|
|
398
|
+
let _ = c.list_registered_graphs().await;
|
|
695
399
|
deferred.settle_with(&channel, move |mut cx| {
|
|
696
400
|
Ok(cx.undefined())
|
|
697
401
|
});
|
|
@@ -753,6 +457,100 @@ impl Chidori {
|
|
|
753
457
|
// // }
|
|
754
458
|
//
|
|
755
459
|
//
|
|
460
|
+
|
|
461
|
+
|
|
462
|
+
|
|
463
|
+
fn register_custom_node_handle(mut cx: FunctionContext) -> JsResult<JsValue> {
|
|
464
|
+
let channel = cx.channel();
|
|
465
|
+
let self_ = cx.this()
|
|
466
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
467
|
+
|
|
468
|
+
let function_name: String = cx.argument::<JsString>(0)?.value(&mut cx);
|
|
469
|
+
let callback = cx.argument::<JsFunction>(1)?.root(&mut cx);
|
|
470
|
+
|
|
471
|
+
let h = callback.to_inner(&mut cx);
|
|
472
|
+
let callback = Arc::new(callback);
|
|
473
|
+
let c = Arc::clone(&self_.c);
|
|
474
|
+
|
|
475
|
+
let rt = runtime(&mut cx)?;
|
|
476
|
+
rt.spawn(async move {
|
|
477
|
+
let mut c = c.lock().await;
|
|
478
|
+
c.register_custom_node_handle(function_name, Handler::new(
|
|
479
|
+
move |n| {
|
|
480
|
+
let channel_clone = channel.clone();
|
|
481
|
+
let handler_clone = Arc::clone(&callback);
|
|
482
|
+
Box::pin(async move {
|
|
483
|
+
// TODO: clean this up, can't use ?
|
|
484
|
+
let (tx, mut rx) = mpsc::channel::<serde_json::Value>(1);
|
|
485
|
+
if let Ok(_) = channel_clone.send(move |mut cx| {
|
|
486
|
+
if let Ok(v) = neon_serde3::to_value(&mut cx, &n) {
|
|
487
|
+
let js_function = JsFunction::new(&mut cx, move |mut cx| {
|
|
488
|
+
if let Ok(v) = cx.argument::<JsValue>(0) {
|
|
489
|
+
let value: Result<serde_json::Value, _> = neon_serde3::from_value(&mut cx, v);
|
|
490
|
+
if let Ok(value) = value {
|
|
491
|
+
tx.blocking_send(value).unwrap();
|
|
492
|
+
}
|
|
493
|
+
}
|
|
494
|
+
Ok(cx.undefined())
|
|
495
|
+
})?;
|
|
496
|
+
let callback = handler_clone.to_inner(&mut cx);
|
|
497
|
+
let _: JsResult<JsValue> = callback.call_with(&mut cx).arg(v).arg(js_function).apply(&mut cx);
|
|
498
|
+
}
|
|
499
|
+
Ok(serde_json::Value::Null)
|
|
500
|
+
}).join() {
|
|
501
|
+
// block until we receive the result from the channel
|
|
502
|
+
if let Some(value) = rx.recv().await {
|
|
503
|
+
Ok(value)
|
|
504
|
+
} else {
|
|
505
|
+
Ok(serde_json::Value::Null)
|
|
506
|
+
}
|
|
507
|
+
} else {
|
|
508
|
+
Err(anyhow::anyhow!("Failed to send result"))
|
|
509
|
+
}
|
|
510
|
+
})
|
|
511
|
+
}
|
|
512
|
+
));
|
|
513
|
+
});
|
|
514
|
+
Ok(cx.undefined().upcast())
|
|
515
|
+
}
|
|
516
|
+
|
|
517
|
+
|
|
518
|
+
fn run_custom_node_loop(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
519
|
+
let channel = cx.channel();
|
|
520
|
+
let (deferred, promise) = cx.promise();
|
|
521
|
+
let self_ = cx.this()
|
|
522
|
+
.downcast_or_throw::<JsBox<NodeChidori>, _>(&mut cx)?;
|
|
523
|
+
let c = Arc::clone(&self_.c);
|
|
524
|
+
let rt = runtime(&mut cx)?;
|
|
525
|
+
rt.spawn(async move {
|
|
526
|
+
let mut c = c.lock().await;
|
|
527
|
+
let _ = c.run_custom_node_loop().await;
|
|
528
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
529
|
+
Ok(cx.undefined())
|
|
530
|
+
});
|
|
531
|
+
|
|
532
|
+
});
|
|
533
|
+
// This promise is never resolved
|
|
534
|
+
Ok(promise)
|
|
535
|
+
}
|
|
536
|
+
|
|
537
|
+
|
|
538
|
+
|
|
539
|
+
}
|
|
540
|
+
|
|
541
|
+
struct NodeGraphBuilder {
|
|
542
|
+
g: Arc<Mutex<GraphBuilder>>,
|
|
543
|
+
}
|
|
544
|
+
|
|
545
|
+
impl Finalize for NodeGraphBuilder {}
|
|
546
|
+
|
|
547
|
+
impl NodeGraphBuilder {
|
|
548
|
+
fn js_new(mut cx: FunctionContext) -> JsResult<JsBox<NodeGraphBuilder>> {
|
|
549
|
+
Ok(cx.boxed(NodeGraphBuilder {
|
|
550
|
+
g: Arc::new(Mutex::new(GraphBuilder::new())),
|
|
551
|
+
}))
|
|
552
|
+
}
|
|
553
|
+
|
|
756
554
|
// // TODO: need to figure out passing a buffer of bytes
|
|
757
555
|
// // TODO: nodes that are added should return a clean definition of what their addition looks like
|
|
758
556
|
// // TODO: adding a node should also display any errors
|
|
@@ -789,12 +587,9 @@ impl Chidori {
|
|
|
789
587
|
// // TODO: adding a node should also display any errors
|
|
790
588
|
|
|
791
589
|
|
|
792
|
-
fn prompt_node(mut cx: FunctionContext) -> JsResult<
|
|
793
|
-
let channel = cx.channel();
|
|
794
|
-
let (deferred, promise) = cx.promise();
|
|
590
|
+
fn prompt_node(mut cx: FunctionContext) -> JsResult<JsBox<RefCell<NodeNodeHandle>>> {
|
|
795
591
|
let self_ = cx.this()
|
|
796
|
-
.downcast_or_throw::<JsBox<
|
|
797
|
-
|
|
592
|
+
.downcast_or_throw::<JsBox<NodeGraphBuilder>, _>(&mut cx)?;
|
|
798
593
|
let arg0 = cx.argument::<JsValue>(0)?;
|
|
799
594
|
let arg0_value: PromptNodeCreateOpts = match neon_serde3::from_value(&mut cx, arg0) {
|
|
800
595
|
Ok(value) => value,
|
|
@@ -802,208 +597,17 @@ impl Chidori {
|
|
|
802
597
|
return cx.throw_error(e.to_string());
|
|
803
598
|
}
|
|
804
599
|
};
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
} else {
|
|
811
|
-
Some(q)
|
|
812
|
-
}
|
|
813
|
-
}).collect()
|
|
814
|
-
} else {
|
|
815
|
-
vec![None]
|
|
816
|
-
};
|
|
817
|
-
|
|
818
|
-
let file_id = self_.file_id.clone();
|
|
819
|
-
let url = self_.url.clone();
|
|
820
|
-
let rt = runtime(&mut cx)?;
|
|
821
|
-
rt.spawn(async move {
|
|
822
|
-
let prompt_node = create_prompt_node(
|
|
823
|
-
arg0_value.name,
|
|
824
|
-
queries,
|
|
825
|
-
arg0_value.template,
|
|
826
|
-
arg0_value.model.unwrap_or("GPT_3_5_TURBO".to_string()),
|
|
827
|
-
arg0_value.output_tables.unwrap_or(vec![]));
|
|
828
|
-
let node = if let Ok(node) = prompt_node {
|
|
829
|
-
node
|
|
830
|
-
} else {
|
|
831
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
832
|
-
// TODO: throw error
|
|
833
|
-
Ok(cx.undefined())
|
|
834
|
-
});
|
|
835
|
-
panic!("Failed to connect to runtime service.");
|
|
836
|
-
};
|
|
837
|
-
|
|
838
|
-
if let Ok(result ) = push_file_merge(&url, &file_id, node).await {
|
|
839
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
840
|
-
Ok(cx.boxed(RefCell::new(result)))
|
|
841
|
-
});
|
|
842
|
-
} else {
|
|
843
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
844
|
-
// TODO: throw error
|
|
845
|
-
Ok(cx.undefined())
|
|
846
|
-
});
|
|
847
|
-
panic!("Failed to connect to runtime service.");
|
|
848
|
-
};
|
|
849
|
-
});
|
|
850
|
-
Ok(promise)
|
|
600
|
+
let mut g = self_.g.blocking_lock();
|
|
601
|
+
match g.prompt_node(arg0_value) {
|
|
602
|
+
Ok(result) => Ok(cx.boxed(RefCell::new(NodeNodeHandle::from(result)))),
|
|
603
|
+
Err(e) => cx.throw_error(e.to_string())
|
|
604
|
+
}
|
|
851
605
|
}
|
|
852
606
|
|
|
853
607
|
|
|
854
|
-
fn
|
|
855
|
-
let channel = cx.channel();
|
|
856
|
-
let (deferred, promise) = cx.promise();
|
|
608
|
+
fn custom_node(mut cx: FunctionContext) -> JsResult<JsBox<RefCell<NodeNodeHandle>>> {
|
|
857
609
|
let self_ = cx.this()
|
|
858
|
-
.downcast_or_throw::<JsBox<
|
|
859
|
-
let file_id = self_.file_id.clone();
|
|
860
|
-
let url = self_.url.clone();
|
|
861
|
-
|
|
862
|
-
let rt = runtime(&mut cx)?;
|
|
863
|
-
rt.spawn(async move {
|
|
864
|
-
let mut client = if let Ok(mut client) = get_client(url).await {
|
|
865
|
-
client
|
|
866
|
-
} else {
|
|
867
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
868
|
-
cx.throw_error::<&str, JsUndefined>("Failed to connect to runtime service.");
|
|
869
|
-
Ok(cx.undefined())
|
|
870
|
-
});
|
|
871
|
-
panic!("Failed to connect to runtime service.");
|
|
872
|
-
};
|
|
873
|
-
if let Ok(result) = client.poll_node_will_execute_events(FilteredPollNodeWillExecuteEventsRequest {
|
|
874
|
-
id: file_id.clone(),
|
|
875
|
-
}).await {
|
|
876
|
-
debug!("poll_local_code_node_execution result = {:?}", result);
|
|
877
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
878
|
-
neon_serde3::to_value(&mut cx, &result.into_inner())
|
|
879
|
-
.or_else(|e| cx.throw_error(e.to_string()))
|
|
880
|
-
});
|
|
881
|
-
} else {
|
|
882
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
883
|
-
// TODO: throw error
|
|
884
|
-
Ok(cx.undefined())
|
|
885
|
-
});
|
|
886
|
-
};
|
|
887
|
-
});
|
|
888
|
-
Ok(promise)
|
|
889
|
-
}
|
|
890
|
-
fn ack_local_code_node_execution(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
891
|
-
let channel = cx.channel();
|
|
892
|
-
let (deferred, promise) = cx.promise();
|
|
893
|
-
let self_ = cx.this()
|
|
894
|
-
.downcast_or_throw::<JsBox<Chidori>, _>(&mut cx)?;
|
|
895
|
-
let file_id = self_.file_id.clone();
|
|
896
|
-
let url = self_.url.clone();
|
|
897
|
-
let branch = cx.argument::<JsNumber>(0)?.value(&mut cx) as u64;
|
|
898
|
-
let counter = cx.argument::<JsNumber>(1)?.value(&mut cx) as u64;
|
|
899
|
-
let rt = runtime(&mut cx)?;
|
|
900
|
-
rt.spawn(async move {
|
|
901
|
-
let mut client = if let Ok(mut client) = get_client(url).await {
|
|
902
|
-
client
|
|
903
|
-
} else {
|
|
904
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
905
|
-
cx.throw_error::<&str, JsUndefined>("Failed to connect to runtime service.");
|
|
906
|
-
Ok(cx.undefined())
|
|
907
|
-
});
|
|
908
|
-
panic!("Failed to connect to runtime service.");
|
|
909
|
-
};
|
|
910
|
-
if let Ok(result) = client.ack_node_will_execute_event(RequestAckNodeWillExecuteEvent {
|
|
911
|
-
id: file_id.clone(),
|
|
912
|
-
branch,
|
|
913
|
-
counter,
|
|
914
|
-
}).await {
|
|
915
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
916
|
-
neon_serde3::to_value(&mut cx, &result.into_inner())
|
|
917
|
-
.or_else(|e| cx.throw_error(e.to_string()))
|
|
918
|
-
});
|
|
919
|
-
} else {
|
|
920
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
921
|
-
// TODO: throw error
|
|
922
|
-
Ok(cx.undefined())
|
|
923
|
-
});
|
|
924
|
-
}
|
|
925
|
-
});
|
|
926
|
-
Ok(promise)
|
|
927
|
-
}
|
|
928
|
-
|
|
929
|
-
fn respond_local_code_node_execution(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
930
|
-
let channel = cx.channel();
|
|
931
|
-
let (deferred, promise) = cx.promise();
|
|
932
|
-
let self_ = cx.this()
|
|
933
|
-
.downcast_or_throw::<JsBox<Chidori>, _>(&mut cx)?;
|
|
934
|
-
let file_id = self_.file_id.clone();
|
|
935
|
-
let url = self_.url.clone();
|
|
936
|
-
|
|
937
|
-
let branch = cx.argument::<JsNumber>(0)?.value(&mut cx) as u64;
|
|
938
|
-
let counter = cx.argument::<JsNumber>(1)?.value(&mut cx) as u64;
|
|
939
|
-
let node_name = cx.argument::<JsString>(2)?.value(&mut cx);
|
|
940
|
-
|
|
941
|
-
let response: Option<JsResult<JsObject>> = match cx.argument_opt(0) {
|
|
942
|
-
Some(v) => Some(v.downcast_or_throw(&mut cx)),
|
|
943
|
-
None => None,
|
|
944
|
-
};
|
|
945
|
-
|
|
946
|
-
// TODO: need parent counters from the original change
|
|
947
|
-
// TODO: need source node
|
|
948
|
-
|
|
949
|
-
let response_paths = if let Some(response) = response {
|
|
950
|
-
// TODO: need better error handling here
|
|
951
|
-
obj_to_paths(&mut cx, response.unwrap()).unwrap()
|
|
952
|
-
} else {
|
|
953
|
-
vec![]
|
|
954
|
-
};
|
|
955
|
-
|
|
956
|
-
let rt = runtime(&mut cx)?;
|
|
957
|
-
rt.spawn(async move {
|
|
958
|
-
let mut client = if let Ok(mut client) = get_client(url).await {
|
|
959
|
-
client
|
|
960
|
-
} else {
|
|
961
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
962
|
-
cx.throw_error::<&str, JsUndefined>("Failed to connect to runtime service.");
|
|
963
|
-
Ok(cx.undefined())
|
|
964
|
-
});
|
|
965
|
-
panic!("Failed to connect to runtime service.");
|
|
966
|
-
};
|
|
967
|
-
|
|
968
|
-
// TODO: need to add the output table paths to these
|
|
969
|
-
let filled_values = response_paths.into_iter().map(|path| {
|
|
970
|
-
ChangeValue {
|
|
971
|
-
path: Some(Path {
|
|
972
|
-
address: path.0,
|
|
973
|
-
}),
|
|
974
|
-
value: Some(path.1),
|
|
975
|
-
branch,
|
|
976
|
-
}
|
|
977
|
-
});
|
|
978
|
-
|
|
979
|
-
// TODO: this needs to look more like a real change
|
|
980
|
-
client.push_worker_event(FileAddressedChangeValueWithCounter {
|
|
981
|
-
branch,
|
|
982
|
-
counter,
|
|
983
|
-
node_name,
|
|
984
|
-
id: file_id.clone(),
|
|
985
|
-
change: Some(ChangeValueWithCounter {
|
|
986
|
-
filled_values: filled_values.collect(),
|
|
987
|
-
parent_monotonic_counters: vec![],
|
|
988
|
-
monotonic_counter: counter,
|
|
989
|
-
branch,
|
|
990
|
-
source_node: "".to_string(),
|
|
991
|
-
})
|
|
992
|
-
}).await.unwrap();
|
|
993
|
-
});
|
|
994
|
-
Ok(promise)
|
|
995
|
-
}
|
|
996
|
-
|
|
997
|
-
// // }
|
|
998
|
-
//
|
|
999
|
-
// // TODO: handle dispatch to this handler - should accept a callback
|
|
1000
|
-
// // https://github.com/PyO3/pyo3/issues/525
|
|
1001
|
-
fn custom_node(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
1002
|
-
let channel = cx.channel();
|
|
1003
|
-
let (deferred, promise) = cx.promise();
|
|
1004
|
-
let self_ = cx.this()
|
|
1005
|
-
.downcast_or_throw::<JsBox<Chidori>, _>(&mut cx)?;
|
|
1006
|
-
|
|
610
|
+
.downcast_or_throw::<JsBox<NodeGraphBuilder>, _>(&mut cx)?;
|
|
1007
611
|
let arg0 = cx.argument::<JsValue>(0)?;
|
|
1008
612
|
let arg0_value: CustomNodeCreateOpts = match neon_serde3::from_value(&mut cx, arg0) {
|
|
1009
613
|
Ok(value) => value,
|
|
@@ -1011,53 +615,16 @@ impl Chidori {
|
|
|
1011
615
|
return cx.throw_error(e.to_string());
|
|
1012
616
|
}
|
|
1013
617
|
};
|
|
1014
|
-
|
|
1015
|
-
|
|
1016
|
-
|
|
1017
|
-
|
|
1018
|
-
|
|
1019
|
-
} else {
|
|
1020
|
-
Some(q)
|
|
1021
|
-
}
|
|
1022
|
-
}).collect()
|
|
1023
|
-
} else {
|
|
1024
|
-
vec![]
|
|
1025
|
-
};
|
|
1026
|
-
|
|
1027
|
-
let file_id = self_.file_id.clone();
|
|
1028
|
-
let url = self_.url.clone();
|
|
1029
|
-
let branch = self_.current_branch;
|
|
1030
|
-
let rt = runtime(&mut cx)?;
|
|
1031
|
-
rt.spawn(async move {
|
|
1032
|
-
// Register the node with the system
|
|
1033
|
-
let node = create_custom_node(
|
|
1034
|
-
arg0_value.name,
|
|
1035
|
-
queries,
|
|
1036
|
-
arg0_value.output.unwrap_or("type O {}".to_string()),
|
|
1037
|
-
arg0_value.node_type_name,
|
|
1038
|
-
arg0_value.output_tables.unwrap_or(vec![])
|
|
1039
|
-
);
|
|
1040
|
-
if let Ok(result ) = push_file_merge(&url, &file_id, node).await {
|
|
1041
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
1042
|
-
Ok(cx.boxed(RefCell::new(result)))
|
|
1043
|
-
});
|
|
1044
|
-
} else {
|
|
1045
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
1046
|
-
// TODO: throw error
|
|
1047
|
-
Ok(cx.undefined())
|
|
1048
|
-
});
|
|
1049
|
-
panic!("Failed to connect to runtime service.");
|
|
1050
|
-
};
|
|
1051
|
-
});
|
|
1052
|
-
Ok(promise)
|
|
618
|
+
let mut g = self_.g.blocking_lock();
|
|
619
|
+
match g.custom_node(arg0_value) {
|
|
620
|
+
Ok(result) => Ok(cx.boxed(RefCell::new(NodeNodeHandle::from(result)))),
|
|
621
|
+
Err(e) => cx.throw_error(e.to_string())
|
|
622
|
+
}
|
|
1053
623
|
}
|
|
1054
624
|
|
|
1055
|
-
fn deno_code_node(mut cx: FunctionContext) -> JsResult<
|
|
1056
|
-
let channel = cx.channel();
|
|
1057
|
-
let (deferred, promise) = cx.promise();
|
|
625
|
+
fn deno_code_node(mut cx: FunctionContext) -> JsResult<JsBox<RefCell<NodeNodeHandle>>> {
|
|
1058
626
|
let self_ = cx.this()
|
|
1059
|
-
.downcast_or_throw::<JsBox<
|
|
1060
|
-
|
|
627
|
+
.downcast_or_throw::<JsBox<NodeGraphBuilder>, _>(&mut cx)?;
|
|
1061
628
|
let arg0 = cx.argument::<JsValue>(0)?;
|
|
1062
629
|
let arg0_value: DenoCodeNodeCreateOpts = match neon_serde3::from_value(&mut cx, arg0) {
|
|
1063
630
|
Ok(value) => value,
|
|
@@ -1065,53 +632,16 @@ impl Chidori {
|
|
|
1065
632
|
return cx.throw_error(e.to_string());
|
|
1066
633
|
}
|
|
1067
634
|
};
|
|
1068
|
-
|
|
1069
|
-
|
|
1070
|
-
|
|
1071
|
-
|
|
1072
|
-
|
|
1073
|
-
} else {
|
|
1074
|
-
Some(q)
|
|
1075
|
-
}
|
|
1076
|
-
}).collect()
|
|
1077
|
-
} else {
|
|
1078
|
-
vec![None]
|
|
1079
|
-
};
|
|
1080
|
-
|
|
1081
|
-
let file_id = self_.file_id.clone();
|
|
1082
|
-
let url = self_.url.clone();
|
|
1083
|
-
let branch = self_.current_branch;
|
|
1084
|
-
|
|
1085
|
-
let rt = runtime(&mut cx)?;
|
|
1086
|
-
rt.spawn(async move {
|
|
1087
|
-
let node = create_code_node(
|
|
1088
|
-
arg0_value.name,
|
|
1089
|
-
queries,
|
|
1090
|
-
arg0_value.output.unwrap_or("type O {}".to_string()),
|
|
1091
|
-
SourceNodeType::Code("DENO".to_string(), arg0_value.code, arg0_value.is_template.unwrap_or(false)),
|
|
1092
|
-
arg0_value.output_tables.unwrap_or(vec![])
|
|
1093
|
-
);
|
|
1094
|
-
if let Ok(result ) = push_file_merge(&url, &file_id, node).await {
|
|
1095
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
1096
|
-
Ok(cx.boxed(RefCell::new(result)))
|
|
1097
|
-
});
|
|
1098
|
-
} else {
|
|
1099
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
1100
|
-
// TODO: throw error
|
|
1101
|
-
Ok(cx.undefined())
|
|
1102
|
-
});
|
|
1103
|
-
panic!("Failed to connect to runtime service.");
|
|
1104
|
-
};
|
|
1105
|
-
});
|
|
1106
|
-
Ok(promise)
|
|
635
|
+
let mut g = self_.g.blocking_lock();
|
|
636
|
+
match g.deno_code_node(arg0_value) {
|
|
637
|
+
Ok(result) => Ok(cx.boxed(RefCell::new(NodeNodeHandle::from(result)))),
|
|
638
|
+
Err(e) => cx.throw_error(e.to_string())
|
|
639
|
+
}
|
|
1107
640
|
}
|
|
1108
641
|
|
|
1109
|
-
fn vector_memory_node(mut cx: FunctionContext) -> JsResult<
|
|
1110
|
-
let channel = cx.channel();
|
|
1111
|
-
let (deferred, promise) = cx.promise();
|
|
642
|
+
fn vector_memory_node(mut cx: FunctionContext) -> JsResult<JsBox<RefCell<NodeNodeHandle>>> {
|
|
1112
643
|
let self_ = cx.this()
|
|
1113
|
-
.downcast_or_throw::<JsBox<
|
|
1114
|
-
|
|
644
|
+
.downcast_or_throw::<JsBox<NodeGraphBuilder>, _>(&mut cx)?;
|
|
1115
645
|
let arg0 = cx.argument::<JsValue>(0)?;
|
|
1116
646
|
let arg0_value: VectorMemoryNodeCreateOpts = match neon_serde3::from_value(&mut cx, arg0) {
|
|
1117
647
|
Ok(value) => value,
|
|
@@ -1119,56 +649,39 @@ impl Chidori {
|
|
|
1119
649
|
return cx.throw_error(e.to_string());
|
|
1120
650
|
}
|
|
1121
651
|
};
|
|
652
|
+
let mut g = self_.g.blocking_lock();
|
|
653
|
+
match g.vector_memory_node(arg0_value) {
|
|
654
|
+
Ok(result) => Ok(cx.boxed(RefCell::new(NodeNodeHandle::from(result)))),
|
|
655
|
+
Err(e) => cx.throw_error(e.to_string())
|
|
656
|
+
}
|
|
657
|
+
}
|
|
1122
658
|
|
|
1123
|
-
let queries: Vec<Option<String>> = if let Some(queries) = arg0_value.queries {
|
|
1124
|
-
queries.into_iter().map(|q| {
|
|
1125
|
-
if q == "None".to_string() {
|
|
1126
|
-
None
|
|
1127
|
-
} else {
|
|
1128
|
-
Some(q)
|
|
1129
|
-
}
|
|
1130
|
-
}).collect()
|
|
1131
|
-
} else {
|
|
1132
|
-
vec![]
|
|
1133
|
-
};
|
|
1134
659
|
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
let
|
|
660
|
+
|
|
661
|
+
fn commit(mut cx: FunctionContext) -> JsResult<JsPromise> {
|
|
662
|
+
let channel = cx.channel();
|
|
663
|
+
let (deferred, promise) = cx.promise();
|
|
664
|
+
let self_ = cx.this()
|
|
665
|
+
.downcast_or_throw::<JsBox<NodeGraphBuilder>, _>(&mut cx)?;
|
|
666
|
+
let node_chidori = cx.argument::<JsBox<NodeChidori>>(0)?;
|
|
667
|
+
let branch = cx.argument::<JsNumber>(1).unwrap_or(JsNumber::new(&mut cx, 0.0)).value(&mut cx) as u64;
|
|
668
|
+
|
|
669
|
+
let c = Arc::clone(&node_chidori.c);
|
|
670
|
+
let g = Arc::clone(&self_.g);
|
|
671
|
+
|
|
1138
672
|
let rt = runtime(&mut cx)?;
|
|
1139
673
|
rt.spawn(async move {
|
|
1140
|
-
let
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
);
|
|
1151
|
-
let node = if let Ok(node) = node {
|
|
1152
|
-
node
|
|
1153
|
-
} else {
|
|
1154
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
1155
|
-
// TODO: throw error
|
|
1156
|
-
Ok(cx.undefined())
|
|
1157
|
-
});
|
|
1158
|
-
panic!("Failed to connect to runtime service.");
|
|
1159
|
-
};
|
|
1160
|
-
|
|
1161
|
-
if let Ok(result ) = push_file_merge(&url, &file_id, node).await {
|
|
1162
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
1163
|
-
Ok(cx.boxed(RefCell::new(result)))
|
|
1164
|
-
});
|
|
1165
|
-
} else {
|
|
1166
|
-
deferred.settle_with(&channel, move |mut cx| {
|
|
1167
|
-
// TODO: throw error
|
|
1168
|
-
Ok(cx.undefined())
|
|
1169
|
-
});
|
|
1170
|
-
panic!("Failed to connect to runtime service.");
|
|
1171
|
-
};
|
|
674
|
+
let mut graph_builder = g.lock().await;
|
|
675
|
+
let mut chidori = c.lock().await;
|
|
676
|
+
let m = graph_builder.commit(&mut chidori, branch).await;
|
|
677
|
+
deferred.settle_with((&channel), move |mut cx| {
|
|
678
|
+
if let Ok(result) = m {
|
|
679
|
+
neon_serde3::to_value(&mut cx, &result)
|
|
680
|
+
.or_else(|e| cx.throw_error(e.to_string()))
|
|
681
|
+
} else {
|
|
682
|
+
cx.throw_error("Error playing")
|
|
683
|
+
}
|
|
684
|
+
});
|
|
1172
685
|
});
|
|
1173
686
|
Ok(promise)
|
|
1174
687
|
}
|
|
@@ -1203,22 +716,24 @@ fn neon_simple_fun(mut cx: FunctionContext) -> JsResult<JsString> {
|
|
|
1203
716
|
#[neon::main]
|
|
1204
717
|
fn main(mut cx: ModuleContext) -> NeonResult<()> {
|
|
1205
718
|
env_logger::init();
|
|
1206
|
-
cx.export_function("
|
|
1207
|
-
cx.export_function("
|
|
1208
|
-
cx.export_function("
|
|
1209
|
-
cx.export_function("
|
|
1210
|
-
cx.export_function("
|
|
1211
|
-
cx.export_function("
|
|
1212
|
-
cx.export_function("
|
|
1213
|
-
cx.export_function("
|
|
1214
|
-
cx.export_function("
|
|
1215
|
-
cx.export_function("
|
|
1216
|
-
cx.export_function("
|
|
1217
|
-
|
|
1218
|
-
cx.export_function("
|
|
1219
|
-
cx.export_function("
|
|
1220
|
-
cx.export_function("
|
|
1221
|
-
cx.export_function("
|
|
719
|
+
cx.export_function("nodehandleRunWhen", NodeNodeHandle::run_when)?;
|
|
720
|
+
// cx.export_function("nodehandleQuery", NodeNodeHandle::query)?;
|
|
721
|
+
cx.export_function("chidoriNew", NodeChidori::js_new)?;
|
|
722
|
+
cx.export_function("chidoriStartServer", NodeChidori::start_server)?;
|
|
723
|
+
cx.export_function("chidoriPlay", NodeChidori::play)?;
|
|
724
|
+
cx.export_function("chidoriPause", NodeChidori::pause)?;
|
|
725
|
+
cx.export_function("chidoriBranch", NodeChidori::branch)?;
|
|
726
|
+
cx.export_function("chidoriQuery", NodeChidori::query)?;
|
|
727
|
+
cx.export_function("chidoriGraphStructure", NodeChidori::display_graph_structure)?;
|
|
728
|
+
cx.export_function("chidoriRegisterCustomNodeHandle", NodeChidori::register_custom_node_handle)?;
|
|
729
|
+
cx.export_function("chidoriRunCustomNodeLoop", NodeChidori::run_custom_node_loop)?;
|
|
730
|
+
|
|
731
|
+
cx.export_function("graphbuilderNew", NodeGraphBuilder::js_new)?;
|
|
732
|
+
cx.export_function("graphbuilderCustomNode", NodeGraphBuilder::custom_node)?;
|
|
733
|
+
cx.export_function("graphbuilderDenoCodeNode", NodeGraphBuilder::deno_code_node)?;
|
|
734
|
+
cx.export_function("graphbuilderPromptNode", NodeGraphBuilder::prompt_node)?;
|
|
735
|
+
cx.export_function("graphbuilderVectorMemoryNode", NodeGraphBuilder::vector_memory_node)?;
|
|
736
|
+
cx.export_function("graphbuilderCommit", NodeGraphBuilder::commit)?;
|
|
1222
737
|
cx.export_function("simpleFun", neon_simple_fun)?;
|
|
1223
738
|
Ok(())
|
|
1224
739
|
}
|