use dynamically generated libraries
This commit is contained in:
parent
4a96c761a6
commit
29f864f248
@ -4,7 +4,6 @@ from __future__ import annotations
|
|||||||
|
|
||||||
import os
|
import os
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
from importlib.util import find_spec
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Dict, Iterable, Optional, Type, Union
|
from typing import Dict, Iterable, Optional, Type, Union
|
||||||
|
|
||||||
@ -41,6 +40,20 @@ def _compile_document_root(root: Component) -> str:
|
|||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def _normalize_library_name(lib: str) -> str:
|
||||||
|
"""Normalize the library name.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
lib: The library name to normalize.
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
The normalized library name.
|
||||||
|
"""
|
||||||
|
if lib == "react":
|
||||||
|
return "React"
|
||||||
|
return lib.replace("@", "").replace("/", "_").replace("-", "_")
|
||||||
|
|
||||||
|
|
||||||
def _compile_app(app_root: Component) -> str:
|
def _compile_app(app_root: Component) -> str:
|
||||||
"""Compile the app template component.
|
"""Compile the app template component.
|
||||||
|
|
||||||
@ -50,25 +63,20 @@ def _compile_app(app_root: Component) -> str:
|
|||||||
Returns:
|
Returns:
|
||||||
The compiled app.
|
The compiled app.
|
||||||
"""
|
"""
|
||||||
chakra_available = find_spec("reflex_chakra") is not None
|
from reflex.components.dynamic import bundled_libraries
|
||||||
|
|
||||||
|
window_libraries = [
|
||||||
|
(_normalize_library_name(name), name) for name in bundled_libraries
|
||||||
|
] + [
|
||||||
|
("utils_context", f"/{constants.Dirs.UTILS}/context.js"),
|
||||||
|
("utils_state", f"/{constants.Dirs.UTILS}/state.js"),
|
||||||
|
]
|
||||||
|
|
||||||
return templates.APP_ROOT.render(
|
return templates.APP_ROOT.render(
|
||||||
imports=utils.compile_imports(app_root._get_all_imports()),
|
imports=utils.compile_imports(app_root._get_all_imports()),
|
||||||
custom_codes=app_root._get_all_custom_code(),
|
custom_codes=app_root._get_all_custom_code(),
|
||||||
hooks={**app_root._get_all_hooks_internal(), **app_root._get_all_hooks()},
|
hooks={**app_root._get_all_hooks_internal(), **app_root._get_all_hooks()},
|
||||||
window_libraries=[
|
window_libraries=window_libraries,
|
||||||
("React", "react"),
|
|
||||||
("utils_context", f"/{constants.Dirs.UTILS}/context.js"),
|
|
||||||
("utils_state", f"/{constants.Dirs.UTILS}/state.js"),
|
|
||||||
("radix", "@radix-ui/themes"),
|
|
||||||
]
|
|
||||||
+ (
|
|
||||||
[
|
|
||||||
("chakra", "@chakra-ui/react"),
|
|
||||||
]
|
|
||||||
if chakra_available
|
|
||||||
else []
|
|
||||||
),
|
|
||||||
render=app_root.render(),
|
render=app_root.render(),
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -1,14 +1,18 @@
|
|||||||
"""Components that are dynamically generated on the backend."""
|
"""Components that are dynamically generated on the backend."""
|
||||||
|
|
||||||
from importlib.util import find_spec
|
from typing import TYPE_CHECKING
|
||||||
|
|
||||||
from reflex import constants
|
from reflex import constants
|
||||||
from reflex.utils import imports
|
from reflex.utils import imports
|
||||||
|
from reflex.utils.exceptions import DynamicComponentMissingLibrary
|
||||||
from reflex.utils.format import format_library_name
|
from reflex.utils.format import format_library_name
|
||||||
from reflex.utils.serializers import serializer
|
from reflex.utils.serializers import serializer
|
||||||
from reflex.vars import Var, get_unique_variable_name
|
from reflex.vars import Var, get_unique_variable_name
|
||||||
from reflex.vars.base import VarData, transform
|
from reflex.vars.base import VarData, transform
|
||||||
|
|
||||||
|
if TYPE_CHECKING:
|
||||||
|
from reflex.components.component import Component
|
||||||
|
|
||||||
|
|
||||||
def get_cdn_url(lib: str) -> str:
|
def get_cdn_url(lib: str) -> str:
|
||||||
"""Get the CDN URL for a library.
|
"""Get the CDN URL for a library.
|
||||||
@ -22,6 +26,23 @@ def get_cdn_url(lib: str) -> str:
|
|||||||
return f"https://cdn.jsdelivr.net/npm/{lib}" + "/+esm"
|
return f"https://cdn.jsdelivr.net/npm/{lib}" + "/+esm"
|
||||||
|
|
||||||
|
|
||||||
|
bundled_libraries = {"react", "@radix-ui/themes"}
|
||||||
|
|
||||||
|
|
||||||
|
def bundle_library(component: "Component"):
|
||||||
|
"""Bundle a library with the component.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
component: The component to bundle the library with.
|
||||||
|
|
||||||
|
Raises:
|
||||||
|
DynamicComponentMissingLibrary: Raised when a dynamic component is missing a library.
|
||||||
|
"""
|
||||||
|
if component.library is None:
|
||||||
|
raise DynamicComponentMissingLibrary("Component must have a library to bundle.")
|
||||||
|
bundled_libraries.add(format_library_name(component.library))
|
||||||
|
|
||||||
|
|
||||||
def load_dynamic_serializer():
|
def load_dynamic_serializer():
|
||||||
"""Load the serializer for dynamic components."""
|
"""Load the serializer for dynamic components."""
|
||||||
# Causes a circular import, so we import here.
|
# Causes a circular import, so we import here.
|
||||||
@ -60,12 +81,7 @@ def load_dynamic_serializer():
|
|||||||
)
|
)
|
||||||
] = None
|
] = None
|
||||||
|
|
||||||
chakra_available = find_spec("reflex_chakra") is not None
|
libs_in_window = bundled_libraries
|
||||||
|
|
||||||
libs_in_window = [
|
|
||||||
"react",
|
|
||||||
"@radix-ui/themes",
|
|
||||||
] + (["@chakra-ui/react"] if chakra_available else [])
|
|
||||||
|
|
||||||
imports = {}
|
imports = {}
|
||||||
for lib, names in component._get_all_imports().items():
|
for lib, names in component._get_all_imports().items():
|
||||||
|
@ -115,3 +115,7 @@ class PrimitiveUnserializableToJSON(ReflexError, ValueError):
|
|||||||
|
|
||||||
class InvalidLifespanTaskType(ReflexError, TypeError):
|
class InvalidLifespanTaskType(ReflexError, TypeError):
|
||||||
"""Raised when an invalid task type is registered as a lifespan task."""
|
"""Raised when an invalid task type is registered as a lifespan task."""
|
||||||
|
|
||||||
|
|
||||||
|
class DynamicComponentMissingLibrary(ReflexError, ValueError):
|
||||||
|
"""Raised when a dynamic component is missing a library."""
|
||||||
|
Loading…
Reference in New Issue
Block a user