Optimize dev mode compile (#1348)
This commit is contained in:
parent
c589af84c1
commit
7397cd795a
@ -18,6 +18,7 @@ from typing import (
|
|||||||
|
|
||||||
from fastapi import FastAPI, UploadFile
|
from fastapi import FastAPI, UploadFile
|
||||||
from fastapi.middleware import cors
|
from fastapi.middleware import cors
|
||||||
|
from rich.progress import MofNCompleteColumn, Progress, TimeElapsedColumn
|
||||||
from socketio import ASGIApp, AsyncNamespace, AsyncServer
|
from socketio import ASGIApp, AsyncNamespace, AsyncServer
|
||||||
from starlette_admin.contrib.sqla.admin import Admin
|
from starlette_admin.contrib.sqla.admin import Admin
|
||||||
from starlette_admin.contrib.sqla.view import ModelView
|
from starlette_admin.contrib.sqla.view import ModelView
|
||||||
@ -437,6 +438,14 @@ class App(Base):
|
|||||||
|
|
||||||
def compile(self):
|
def compile(self):
|
||||||
"""Compile the app and output it to the pages folder."""
|
"""Compile the app and output it to the pages folder."""
|
||||||
|
# Create a progress bar.
|
||||||
|
progress = Progress(
|
||||||
|
*Progress.get_default_columns()[:-1],
|
||||||
|
MofNCompleteColumn(),
|
||||||
|
TimeElapsedColumn(),
|
||||||
|
)
|
||||||
|
task = progress.add_task("Compiling: ", total=len(self.pages))
|
||||||
|
|
||||||
for render, kwargs in DECORATED_ROUTES:
|
for render, kwargs in DECORATED_ROUTES:
|
||||||
self.add_page(render, **kwargs)
|
self.add_page(render, **kwargs)
|
||||||
|
|
||||||
@ -450,47 +459,60 @@ class App(Base):
|
|||||||
# Empty the .web pages directory
|
# Empty the .web pages directory
|
||||||
compiler.purge_web_pages_dir()
|
compiler.purge_web_pages_dir()
|
||||||
|
|
||||||
# Compile the root document with base styles and fonts.
|
# Store the compile results.
|
||||||
compiler.compile_document_root(self.stylesheets)
|
compile_results = []
|
||||||
|
|
||||||
# Compile the theme.
|
# Compile the pages in parallel.
|
||||||
compiler.compile_theme(self.style)
|
|
||||||
|
|
||||||
# Compile the Tailwind config.
|
|
||||||
compiler.compile_tailwind(
|
|
||||||
dict(**config.tailwind, content=constants.TAILWIND_CONTENT)
|
|
||||||
if config.tailwind is not None
|
|
||||||
else {}
|
|
||||||
)
|
|
||||||
|
|
||||||
# Compile the pages.
|
|
||||||
custom_components = set()
|
custom_components = set()
|
||||||
thread_pool = ThreadPool()
|
thread_pool = ThreadPool()
|
||||||
compile_results = []
|
with progress:
|
||||||
for route, component in self.pages.items():
|
for route, component in self.pages.items():
|
||||||
component.add_style(self.style)
|
progress.advance(task)
|
||||||
compile_results.append(
|
component.add_style(self.style)
|
||||||
thread_pool.apply_async(
|
compile_results.append(
|
||||||
compiler.compile_page,
|
thread_pool.apply_async(
|
||||||
args=(
|
compiler.compile_page,
|
||||||
route,
|
args=(
|
||||||
component,
|
route,
|
||||||
self.state,
|
component,
|
||||||
self.connect_error_component,
|
self.state,
|
||||||
),
|
self.connect_error_component,
|
||||||
|
),
|
||||||
|
)
|
||||||
)
|
)
|
||||||
)
|
# Add the custom components from the page to the set.
|
||||||
# Add the custom components from the page to the set.
|
custom_components |= component.get_custom_components()
|
||||||
custom_components |= component.get_custom_components()
|
|
||||||
thread_pool.close()
|
thread_pool.close()
|
||||||
thread_pool.join()
|
thread_pool.join()
|
||||||
|
|
||||||
# check the results of all the threads in case an exception was raised.
|
# Get the results.
|
||||||
for r in compile_results:
|
compile_results = [result.get() for result in compile_results]
|
||||||
r.get()
|
|
||||||
|
|
||||||
# Compile the custom components.
|
# Compile the custom components.
|
||||||
compiler.compile_components(custom_components)
|
compile_results.append(compiler.compile_components(custom_components))
|
||||||
|
|
||||||
|
# Compile the root document with base styles and fonts.
|
||||||
|
compile_results.append(compiler.compile_document_root(self.stylesheets))
|
||||||
|
|
||||||
|
# Compile the theme.
|
||||||
|
compile_results.append(compiler.compile_theme(self.style))
|
||||||
|
|
||||||
|
# Compile the Tailwind config.
|
||||||
|
compile_results.append(
|
||||||
|
compiler.compile_tailwind(
|
||||||
|
dict(**config.tailwind, content=constants.TAILWIND_CONTENT)
|
||||||
|
if config.tailwind is not None
|
||||||
|
else {}
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
# Write the pages at the end to trigger the NextJS hot reload only once.
|
||||||
|
thread_pool = ThreadPool()
|
||||||
|
for output_path, code in compile_results:
|
||||||
|
compiler_utils.write_page(output_path, code)
|
||||||
|
thread_pool.apply_async(compiler_utils.write_page, args=(output_path, code))
|
||||||
|
thread_pool.close()
|
||||||
|
thread_pool.join()
|
||||||
|
|
||||||
|
|
||||||
async def process(
|
async def process(
|
||||||
|
@ -1,14 +1,12 @@
|
|||||||
"""Compiler for the reflex apps."""
|
"""Compiler for the reflex apps."""
|
||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
from functools import wraps
|
from typing import List, Set, Tuple, Type
|
||||||
from typing import Callable, List, Set, Tuple, Type
|
|
||||||
|
|
||||||
from reflex import constants
|
from reflex import constants
|
||||||
from reflex.compiler import templates, utils
|
from reflex.compiler import templates, utils
|
||||||
from reflex.components.component import Component, CustomComponent
|
from reflex.components.component import Component, ComponentStyle, CustomComponent
|
||||||
from reflex.state import State
|
from reflex.state import State
|
||||||
from reflex.style import Style
|
|
||||||
from reflex.utils import imports
|
from reflex.utils import imports
|
||||||
from reflex.vars import ImportVar
|
from reflex.vars import ImportVar
|
||||||
|
|
||||||
@ -144,36 +142,6 @@ def _compile_tailwind(
|
|||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def write_output(fn: Callable[..., Tuple[str, str]]):
|
|
||||||
"""Write the output of the function to a file.
|
|
||||||
|
|
||||||
Args:
|
|
||||||
fn: The function to decorate.
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
The decorated function.
|
|
||||||
"""
|
|
||||||
|
|
||||||
@wraps(fn)
|
|
||||||
def wrapper(*args, write: bool = True) -> Tuple[str, str]:
|
|
||||||
"""Write the output of the function to a file.
|
|
||||||
|
|
||||||
Args:
|
|
||||||
*args: The arguments to pass to the function.
|
|
||||||
write: Whether to write the output to a file.
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
The path and code of the output.
|
|
||||||
"""
|
|
||||||
path, code = fn(*args)
|
|
||||||
if write:
|
|
||||||
utils.write_page(path, code)
|
|
||||||
return path, code
|
|
||||||
|
|
||||||
return wrapper
|
|
||||||
|
|
||||||
|
|
||||||
@write_output
|
|
||||||
def compile_document_root(stylesheets: List[str]) -> Tuple[str, str]:
|
def compile_document_root(stylesheets: List[str]) -> Tuple[str, str]:
|
||||||
"""Compile the document root.
|
"""Compile the document root.
|
||||||
|
|
||||||
@ -194,8 +162,7 @@ def compile_document_root(stylesheets: List[str]) -> Tuple[str, str]:
|
|||||||
return output_path, code
|
return output_path, code
|
||||||
|
|
||||||
|
|
||||||
@write_output
|
def compile_theme(style: ComponentStyle) -> Tuple[str, str]:
|
||||||
def compile_theme(style: Style) -> Tuple[str, str]:
|
|
||||||
"""Compile the theme.
|
"""Compile the theme.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
@ -214,7 +181,6 @@ def compile_theme(style: Style) -> Tuple[str, str]:
|
|||||||
return output_path, code
|
return output_path, code
|
||||||
|
|
||||||
|
|
||||||
@write_output
|
|
||||||
def compile_page(
|
def compile_page(
|
||||||
path: str,
|
path: str,
|
||||||
component: Component,
|
component: Component,
|
||||||
@ -240,7 +206,6 @@ def compile_page(
|
|||||||
return output_path, code
|
return output_path, code
|
||||||
|
|
||||||
|
|
||||||
@write_output
|
|
||||||
def compile_components(components: Set[CustomComponent]):
|
def compile_components(components: Set[CustomComponent]):
|
||||||
"""Compile the custom components.
|
"""Compile the custom components.
|
||||||
|
|
||||||
@ -258,7 +223,6 @@ def compile_components(components: Set[CustomComponent]):
|
|||||||
return output_path, code
|
return output_path, code
|
||||||
|
|
||||||
|
|
||||||
@write_output
|
|
||||||
def compile_tailwind(
|
def compile_tailwind(
|
||||||
config: dict,
|
config: dict,
|
||||||
):
|
):
|
||||||
|
@ -18,7 +18,7 @@ from reflex.components.base import (
|
|||||||
Script,
|
Script,
|
||||||
Title,
|
Title,
|
||||||
)
|
)
|
||||||
from reflex.components.component import Component, CustomComponent
|
from reflex.components.component import Component, ComponentStyle, CustomComponent
|
||||||
from reflex.event import get_hydrate_event
|
from reflex.event import get_hydrate_event
|
||||||
from reflex.state import State
|
from reflex.state import State
|
||||||
from reflex.style import Style
|
from reflex.style import Style
|
||||||
@ -188,7 +188,7 @@ def create_document_root(stylesheets: List[str]) -> Component:
|
|||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def create_theme(style: Style) -> Dict:
|
def create_theme(style: ComponentStyle) -> Dict:
|
||||||
"""Create the base style for the app.
|
"""Create the base style for the app.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
|
@ -190,7 +190,7 @@ CONFIG_FILE = f"{CONFIG_MODULE}{PY_EXT}"
|
|||||||
# The previous config file.
|
# The previous config file.
|
||||||
OLD_CONFIG_FILE = f"pcconfig{PY_EXT}"
|
OLD_CONFIG_FILE = f"pcconfig{PY_EXT}"
|
||||||
# The deployment URL.
|
# The deployment URL.
|
||||||
PRODUCTION_BACKEND_URL = "https://{username}-{app_name}.api.reflex.app"
|
PRODUCTION_BACKEND_URL = "https://{username}-{app_name}.api.pynecone.app"
|
||||||
# Token expiration time in seconds.
|
# Token expiration time in seconds.
|
||||||
TOKEN_EXPIRATION = 60 * 60
|
TOKEN_EXPIRATION = 60 * 60
|
||||||
|
|
||||||
|
@ -178,8 +178,7 @@ def deploy(dry_run: bool = typer.Option(False, help="Whether to run a dry run.")
|
|||||||
|
|
||||||
# Compile the app in production mode.
|
# Compile the app in production mode.
|
||||||
typer.echo("Compiling production app")
|
typer.echo("Compiling production app")
|
||||||
app = prerequisites.get_app().app
|
export(for_reflex_deploy=True)
|
||||||
build.export_app(app, zip=True, deploy_url=config.deploy_url)
|
|
||||||
|
|
||||||
# Exit early if this is a dry run.
|
# Exit early if this is a dry run.
|
||||||
if dry_run:
|
if dry_run:
|
||||||
|
@ -5,7 +5,6 @@ from __future__ import annotations
|
|||||||
import os
|
import os
|
||||||
import platform
|
import platform
|
||||||
import subprocess
|
import subprocess
|
||||||
from datetime import datetime
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
from rich import print
|
from rich import print
|
||||||
@ -42,22 +41,12 @@ def run_process_and_launch_url(
|
|||||||
cwd=constants.WEB_DIR,
|
cwd=constants.WEB_DIR,
|
||||||
)
|
)
|
||||||
|
|
||||||
current_time = datetime.now()
|
|
||||||
if process.stdout:
|
if process.stdout:
|
||||||
for line in process.stdout:
|
for line in process.stdout:
|
||||||
if "ready started server on" in line:
|
if "ready started server on" in line:
|
||||||
url = line.split("url: ")[-1].strip()
|
url = line.split("url: ")[-1].strip()
|
||||||
print(f"App running at: [bold green]{url}")
|
print(f"App running at: [bold green]{url}")
|
||||||
if (
|
if loglevel == constants.LogLevel.DEBUG:
|
||||||
"Fast Refresh" in line
|
|
||||||
or "compiling..." in line
|
|
||||||
and (datetime.now() - current_time).total_seconds() > 1
|
|
||||||
):
|
|
||||||
current_time = datetime.now()
|
|
||||||
print(
|
|
||||||
f"[yellow][Updating App][/yellow] Applying changes and refreshing. Time: {current_time}"
|
|
||||||
)
|
|
||||||
elif loglevel == constants.LogLevel.DEBUG:
|
|
||||||
print(line, end="")
|
print(line, end="")
|
||||||
|
|
||||||
|
|
||||||
@ -130,8 +119,8 @@ def run_backend(
|
|||||||
"--log-level",
|
"--log-level",
|
||||||
loglevel,
|
loglevel,
|
||||||
"--reload",
|
"--reload",
|
||||||
"--reload-exclude",
|
"--reload-dir",
|
||||||
f"'{constants.WEB_DIR}/*'",
|
app_name.split(".")[0],
|
||||||
]
|
]
|
||||||
process = subprocess.Popen(cmd)
|
process = subprocess.Popen(cmd)
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user