Spaces:
Running
Running
Merge pull request #123 from biggraph/darabos-small-stuff
Browse files- examples/Model definition +15 -27
- examples/Model use +0 -0
- lynxkite-app/src/lynxkite_app/crdt.py +3 -0
- lynxkite-app/web/src/workspace/nodes/NodeParameter.tsx +1 -1
- lynxkite-app/web/src/workspace/nodes/NodeWithParams.tsx +1 -1
- lynxkite-app/web/src/workspace/nodes/NodeWithTableView.tsx +20 -11
- lynxkite-graph-analytics/src/lynxkite_graph_analytics/lynxkite_ops.py +17 -1
examples/Model definition
CHANGED
@@ -235,7 +235,7 @@
|
|
235 |
"id": "Input: tensor 3",
|
236 |
"position": {
|
237 |
"x": 485.8840220312055,
|
238 |
-
"y": -
|
239 |
},
|
240 |
"type": "basic",
|
241 |
"width": 200.0
|
@@ -285,8 +285,8 @@
|
|
285 |
"height": 200.0,
|
286 |
"id": "MSE loss 2",
|
287 |
"position": {
|
288 |
-
"x":
|
289 |
-
"y": -
|
290 |
},
|
291 |
"type": "basic",
|
292 |
"width": 200.0
|
@@ -389,10 +389,6 @@
|
|
389 |
}
|
390 |
}
|
391 |
},
|
392 |
-
"position": {
|
393 |
-
"x": 667.0,
|
394 |
-
"y": 432.0
|
395 |
-
},
|
396 |
"type": "basic"
|
397 |
},
|
398 |
"params": {
|
@@ -439,10 +435,6 @@
|
|
439 |
}
|
440 |
}
|
441 |
},
|
442 |
-
"position": {
|
443 |
-
"x": 675.0,
|
444 |
-
"y": 499.0
|
445 |
-
},
|
446 |
"type": "basic"
|
447 |
},
|
448 |
"params": {
|
@@ -496,10 +488,6 @@
|
|
496 |
}
|
497 |
}
|
498 |
},
|
499 |
-
"position": {
|
500 |
-
"x": 1061.0,
|
501 |
-
"y": 239.0
|
502 |
-
},
|
503 |
"type": "basic"
|
504 |
},
|
505 |
"params": {
|
@@ -513,8 +501,8 @@
|
|
513 |
"height": 258.0,
|
514 |
"id": "Constant vector 1",
|
515 |
"position": {
|
516 |
-
"x":
|
517 |
-
"y": -
|
518 |
},
|
519 |
"type": "basic",
|
520 |
"width": 238.0
|
@@ -554,10 +542,6 @@
|
|
554 |
}
|
555 |
},
|
556 |
"params": {},
|
557 |
-
"position": {
|
558 |
-
"x": 1077.0,
|
559 |
-
"y": 334.0
|
560 |
-
},
|
561 |
"type": "basic"
|
562 |
},
|
563 |
"params": {},
|
@@ -568,8 +552,8 @@
|
|
568 |
"height": 200.0,
|
569 |
"id": "Add 1",
|
570 |
"position": {
|
571 |
-
"x":
|
572 |
-
"y": -
|
573 |
},
|
574 |
"type": "basic",
|
575 |
"width": 200.0
|
@@ -601,10 +585,14 @@
|
|
601 |
}
|
602 |
}
|
603 |
},
|
604 |
-
"params": {
|
605 |
-
|
606 |
-
|
607 |
-
|
|
|
|
|
|
|
|
|
608 |
},
|
609 |
"type": "basic"
|
610 |
},
|
|
|
235 |
"id": "Input: tensor 3",
|
236 |
"position": {
|
237 |
"x": 485.8840220312055,
|
238 |
+
"y": -268.0485936515193
|
239 |
},
|
240 |
"type": "basic",
|
241 |
"width": 200.0
|
|
|
285 |
"height": 200.0,
|
286 |
"id": "MSE loss 2",
|
287 |
"position": {
|
288 |
+
"x": 384.54674698852955,
|
289 |
+
"y": -1184.4701545316577
|
290 |
},
|
291 |
"type": "basic",
|
292 |
"width": 200.0
|
|
|
389 |
}
|
390 |
}
|
391 |
},
|
|
|
|
|
|
|
|
|
392 |
"type": "basic"
|
393 |
},
|
394 |
"params": {
|
|
|
435 |
}
|
436 |
}
|
437 |
},
|
|
|
|
|
|
|
|
|
438 |
"type": "basic"
|
439 |
},
|
440 |
"params": {
|
|
|
488 |
}
|
489 |
}
|
490 |
},
|
|
|
|
|
|
|
|
|
491 |
"type": "basic"
|
492 |
},
|
493 |
"params": {
|
|
|
501 |
"height": 258.0,
|
502 |
"id": "Constant vector 1",
|
503 |
"position": {
|
504 |
+
"x": 886.708922897265,
|
505 |
+
"y": -298.4394167425953
|
506 |
},
|
507 |
"type": "basic",
|
508 |
"width": 238.0
|
|
|
542 |
}
|
543 |
},
|
544 |
"params": {},
|
|
|
|
|
|
|
|
|
545 |
"type": "basic"
|
546 |
},
|
547 |
"params": {},
|
|
|
552 |
"height": 200.0,
|
553 |
"id": "Add 1",
|
554 |
"position": {
|
555 |
+
"x": 722.1292469875319,
|
556 |
+
"y": -762.6853551968964
|
557 |
},
|
558 |
"type": "basic",
|
559 |
"width": 200.0
|
|
|
585 |
}
|
586 |
}
|
587 |
},
|
588 |
+
"params": {
|
589 |
+
"name": {
|
590 |
+
"default": null,
|
591 |
+
"name": "name",
|
592 |
+
"type": {
|
593 |
+
"type": "None"
|
594 |
+
}
|
595 |
+
}
|
596 |
},
|
597 |
"type": "basic"
|
598 |
},
|
examples/Model use
CHANGED
The diff for this file is too large to render.
See raw diff
|
|
lynxkite-app/src/lynxkite_app/crdt.py
CHANGED
@@ -91,6 +91,9 @@ def clean_input(ws_pyd):
|
|
91 |
node.data.input_metadata = None
|
92 |
node.data.error = None
|
93 |
node.data.status = workspace.NodeStatus.done
|
|
|
|
|
|
|
94 |
node.position.x = 0
|
95 |
node.position.y = 0
|
96 |
if node.model_extra:
|
|
|
91 |
node.data.input_metadata = None
|
92 |
node.data.error = None
|
93 |
node.data.status = workspace.NodeStatus.done
|
94 |
+
for p in list(node.data.params):
|
95 |
+
if p.startswith("_"):
|
96 |
+
del node.data.params[p]
|
97 |
node.position.x = 0
|
98 |
node.position.y = 0
|
99 |
if node.model_extra:
|
lynxkite-app/web/src/workspace/nodes/NodeParameter.tsx
CHANGED
@@ -25,7 +25,7 @@ function Input({
|
|
25 |
<input
|
26 |
className="input input-bordered w-full"
|
27 |
ref={inputRef}
|
28 |
-
value={value
|
29 |
onChange={(evt) => onChange(evt.currentTarget.value, { delay: 2 })}
|
30 |
onBlur={(evt) => onChange(evt.currentTarget.value, { delay: 0 })}
|
31 |
onKeyDown={(evt) => evt.code === "Enter" && onChange(evt.currentTarget.value, { delay: 0 })}
|
|
|
25 |
<input
|
26 |
className="input input-bordered w-full"
|
27 |
ref={inputRef}
|
28 |
+
value={value ?? ""}
|
29 |
onChange={(evt) => onChange(evt.currentTarget.value, { delay: 2 })}
|
30 |
onBlur={(evt) => onChange(evt.currentTarget.value, { delay: 0 })}
|
31 |
onKeyDown={(evt) => evt.code === "Enter" && onChange(evt.currentTarget.value, { delay: 0 })}
|
lynxkite-app/web/src/workspace/nodes/NodeWithParams.tsx
CHANGED
@@ -35,7 +35,7 @@ function NodeWithParams(props: any) {
|
|
35 |
|
36 |
return (
|
37 |
<LynxKiteNode {...props}>
|
38 |
-
{props.collapsed && (
|
39 |
<div className="params-expander" onClick={() => setCollapsed(!collapsed)}>
|
40 |
<Triangle className={`flippy ${collapsed ? "flippy-90" : ""}`} />
|
41 |
</div>
|
|
|
35 |
|
36 |
return (
|
37 |
<LynxKiteNode {...props}>
|
38 |
+
{props.collapsed && params.length > 0 && (
|
39 |
<div className="params-expander" onClick={() => setCollapsed(!collapsed)}>
|
40 |
<Triangle className={`flippy ${collapsed ? "flippy-90" : ""}`} />
|
41 |
</div>
|
lynxkite-app/web/src/workspace/nodes/NodeWithTableView.tsx
CHANGED
@@ -1,3 +1,4 @@
|
|
|
|
1 |
import { useState } from "react";
|
2 |
import React from "react";
|
3 |
import Markdown from "react-markdown";
|
@@ -14,23 +15,35 @@ function toMD(v: any): string {
|
|
14 |
return JSON.stringify(v);
|
15 |
}
|
16 |
|
|
|
|
|
17 |
export default function NodeWithTableView(props: any) {
|
18 |
-
const
|
|
|
19 |
const display = props.data.display?.value;
|
20 |
const single = display?.dataframes && Object.keys(display?.dataframes).length === 1;
|
21 |
const dfs = Object.entries(display?.dataframes || {});
|
22 |
dfs.sort();
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
23 |
return (
|
24 |
<LynxKiteNode {...props}>
|
25 |
{display && [
|
26 |
dfs.map(([name, df]: [string, any]) => (
|
27 |
<React.Fragment key={name}>
|
28 |
{!single && (
|
29 |
-
<div
|
30 |
-
key={`${name}-header`}
|
31 |
-
className="df-head"
|
32 |
-
onClick={() => setOpen({ ...open, [name]: !open[name] })}
|
33 |
-
>
|
34 |
{name}
|
35 |
</div>
|
36 |
)}
|
@@ -55,11 +68,7 @@ export default function NodeWithTableView(props: any) {
|
|
55 |
)),
|
56 |
Object.entries(display.others || {}).map(([name, o]) => (
|
57 |
<>
|
58 |
-
<div
|
59 |
-
key={`${name}-header`}
|
60 |
-
className="df-head"
|
61 |
-
onClick={() => setOpen({ ...open, [name]: !open[name] })}
|
62 |
-
>
|
63 |
{name}
|
64 |
</div>
|
65 |
{open[name] && <pre>{(o as any).toString()}</pre>}
|
|
|
1 |
+
import { useReactFlow } from "@xyflow/react";
|
2 |
import { useState } from "react";
|
3 |
import React from "react";
|
4 |
import Markdown from "react-markdown";
|
|
|
15 |
return JSON.stringify(v);
|
16 |
}
|
17 |
|
18 |
+
type OpenState = { [name: string]: boolean };
|
19 |
+
|
20 |
export default function NodeWithTableView(props: any) {
|
21 |
+
const reactFlow = useReactFlow();
|
22 |
+
const [open, setOpen] = useState((props.data?.params?._tables_open ?? {}) as OpenState);
|
23 |
const display = props.data.display?.value;
|
24 |
const single = display?.dataframes && Object.keys(display?.dataframes).length === 1;
|
25 |
const dfs = Object.entries(display?.dataframes || {});
|
26 |
dfs.sort();
|
27 |
+
function setParam(name: string, newValue: any) {
|
28 |
+
reactFlow.updateNodeData(props.id, (prevData: any) => ({
|
29 |
+
...prevData,
|
30 |
+
params: { ...prevData.data.params, [name]: newValue },
|
31 |
+
}));
|
32 |
+
}
|
33 |
+
function toggleTable(name: string) {
|
34 |
+
setOpen((prevOpen: OpenState) => {
|
35 |
+
const newOpen = { ...prevOpen, [name]: !prevOpen[name] };
|
36 |
+
setParam("_tables_open", newOpen);
|
37 |
+
return newOpen;
|
38 |
+
});
|
39 |
+
}
|
40 |
return (
|
41 |
<LynxKiteNode {...props}>
|
42 |
{display && [
|
43 |
dfs.map(([name, df]: [string, any]) => (
|
44 |
<React.Fragment key={name}>
|
45 |
{!single && (
|
46 |
+
<div key={`${name}-header`} className="df-head" onClick={() => toggleTable(name)}>
|
|
|
|
|
|
|
|
|
47 |
{name}
|
48 |
</div>
|
49 |
)}
|
|
|
68 |
)),
|
69 |
Object.entries(display.others || {}).map(([name, o]) => (
|
70 |
<>
|
71 |
+
<div key={`${name}-header`} className="df-head" onClick={() => toggleTable(name)}>
|
|
|
|
|
|
|
|
|
72 |
{name}
|
73 |
</div>
|
74 |
{open[name] && <pre>{(o as any).toString()}</pre>}
|
lynxkite-graph-analytics/src/lynxkite_graph_analytics/lynxkite_ops.py
CHANGED
@@ -291,7 +291,8 @@ def visualize_graph(
|
|
291 |
|
292 |
|
293 |
@op("View tables", view="table_view")
|
294 |
-
def view_tables(bundle: core.Bundle, *, limit: int = 100):
|
|
|
295 |
return bundle.to_dict(limit=limit)
|
296 |
|
297 |
|
@@ -389,6 +390,7 @@ def train_model(
|
|
389 |
losses.append(loss)
|
390 |
m.trained = True
|
391 |
bundle = bundle.copy()
|
|
|
392 |
bundle.other[model_name] = m
|
393 |
return bundle
|
394 |
|
@@ -431,3 +433,17 @@ def train_test_split(bundle: core.Bundle, *, table_name: str, test_ratio: float
|
|
431 |
bundle.dfs[f"{table_name}_train"] = train
|
432 |
bundle.dfs[f"{table_name}_test"] = test
|
433 |
return bundle
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
291 |
|
292 |
|
293 |
@op("View tables", view="table_view")
|
294 |
+
def view_tables(bundle: core.Bundle, *, _tables_open: str = "", limit: int = 100):
|
295 |
+
_tables_open = _tables_open # The frontend uses this parameter to track which tables are open.
|
296 |
return bundle.to_dict(limit=limit)
|
297 |
|
298 |
|
|
|
390 |
losses.append(loss)
|
391 |
m.trained = True
|
392 |
bundle = bundle.copy()
|
393 |
+
bundle.dfs["training"] = pd.DataFrame({"training_loss": losses})
|
394 |
bundle.other[model_name] = m
|
395 |
return bundle
|
396 |
|
|
|
433 |
bundle.dfs[f"{table_name}_train"] = train
|
434 |
bundle.dfs[f"{table_name}_test"] = test
|
435 |
return bundle
|
436 |
+
|
437 |
+
|
438 |
+
@op("View loss", view="visualization")
|
439 |
+
def view_loss(
|
440 |
+
bundle: core.Bundle,
|
441 |
+
):
|
442 |
+
loss = bundle.dfs["training"].training_loss.tolist()
|
443 |
+
v = {
|
444 |
+
"title": {"text": "Training loss"},
|
445 |
+
"xAxis": {"type": "category"},
|
446 |
+
"yAxis": {"type": "value"},
|
447 |
+
"series": [{"data": loss, "type": "line"}],
|
448 |
+
}
|
449 |
+
return v
|