*Multiple repos vs Monolith repo*
Paris work week is happening during this week, we're going to have some
discussions about how to go for our repository strategies. Here are some of
my thoughts and surveys for these two major strategies.
*Background*
Based on technology and language we use, npm, Semantic Versioning
<
http://semver.org> and webpack are some awesome approaches which really
fit both repo strategies.
*NPM*
Flat dependency tree is an amazing feature in npm v3
<
https://docs.npmjs.com/how-npm-works/npm3> , which let you installs
dependencies in a flat structure rather than in a nested way. It means that
duplicated modules in node_modules has gone away unless someone requires a
different version of the same module.
*SemVer*
Follow the rule of semantic versioning (major.minor.patch), we can maintain
and upgrade our packages in a safe way without breaking every repository.
New workflow based on SemVer is growing, like semantic release
<
https://github.com/semantic-release/semantic-release>, which can help us
to speed up package releasing.
*Webpack v2*
As you may know, webpack has upgraded to v2 for a while. After migrating to
v2 we can get more benefits like Lazy Loading - React
<
https://webpack.js.org/guides/lazy-load-react/> and Tree Shaking
<
https://webpack.js.org/guides/tree-shaking/>.
The trouble of bundle duplication can be mitigated through the combo of
npm, SemVer and Webpack2. Here is a good demo illustrates how to solve
duplication with a webpack plugin RootMostResolvePlugin
<
https://github.com/webpack/webpack/issues/985#issuecomment-260230782> with
a simple configuration
<
https://github.com/aurelia/skeleton-navigation/blob/3eb4d3fa65b60731493c79235e547792324cc3e7/skeleton-typescript-webpack-experimental/webpack.config.ts#L367-L370>
.
Above technologies can work out some critical issues no matter we adopt
multiple repos or monolith repo. Following comparison is about advantages
and disadvantages between multi-repos and mono-repo structures.
*Multiple repositories*
Standalone repository for each panel (inspector, debugger, console,
netmonitor...etc). One central repository which provides a basic build
configuration and being able to opt-in / opt-out all sub-repos. For Github
issue page, unclear component bugs goes to the central repo and clear
component bugs goes to each sub-repo's issues page.
Pros
- Clear ownership for each repo
- Lightweight repository
- Mitigate development pain like we had to download and build entire
m-c but merely touch devtools folder in most of the time.
- Project size will be bloated and git command execution time
will slow down.
- Gaia <
https://github.com/mozilla-b2g/gaia> hit this bloated
project soon when it came to becoming monolithic repo.
- High flexibility of dependency upgrade
- Each sub-repo has a chance to upgrade frameworks / libraries as
needed.
- For example, we can start to upgrade React version from an
independent sub-repo throughout other sub-repos step by step without
breaking others.
Cons
- Unmanageable Github issues
- Bad for managing and triaging issues across multi-repos (ex: move
incorrect issue to correct issue page).
- Cross-repos changes
- Significant overhead will be added when we need to make change to
many sub-modules.
- Maybe it boils down to one thing - we should do more module
extraction.
*Monolith repository*
One Github repo and issue page, it's likely to adopt current
mozilla-central/devtools structure for our front-end (client) code. We can
continue to use shared folder as well.
Pros
- Manageable Github issues
- Certainly, there is only one place to keep all issues and it's easy
to triage issues cross sub-modules.
- A centralized Github repo
- Higher repo star count and attention in community
- Easy to count up to contributors cross all sub-modules
- Cross-repos changes
- In contrast with the multi-repos, one pull request can cross
sub-modules.
- For example, it will be very easy to modify code style cross all
sub-modules.
- It will be easy to develop and test features cross sub-modules.
- Shared folder strategy
- So far the shared folder approach has been using nicely for a long
time. We can still adopt this good approach and maintain all components /
modules in shared folder (including Reps, Splitbox, theme...etc).
- Shared component changes is likely to cause cross-repo changes.
This way can reduces overhead of managing submodules workflow.
Cons
- Unclear ownership
- Bloated repository
- Codebase looks more intimidating
- All commit changes will increase quickly, repo sooner will be
bloated.
- Low flexibility of dependency upgrade
- In contrast with the multi-repos, framework upgrade will impact on
other panels since there is only one framework instance. It
would be a risk
to upgrade framework major version for one panel but we have to fix all
issues at once time.
*Possible solution*
Note that there are more and more framework adopted mono-repo like Babel
<
https://github.com/babel/babel/tree/master/packages>, React
<
https://github.com/facebook/react/tree/master/packages>, Meteor
<
https://github.com/meteor/meteor/tree/devel/packages>, Angular
<
https://github.com/angular/angular/tree/master/modules>, Ember
<
https://github.com/emberjs/ember.js/tree/master/packages>...and others.
However, they aren't following the traditional mono-repo strategic but a
newer solution for mitigating some pain points in mono-repo - *Mono-repo
with multiple packages*.
Lerna <
https://github.com/lerna/lerna> is a tool for managing
multi-packages in mono-repo. In that way, we can follow the recommended
structure and create a packages folder for maintaining sub-repos including
all panels, shared components, theme...etc. And I've seeing devtools-core
<
https://github.com/devtools-html/devtools-core> that has been adopting
this model as well.
*Issues in Webpack + Lerna*
We should keep an eye on duplicated module issue
<
https://github.com/webpack/webpack/issues/3463#issuecomment-272568348>
when combining Webpack and Lerna. It seems that there are still no
agreement in solving this problem at build level or at dependency manager
level.
My feeling is that multi-repos could be the ultimate repo structure but the
pain point of overhead in cross-repo changes is crucial to the project
development, and it is hard to be erased. So that's why there are more and
more projects embracing mono-repo. I think problems like duplicated module
issue
<
https://github.com/webpack/webpack/issues/3463#issuecomment-272568348> could
be addressed sooner and later since many projects and companies have moved
to this architecture, and involved with improving tooling.
I'm not going to say mono-repo is the right way to go, but here are some
reasons to tell you why many projects prefer to go this way. So I'd like to
share this background and survey result and open to discussions. Any
feedback and thoughts are welcome :)