Browse Source

Continuing editing about css files and prebuilt extensions.

Jason Grout 4 years ago
parent
commit
ecda1b772b
1 changed files with 17 additions and 32 deletions
  1. 17 32
      docs/source/extension/extension_dev.rst

+ 17 - 32
docs/source/extension/extension_dev.rst

@@ -349,9 +349,6 @@ When an extension (the "consumer") is optionally using a service identified by a
       }
     }
 
-
-
-
 .. TODO: fill out the following text to a more complete explanation of how the deduplication works.
 
    Prebuilt extensions need to deduplicate many of their dependencies with other prebuilt extensions and with source extensions. This deduplication happens in two phases:
@@ -447,14 +444,12 @@ A typical setup for e.g. a jupyter-widget based package will then be::
 
 Currently supported package managers are ``pip`` and ``conda``.
 
-CSS Imports
-^^^^^^^^^^^
+Extension CSS
+^^^^^^^^^^^^^
 
-- Discuss how JupyterLab puts your extension CSS on the page
-- Cover duplication of CSS issues
-- Mention the package.json styleModule key
+If your extension has a top-level ``style`` key in ``package.json``, and is not a theme extension (i.e., has no ``jupyterlab.themePath`` key), the CSS file it points to will be included on the page automatically.
 
-JupyterLab will prefer to put the ``styleModule`` key, then the style key, if they exist.
+A convention in JupyterLab for deduplicating CSS on the page is that if your extension has a top-level ``styleModule`` key in ``package.json`` giving a JavaScript module that can be imported, it will be preferred over the ``style`` key CSS file.
 
 
 Prebuilt Extensions
@@ -487,10 +482,9 @@ Custom webpack config
 """""""""""""""""""""
 
 .. warning::
-   This feature is *experimental* and may change without notice since it exposes internal implementation details (namely ``webpack``). Be careful in using it, as a misconfiguration may break the prebuilt extension system.
+   This feature is *experimental* and may change without notice since it exposes internal implementation details (namely webpack). Be careful in using it, as a misconfiguration may break the prebuilt extension system.
 
-The prebuilt extension system uses ``webpack`` to build extensions, relying on the
-`Module Federation System <https://webpack.js.org/concepts/module-federation/>`_ added in webpack 5. Normally this is an implementation detail that prebuilt extension authors do not need to worry about, but occasionally extension authors will want to tweak the configuration used to build their extension to enable various webpack features. Extension authors can specify a custom webpack config file that will be merged with the webpack config generated by the prebuilt extension system using the ``jupyterlab.webpackConfig`` field in ``package.json``. The value should be the relative path to the config file:
+The prebuilt extension system uses the Webpack `Module Federation System <https://webpack.js.org/concepts/module-federation/>`_. Normally this is an implementation detail that prebuilt extension authors do not need to worry about, but occasionally extension authors will want to tweak the configuration used to build their extension to enable various webpack features. Extension authors can specify a custom webpack config file that will be merged with the webpack config generated by the prebuilt extension system using the ``jupyterlab.webpackConfig`` field in ``package.json``. The value should be the relative path to the config file:
 
 .. code-block:: json
 
@@ -498,7 +492,7 @@ The prebuilt extension system uses ``webpack`` to build extensions, relying on t
       "webpackConfig": "./webpack.config.js"
     }
 
-Here is an example of a ``webpack.config.js`` custom config that enables the async WebAssembly and top-level ``await`` experimental features of webpack:
+Custom webpack configuration can be used to enable webpack features, configure additional file loaders, and for many other things. Here is an example of a ``webpack.config.js`` custom config that enables the async WebAssembly and top-level ``await`` experimental features of webpack:
 
 .. code-block:: javascript
 
@@ -527,29 +521,20 @@ Since prebuilt extensions are distributed in many ways (Python pip packages, con
 * ``packageName``: This is the package name of the prebuilt extension in the package manager above, which may be different than the package name in ``package.json``.
 * ``uninstallInstructions``: This is a short block of text giving the user instructions for uninstalling the prebuilt extension. For example, it might instruct them to use a system package manager or talk to a system administrator.
 
-Steps for building
-^^^^^^^^^^^^^^^^^^
-- We provide a ``jupyter labextension build`` script that is used to build prebuilt bundles
-   - The command produces a set of static assets that are shipped along with a package (notionally on ``pip``/``conda``)
-   - It is a Python cli so that it can use the dependency metadata from the active JupyterLab
-   - The assets include a module federation ``remoteEntry.*.js``, generated bundles, and some other files that we use
-   - ``package.json`` is the original ``package.json`` file that we use to gather metadata about the package, with some included build metadata
-   - we use the previously existing ``@jupyterlab/builder -> build`` to generate the ``imports.css``, ``schemas`` and ``themes`` file structure
-- We provide a ``labextensions`` handler in ``jupyterlab_server`` that loads static assets from ``labextensions`` paths, following a similar logic to how ``nbextensions`` are discovered and loaded from disk
-- The ``settings`` and ``themes`` handlers in ``jupyterlab_server`` has been updated to load from the new ``labextensions`` locations, favoring the prebuilt extension locations over the bundled ones
-- A ``labextension develop`` command has been added to install an in-development extension into JupyterLab.  The default behavior is to create a symlink in the ``sys-prefix/share/jupyter/labextensions/package-name`` to the static directory of the extension
-- We provide a ``cookiecutter`` that handles all of the scaffolding for an extension author, including the shipping of ``data_files`` so that when the user installs the package, the static assets end up in ``share/jupyter/labextensions``
-
-Implementation details
-^^^^^^^^^^^^^^^^^^^^^^
+Building a prebuilt extension
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-How prebuilt extensions work
-""""""""""""""""""""""""""""
+JupyterLab provides a ``jupyter labextension build`` command that is used to build prebuilt extensions. The command uses dependency metadata from the active JupyterLab to produce a set of files from a source extension that comprise the prebuilt extension. The files include a main entry point ``remoteEntry.<hash>.js``, dependencies bundled into JavaScript files, ``package.json`` (with some extra build metadata), as well as plugin settings and theme directory structures if needed.
 
+A ``jupyter labextension develop`` command installs an in-development prebuilt extension into JupyterLab. It essentially creates a symlink in the ``sys-prefix/share/jupyter/labextensions/package-name`` to the prebuilt extension output directory.
 
-Directory walkthrough
-"""""""""""""""""""""
+We provide a `cookiecutter <https://github.com/jupyterlab/extension-cookiecutter-ts>`_ that handles all of the scaffolding for an extension author, including the shipping of appropriate data files, so that when the user installs the package, the prebuilt extension ends up in ``share/jupyter/labextensions``
+
+
+Serving a prebuilt extension
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
+A prebuilt extension is copied into a directory such as ``sys-prefix/share/jupyter/labextensions/package-name``. The JupyterLab server makes these files available via a `/labextensions/` server handler. The settings and themes handlers in the server also load settings and themes from the prebuilt extension installation directories. If a prebuilt extension has the same name as a source extension, the prebuilt extension is preferred.
 
 
 Packaging extensions