Introduction ============ Monorepo structure ------------------ The BSB uses a monorepo pattern for organizing the framework code, packages, and first party plugins: .. code-block:: packages ├── bsb ├── bsb-core ├── ... libs └── ... The ``bsb`` package contains a metadata-only package that will install the main framework, and all of the bundled first-party plugins we recommend. The ``bsb-core`` package contains the main framework code. Any other packages under ``packages`` are our first-party plugin packages, some of which will come bundled immediately when you ``pip install bsb``, some won't. The ``libs`` folder contains shared utility packages that are not interesting for users to install, but we as developers might need multiple times over for a variety of the packages we maintain. The root of our source code repository houses all of the monorepo configuration files. We use `Nx `_ as our monorepo manager, with the `@nxlv/python `_ plugin to adapt it to Python from its typical JS use-case. .. _dev-install: Installation ------------ .. start-dev-install First, make sure you have followed the :ref:`Parallel support ` guidelines. In order for you to manage the monorepo aspects using ``nx``, you'll have to install NodeJS. There is helper scripts for each platform in ``devtools/bootstrap-*``: .. tab-set:: .. tab-item:: Ubuntu :sync: bash .. code-block:: bash git clone https://github.com/dbbs-lab/bsb cd bsb ./devtools/bootstrap-linux.sh .. tab-item:: MacOS :sync: bash .. code-block:: bash git clone https://github.com/dbbs-lab/bsb cd bsb ./devtools/bootstrap-mac.sh .. tab-item:: Windows :sync: shell .. code-block:: bash git clone https://github.com/dbbs-lab/bsb cd bsb .\devtools\bootstrap-windows.ps1 .. note:: As a non-JavaScript Nx repo we use an alternative installation method which does not have a ``package.json`` file at the root, and instead declares its bootstrapping in the ``installation`` key of ``nx.json``. Whenever you run ``./nx``, the scripts - via ``.nx/nxw.js`` - will bootstrap an Nx installation in the ``.nx`` folder, with the typical ``package.json`` and ``node_modules`` maintained in the ``.nx/installation`` folder. .. hint:: You can ``npm install -g nx`` so that you can use regular ``nx`` command without having to point to the ``./nx`` path. .. end-dev-install Usage ----- Nx works by providing you with a set of generators, and managing a collection of projects, that can each define a set of targets that run certain executors. Generators let you quickly create boilerplate, and make automated changes to all of your projects in the monorepo, such as adding new projects, creating publishable Python package stubs, ... Each project in a monorepo represents a code entity that will produce its own set of output artifacts, such as its own Python package that we'd publish to PyPI. e.g., ``bsb-yaml``, ``bsb-json``, ... These projects are independent once distributed to the public, but they're gathered here in this monorepo because their tooling and release cycle tightly depend on each other, and are a large burden to maintain separately. Without a monorepo we'd have X PRs, X release cycles, X docfixes, ... with a monorepo that can all be done in 1 PR, 1 release cycle. Each project is defined in ``project.json``, and there declares a set of targets, each with an executor provided by Nx or a plugin. An executor runs a certain workflow, such as building, linting, formatting, building docs, ... Adding a project ~~~~~~~~~~~~~~~~ To add a project run the `@nxlv/python:uv-project` generator: .. code-block:: nx generate @nxlv/python:uv-project my-new-project Running a target ~~~~~~~~~~~~~~~~ To run a target, use ``nx run`` followed by ``project:target``: .. code-block:: bash nx run bsb-core:docs This would build the `bsb-core` documentation. You can also run the same target for all the projects that have it: .. code-block:: bash nx run-many -t docs Nx caches the targets that have been already completed successfully, so that it does not re-run them if you did not modify the linked project. If you want Nx to force run a target, ignoring the cache then use the ``--skipNxCache`` flag. Main targets ~~~~~~~~~~~~ In practice, Nx uses `Uv `_ to create an independent python environment (inside a ``.venv`` subfolder) for each of its subpackages. Uv will be installed with Nx thanks to the ``devtools/bootstrap-*`` script. Hence, some of the `Uv commands `_ are also available through Nx: - ``./nx run bsb-core:add my-package`` adds `my-package` to the list of dependencies of `bsb-core` - ``./nx run bsb-core:remove my-package`` removes `my-package` to the list of dependencies of `bsb-core` - ``./nx run bsb-core:sync`` updates the environment of `bsb-core` project based on its lock file and toml - ``./nx run bsb-core:install`` similar to the ``sync`` command. - ``./nx run bsb-core:lock`` updates the lock file of `bsb-core` project - ``./nx run bsb-core:update`` will upgrade the libraries of the lock file when possible and ``sync`` the new environment. .. hint:: Note that you can run any command within each subpackage environment with uv: .. code-block:: bash cd packages/bsb-core uv run bsb compile [...] Next are all the commands used in the development workflow: - ``./nx run bsb-core:test`` performs the unittests for `bsb-core` - ``./nx run bsb-core:docs`` builds the documentation for `bsb-core` - ``./nx run bsb-core:lint`` checks if the code of `bsb-core` passes the lint tests with `ruff `_ - ``./nx run bsb-core:format`` formats the code of `bsb-core` according to `black` guidelines - ``./nx run bsb-core:build`` packages the code of `bsb-core` The remaining commands are used to deploy the BSB on ``Pypi`` which should be done automatically by Github.