<commit_before>Project Development
-------------------

This document describes how to build real-world applications written in
Reflex.

.. contents:: Table of Contents

Creating the Project
--------------------

First, create a directory for your project. This will contain all of the
files needed for the build process and a checkout of
``reflex-platform``, which will provide all of the Haskell libraries and
compilers the project will depend on. To get ``reflex-platform``, it is
easiest to use `git <https://git-scm.com/>`__ and add it as a submodule,
so that the version being used is consistent amongst your team and
updating it is easy.

.. code:: bash

   $ mkdir my-project
   $ cd my-project
   $ git init
   $ git submodule add https://github.com/reflex-frp/reflex-platform

If you’ve never built a project with ``reflex-platform`` before, you may
need to install `Nix <https://nixos.org/nix/>`__ and configure Reflex’s
binary cache. ``reflex-platform`` provides the ``try-reflex`` script,
which will do this for you and download some of the basic tools and
libraries we’ll need ahead of time.

.. code:: bash

   $ reflex-platform/try-reflex

After running this command, you’ll find yourself in a different shell.
This is the ``try-reflex`` sandbox, which provides GHC and GHCJS with
``reflex-dom`` preinstalled. You can use this environment to quickly
test things out, but this document only uses it to install Nix, so go
ahead and ``exit`` out of this shell.

In Reflex-DOM projects, it’s common to have three separate Haskell
components: the frontend, the backend, and the common code shared
between them. It’s easiest to have a separate cabal package for each of
these. We’re going to teach Nix how to build them and how to give us an
environment where they can be built by hand.

Create a directory for each package, then run ``cabal init`` inside them
to create the ``*.cabal`` file and directory structure. If you don’t
have ``cabal`` installed on your system, you can enter the
``try-reflex`` sandbox to use the version that comes with that. We will
see a better way to get the ``cabal`` command later.

.. code:: bash

   $ mkdir common backend frontend
   $ (cd common && cabal init)
   $ (cd backend && cabal init)
   $ (cd frontend && cabal init)

This will prompt for various bits of metadata. ``common`` should be a
library, and ``frontend`` and ``backend`` should be executables. These
cabal files are where the dependencies and build targets of each Haskell
component can be described.

In ``frontend/frontend.cabal`` and ``backend/backend.cabal``, add
``common`` and ``reflex-dom`` as Haskell dependencies.

.. code:: yaml

   ...
     build-depends: base
                  , common
                  , reflex-dom
   ...

Finally, Nix will fail to build ``common`` if it exports no modules.

.. code:: haskell

   -- common/src/Common.hs
   module Common where

.. code:: yaml

   ...
     exposed-modules: Common
   ...

Building with Nix
-----------------
<commit_msg>[documentation] Added precision on common.cabal<commit_after>Project Development
-------------------

This document describes how to build real-world applications written in
Reflex.

.. contents:: Table of Contents

Creating the Project
--------------------

First, create a directory for your project. This will contain all of the
files needed for the build process and a checkout of
``reflex-platform``, which will provide all of the Haskell libraries and
compilers the project will depend on. To get ``reflex-platform``, it is
easiest to use `git <https://git-scm.com/>`__ and add it as a submodule,
so that the version being used is consistent amongst your team and
updating it is easy.

.. code:: bash

   $ mkdir my-project
   $ cd my-project
   $ git init
   $ git submodule add https://github.com/reflex-frp/reflex-platform

If you’ve never built a project with ``reflex-platform`` before, you may
need to install `Nix <https://nixos.org/nix/>`__ and configure Reflex’s
binary cache. ``reflex-platform`` provides the ``try-reflex`` script,
which will do this for you and download some of the basic tools and
libraries we’ll need ahead of time.

.. code:: bash

   $ reflex-platform/try-reflex

After running this command, you’ll find yourself in a different shell.
This is the ``try-reflex`` sandbox, which provides GHC and GHCJS with
``reflex-dom`` preinstalled. You can use this environment to quickly
test things out, but this document only uses it to install Nix, so go
ahead and ``exit`` out of this shell.

In Reflex-DOM projects, it’s common to have three separate Haskell
components: the frontend, the backend, and the common code shared
between them. It’s easiest to have a separate cabal package for each of
these. We’re going to teach Nix how to build them and how to give us an
environment where they can be built by hand.

Create a directory for each package, then run ``cabal init`` inside them
to create the ``*.cabal`` file and directory structure. If you don’t
have ``cabal`` installed on your system, you can enter the
``try-reflex`` sandbox to use the version that comes with that. We will
see a better way to get the ``cabal`` command later.

.. code:: bash

   $ mkdir common backend frontend
   $ (cd common && cabal init)
   $ (cd backend && cabal init)
   $ (cd frontend && cabal init)

This will prompt for various bits of metadata. ``common`` should be a
library, and ``frontend`` and ``backend`` should be executables. These
cabal files are where the dependencies and build targets of each Haskell
component can be described.

In ``frontend/frontend.cabal`` and ``backend/backend.cabal``, add
``common`` and ``reflex-dom`` as Haskell dependencies.

.. code:: yaml

   ...
     build-depends: base
                  , common
                  , reflex-dom
   ...

Finally, Nix will fail to build ``common`` if it exports no modules.

.. code:: haskell

   -- common/src/Common.hs
   module Common where

.. code:: yaml

   ...
   # common/common.cabal
   library
     builds-depends: base
     exposed-modules: Common
   ...

Building with Nix
-----------------

{'fraction_non_alphanumeric': 0.10400262467191601, 'fraction_numerical': 0.0, 'mean_word_length': 3.2487804878048783, 'pattern_counts': {'":': 0, '<': 7, '<?xml version=': 0, '>': 7, 'https://': 6, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 4, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2106480', 'n_tokens_mistral': 1740, 'n_tokens_neox': 1671, 'n_words': 834}