fal 0.15.0__tar.gz → 1.0.0__tar.gz
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.
Potentially problematic release.
This version of fal might be problematic. Click here for more details.
- fal-1.0.0/.gitignore +1 -0
- {fal-0.15.0 → fal-1.0.0}/PKG-INFO +33 -5
- {fal-0.15.0 → fal-1.0.0}/README.md +27 -0
- {fal-0.15.0 → fal-1.0.0}/fal.egg-info/PKG-INFO +33 -5
- {fal-0.15.0 → fal-1.0.0}/fal.egg-info/SOURCES.txt +21 -2
- fal-1.0.0/fal.egg-info/entry_points.txt +2 -0
- {fal-0.15.0 → fal-1.0.0}/fal.egg-info/requires.txt +5 -4
- {fal-0.15.0 → fal-1.0.0}/pyproject.toml +16 -5
- fal-1.0.0/src/fal/__init__.py +29 -0
- fal-1.0.0/src/fal/__main__.py +4 -0
- fal-1.0.0/src/fal/_fal_version.py +16 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/_serialization.py +15 -9
- fal-1.0.0/src/fal/_version.py +6 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/api.py +32 -14
- {fal-0.15.0 → fal-1.0.0}/src/fal/app.py +54 -5
- {fal-0.15.0 → fal-1.0.0}/src/fal/auth/__init__.py +2 -1
- {fal-0.15.0 → fal-1.0.0}/src/fal/auth/auth0.py +4 -2
- {fal-0.15.0 → fal-1.0.0}/src/fal/auth/local.py +2 -1
- fal-1.0.0/src/fal/cli/__init__.py +1 -0
- fal-1.0.0/src/fal/cli/apps.py +313 -0
- fal-1.0.0/src/fal/cli/auth.py +59 -0
- fal-1.0.0/src/fal/cli/debug.py +65 -0
- fal-1.0.0/src/fal/cli/deploy.py +146 -0
- fal-1.0.0/src/fal/cli/keys.py +118 -0
- fal-1.0.0/src/fal/cli/main.py +82 -0
- fal-1.0.0/src/fal/cli/parser.py +74 -0
- fal-1.0.0/src/fal/cli/run.py +33 -0
- fal-1.0.0/src/fal/cli/secrets.py +107 -0
- fal-1.0.0/src/fal/exceptions/__init__.py +3 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/flags.py +0 -3
- {fal-0.15.0 → fal-1.0.0}/src/fal/logging/isolate.py +4 -4
- {fal-0.15.0 → fal-1.0.0}/src/fal/sdk.py +39 -2
- {fal-0.15.0 → fal-1.0.0}/src/fal/sync.py +7 -3
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/file/file.py +14 -6
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/file/providers/fal.py +20 -3
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/image/image.py +1 -1
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/optimize.py +0 -1
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/utils/download_utils.py +6 -3
- fal-1.0.0/src/fal/utils.py +55 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/workflows.py +7 -2
- fal-1.0.0/tests/cli/__init__.py +0 -0
- fal-1.0.0/tests/cli/test_apps.py +63 -0
- fal-1.0.0/tests/cli/test_auth.py +17 -0
- fal-1.0.0/tests/cli/test_deploy.py +8 -0
- fal-1.0.0/tests/cli/test_keys.py +27 -0
- fal-1.0.0/tests/cli/test_run.py +8 -0
- fal-1.0.0/tests/cli/test_secrets.py +19 -0
- {fal-0.15.0 → fal-1.0.0}/tests/conftest.py +0 -1
- {fal-0.15.0 → fal-1.0.0}/tests/integration_test.py +35 -16
- {fal-0.15.0 → fal-1.0.0}/tests/test_apps.py +26 -26
- {fal-0.15.0 → fal-1.0.0}/tests/test_stability.py +31 -7
- {fal-0.15.0 → fal-1.0.0}/tests/toolkit/file_test.py +2 -1
- {fal-0.15.0 → fal-1.0.0}/tests/toolkit/image_test.py +13 -4
- fal-0.15.0/fal.egg-info/entry_points.txt +0 -2
- fal-0.15.0/src/fal/__init__.py +0 -37
- fal-0.15.0/src/fal/__main__.py +0 -4
- fal-0.15.0/src/fal/cli.py +0 -619
- fal-0.15.0/src/fal/exceptions/__init__.py +0 -31
- fal-0.15.0/src/fal/exceptions/handlers.py +0 -58
- {fal-0.15.0 → fal-1.0.0}/fal.egg-info/dependency_links.txt +0 -0
- {fal-0.15.0 → fal-1.0.0}/fal.egg-info/top_level.txt +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/README.md +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/applications/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/applications/app_metadata.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/billing/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/billing/get_user_details.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/files/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/files/check_dir_hash.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/files/upload_local_file.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/workflows/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/workflows/create_or_update_workflow_workflows_post.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/workflows/delete_workflow_workflows_user_id_workflow_name_delete.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/workflows/execute_workflow_workflows_user_id_workflow_name_post.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/workflows/get_workflow_workflows_user_id_workflow_name_get.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/api/workflows/get_workflows_workflows_get.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/client.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/errors.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/app_metadata_response_app_metadata.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/body_upload_local_file.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/customer_details.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/execute_workflow_workflows_user_id_workflow_name_post_json_body_type_0.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/execute_workflow_workflows_user_id_workflow_name_post_response_200_type_0.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/hash_check.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/http_validation_error.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/lock_reason.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/page_workflow_item.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/typed_workflow.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/validation_error.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_contents.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_contents_nodes.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_contents_output.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_detail.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_detail_contents_type_0.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_item.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_node.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_node_type.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_schema.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_schema_input.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/models/workflow_schema_output.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/py.typed +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/openapi_fal_rest/types.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi-fal-rest/pyproject.toml +0 -0
- {fal-0.15.0 → fal-1.0.0}/openapi_rest.config.yaml +0 -0
- {fal-0.15.0 → fal-1.0.0}/setup.cfg +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/apps.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/console/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/console/icons.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/console/ux.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/exceptions/_base.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/exceptions/auth.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/logging/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/logging/style.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/logging/trace.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/logging/user.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/py.typed +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/rest_client.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/exceptions.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/file/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/file/providers/gcp.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/file/providers/r2.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/file/types.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/image/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/src/fal/toolkit/utils/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/tests/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/tests/mainify_package/__init__.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/tests/mainify_package/impl.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/tests/mainify_package/utils.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/tests/mainify_target.py +0 -0
- {fal-0.15.0 → fal-1.0.0}/tools/demo_script.py +0 -0
fal-1.0.0/.gitignore
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
/src/fal/_fal_version.py
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: fal
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 1.0.0
|
|
4
4
|
Summary: fal is an easy-to-use Serverless Python Framework
|
|
5
5
|
Author: Features & Labels <hello@fal.ai>
|
|
6
6
|
Requires-Python: >=3.8
|
|
7
7
|
Description-Content-Type: text/markdown
|
|
8
8
|
Requires-Dist: isolate[build]<1.0,>=0.12.3
|
|
9
|
-
Requires-Dist: isolate-proto==0.
|
|
9
|
+
Requires-Dist: isolate-proto==0.4.0
|
|
10
10
|
Requires-Dist: grpcio<2,>=1.50.0
|
|
11
11
|
Requires-Dist: dill==0.3.7
|
|
12
12
|
Requires-Dist: cloudpickle==3.0.0
|
|
@@ -19,7 +19,7 @@ Requires-Dist: grpc-interceptor<1,>=0.15.0
|
|
|
19
19
|
Requires-Dist: colorama<1,>=0.4.6
|
|
20
20
|
Requires-Dist: portalocker<3,>=2.7.0
|
|
21
21
|
Requires-Dist: rich<14,>=13.3.2
|
|
22
|
-
Requires-Dist:
|
|
22
|
+
Requires-Dist: rich_argparse
|
|
23
23
|
Requires-Dist: packaging<22,>=21.3
|
|
24
24
|
Requires-Dist: pathspec<1,>=0.11.1
|
|
25
25
|
Requires-Dist: pydantic!=2.0.*,!=2.1.*,!=2.2.*,!=2.3.*,!=2.4.*,<3
|
|
@@ -36,9 +36,10 @@ Requires-Dist: pillow<11,>=10.2.0
|
|
|
36
36
|
Requires-Dist: pyjwt[crypto]<3,>=2.8.0
|
|
37
37
|
Requires-Dist: uvicorn<1,>=0.29.0
|
|
38
38
|
Provides-Extra: test
|
|
39
|
-
Requires-Dist: pytest; extra == "test"
|
|
40
|
-
Requires-Dist: pytest-xdist; extra == "test"
|
|
39
|
+
Requires-Dist: pytest<8; extra == "test"
|
|
41
40
|
Requires-Dist: pytest-asyncio; extra == "test"
|
|
41
|
+
Requires-Dist: pytest-xdist; extra == "test"
|
|
42
|
+
Requires-Dist: flaky; extra == "test"
|
|
42
43
|
Provides-Extra: dev
|
|
43
44
|
Requires-Dist: fal[test]; extra == "dev"
|
|
44
45
|
Requires-Dist: openapi-python-client<1,>=0.14.1; extra == "dev"
|
|
@@ -89,3 +90,30 @@ A new virtual environment will be created by fal in the cloud and the set of req
|
|
|
89
90
|
## Next steps
|
|
90
91
|
|
|
91
92
|
If you would like to find out more about the capabilities of fal, check out to the [docs](https://fal.ai/docs). You can learn more about persistent storage, function caches and deploying your functions as API endpoints.
|
|
93
|
+
|
|
94
|
+
## Contributing
|
|
95
|
+
|
|
96
|
+
### Installing in editable mode with dev dependencies
|
|
97
|
+
|
|
98
|
+
```py
|
|
99
|
+
pip install -e 'projects/fal[dev]'
|
|
100
|
+
pip install -e 'projects/fal_client[dev]'
|
|
101
|
+
pip install -e 'projects/isolate_proto[dev]'
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### Running tests
|
|
105
|
+
|
|
106
|
+
```py
|
|
107
|
+
pytest
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
### Pre-commit
|
|
111
|
+
|
|
112
|
+
```
|
|
113
|
+
cd projects/fal
|
|
114
|
+
pre-commit install
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
### Commit format
|
|
118
|
+
|
|
119
|
+
Please follow [conventional commits specification](https://www.conventionalcommits.org/) for descriptions/messages.
|
|
@@ -44,3 +44,30 @@ A new virtual environment will be created by fal in the cloud and the set of req
|
|
|
44
44
|
## Next steps
|
|
45
45
|
|
|
46
46
|
If you would like to find out more about the capabilities of fal, check out to the [docs](https://fal.ai/docs). You can learn more about persistent storage, function caches and deploying your functions as API endpoints.
|
|
47
|
+
|
|
48
|
+
## Contributing
|
|
49
|
+
|
|
50
|
+
### Installing in editable mode with dev dependencies
|
|
51
|
+
|
|
52
|
+
```py
|
|
53
|
+
pip install -e 'projects/fal[dev]'
|
|
54
|
+
pip install -e 'projects/fal_client[dev]'
|
|
55
|
+
pip install -e 'projects/isolate_proto[dev]'
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
### Running tests
|
|
59
|
+
|
|
60
|
+
```py
|
|
61
|
+
pytest
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
### Pre-commit
|
|
65
|
+
|
|
66
|
+
```
|
|
67
|
+
cd projects/fal
|
|
68
|
+
pre-commit install
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
### Commit format
|
|
72
|
+
|
|
73
|
+
Please follow [conventional commits specification](https://www.conventionalcommits.org/) for descriptions/messages.
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: fal
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 1.0.0
|
|
4
4
|
Summary: fal is an easy-to-use Serverless Python Framework
|
|
5
5
|
Author: Features & Labels <hello@fal.ai>
|
|
6
6
|
Requires-Python: >=3.8
|
|
7
7
|
Description-Content-Type: text/markdown
|
|
8
8
|
Requires-Dist: isolate[build]<1.0,>=0.12.3
|
|
9
|
-
Requires-Dist: isolate-proto==0.
|
|
9
|
+
Requires-Dist: isolate-proto==0.4.0
|
|
10
10
|
Requires-Dist: grpcio<2,>=1.50.0
|
|
11
11
|
Requires-Dist: dill==0.3.7
|
|
12
12
|
Requires-Dist: cloudpickle==3.0.0
|
|
@@ -19,7 +19,7 @@ Requires-Dist: grpc-interceptor<1,>=0.15.0
|
|
|
19
19
|
Requires-Dist: colorama<1,>=0.4.6
|
|
20
20
|
Requires-Dist: portalocker<3,>=2.7.0
|
|
21
21
|
Requires-Dist: rich<14,>=13.3.2
|
|
22
|
-
Requires-Dist:
|
|
22
|
+
Requires-Dist: rich_argparse
|
|
23
23
|
Requires-Dist: packaging<22,>=21.3
|
|
24
24
|
Requires-Dist: pathspec<1,>=0.11.1
|
|
25
25
|
Requires-Dist: pydantic!=2.0.*,!=2.1.*,!=2.2.*,!=2.3.*,!=2.4.*,<3
|
|
@@ -36,9 +36,10 @@ Requires-Dist: pillow<11,>=10.2.0
|
|
|
36
36
|
Requires-Dist: pyjwt[crypto]<3,>=2.8.0
|
|
37
37
|
Requires-Dist: uvicorn<1,>=0.29.0
|
|
38
38
|
Provides-Extra: test
|
|
39
|
-
Requires-Dist: pytest; extra == "test"
|
|
40
|
-
Requires-Dist: pytest-xdist; extra == "test"
|
|
39
|
+
Requires-Dist: pytest<8; extra == "test"
|
|
41
40
|
Requires-Dist: pytest-asyncio; extra == "test"
|
|
41
|
+
Requires-Dist: pytest-xdist; extra == "test"
|
|
42
|
+
Requires-Dist: flaky; extra == "test"
|
|
42
43
|
Provides-Extra: dev
|
|
43
44
|
Requires-Dist: fal[test]; extra == "dev"
|
|
44
45
|
Requires-Dist: openapi-python-client<1,>=0.14.1; extra == "dev"
|
|
@@ -89,3 +90,30 @@ A new virtual environment will be created by fal in the cloud and the set of req
|
|
|
89
90
|
## Next steps
|
|
90
91
|
|
|
91
92
|
If you would like to find out more about the capabilities of fal, check out to the [docs](https://fal.ai/docs). You can learn more about persistent storage, function caches and deploying your functions as API endpoints.
|
|
93
|
+
|
|
94
|
+
## Contributing
|
|
95
|
+
|
|
96
|
+
### Installing in editable mode with dev dependencies
|
|
97
|
+
|
|
98
|
+
```py
|
|
99
|
+
pip install -e 'projects/fal[dev]'
|
|
100
|
+
pip install -e 'projects/fal_client[dev]'
|
|
101
|
+
pip install -e 'projects/isolate_proto[dev]'
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### Running tests
|
|
105
|
+
|
|
106
|
+
```py
|
|
107
|
+
pytest
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
### Pre-commit
|
|
111
|
+
|
|
112
|
+
```
|
|
113
|
+
cd projects/fal
|
|
114
|
+
pre-commit install
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
### Commit format
|
|
118
|
+
|
|
119
|
+
Please follow [conventional commits specification](https://www.conventionalcommits.org/) for descriptions/messages.
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
.gitignore
|
|
1
2
|
README.md
|
|
2
3
|
openapi_rest.config.yaml
|
|
3
4
|
pyproject.toml
|
|
@@ -53,27 +54,38 @@ openapi-fal-rest/openapi_fal_rest/models/workflow_schema_input.py
|
|
|
53
54
|
openapi-fal-rest/openapi_fal_rest/models/workflow_schema_output.py
|
|
54
55
|
src/fal/__init__.py
|
|
55
56
|
src/fal/__main__.py
|
|
57
|
+
src/fal/_fal_version.py
|
|
56
58
|
src/fal/_serialization.py
|
|
59
|
+
src/fal/_version.py
|
|
57
60
|
src/fal/api.py
|
|
58
61
|
src/fal/app.py
|
|
59
62
|
src/fal/apps.py
|
|
60
|
-
src/fal/cli.py
|
|
61
63
|
src/fal/flags.py
|
|
62
64
|
src/fal/py.typed
|
|
63
65
|
src/fal/rest_client.py
|
|
64
66
|
src/fal/sdk.py
|
|
65
67
|
src/fal/sync.py
|
|
68
|
+
src/fal/utils.py
|
|
66
69
|
src/fal/workflows.py
|
|
67
70
|
src/fal/auth/__init__.py
|
|
68
71
|
src/fal/auth/auth0.py
|
|
69
72
|
src/fal/auth/local.py
|
|
73
|
+
src/fal/cli/__init__.py
|
|
74
|
+
src/fal/cli/apps.py
|
|
75
|
+
src/fal/cli/auth.py
|
|
76
|
+
src/fal/cli/debug.py
|
|
77
|
+
src/fal/cli/deploy.py
|
|
78
|
+
src/fal/cli/keys.py
|
|
79
|
+
src/fal/cli/main.py
|
|
80
|
+
src/fal/cli/parser.py
|
|
81
|
+
src/fal/cli/run.py
|
|
82
|
+
src/fal/cli/secrets.py
|
|
70
83
|
src/fal/console/__init__.py
|
|
71
84
|
src/fal/console/icons.py
|
|
72
85
|
src/fal/console/ux.py
|
|
73
86
|
src/fal/exceptions/__init__.py
|
|
74
87
|
src/fal/exceptions/_base.py
|
|
75
88
|
src/fal/exceptions/auth.py
|
|
76
|
-
src/fal/exceptions/handlers.py
|
|
77
89
|
src/fal/logging/__init__.py
|
|
78
90
|
src/fal/logging/isolate.py
|
|
79
91
|
src/fal/logging/style.py
|
|
@@ -98,6 +110,13 @@ tests/integration_test.py
|
|
|
98
110
|
tests/mainify_target.py
|
|
99
111
|
tests/test_apps.py
|
|
100
112
|
tests/test_stability.py
|
|
113
|
+
tests/cli/__init__.py
|
|
114
|
+
tests/cli/test_apps.py
|
|
115
|
+
tests/cli/test_auth.py
|
|
116
|
+
tests/cli/test_deploy.py
|
|
117
|
+
tests/cli/test_keys.py
|
|
118
|
+
tests/cli/test_run.py
|
|
119
|
+
tests/cli/test_secrets.py
|
|
101
120
|
tests/mainify_package/__init__.py
|
|
102
121
|
tests/mainify_package/impl.py
|
|
103
122
|
tests/mainify_package/utils.py
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
isolate[build]<1.0,>=0.12.3
|
|
2
|
-
isolate-proto==0.
|
|
2
|
+
isolate-proto==0.4.0
|
|
3
3
|
grpcio<2,>=1.50.0
|
|
4
4
|
dill==0.3.7
|
|
5
5
|
cloudpickle==3.0.0
|
|
@@ -12,7 +12,7 @@ grpc-interceptor<1,>=0.15.0
|
|
|
12
12
|
colorama<1,>=0.4.6
|
|
13
13
|
portalocker<3,>=2.7.0
|
|
14
14
|
rich<14,>=13.3.2
|
|
15
|
-
|
|
15
|
+
rich_argparse
|
|
16
16
|
packaging<22,>=21.3
|
|
17
17
|
pathspec<1,>=0.11.1
|
|
18
18
|
pydantic!=2.0.*,!=2.1.*,!=2.2.*,!=2.3.*,!=2.4.*,<3
|
|
@@ -36,6 +36,7 @@ fal[test]
|
|
|
36
36
|
openapi-python-client<1,>=0.14.1
|
|
37
37
|
|
|
38
38
|
[test]
|
|
39
|
-
pytest
|
|
40
|
-
pytest-xdist
|
|
39
|
+
pytest<8
|
|
41
40
|
pytest-asyncio
|
|
41
|
+
pytest-xdist
|
|
42
|
+
flaky
|
|
@@ -7,6 +7,7 @@ root = "../../"
|
|
|
7
7
|
git_describe_command= 'git describe --tags --abbrev=0 --dirty --match "fal_v*"'
|
|
8
8
|
tag_regex = "^fal_v(?P<version>.*)$"
|
|
9
9
|
fallback_version = "0.0.0"
|
|
10
|
+
version_file = "src/fal/_fal_version.py"
|
|
10
11
|
|
|
11
12
|
[tool.setuptools.packages.find]
|
|
12
13
|
where = ["src", "openapi-fal-rest"]
|
|
@@ -22,7 +23,7 @@ readme = "README.md"
|
|
|
22
23
|
requires-python = ">=3.8"
|
|
23
24
|
dependencies = [
|
|
24
25
|
"isolate[build]>=0.12.3,<1.0",
|
|
25
|
-
"isolate-proto==0.
|
|
26
|
+
"isolate-proto==0.4.0",
|
|
26
27
|
"grpcio>=1.50.0,<2",
|
|
27
28
|
"dill==0.3.7",
|
|
28
29
|
"cloudpickle==3.0.0",
|
|
@@ -35,7 +36,7 @@ dependencies = [
|
|
|
35
36
|
"colorama>=0.4.6,<1",
|
|
36
37
|
"portalocker>=2.7.0,<3",
|
|
37
38
|
"rich>=13.3.2,<14",
|
|
38
|
-
"
|
|
39
|
+
"rich_argparse",
|
|
39
40
|
"packaging>=21.3,<22",
|
|
40
41
|
"pathspec>=0.11.1,<1",
|
|
41
42
|
"pydantic!=2.0.*,!=2.1.*,!=2.2.*,!=2.3.*,!=2.4.*,<3",
|
|
@@ -58,9 +59,10 @@ dependencies = [
|
|
|
58
59
|
|
|
59
60
|
[project.optional-dependencies]
|
|
60
61
|
test = [
|
|
61
|
-
"pytest",
|
|
62
|
-
"pytest-xdist",
|
|
62
|
+
"pytest<8",
|
|
63
63
|
"pytest-asyncio",
|
|
64
|
+
"pytest-xdist",
|
|
65
|
+
"flaky",
|
|
64
66
|
]
|
|
65
67
|
dev = [
|
|
66
68
|
"fal[test]",
|
|
@@ -68,4 +70,13 @@ dev = [
|
|
|
68
70
|
]
|
|
69
71
|
|
|
70
72
|
[project.scripts]
|
|
71
|
-
fal = "fal.cli:
|
|
73
|
+
fal = "fal.cli:main"
|
|
74
|
+
|
|
75
|
+
[tool.ruff]
|
|
76
|
+
target-version = "py38"
|
|
77
|
+
|
|
78
|
+
[tool.ruff.lint]
|
|
79
|
+
select = ["E", "F", "W", "PLC", "PLE", "PLW", "I", "UP"]
|
|
80
|
+
|
|
81
|
+
[tool.ruff.lint.pyupgrade]
|
|
82
|
+
keep-runtime-typing = true
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
from fal import apps # noqa: F401
|
|
4
|
+
from fal.api import FalServerlessHost, LocalHost, cached, function
|
|
5
|
+
from fal.api import function as isolated # noqa: F401
|
|
6
|
+
from fal.app import App, endpoint, realtime, wrap_app # noqa: F401
|
|
7
|
+
from fal.sdk import FalServerlessKeyCredentials
|
|
8
|
+
from fal.sync import sync_dir
|
|
9
|
+
|
|
10
|
+
from ._version import __version__, version_tuple # noqa: F401
|
|
11
|
+
|
|
12
|
+
local = LocalHost()
|
|
13
|
+
serverless = FalServerlessHost()
|
|
14
|
+
|
|
15
|
+
# DEPRECATED - use serverless instead
|
|
16
|
+
cloud = FalServerlessHost()
|
|
17
|
+
|
|
18
|
+
__all__ = [
|
|
19
|
+
"function",
|
|
20
|
+
"cached",
|
|
21
|
+
"App",
|
|
22
|
+
"endpoint",
|
|
23
|
+
"realtime",
|
|
24
|
+
# "wrap_app",
|
|
25
|
+
"FalServerlessKeyCredentials",
|
|
26
|
+
"sync_dir",
|
|
27
|
+
"__version__",
|
|
28
|
+
"version_tuple",
|
|
29
|
+
]
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
# file generated by setuptools_scm
|
|
2
|
+
# don't change, don't track in version control
|
|
3
|
+
TYPE_CHECKING = False
|
|
4
|
+
if TYPE_CHECKING:
|
|
5
|
+
from typing import Tuple, Union
|
|
6
|
+
VERSION_TUPLE = Tuple[Union[int, str], ...]
|
|
7
|
+
else:
|
|
8
|
+
VERSION_TUPLE = object
|
|
9
|
+
|
|
10
|
+
version: str
|
|
11
|
+
__version__: str
|
|
12
|
+
__version_tuple__: VERSION_TUPLE
|
|
13
|
+
version_tuple: VERSION_TUPLE
|
|
14
|
+
|
|
15
|
+
__version__ = version = '1.0.0'
|
|
16
|
+
__version_tuple__ = version_tuple = (1, 0, 0)
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
|
+
import pickle
|
|
3
4
|
from typing import Any, Callable
|
|
4
5
|
|
|
5
|
-
import pickle
|
|
6
6
|
import cloudpickle
|
|
7
7
|
|
|
8
8
|
|
|
@@ -98,11 +98,12 @@ def _patch_pydantic_field_serialization() -> None:
|
|
|
98
98
|
|
|
99
99
|
|
|
100
100
|
def _patch_pydantic_model_serialization() -> None:
|
|
101
|
-
# If user has created new pydantic models in his namespace, we will try to pickle
|
|
102
|
-
# by value, which means recreating class skeleton, which will stumble upon
|
|
103
|
-
# __pydantic_parent_namespace__ in its __dict__ and it may contain modules that
|
|
104
|
-
# to be imported in the namespace but are not actually used, resulting
|
|
105
|
-
# Unfortunately this also means that `model_rebuid()` might
|
|
101
|
+
# If user has created new pydantic models in his namespace, we will try to pickle
|
|
102
|
+
# those by value, which means recreating class skeleton, which will stumble upon
|
|
103
|
+
# __pydantic_parent_namespace__ in its __dict__ and it may contain modules that
|
|
104
|
+
# happened to be imported in the namespace but are not actually used, resulting
|
|
105
|
+
# in pickling errors. Unfortunately this also means that `model_rebuid()` might
|
|
106
|
+
# not work.
|
|
106
107
|
try:
|
|
107
108
|
import pydantic
|
|
108
109
|
except ImportError:
|
|
@@ -133,7 +134,8 @@ def _patch_lru_cache() -> None:
|
|
|
133
134
|
# https://github.com/cloudpipe/cloudpickle/issues/178
|
|
134
135
|
# https://github.com/uqfoundation/dill/blob/70f569b0dd268d2b1e85c0f300951b11f53c5d53/dill/_dill.py#L1429
|
|
135
136
|
|
|
136
|
-
from functools import
|
|
137
|
+
from functools import _lru_cache_wrapper as LRUCacheType
|
|
138
|
+
from functools import lru_cache
|
|
137
139
|
|
|
138
140
|
def create_lru_cache(func: Callable, kwargs: dict) -> LRUCacheType:
|
|
139
141
|
return lru_cache(**kwargs)(func)
|
|
@@ -155,8 +157,8 @@ def _patch_lru_cache() -> None:
|
|
|
155
157
|
|
|
156
158
|
def _patch_lock() -> None:
|
|
157
159
|
# https://github.com/uqfoundation/dill/blob/70f569b0dd268d2b1e85c0f300951b11f53c5d53/dill/_dill.py#L1310
|
|
158
|
-
from threading import Lock
|
|
159
160
|
from _thread import LockType
|
|
161
|
+
from threading import Lock
|
|
160
162
|
|
|
161
163
|
def create_lock(locked: bool) -> Lock:
|
|
162
164
|
lock = Lock()
|
|
@@ -199,7 +201,11 @@ def _patch_console_thread_locals() -> None:
|
|
|
199
201
|
return ConsoleThreadLocals(**kwargs)
|
|
200
202
|
|
|
201
203
|
def pickle_locals(obj: ConsoleThreadLocals) -> tuple[Callable, tuple]:
|
|
202
|
-
kwargs = {
|
|
204
|
+
kwargs = {
|
|
205
|
+
"theme_stack": obj.theme_stack,
|
|
206
|
+
"buffer": obj.buffer,
|
|
207
|
+
"buffer_index": obj.buffer_index,
|
|
208
|
+
}
|
|
203
209
|
return create_locals, (kwargs, )
|
|
204
210
|
|
|
205
211
|
_register(ConsoleThreadLocals, pickle_locals)
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
3
|
import inspect
|
|
4
|
+
import os
|
|
4
5
|
import sys
|
|
5
6
|
import threading
|
|
6
7
|
from collections import defaultdict
|
|
@@ -40,8 +41,8 @@ from pydantic import __version__ as pydantic_version
|
|
|
40
41
|
from typing_extensions import Concatenate, ParamSpec
|
|
41
42
|
|
|
42
43
|
import fal.flags as flags
|
|
43
|
-
from fal.exceptions import FalServerlessException
|
|
44
44
|
from fal._serialization import include_modules_from, patch_pickle
|
|
45
|
+
from fal.exceptions import FalServerlessException
|
|
45
46
|
from fal.logging.isolate import IsolateLogPrinter
|
|
46
47
|
from fal.sdk import (
|
|
47
48
|
FAL_SERVERLESS_DEFAULT_KEEP_ALIVE,
|
|
@@ -57,7 +58,7 @@ from fal.sdk import (
|
|
|
57
58
|
)
|
|
58
59
|
|
|
59
60
|
ArgsT = ParamSpec("ArgsT")
|
|
60
|
-
ReturnT = TypeVar("ReturnT", covariant=True)
|
|
61
|
+
ReturnT = TypeVar("ReturnT", covariant=True) # noqa: PLC0105
|
|
61
62
|
|
|
62
63
|
BasicConfig = Dict[str, Any]
|
|
63
64
|
_UNSET = object()
|
|
@@ -113,8 +114,8 @@ class Host(Generic[ArgsT, ReturnT]):
|
|
|
113
114
|
environment options."""
|
|
114
115
|
|
|
115
116
|
options = Options()
|
|
116
|
-
for
|
|
117
|
-
key, value = cls.parse_key(
|
|
117
|
+
for item in config.items():
|
|
118
|
+
key, value = cls.parse_key(*item)
|
|
118
119
|
if key in cls._SUPPORTED_KEYS:
|
|
119
120
|
options.host[key] = value
|
|
120
121
|
elif key in cls._GATEWAY_KEYS:
|
|
@@ -545,7 +546,8 @@ _DEFAULT_HOST = FalServerlessHost()
|
|
|
545
546
|
_SERVE_PORT = 8080
|
|
546
547
|
|
|
547
548
|
# Overload @function to help users identify the correct signature.
|
|
548
|
-
# NOTE: This is both in sync with host options and with environment configs from
|
|
549
|
+
# NOTE: This is both in sync with host options and with environment configs from
|
|
550
|
+
# `isolate` package.
|
|
549
551
|
|
|
550
552
|
|
|
551
553
|
## virtualenv
|
|
@@ -785,7 +787,8 @@ class FalFastAPI(FastAPI):
|
|
|
785
787
|
"""
|
|
786
788
|
Add x-fal-order-* keys to the OpenAPI specification to help the rendering of UI.
|
|
787
789
|
|
|
788
|
-
NOTE: We rely on the fact that fastapi and Python dicts keep the order of
|
|
790
|
+
NOTE: We rely on the fact that fastapi and Python dicts keep the order of
|
|
791
|
+
properties.
|
|
789
792
|
"""
|
|
790
793
|
|
|
791
794
|
def mark_order(obj: dict[str, Any], key: str):
|
|
@@ -830,6 +833,9 @@ class BaseServable:
|
|
|
830
833
|
"""
|
|
831
834
|
pass
|
|
832
835
|
|
|
836
|
+
def _add_extra_routes(self, app: FastAPI):
|
|
837
|
+
pass
|
|
838
|
+
|
|
833
839
|
@asynccontextmanager
|
|
834
840
|
async def lifespan(self, app: FastAPI):
|
|
835
841
|
yield
|
|
@@ -840,7 +846,10 @@ class BaseServable:
|
|
|
840
846
|
from fastapi.responses import JSONResponse
|
|
841
847
|
from starlette_exporter import PrometheusMiddleware
|
|
842
848
|
|
|
843
|
-
_app = FalFastAPI(
|
|
849
|
+
_app = FalFastAPI(
|
|
850
|
+
lifespan=self.lifespan,
|
|
851
|
+
root_path=os.getenv("FAL_APP_ROOT_PATH") or "",
|
|
852
|
+
)
|
|
844
853
|
|
|
845
854
|
_app.add_middleware(
|
|
846
855
|
CORSMiddleware,
|
|
@@ -891,6 +900,8 @@ class BaseServable:
|
|
|
891
900
|
methods=["POST"],
|
|
892
901
|
)
|
|
893
902
|
|
|
903
|
+
self._add_extra_routes(_app)
|
|
904
|
+
|
|
894
905
|
return _app
|
|
895
906
|
|
|
896
907
|
def openapi(self) -> dict[str, Any]:
|
|
@@ -918,7 +929,9 @@ class BaseServable:
|
|
|
918
929
|
asyncio.create_task(metrics_server.serve()): metrics_server,
|
|
919
930
|
}
|
|
920
931
|
|
|
921
|
-
_, pending = await asyncio.wait(
|
|
932
|
+
_, pending = await asyncio.wait(
|
|
933
|
+
tasks.keys(), return_when=asyncio.FIRST_COMPLETED,
|
|
934
|
+
)
|
|
922
935
|
if not pending:
|
|
923
936
|
return
|
|
924
937
|
|
|
@@ -1007,13 +1020,15 @@ class IsolatedFunction(Generic[ArgsT, ReturnT]):
|
|
|
1007
1020
|
lines = []
|
|
1008
1021
|
for used_modules, references in pairs:
|
|
1009
1022
|
lines.append(
|
|
1010
|
-
f"\t- {used_modules!r}
|
|
1023
|
+
f"\t- {used_modules!r} "
|
|
1024
|
+
f"(accessed through {', '.join(map(repr, references))})"
|
|
1011
1025
|
)
|
|
1012
1026
|
|
|
1013
1027
|
function_name = self.func.__name__
|
|
1014
1028
|
raise FalServerlessError(
|
|
1015
|
-
f"Couldn't deserialize your function on the remote server. \n\n
|
|
1016
|
-
f"function uses the following modules
|
|
1029
|
+
f"Couldn't deserialize your function on the remote server. \n\n"
|
|
1030
|
+
f"[Hint] {function_name!r} function uses the following modules "
|
|
1031
|
+
"which weren't present in the environment definition:\n"
|
|
1017
1032
|
+ "\n".join(lines)
|
|
1018
1033
|
) from None
|
|
1019
1034
|
except Exception as exc:
|
|
@@ -1065,7 +1080,8 @@ class IsolatedFunction(Generic[ArgsT, ReturnT]):
|
|
|
1065
1080
|
def func(self) -> Callable[ArgsT, ReturnT]:
|
|
1066
1081
|
serve_mode = self.options.gateway.get("serve")
|
|
1067
1082
|
if serve_mode:
|
|
1068
|
-
# This type can be safely ignored because this case only happens when it
|
|
1083
|
+
# This type can be safely ignored because this case only happens when it
|
|
1084
|
+
# is a ServedIsolatedFunction
|
|
1069
1085
|
serve_func: Callable[[], None] = ServeWrapper(self.raw_func)
|
|
1070
1086
|
return serve_func # type: ignore
|
|
1071
1087
|
else:
|
|
@@ -1098,8 +1114,10 @@ class ServedIsolatedFunction(
|
|
|
1098
1114
|
|
|
1099
1115
|
class Server(uvicorn.Server):
|
|
1100
1116
|
"""Server is a uvicorn.Server that actually plays nicely with signals.
|
|
1101
|
-
By default, uvicorn's Server class overwrites the signal handler for SIGINT,
|
|
1102
|
-
|
|
1117
|
+
By default, uvicorn's Server class overwrites the signal handler for SIGINT,
|
|
1118
|
+
swallowing the signal and preventing other tasks from cancelling.
|
|
1119
|
+
This class allows the task to be gracefully cancelled using asyncio's built-in task
|
|
1120
|
+
cancellation or with an event, like aiohttp.
|
|
1103
1121
|
"""
|
|
1104
1122
|
|
|
1105
1123
|
def install_signal_handlers(self) -> None:
|