Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 6 additions & 13 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -7,25 +7,18 @@ SRC_DIR = flyde
TEST_DIR = tests

# Targets
.PHONY: ts test cover
.PHONY: gen test cover

ts:
@echo "Building the project..."
# For each *.py file in the examples/mylib directory run the ./flyde.py gen command to generate TS bindings
@for file in $(LIB_DIR)/*.py; do \
./flyde.py gen $$file; \
done
gen:
@echo "Generating component definitions..."
# Generate JSON definitions for the examples/mylib directory
@./pyflyde gen $(LIB_DIR)/

lint:
@echo "Running linters..."
@black $(LIB_DIR) $(TEST_DIR);
@flake8 $(LIB_DIR) $(TEST_DIR);

stubgen:
@echo "Generating type stubs..."
@rm -f $(SRC_DIR)/*.pyi;
@stubgen $(SRC_DIR) --include-docstrings --include-private -o .;

test:
@echo "Running tests..."
@$(PYTHON) -m unittest discover -s $(TEST_DIR) -p "test_$(if $(mod),$(mod),*).py";
Expand All @@ -46,7 +39,7 @@ builddist:
@rm -f ./dist/*
@$(PYTHON) -m build;

release: lint test stubgen builddist
release: lint test gen builddist
@echo "Releasing the project...";

upload:
Expand Down
6 changes: 3 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -61,13 +61,13 @@ Install Flyde VSCode extension from the [marketplace](https://marketplace.visual

You can browse the component library in the panel on the right. To see your local components click the "View all" button. They will appear under the "Current project". Note that PyFlyde doesn't implement all of the Flyde's stdlib components, only a few essential ones.

Whenever you change your component library classes or their interfaces, use `pyflyde gen` command to generate `.flyde.ts` definitions, e.g.:
Whenever you change your component library classes or their interfaces, use `pyflyde gen` command to generate `flyde-nodes.json` definitions, e.g.:

```bash
pyflyde gen examples/mylib/components.py
pyflyde gen examples/
```

Flyde editor needs `.flyde.ts` files in order to "see" your components.
This will recursively scan all Python files in the directory and its subdirectories to find PyFlyde components and generate a `flyde-nodes.json` file with relative paths. Flyde editor needs `flyde-nodes.json` files in order to "see" your components.

### Running a Machine Learning example and creating your first project

Expand Down
18 changes: 16 additions & 2 deletions docs/quickstart.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,12 +37,20 @@ where = ["mylib"] # With this line
Install the dependencies:

```bash
pip install examples/
pip install examples/
```

## Running the Hello World example

Run the example flow:
First, generate the component metadata for the examples:

```bash
pyflyde gen examples/
```

This will recursively scan all Python files in the `examples/` directory and generate a `flyde-nodes.json` file with metadata for all PyFlyde components found.

Then run the example flow:

```bash
pyflyde examples/HelloPy.flyde
Expand All @@ -54,6 +62,12 @@ It should print "Hello Flyde!" in the console.

`examples/Clustering.flyde` is a more complex example which uses Pandas and Scikit-Learn to run K-means clustering on a [wine clustering dataset from Kaggle](https://www.kaggle.com/harrywang/wine-dataset-for-clustering). It's a PyFlyde version of https://github.com/Shivangi0503/Wine_Clustering_KMeans.

The component metadata should already be generated from the previous step, but if you add new components, remember to run:

```bash
pyflyde gen examples/
```

Open the `examples/Clustering.flyde` in Flyde VSCode visual editor to see how it looks like.

To run this example, use the `pyflyde` command line tool:
Expand Down
20 changes: 14 additions & 6 deletions docs/usage.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,16 +14,24 @@ You can omit the `run` command because it is the default one. The following comm
pyflyde examples/HelloWorld.flyde
```

## Generating TS definitions for Flyde visual editor
## Generating component definitions for Flyde visual editor

Flyde visual editor is written for TypeScript runtime and is not aware of your Python nodes. To make your local nodes appear in the Flyde editor, you need to generate `.flyde.ts` files for them.
To make your Python nodes appear in the Flyde visual editor, you need to generate `flyde-nodes.json` metadata files for them.

For example:
Generate JSON definitions for a directory:

```bash
pyflyde gen mypackage/supermodule.py
pyflyde gen mypackage/
```

will generate `mypackage/supermodule.flyde.ts` TypeScript defintions for Flyde using the contents of your `mypackage.submodule` module.
This will recursively scan all `.py` files in the directory and its subdirectories, then generate a `flyde-nodes.json` file in the specified directory containing metadata for all PyFlyde components found. The paths in the generated JSON file are relative to the directory containing the `flyde-nodes.json` file, making the component library portable.

You should run `pyflyde gen` every time your create new modules containing PyFlyde nodes or whenever you update node signature (name, description, inputs, outputs, etc.).
For example, if you have components in:
- `mypackage/components.py`
- `mypackage/utils/helpers.py`

The generated `flyde-nodes.json` will reference them as:
- `custom://components.py/ComponentName`
- `custom://utils/helpers.py/HelperComponentName`

You should run `pyflyde gen` every time you create new modules containing PyFlyde nodes or whenever you update node signatures (name, description, inputs, outputs, etc.).
164 changes: 118 additions & 46 deletions examples/Clustering.flyde
Original file line number Diff line number Diff line change
@@ -1,31 +1,27 @@
imports:
"@flyde/stdlib":
- InlineValue
- GetAttribute
mylib/dataframe.flyde.ts:
- LoadDataset
- Scale
mylib/kmeans.flyde.ts:
- KMeansNClusters
- KMeansCluster
- PCA2
- Visualize
imports: {}
node:
instances:
- pos:
x: -44.67793457031249
y: -40.51885223388672
x: -688.3592700195312
y: 60.69355010986328
id: LoadDataset-1a039uk
inputConfig: {}
nodeId: LoadDataset
config:
file_path:
type: dynamic
value: "{{file_path}}"
type: code
source:
type: custom
data: custom://mylib/dataframe.py/LoadDataset
- pos:
x: -81.67130859374998
y: -124.01171112060547
x: -939.2435131835937
y: 61.415870666503906
id: mc4t4fqqezd1gns4fb7ckxmc
inputConfig: {}
nodeId: InlineValue__mc4t4fqqezd1gns4fb7ckxmc
macroId: InlineValue
macroData:
nodeId: InlineValue
config:
type:
type: string
value: string
Expand All @@ -35,32 +31,65 @@ node:
label:
type: string
value: wine-clustering.csv
type: code
source:
type: package
data: "@flyde/nodes"
- pos:
x: -21.232984619140666
y: 59.69538116455078
x: -436.9881726074219
y: 60.95093536376953
id: Scale-dz139az
inputConfig: {}
nodeId: Scale
config:
dataframe:
type: dynamic
value: "{{dataframe}}"
type: code
source:
type: custom
data: custom://mylib/dataframe.py/Scale
- pos:
x: 115.65844161987303
y: 212.51250839233398
x: -24.11493484497072
y: 62.353389739990234
id: KMeansNClusters-5m2390u
inputConfig: {}
nodeId: KMeansNClusters
config:
scaled_dataframe:
type: dynamic
value: "{{scaled_dataframe}}"
max_clusters:
type: dynamic
value: "{{max_clusters}}"
type: code
source:
type: custom
data: custom://mylib/kmeans.py/KMeansNClusters
- pos:
x: -21.067138671875
y: 348.4979133605957
x: 234.1243896484375
y: 185.80514907836914
id: KMeansCluster-ql339i4
inputConfig: {}
nodeId: KMeansCluster
config:
scaled_dataframe:
type: dynamic
value: "{{scaled_dataframe}}"
n_clusters:
type: dynamic
value: "{{n_clusters}}"
type: code
source:
type: custom
data: custom://mylib/kmeans.py/KMeansCluster
- pos:
x: 233.42520244598387
y: 80.12830471992493
x: -431.2221974563599
y: -46.37674593925476
id: yquy5xqil6xp9tmb42ktmosp
inputConfig: {}
nodeId: InlineValue__yquy5xqil6xp9tmb42ktmosp
macroId: InlineValue
macroData:
nodeId: InlineValue
config:
value:
type: number
value: 20
Expand All @@ -70,42 +99,81 @@ node:
label:
type: string
value: "20"
type: code
source:
type: package
data: "@flyde/nodes"
- pos:
x: -264.7014599609375
y: 436.35204895019535
x: 234.12208740234377
y: 410.2254124450684
id: PCA2-mz439jk
inputConfig: {}
nodeId: PCA2
config:
scaled_dataframe:
type: dynamic
value: "{{scaled_dataframe}}"
type: code
source:
type: custom
data: custom://mylib/kmeans.py/PCA2
- pos:
x: -194.03480346679686
y: 829.8976345825196
x: 1010.514711303711
y: 252.2306843566895
id: Visualize-yz539m4
inputConfig: {}
nodeId: Visualize
config:
pca_components:
type: dynamic
value: "{{pca_components}}"
pca_centroids:
type: dynamic
value: "{{pca_centroids}}"
kmeans_result:
type: dynamic
value: "{{kmeans_result}}"
type: code
source:
type: custom
data: custom://mylib/kmeans.py/Visualize
- pos:
x: -85.56712158203123
y: 675.0107851791382
x: 736.7720812988282
y: 149.70720727920536
id: PCA2-e5639ct
inputConfig: {}
nodeId: PCA2
config:
scaled_dataframe:
type: dynamic
value: "{{scaled_dataframe}}"
type: code
source:
type: custom
data: custom://mylib/kmeans.py/PCA2
- pos:
x: -158.16623901367188
y: 567.0884128027336
x: 513.1246850585937
y: 141.11043981841965
id: nmt2k6i80qpwu9fyuckbqefw
inputConfig: {}
nodeId: GetAttribute__nmt2k6i80qpwu9fyuckbqefw
macroId: GetAttribute
macroData:
nodeId: GetAttribute
config:
key:
type: dynamic
object:
type: dynamic
value: "{{object}}"
type: code
source:
type: package
data: "@flyde/nodes"
- pos:
x: -94.66524780273448
y: 458.4299138098137
x: 234.12473022460927
y: 310.8023236303703
id: xb5xo767x6u0ubdvvegi0e53
inputConfig: {}
nodeId: InlineValue__xb5xo767x6u0ubdvvegi0e53
macroId: InlineValue
macroData:
nodeId: InlineValue
config:
type:
type: string
value: string
Expand All @@ -115,6 +183,10 @@ node:
label:
type: string
value: '"centroids"'
type: code
source:
type: package
data: "@flyde/nodes"
connections:
- from:
insId: mc4t4fqqezd1gns4fb7ckxmc
Expand Down
Loading