# Monorepo Structure
## Repo Structure
Inside ```libs/``` we are distinguishing between **grouping** directories, **shared**, and **app-specific** libraries (ordered by specificity).
### Grouping Libraries
Libraries should be grouped by scope which refers to either an application the library belongs to or (for larger applications) a section within that application (https://nx.dev/more-concepts/grouping-libraries#grouping-libraries).
Applied to **bpd-web-ui** an app-specific library should be either located at ```libs/bpd-web-ui/feature-lib``` or ```libs/bpd-web-ui/section/feature-lib```
### Sharing Libraries
Provide reusable solutions to a common problem that can be reused across many different applications (https://nx.dev/more-concepts/grouping-libraries#sharing-libraries).
Shared libs should preferably contain pure abstraction, such as UI components, hooks, utils , etc.
These abstractions will eventually be used inside an app-specific library by composition.
### Example
<sub>The structure of a feature library will be explained in detail inside the lib types section)</sub>
```sh
root
|
+-- apps
|
+-- bpd-web-ui # app shell consumes app-specific feature libs and composes their respective routes, stores, etc.
|
+-- bpd-web-ui-e2e # e2e
|
+-- libs
|
+-- logger # highly-generalised abstraction, can be reused across apps (even repos as publishable)
|
+-- bpd-web-ui/ # grouping directory for bpd-web-ui specfic code
|
+-- location-analysis/ # grouping directory for bpd-web-ui-location-analysis specfic code
|
+-- feature-location-analysis-eu/ # feature library
|
+-- feature-location-analysis-jp/ # feature library
|
+-- shared/ # grouped sharing library for sharing abstractions across location-analysis features
|
+-- ui/ # feature library
|
+-- utils/ # feature library
|
+-- market-analysis/ # grouping directory for bpd-web-ui market-analysis specfic code
|
+-- feature-market-analysis-eu/ # feature library
|
+-- feature-market-analysis-jp/ # feature library
|
+-- shared/ # grouped sharing library for sharing abstractions across market-analysis features
|
+-- shared/ # grouped sharing library for sharing abstractions across all bpd features
```
## Lib Types
Generally, we can differentiate between **3 distinct libs types** (https://nx.dev/more-concepts/library-types):
* Utility
* UI
* Feature
#### Utility Library
Utilities are low-level abstractions used by many libraries and applications. Since their utilization can be very broad and framework-agnostic, a highly generalized utility lib could be placed directly inside ```libs/```.
#### UI Library
UI libraries contain purely presentational components. These pure (React) abstractions are consumed and composed by the specific feature libs.
#### Feature Library
Feature libraries are the highest-level libraries that implement business use case-specific smart UIs (including access to data sources).
Generally, it is recommended to keep libraries modular to promote encapsulation and thus facilitate code sharing.
Nevertheless, since a feature's code base is growing over time we also want to keep a coherent organization on this level.
Therefore, we recommend adhering to the following library structure (with an exception for very atomic utility libraries where this approach might be unsuitable):
```sh
location-analysis-jp/lib
|
+-- index.ts
|
+-- src/
|
+-- api # exported API request declarations and api hooks related to a specific feature
|
+-- assets # assets folder can contain all the static files for a specific feature
|
+-- components # components scoped to a specific feature
|
+-- hooks # hooks scoped to a specific feature
|
+-- routes # route components for a specific feature pages
|
+-- stores # state stores for a specific feature
|
+-- types # typescript types for TS specific feature domain
|
+-- utils # utility functions for a specific feature
```
(https://github.com/alan2207/bulletproof-react/blob/master/docs/project-structure.md)
Including a lib directory that contains an index.ts and a src directory is an NX convention that establishes a clear separation between internal and external API.
### Generators
To ensure we respect to our self-imposed project structure, and keep the code base coherent we make use of NX's code generators:
**Utility Library**
```nx g @nrwl/js:lib <name>```
**React Library**
```nx g @nrwl/react:library --directory <directory> --component false --name <name>```
**React Component**
```nx g @nrwl/react:component --export true --directory lib/components --flat true --project <project> --name <name>```
**React RTK**
```nx g @nrwl/react:redux --directory store --project <project> --name <name>```
**Feature Library**
...
**Move Library**
```nx g @nrwl/workspace:move --project my-feature-lib --destination shared/my-feature-lib```
### Conventions
* Use kebab-case for naming libraries and files (NX generator default)
* Prefix feature libraries with feature-
* Group non-feature libraries into a sharing library (shared/) to expose intent
* Promote modularity by purpose
* Do group by types, such as ui, utils, .etc inside shared/
* Promote once further abstractions would be sensible
## References
#### Examples
https://github.com/onextech/bpd-nx-poc
https://github.com/nrwl/nx-incremental-large-repo
#### Repo Organisation
https://nx.dev/more-concepts/grouping-libraries#grouping-libraries
https://nx.dev/more-concepts/grouping-libraries#sharing-libraries
https://nx.dev/more-concepts/library-types
https://github.com/alan2207/bulletproof-react/blob/master/docs/project-structure.md
## FAQs
1. How would the new **maps** and **auth** folder structures look like?
2. How would the folder structure for **subfeatures** of the LocationAnalysis module with the hierachy look like? e.g. LocationAnalysis will house other sublevel features like MarketAnalysis, SectorAnalysis, etc. Will LocationAnalysisJP contain MarketAnalysisJP extended from ../shared/MarketAnalysis like the Drawer in the above example?
3. Going into a further details of the app, what would the top-level folder structure of the contents of **/libs/bpd-web** look like based on this new convention?
4. Planning ahead for the kick-off on the **SectorAnalytics** module, how would that folder structure look like knowing that it's similar to **LocationAnalysis**. Are they sibling folders at /libs?
5. What are the **next steps** we need take to get the SectorAnalytics module up?