diff --git a/.gitignore b/.gitignore index 75485ddbf..50febabbe 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,6 @@ +# --- Build Artifacts --- +src/idom/_client + # --- Jupyter --- *.ipynb_checkpoints *Untitled*.ipynb @@ -37,6 +40,5 @@ pip-wheel-metadata .vscode # --- JS --- - node_modules -src/idom/client + diff --git a/MANIFEST.in b/MANIFEST.in index 39ea6e477..b49a2df3d 100644 --- a/MANIFEST.in +++ b/MANIFEST.in @@ -1,3 +1,3 @@ -recursive-include src/idom/client * +recursive-include src/idom/_client * recursive-include src/idom/web/templates * include src/idom/py.typed diff --git a/docs/app.py b/docs/app.py index dfdf98040..ea71b2293 100644 --- a/docs/app.py +++ b/docs/app.py @@ -5,8 +5,8 @@ from sanic import Sanic, response from idom import component +from idom.backend.sanic import Options, configure, use_request from idom.core.types import ComponentConstructor -from idom.server.sanic import Options, configure, use_request from .examples import get_normalized_example_name, load_examples diff --git a/docs/source/about/changelog.rst b/docs/source/about/changelog.rst index 352178dc8..75ae2669e 100644 --- a/docs/source/about/changelog.rst +++ b/docs/source/about/changelog.rst @@ -48,6 +48,11 @@ Changed: - IDOM's client now uses Preact instead of React - :pull:`721` +- Renamed ``idom.server`` to ``idom.backend`` - :pull:`726` + + Other references to "server implementations" have been renamed to "backend + implementations" throughout the documentation and code. + Removed: - ``redirect_root`` server option - :pull:`721` diff --git a/docs/source/about/contributor-guide.rst b/docs/source/about/contributor-guide.rst index b70b7cd32..caf882977 100644 --- a/docs/source/about/contributor-guide.rst +++ b/docs/source/about/contributor-guide.rst @@ -32,12 +32,6 @@ Still aren't sure what you have to offer? Just :discussion-type:`ask us ` and we'll answer them. - - Making a Pull Request --------------------- @@ -53,21 +47,25 @@ about how to get started. To make a change to IDOM you'll do the following: You use a ``git clone`` command to copy the code from GitHub to your computer. `Create a new branch `__: - You'll ``git checkout -b your-first-branch`` to create a new space to start your work + You'll ``git checkout -b your-first-branch`` to create a new space to start your work. :ref:`Prepare your Development Environment `: - We explain in more detail below how to install all IDOM's dependencies + We explain in more detail below how to install all IDOM's dependencies. `Push your changes `__: Once you've made changes to IDOM, you'll ``git push`` them to your fork. +:ref:`Create a changelog entry `: + Record your changes in the :ref:`changelog` so we can publicize them in the next release. + `Create a Pull Request `__: We'll review your changes, run some :ref:`tests ` and :ref:`equality checks ` and, with any luck, accept your request. At that point your contribution will be merged into the main codebase! + Creating a Changelog Entry -.......................... +-------------------------- As part of your pull request, you'll want to edit the `Changelog `__ by @@ -112,6 +110,11 @@ might look like: Development Environment ----------------------- +.. note:: + + If you have any questions during set up or development post on our + :discussion-type:`discussion board ` and we'll answer them. + In order to develop IDOM locally you'll first need to install the following: .. list-table:: @@ -120,7 +123,7 @@ In order to develop IDOM locally you'll first need to install the following: * - What to Install - How to Install - * - Git_ + * - Git - https://git-scm.com/book/en/v2/Getting-Started-Installing-Git * - Python >= 3.7 diff --git a/docs/source/guides/adding-interactivity/components-with-state/index.rst b/docs/source/guides/adding-interactivity/components-with-state/index.rst index 3925b3cf2..5317b98a2 100644 --- a/docs/source/guides/adding-interactivity/components-with-state/index.rst +++ b/docs/source/guides/adding-interactivity/components-with-state/index.rst @@ -22,7 +22,7 @@ does not work: Try clicking the button to see that it does not cause a change. -After clicking "Next", if you check the server logs, you'll discover an +After clicking "Next", if you check your web server's logs, you'll discover an ``UnboundLocalError`` error. It turns out that in this case, the ``index = index + 1`` statement is similar to `trying to set global variables `__. diff --git a/docs/source/guides/adding-interactivity/responding-to-events/index.rst b/docs/source/guides/adding-interactivity/responding-to-events/index.rst index 3b3033bf6..6e916b6bf 100644 --- a/docs/source/guides/adding-interactivity/responding-to-events/index.rst +++ b/docs/source/guides/adding-interactivity/responding-to-events/index.rst @@ -100,7 +100,7 @@ Event Data Serialization Not all event data is serialized. The most notable example of this is the lack of a ``target`` key in the dictionary sent back to the handler. Instead, data which is not -inherhently JSON serializable must be treated on a case-by-case basis. A simple case +inherently JSON serializable must be treated on a case-by-case basis. A simple case to demonstrate this is the ``currentTime`` attribute of ``audio`` and ``video`` elements. Normally this would be accessible via ``event.target.currentTime``, but here it's simply passed in under the key ``currentTime``: diff --git a/docs/source/guides/creating-interfaces/index.rst b/docs/source/guides/creating-interfaces/index.rst index 74c662969..f8ec0016c 100644 --- a/docs/source/guides/creating-interfaces/index.rst +++ b/docs/source/guides/creating-interfaces/index.rst @@ -45,7 +45,7 @@ conditionally display more complex UIs. Section 1: HTML with IDOM ------------------------- -In a typical Python-base web application the resonsibility of defining the view along +In a typical Python-base web application the responsibility of defining the view along with its backing data and logic are distributed between a client and server respectively. With IDOM, both these tasks are centralized in a single place. The most foundational pilar of this capability is formed by allowing HTML interfaces to be @@ -112,7 +112,7 @@ Section 3: Rendering Data The last pillar of knowledge you need before you can start making :ref:`interactive interfaces ` is the ability to render sections of the UI given a collection of data. This will require you to understand how elements which are derived -from data in this way must be orgnized with :ref:`"keys" `. +from data in this way must be organized with :ref:`"keys" `. One case where we might want to do this is if items in a todo list come from a list of data that we want to sort and filter: diff --git a/docs/source/guides/escape-hatches/index.rst b/docs/source/guides/escape-hatches/index.rst index f17a3beb4..3ef1b7122 100644 --- a/docs/source/guides/escape-hatches/index.rst +++ b/docs/source/guides/escape-hatches/index.rst @@ -6,8 +6,8 @@ Escape Hatches javascript-components distributing-javascript - writing-your-own-server - writing-your-own-client + using-a-custom-backend + using-a-custom-client .. note:: diff --git a/docs/source/guides/escape-hatches/using-a-custom-backend.rst b/docs/source/guides/escape-hatches/using-a-custom-backend.rst new file mode 100644 index 000000000..f9d21208a --- /dev/null +++ b/docs/source/guides/escape-hatches/using-a-custom-backend.rst @@ -0,0 +1,9 @@ +.. _Writing Your Own Backend: +.. _Using a Custom Backend: + +Using a Custom Backend 🚧 +========================= + +.. note:: + + Under construction 🚧 diff --git a/docs/source/guides/escape-hatches/using-a-custom-client.rst b/docs/source/guides/escape-hatches/using-a-custom-client.rst new file mode 100644 index 000000000..95de23e59 --- /dev/null +++ b/docs/source/guides/escape-hatches/using-a-custom-client.rst @@ -0,0 +1,9 @@ +.. _Writing Your Own Client: +.. _Using a Custom Client: + +Using a Custom Client 🚧 +======================== + +.. note:: + + Under construction 🚧 diff --git a/docs/source/guides/escape-hatches/writing-your-own-client.rst b/docs/source/guides/escape-hatches/writing-your-own-client.rst deleted file mode 100644 index f52235813..000000000 --- a/docs/source/guides/escape-hatches/writing-your-own-client.rst +++ /dev/null @@ -1,8 +0,0 @@ -.. _Writing Your Own Client: - -Writing Your Own Client 🚧 -========================== - -.. note:: - - Under construction 🚧 diff --git a/docs/source/guides/escape-hatches/writing-your-own-server.rst b/docs/source/guides/escape-hatches/writing-your-own-server.rst deleted file mode 100644 index 51f0a70e9..000000000 --- a/docs/source/guides/escape-hatches/writing-your-own-server.rst +++ /dev/null @@ -1,8 +0,0 @@ -.. _Writing Your Own Server: - -Writing Your Own Server 🚧 -========================== - -.. note:: - - Under construction 🚧 diff --git a/docs/source/guides/getting-started/_examples/run_fastapi.py b/docs/source/guides/getting-started/_examples/run_fastapi.py index f114333bb..607ad7776 100644 --- a/docs/source/guides/getting-started/_examples/run_fastapi.py +++ b/docs/source/guides/getting-started/_examples/run_fastapi.py @@ -1,7 +1,7 @@ # :lines: 11- from idom import run -from idom.server import fastapi as fastapi_server +from idom.backend import fastapi as fastapi_server # the run() function is the entry point for examples @@ -11,7 +11,7 @@ from fastapi import FastAPI from idom import component, html -from idom.server.fastapi import configure +from idom.backend.fastapi import configure @component diff --git a/docs/source/guides/getting-started/_examples/run_flask.py b/docs/source/guides/getting-started/_examples/run_flask.py index 9f64d0e15..310aca60e 100644 --- a/docs/source/guides/getting-started/_examples/run_flask.py +++ b/docs/source/guides/getting-started/_examples/run_flask.py @@ -1,7 +1,7 @@ # :lines: 11- from idom import run -from idom.server import flask as flask_server +from idom.backend import flask as flask_server # the run() function is the entry point for examples @@ -11,7 +11,7 @@ from flask import Flask from idom import component, html -from idom.server.flask import configure +from idom.backend.flask import configure @component diff --git a/docs/source/guides/getting-started/_examples/run_sanic.py b/docs/source/guides/getting-started/_examples/run_sanic.py index 449e2b2e1..d5e8434db 100644 --- a/docs/source/guides/getting-started/_examples/run_sanic.py +++ b/docs/source/guides/getting-started/_examples/run_sanic.py @@ -1,7 +1,7 @@ # :lines: 11- from idom import run -from idom.server import sanic as sanic_server +from idom.backend import sanic as sanic_server # the run() function is the entry point for examples @@ -11,7 +11,7 @@ from sanic import Sanic from idom import component, html -from idom.server.sanic import configure +from idom.backend.sanic import configure @component diff --git a/docs/source/guides/getting-started/_examples/run_starlette.py b/docs/source/guides/getting-started/_examples/run_starlette.py index f287b831b..0010c5271 100644 --- a/docs/source/guides/getting-started/_examples/run_starlette.py +++ b/docs/source/guides/getting-started/_examples/run_starlette.py @@ -1,7 +1,7 @@ # :lines: 11- from idom import run -from idom.server import starlette as starlette_server +from idom.backend import starlette as starlette_server # the run() function is the entry point for examples @@ -11,7 +11,7 @@ from starlette.applications import Starlette from idom import component, html -from idom.server.starlette import configure +from idom.backend.starlette import configure @component diff --git a/docs/source/guides/getting-started/_examples/run_tornado.py b/docs/source/guides/getting-started/_examples/run_tornado.py index 313fdf4fe..0c1b35353 100644 --- a/docs/source/guides/getting-started/_examples/run_tornado.py +++ b/docs/source/guides/getting-started/_examples/run_tornado.py @@ -1,7 +1,7 @@ # :lines: 11- from idom import run -from idom.server import tornado as tornado_server +from idom.backend import tornado as tornado_server # the run() function is the entry point for examples @@ -12,7 +12,7 @@ import tornado.web from idom import component, html -from idom.server.tornado import configure +from idom.backend.tornado import configure @component diff --git a/docs/source/guides/getting-started/_static/embed-idom-view/main.py b/docs/source/guides/getting-started/_static/embed-idom-view/main.py index e33173173..32db294ee 100644 --- a/docs/source/guides/getting-started/_static/embed-idom-view/main.py +++ b/docs/source/guides/getting-started/_static/embed-idom-view/main.py @@ -2,7 +2,7 @@ from sanic.response import file from idom import component, html -from idom.server.sanic import Options, configure +from idom.backend.sanic import Options, configure app = Sanic("MyApp") diff --git a/docs/source/guides/getting-started/index.rst b/docs/source/guides/getting-started/index.rst index 1aed237d9..7d05d868e 100644 --- a/docs/source/guides/getting-started/index.rst +++ b/docs/source/guides/getting-started/index.rst @@ -106,9 +106,9 @@ Section 2: Running IDOM Once you've :ref:`installed IDOM `, you'll want to learn how to run an application. Throughout most of the examples in this documentation, you'll see the -:func:`~idom.server.utils.run` function used. While it's convenient tool for development -it shouldn't be used in production settings - it's slow, and could leak secrets through -debug log messages. +:func:`~idom.backend.utils.run` function used. While it's convenient tool for +development it shouldn't be used in production settings - it's slow, and could leak +secrets through debug log messages. .. idom:: _examples/hello_world diff --git a/docs/source/guides/getting-started/installing-idom.rst b/docs/source/guides/getting-started/installing-idom.rst index 06dffe0a7..352d82294 100644 --- a/docs/source/guides/getting-started/installing-idom.rst +++ b/docs/source/guides/getting-started/installing-idom.rst @@ -1,28 +1,28 @@ Installing IDOM =============== -Installing IDOM with ``pip`` will generally require doing so alongside a supported -server implementation. This can be done by specifying an installation extra using square -brackets. For example, if we want to run IDOM using `Starlette -`__ we would run: +You will typically ``pip`` install IDOM to alongside one of it's natively supported +backends. For example, if we want to run IDOM using the `Starlette +`__ backend you would run .. code-block:: bash pip install "idom[starlette]" -If you want to install a "pure" version of IDOM without a server implementation you can -do so without any installation extras. You might do this if you wanted to user a server -which is not officially supported or if you wanted to manually pin your dependencies: +If you want to install a "pure" version of IDOM without a backend implementation you can +do so without any installation extras. You might do this if you wanted to :ref:`use a +custom backend ` or if you wanted to manually pin your +dependencies: .. code-block:: bash pip install idom -Officially Supported Servers ----------------------------- +Native Backends +--------------- -IDOM includes built-in support for a variety web server implementations. To install the +IDOM includes built-in support for a variety backend implementations. To install the required dependencies for each you should substitute ``starlette`` from the ``pip install`` command above with one of the options below: @@ -39,15 +39,15 @@ If you need to, you can install more than one option by separating them with com pip install "idom[fastapi,flask,sanic,starlette,tornado]" Once this is complete you should be able to :ref:`run IDOM ` with your -chosen server implementation. +chosen implementation. -Installing In Other Frameworks ------------------------------- +Other Backends +-------------- -While IDOM can run in a variety of contexts, sometimes web frameworks require extra work -in order to integrate with them. In these cases, the IDOM team distributes bindings for -various frameworks as separate Python packages. For documentation on how to install and +While IDOM can run in a variety of contexts, sometimes frameworks require extra work in +order to integrate with them. In these cases, the IDOM team distributes bindings for +those frameworks as separate Python packages. For documentation on how to install and run IDOM in these supported frameworks, follow the links below: .. raw:: html @@ -96,8 +96,8 @@ run IDOM in these supported frameworks, follow the links below: :transparent-text-color:`Plotly Dash` -Installing for Development --------------------------- +For Development +--------------- If you want to contribute to the development of IDOM or modify it, you'll want to install a development version of IDOM. This involves cloning the repository where IDOM's diff --git a/docs/source/guides/getting-started/running-idom.rst b/docs/source/guides/getting-started/running-idom.rst index 0b5ea60e3..c0ae0e449 100644 --- a/docs/source/guides/getting-started/running-idom.rst +++ b/docs/source/guides/getting-started/running-idom.rst @@ -1,7 +1,7 @@ Running IDOM ============ -The simplest way to run IDOM is with the :func:`~idom.server.utils.run` function. This +The simplest way to run IDOM is with the :func:`~idom.backend.utils.run` function. This is the method you'll see used throughout this documentation. However, this executes your application using a development server which is great for testing, but probably not what if you're :ref:`deploying in production `. Below are some @@ -12,18 +12,18 @@ Running IDOM in Production -------------------------- The first thing you'll need to do if you want to run IDOM in production is choose a -server implementation and follow its documentation on how to create and run an -application. This is the server :ref:`you probably chose ` -when installing IDOM. Then you'll need to configure that application with an IDOM view. -We should the basics how how to run each supported server below, but all implementations -will follow a pattern similar to the following: +backend implementation and follow its documentation on how to create and run an +application. This is the backend :ref:`you probably chose ` when +installing IDOM. Then you'll need to configure that application with an IDOM view. We +show the basics of how to set up, and then run, each supported backend below, but all +implementations will follow a pattern similar to the following: .. code-block:: - from my_chosen_server import Application + from my_chosen_backend import Application from idom import component, html - from idom.server.my_chosen_server import configure + from idom.backend.my_chosen_backend import configure @component @@ -34,8 +34,8 @@ will follow a pattern similar to the following: app = Application() configure(app, HelloWorld) -You'll then run this ``app`` using a `ASGI `__ or -`WSGI `__ server from the command line. +You'll then run this ``app`` using an `ASGI `__ +or `WSGI `__ server from the command line. Running with `FastAPI `__ @@ -43,8 +43,8 @@ Running with `FastAPI `__ .. idom:: _examples/run_fastapi -Then assuming you put this in ``main.py``, you can run the ``app`` using `Uvicorn -`__: +Then assuming you put this in ``main.py``, you can run the ``app`` using the `Uvicorn +`__ ASGI server: .. code-block:: bash @@ -56,8 +56,8 @@ Running with `Flask `__ .. idom:: _examples/run_flask -Then assuming you put this in ``main.py``, you can run the ``app`` using `Gunicorn -`__: +Then assuming you put this in ``main.py``, you can run the ``app`` using the `Gunicorn +`__ WSGI server: .. code-block:: bash @@ -82,8 +82,8 @@ Running with `Starlette `__ .. idom:: _examples/run_starlette -Then assuming you put this in ``main.py``, you can run the application using `Uvicorn -`__: +Then assuming you put this in ``main.py``, you can run the application using the +`Uvicorn `__ ASGI server: .. code-block:: bash @@ -143,25 +143,25 @@ Errors will be displayed where the uppermost component is located in the view: .. idom:: _examples/debug_error_example -Server Configuration Options ----------------------------- +Backend Configuration Options +----------------------------- -IDOM's various server implementations come with ``Options`` that can be passed to their +IDOM's various backend implementations come with ``Options`` that can be passed to their respective ``configure()`` functions in the following way: .. code-block:: - from idom.server. import configure, Options + from idom.backend. import configure, Options configure(app, MyComponent, Options(...)) -To learn more read about the options for your chosen server ````: +To learn more read about the options for your chosen backend ````: -- :class:`idom.server.fastapi.Options` -- :class:`idom.server.flask.Options` -- :class:`idom.server.sanic.Options` -- :class:`idom.server.starlette.Options` -- :class:`idom.server.tornado.Options` +- :class:`idom.backend.fastapi.Options` +- :class:`idom.backend.flask.Options` +- :class:`idom.backend.sanic.Options` +- :class:`idom.backend.starlette.Options` +- :class:`idom.backend.tornado.Options` Embed in an Existing Webpage @@ -187,8 +187,8 @@ embedding one the examples from this documentation into your own webpage: .. note:: For more information on how to use the client see the :ref:`Javascript API` - reference. Or if you need to, your can :ref:`write your own server implementation - `. + reference. Or if you need to, your can :ref:`write your own backend implementation + `. As mentioned though, this is connecting to the server that is hosting this documentation. If you want to connect to a view from your own server, you'll need to diff --git a/docs/source/index.rst b/docs/source/index.rst index 1a48693f9..5260157fc 100644 --- a/docs/source/index.rst +++ b/docs/source/index.rst @@ -73,8 +73,13 @@ of HTML element called an ``h1`` `section heading `__. Importantly though, a ``@component`` decorator has been applied to the ``App`` function to turn it into a :ref:`component `. Finally, we :ref:`run -` an application server by passing the ``App`` component to the ``run()`` -function. +` a development web server by passing the ``App`` component to the +``run()`` function. + +.. note:: + + See :ref:`Running IDOM in Production` to learn how to use a production-grade server + to run IDOM. Learning IDOM diff --git a/scripts/live_docs.py b/scripts/live_docs.py index e21339326..540af79db 100644 --- a/scripts/live_docs.py +++ b/scripts/live_docs.py @@ -14,7 +14,7 @@ ) from docs.app import IDOM_MODEL_SERVER_URL_PREFIX, Example, make_app, reload_examples -from idom.server.sanic import Options, configure, serve_development_app +from idom.backend.sanic import Options, configure, serve_development_app from idom.testing import clear_idom_web_modules_dir diff --git a/src/client/snowpack.config.js b/src/client/snowpack.config.js index 265fd674c..5076548e2 100644 --- a/src/client/snowpack.config.js +++ b/src/client/snowpack.config.js @@ -1,7 +1,7 @@ module.exports = { workspaceRoot: false, testOptions: { files: ["**/tests/**/*", "**/*.test.*"] }, - buildOptions: { out: "../idom/client" }, + buildOptions: { out: "../idom/_client" }, mount: { public: { url: "/", static: true } }, optimize: { bundle: true, target: "es2018" }, alias: { diff --git a/src/idom/__init__.py b/src/idom/__init__.py index 8fd4da745..44b9ef451 100644 --- a/src/idom/__init__.py +++ b/src/idom/__init__.py @@ -1,4 +1,5 @@ -from . import config, html, logging, sample, server, types, web +from . import backend, config, html, logging, sample, types, web +from .backend.utils import run from .core import hooks from .core.component import component from .core.events import event @@ -15,7 +16,6 @@ from .core.layout import Layout from .core.serve import Stop from .core.vdom import vdom -from .server.utils import run from .utils import Ref, html_to_vdom from .widgets import hotswap @@ -37,7 +37,7 @@ "Ref", "run", "sample", - "server", + "backend", "Stop", "types", "use_callback", diff --git a/src/idom/server/__init__.py b/src/idom/backend/__init__.py similarity index 100% rename from src/idom/server/__init__.py rename to src/idom/backend/__init__.py diff --git a/src/idom/server/_asgi.py b/src/idom/backend/_asgi.py similarity index 100% rename from src/idom/server/_asgi.py rename to src/idom/backend/_asgi.py diff --git a/src/idom/server/default.py b/src/idom/backend/default.py similarity index 90% rename from src/idom/server/default.py rename to src/idom/backend/default.py index e87bfcbba..0cd593388 100644 --- a/src/idom/server/default.py +++ b/src/idom/backend/default.py @@ -5,7 +5,7 @@ from idom.types import RootComponentConstructor -from .types import Location, ServerImplementation +from .types import BackendImplementation, Location from .utils import all_implementations @@ -45,10 +45,10 @@ def use_location() -> Location: return _default_implementation().use_location() -_DEFAULT_IMPLEMENTATION: ServerImplementation[Any] | None = None +_DEFAULT_IMPLEMENTATION: BackendImplementation[Any] | None = None -def _default_implementation() -> ServerImplementation[Any]: +def _default_implementation() -> BackendImplementation[Any]: """Get the first available server implementation""" global _DEFAULT_IMPLEMENTATION diff --git a/src/idom/server/fastapi.py b/src/idom/backend/fastapi.py similarity index 100% rename from src/idom/server/fastapi.py rename to src/idom/backend/fastapi.py diff --git a/src/idom/server/flask.py b/src/idom/backend/flask.py similarity index 99% rename from src/idom/server/flask.py rename to src/idom/backend/flask.py index cf3f34dd1..6eacbe2c3 100644 --- a/src/idom/server/flask.py +++ b/src/idom/backend/flask.py @@ -25,11 +25,11 @@ from werkzeug.serving import BaseWSGIServer, make_server import idom +from idom.backend.types import Location from idom.core.hooks import Context, create_context, use_context from idom.core.layout import LayoutEvent, LayoutUpdate from idom.core.serve import serve_json_patch from idom.core.types import ComponentType, RootComponentConstructor -from idom.server.types import Location from idom.utils import Ref from .utils import safe_client_build_dir_path, safe_web_modules_dir_path diff --git a/src/idom/server/sanic.py b/src/idom/backend/sanic.py similarity index 99% rename from src/idom/server/sanic.py rename to src/idom/backend/sanic.py index 7fa23abae..bb3397e74 100644 --- a/src/idom/server/sanic.py +++ b/src/idom/backend/sanic.py @@ -14,6 +14,7 @@ from sanic_cors import CORS from websockets.legacy.protocol import WebSocketCommonProtocol +from idom.backend.types import Location from idom.core.hooks import Context, create_context, use_context from idom.core.layout import Layout, LayoutEvent from idom.core.serve import ( @@ -24,7 +25,6 @@ serve_json_patch, ) from idom.core.types import RootComponentConstructor -from idom.server.types import Location from ._asgi import serve_development_asgi from .utils import safe_client_build_dir_path, safe_web_modules_dir_path diff --git a/src/idom/server/starlette.py b/src/idom/backend/starlette.py similarity index 99% rename from src/idom/server/starlette.py rename to src/idom/backend/starlette.py index d2fb369b6..5b78c8111 100644 --- a/src/idom/server/starlette.py +++ b/src/idom/backend/starlette.py @@ -12,6 +12,7 @@ from starlette.types import Receive, Scope, Send from starlette.websockets import WebSocket, WebSocketDisconnect +from idom.backend.types import Location from idom.config import IDOM_WEB_MODULES_DIR from idom.core.hooks import Context, create_context, use_context from idom.core.layout import Layout, LayoutEvent @@ -22,7 +23,6 @@ serve_json_patch, ) from idom.core.types import RootComponentConstructor -from idom.server.types import Location from ._asgi import serve_development_asgi from .utils import CLIENT_BUILD_DIR, safe_client_build_dir_path diff --git a/src/idom/server/tornado.py b/src/idom/backend/tornado.py similarity index 99% rename from src/idom/server/tornado.py rename to src/idom/backend/tornado.py index d8d9cf051..113013376 100644 --- a/src/idom/server/tornado.py +++ b/src/idom/backend/tornado.py @@ -16,12 +16,12 @@ from tornado.websocket import WebSocketHandler from tornado.wsgi import WSGIContainer +from idom.backend.types import Location from idom.config import IDOM_WEB_MODULES_DIR from idom.core.hooks import Context, create_context, use_context from idom.core.layout import Layout, LayoutEvent from idom.core.serve import VdomJsonPatch, serve_json_patch from idom.core.types import ComponentConstructor -from idom.server.types import Location from .utils import CLIENT_BUILD_DIR, safe_client_build_dir_path diff --git a/src/idom/server/types.py b/src/idom/backend/types.py similarity index 88% rename from src/idom/server/types.py rename to src/idom/backend/types.py index 236ec70a5..8a793b4f1 100644 --- a/src/idom/server/types.py +++ b/src/idom/backend/types.py @@ -6,15 +6,15 @@ from typing_extensions import Protocol, runtime_checkable -from idom.types import RootComponentConstructor +from idom.core.types import RootComponentConstructor _App = TypeVar("_App") @runtime_checkable -class ServerImplementation(Protocol[_App]): - """Common interface for IDOM's builti-in server implementations""" +class BackendImplementation(Protocol[_App]): + """Common interface for built-in web server/framework integrations""" def configure( self, diff --git a/src/idom/server/utils.py b/src/idom/backend/utils.py similarity index 88% rename from src/idom/server/utils.py rename to src/idom/backend/utils.py index ab647b483..b4c864d97 100644 --- a/src/idom/server/utils.py +++ b/src/idom/backend/utils.py @@ -13,11 +13,11 @@ from idom.config import IDOM_WEB_MODULES_DIR from idom.types import RootComponentConstructor -from .types import ServerImplementation +from .types import BackendImplementation logger = logging.getLogger(__name__) -CLIENT_BUILD_DIR = Path(idom.__file__).parent / "client" +CLIENT_BUILD_DIR = Path(idom.__file__).parent / "_client" SUPPORTED_PACKAGES = ( "starlette", @@ -32,7 +32,7 @@ def run( component: RootComponentConstructor, host: str = "127.0.0.1", port: int | None = None, - implementation: ServerImplementation[Any] | None = None, + implementation: BackendImplementation[Any] | None = None, ) -> None: """Run a component with a development server""" logger.warn( @@ -113,15 +113,17 @@ def find_available_port( ) -def all_implementations() -> Iterator[ServerImplementation[Any]]: +def all_implementations() -> Iterator[BackendImplementation[Any]]: """Yield all available server implementations""" for name in SUPPORTED_PACKAGES: try: - module = import_module(f"idom.server.{name}") + relative_import_name = f"{__name__.rsplit('.', 1)[0]}.{name}" + module = import_module(relative_import_name) except ImportError: # pragma: no cover + logger.debug(f"Failed to import {name!r}", exc_info=True) continue - if not isinstance(module, ServerImplementation): + if not isinstance(module, BackendImplementation): raise TypeError( # pragma: no cover f"{module.__name__!r} is an invalid implementation" ) diff --git a/src/idom/testing/server.py b/src/idom/testing/server.py index 862d50a7d..6ca26429b 100644 --- a/src/idom/testing/server.py +++ b/src/idom/testing/server.py @@ -7,9 +7,9 @@ from typing import Any, Optional, Tuple, Type, Union from urllib.parse import urlencode, urlunparse -from idom.server import default as default_server -from idom.server.types import ServerImplementation -from idom.server.utils import find_available_port +from idom.backend import default as default_server +from idom.backend.types import BackendImplementation +from idom.backend.utils import find_available_port from idom.widgets import hotswap from .logs import LogAssertionError, capture_idom_logs, list_logged_exceptions @@ -36,7 +36,7 @@ def __init__( host: str = "127.0.0.1", port: Optional[int] = None, app: Any | None = None, - implementation: ServerImplementation[Any] | None = None, + implementation: BackendImplementation[Any] | None = None, options: Any | None = None, ) -> None: self.host = host diff --git a/src/idom/types.py b/src/idom/types.py index ae11844eb..4f208068a 100644 --- a/src/idom/types.py +++ b/src/idom/types.py @@ -4,6 +4,7 @@ - :mod:`idom.server.types` """ +from .backend.types import BackendImplementation, Location from .core.hooks import Context from .core.types import ( ComponentConstructor, @@ -23,7 +24,6 @@ VdomDict, VdomJson, ) -from .server.types import Location, ServerImplementation __all__ = [ @@ -45,5 +45,5 @@ "VdomChildren", "VdomDict", "VdomJson", - "ServerImplementation", + "BackendImplementation", ] diff --git a/temp.py b/temp.py index eff7c494a..a67caa896 100644 --- a/temp.py +++ b/temp.py @@ -1,5 +1,5 @@ from idom import component, html, run -from idom.server import starlette as server +from idom.backend import starlette as server @component diff --git a/tests/test_server/test_common.py b/tests/test_server/test_common.py index 733286fbb..91c6dc41e 100644 --- a/tests/test_server/test_common.py +++ b/tests/test_server/test_common.py @@ -4,9 +4,9 @@ import idom from idom import html -from idom.server import default as default_implementation -from idom.server.types import Location -from idom.server.utils import all_implementations +from idom.backend import default as default_implementation +from idom.backend.types import Location +from idom.backend.utils import all_implementations from idom.testing import DisplayFixture, ServerFixture, poll diff --git a/tests/test_server/test_utils.py b/tests/test_server/test_utils.py index 7d82898f4..4820b6031 100644 --- a/tests/test_server/test_utils.py +++ b/tests/test_server/test_utils.py @@ -6,11 +6,11 @@ import pytest from playwright.async_api import Page +from idom.backend import flask as flask_implementation +from idom.backend.utils import find_available_port +from idom.backend.utils import run as sync_run +from idom.backend.utils import traversal_safe_path from idom.sample import SampleApp as SampleApp -from idom.server import flask as flask_implementation -from idom.server.utils import find_available_port -from idom.server.utils import run as sync_run -from idom.server.utils import traversal_safe_path from tests.tooling.loop import open_event_loop diff --git a/tests/test_testing.py b/tests/test_testing.py index abd738643..70d882a81 100644 --- a/tests/test_testing.py +++ b/tests/test_testing.py @@ -4,9 +4,9 @@ import pytest from idom import testing +from idom.backend import starlette as starlette_implementation from idom.logging import ROOT_LOGGER from idom.sample import SampleApp as SampleApp -from idom.server import starlette as starlette_implementation def test_assert_idom_logged_does_not_supress_errors(): diff --git a/tests/test_web/test_module.py b/tests/test_web/test_module.py index 57f2fb2e0..16846d2f5 100644 --- a/tests/test_web/test_module.py +++ b/tests/test_web/test_module.py @@ -4,7 +4,7 @@ from sanic import Sanic import idom -from idom.server import sanic as sanic_implementation +from idom.backend import sanic as sanic_implementation from idom.testing import ( DisplayFixture, ServerFixture,