-
Notifications
You must be signed in to change notification settings - Fork 490
build: implement a monorepo with Lerna #1284
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
16a70fa to
248c770
Compare
|
The PR looks good to me I just have one question. Regarding the templates do you think it would also be possible to extract them from embark and put them inside a templates directory? |
a6e401c to
8809b51
Compare
Yes, definitely possible to extract the templates, and I think we should. I tried making them siblings of embark in
The monorepo pattern is ideal when you have a set of packages grouped together and you want to do the same steps for each of them, e.g. invoke package.json Ideally, I think |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Feedback
Firstly, hats off to some great work! I know this took an insane amount of effort and head banging, so congrats on getting it across the line! The PR looks great. I have been playing around with it since I based the remap import updates off of this branch, and I have to say that it is definitely easier to get around the different yarn/npm commands than the current master. I believe we will get used to these changes quite quickly.
The test_dapps is a great idea for detecting changes. I've noticed that trying to embark run the test dapps inside of their location in the monorepo triggers the check on the dapp regarding the dapp path length, which is known to cause errors starting geth. Obviously the way around this is to copy out the test apps to a different location in the filesystem. Because these test dapps are now in their own mono repo, would it be possible to quickly npx install them in to a folder and run them from there?
Regarding nohoist, I noticed this is only for the two packages added for use in the embark unit tests (embark/embark-test-contract-0 and embark/embark-test-contract-1). I believe we could actually move these two packages to devDependencies of packages/embark. Would that move alter the need for nohoist?
I used yarn globalize and have two points of feedback:
- Firstly, I had an existing symlink
/usr/local/bin/embarkso it errored. Not a big deal, I deleted the original and re-ranyarn globalize. - After running
yarn globalize, the symlink was created, but runningwhich embarkstill shows/Users/emizzle/.nvm/versions/node/v10.5.0/bin/embark, as it is in my PATH first. I'm assuming NVM does this for me. I guess there isn't much of a way around this, and maybe this is overkill, but there could be a check afteryarn globalizecomparing the output ofwhich embarkto it's expected value and warning the user if they don't match.
Hot topics
- What should be done about the README for packages/embark? Should the top-level README be duplicated in that package?
- Could we maybe just have a link to the top-level README?
- Lerna is setup to use Fixed/Locked mode, and accordingly packages/embark-ui is set to 4.0.0-beta.0. The same will be true when adding embarkjs, swarm-api, etc. to the monorepo. Is this acceptable or do we want to use Independent mode?
- Hmm that is a good question. Personally, I would say that it wouldn't make sense to bump all modules/packages every time embark is updated as the majority of the modules/package would actually not have changed, so personally I would prefer Independent Mode.
|
I also think we should use independent mode |
Maybe we can remove that check on the dapp path length owing to the changes in #1214. It probably should have been removed in that PR to begin with (something I overlooked). Independent of that concern, in a
Unfortunately, it would not remove the need; note that they are already devDeps of
I will look into those issues shortly.
@iurimatias any thoughts?
That's not the behavior of fixed mode, though granted that's what the name seems to imply. I am going to write-up a reply to Iuri's comment re: the mode choice and attempt to explain why it may be better to stick with fixed mode, for now. |
jrainville
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Very nice work. Just a couple of small questions
| "engines": { | ||
| "node": ">=8.11.3", | ||
| "npm": ">666", | ||
| "node": ">=8.12.0", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why bump the node version? Is 8.11 no good now?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The
"engines"specified in top-level and packages'package.jsonreflect a node and npm pair that match (a source of confusion in the past). The pair was chosen according to the first post v5 npm that's bundled with node. A"runtime"key/object has been introduced inpackages/embark/package.jsonwhich is used as the basis for specifying the minimum version of node that can be used to run embark, and that's what is checked bybin/embark.
By "that match", I meant they are bundled together, i.e. if you install node v8.12.0 you get npm v6.4.1. Any earlier version of node includes npm v5.x.
For the runtime, node v8.11.3 is still our minimum supported version.
| "node": ">=8.11.3", | ||
| "npm": ">666", | ||
| "node": ">=8.12.0", | ||
| "npm": ">=6.4.1", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So, we can install with npm now? Or is yarn still recommended? (I'll still use yarn, just curious)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's important to use yarn at the top-level since "workspaces" is not supported by npm.
npm is still used in various ways in the development setup, and since v5 is pretty buggy, I pegged it to the first v6.x npm that got bundled with a node release, i.e. node v8.12.0. Given when/how npm enforces the engines check with respect to itself, it's more of a "signal to humans" than an automatic protection. In any case, it only applies to developers working on embark itself.
Note that owing to the monorepo setup, it becomes impossible to install embark directly from github since hosted-git-info (used internally by npm) doesn't have a mechanism for identifying a specific package within the directory structure of a git repository. Yarn doesn't offer support for that either. It's a trade-off: installing from a repo is a nice capability, sad to lose it, but the benefits of the monorepo will hopefully outweigh the loss.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe we can adapt #1263 so that if a developer tries to npm install a clone of the repo (npm install embark from registry is fine), then it will fail with an error message saying "use yarn". Thoughts?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I looked into the technique of #1263 and found it won't work. There doesn't seem to be a way, via environment variables available to the preinstall script, to distinguish npm install in the repo vs. npm install [pkg], where [pkg] is a tarball path or identifier on the registry or was listed as a dev/Dep in a package.json.
Since we want users to be able to install embark from the registry using npm, I think it's a no-go. We'll just need to educate developers who want to work on embark or run a development build of embark that they need to yarn install in the top-level of the cloned repo instead of doing npm install.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, personally I think that is probably the right approach. Since npm installing embark from the registry is OK, and only developers wishing to contribute to embark are required to use yarn, adding some information where necessary (on the README and website) would be sufficient.
| fs.removeSync('.embark/'); | ||
| fs.removeSync('node_modules/.cache'); | ||
| fs.removeSync('dist/'); | ||
| fs.removeSync('embarkArtifacts/'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This can be configured by the user. Maybe we should check what's in embark.json first. Same for dist/
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good point. I guess embark reset needs some attention, but do you think it's okay to address that in a future PR?
|
@iurimatias @emizzle regarding fixed vs. independent mode: I think, based on the gitter chat log, that one point of confusion has already been cleared up: both fixed and independent modes only bump a version and publish a package if that package has changed. By using caret ranges for our monorepo packages, if we're committed to adhering to semver for our own stuff, we get some nice flexibility for ourselves and also our users, e.g. FixedI think the advantage of fixed mode is that we don't have to make manual semver calculations when we hit a major release. For example: if we introduce a breaking change in That the sibling packages all bump isn't strictly required by semver, e.g. IndependentI think independent mode probably becomes useful when you have loosely related groups of packages all in one monorepo and it's undesirable that a major version bump to one package in one group will induce a major bump in all of the packages across all groups. The trade-off is that independent mode will require less-automated semver calculations (and more of them) when doing releases, and I suppose that could be an error-prone exercise in a large monorepo. I don't think our monorepo will have that structure in the near term, so for now I think it's simpler for us to stick with fixed mode, and reconsider if we find it limiting. |
Can you check the output of |
ca52a2f to
d9b816f
Compare
Agreed.
A permissions issue does ring a bell and that was most likely the cause.
|
|
I know I'm a little late to the party but here's my feedback considering all comments made: README
So either way, I think the top level readme should make the following points very clear:
I guess the idea would be to keep the README short and concise and every project should have its own README (CLI, Cockpit, soon Jetpack and Embark SDK(?)) Fixed vs Independent mode
Some random thoughts on this:
I assume that it's not possible to have a "mixed" mode where for some packages we have fixed mode and for others independent mode. But considering the thoughts above, I have the feeling independent mode is what makes more sense. yarn globalize
|
|
@emizzle it should work correctly if you do If I That shouldn't happen because of the Long story short: you can do |
Unfortunately, there's no "mixed" mode. For independent mode, I think I'll need to slightly adjust the release script, as I'm not sure if/how the
For perspective: my goal with In any case, after additional experiments this morning, I've realized having our own For everyone working on embark, once we merge this PR I highly recommend no longer using
My guess is you ran afoul of a bug in yarn, which I discovered and then forgot about when I started working around it, see my comment to Eric above. My apologies for not giving a heads-up earlier re: that bug; hopefully the yarn maintainers will fix it. |
TL;DR ===== `yarn install` in a fresh clone of the repo. `yarn reboot` when switching branches. When pulling in these changes, there may be untracked files at the root in all/some of: ``` .embark/ .nyc_output/ coverage/ dist/ embark-ui/ test_apps/ ``` They can be safely deleted since those paths are no longer in use at the root. Many of the scripts in the top-level `package.json` support Lerna's [filter options]. For example: `yarn build --scope embark` build only `packages/embark`. `yarn build --ignore embark-ui` build everything except `packages/embark-ui`. Scoping scripts will be more useful when there are more packages in the monorepo and, for example, `yarn start` doesn't need to be invoked for all of them while working on just a few of them simultaneously, e.g `embark` and `embarkjs`. It's also possible to `cd` into a particular package and run its scripts directly: ``` cd packages/embark && yarn watch ``` Hot Topics & Questions ====================== What should be done about the [README][embark-readme] for `packages/embark`? Should the top-level README be duplicated in that package? Lerna is setup to use [Fixed/Locked mode][fixed-locked], and accordingly `packages/embark-ui` is set to `4.0.0-beta.0`. The same will be true when adding embarkjs, swarm-api, etc. to the monorepo. Is this acceptable or do we want to use [Independent mode][independent]? Scripts ======= If a package doesn't have a matching script, `lerna run` skips it automatically. For example, `packages/embark-ui` doesn't have a `typecheck` script. `yarn build` ------------ Runs babel, webpack, etc. according to a package's `build` script. `yarn build:no-ui` is a shortcut for `yarn build --ignore embark-ui`. `yarn ci` --------- Runs a series of scripts relevant in a CI context according to a package's `ci` script. For `packages/embark` that's `lint typecheck build test package`. Also runs the `ci` script of the embedded `test_dapps` monorepo. `yarn clean` ------------ Runs rimraf, etc. according to a package's `clean` script. `yarn globalize` ---------------- Makes the development embark available on the global PATH, either via symlink (Linux, macOS) or a shim script (Windows). `yarn lint` ----------- Runs eslint, etc. according to a package's `lint` script. `yarn package` -------------- Invokes `npm pack` according to a package's `package` script. `yarn qa` --------- Very similar to `ci`, runs a series of scripts according to a package's `qa` script. The big difference between `ci` and `qa` is that at the top-level `qa` first kicks off `reboot:full`. There is a `preqa` script ([invoked automatically][npm-scripts]), which is a bit of a wart. It makes sure that `embark reset` can be run successfully in `packages/embark/templates/*` when the `reboot` script invokes the `reset` script. The `qa` script is invoked by `yarn release` before the latter proceeds to invoke `lerna publish`. `yarn reboot` ------------- Invokes the `reset` script and then does `yarn install`. The `reboot:full` variant invokes `reset:full` and then does `yarn install`. `yarn release` -------------- Works in concert with [lerna publish], which will prompt to verify the version before proceeding. Use `n` to cancel instead of `ctrl-c` as `lerna publish` has been seen to occasionally misbehave when not exited cleanly (e.g. creating a tag when it shouldn't have). ``` yarn release [bump] [--options] ``` * `[bump]` see [`publish` positionals][pub-pos] and [`version` positionals][ver-pos]; an exact version can also be specified. * `--preid` prerelease identifier, e.g. `beta`; when doing a prerelease bump will default to whatever identifier is currently in use. * `--dist-tag` registry distribution tag, defaults to `latest`. * `--message` commit message format, defaults to `chore(release): %v`. * `--sign` indicates that the git commit and tag should be signed; not signed by default. * `--release-branch` default is `master`; must match the current branch. * `--git-remote` default is `origin`. * `--registry` default is `https://registry.npmjs.org/` per the top-level [`lerna.json`][lerna-json]. To release `4.0.0-beta.1` as `embark@next` (assuming version is currently at `4.0.0-beta.0`) could do: ``` yarn release prerelease --dist-tag next ``` For *test releases* (there is no longer a `--dry-run` option) [verdaccio] and a filesystem git remote can be used. Condensend instructions: ``` mkdir -p ~/temp/clones && cd ~/temp/clones git clone git@github.com:embark-framework/embark.git cd ~/repos/embark git remote add FAKEembark ~/temp/clones/embark ``` in another terminal: ``` npm i -g verdaccio && verdaccio ``` in the first terminal: ``` yarn release --git-remote FAKEembark --registry http://localhost:4873/ ``` `yarn reset` ------------ Invokes cleaning and resetting steps according to a package's `reset` script. The big difference between `clean` and `reset` is that `reset` is intended to delete a package's `node_modules`. The `reset:full` variant deletes the monorepo's top-level `node_modules` at the end. That shouldn't be necessary too often, e.g. in day-to-day work when switching branches, which is why there is `reboot` / `reset` vs. `reboot:full` / `reset:full`. Errors may be seen related to invocation of `embark reset` if embark is not built, but `reset` will still complete successfully. `yarn start` ------------ Runs babel, webpack, tsc, etc. (in parallel, in watch mode) according to a package's `start` script. `yarn test` ----------- Run mocha, etc. according to a package's `test` script. The `test:full` variant runs a series of scripts: `lint typecheck test test_dapps`. `yarn test_dapps` ----------------- Runs the `test` script of the embedded `test_dapps` monorepo. The `test_dapps:ci` and `test_dapps:qa` variants run the `ci` and `qa` scripts of the embedded `test_dapps` monorepo, respectively. `yarn typecheck` ---------------- Runs tsc, etc. according to a package's `typecheck` script. Notes ===== `npx` is used in some of the top-level and package scripts to ensure the scripts can run even if `node_modules` is missing. [`"nohoist"`][nohoist] specifies a couple of embark packages because [`restrictPath`][restrictpath] is interfering with access to modules that are located in a higher-up `node_modules`. All dependencies in `packages/embark-ui` have been made `devDependencies` since its production build is self-contained. `packages/embark`'s existing CHANGELOG's formatting has been slightly adjusted to match the formatting that Lerna will use going forward (entries in the log haven't been modified). Lerna will generate a CHANGELOG at the top-level and in each package. Since we're transitioning to a monorepo, things may look a little wonky with respect to old entries in `packages/embark/CHANGELOG.md` and going forward we need to consider how scoping our commits corresponds to member-packages of the monorepo. In `packages/embark`, `test` invokes `scripts/test`, which starts a child process wherein `process.env.DAPP_PATH` is a temporary path that has all of `packages/embark/dist/test` copied into it, so that paths to test helpers/fixtures don't need to be prefixed with `dist/test/` and so that a `.embark` directory doesn't get written into `packages/embark`. The `"engines"` specified in top-level and packages' `package.json` reflect a node and npm pair that match (a source of confusion in the past). The pair was chosen according to the first post v5 npm that's bundled with node. A `"runtime"` key/object has been introduced in `packages/embark/package.json` which is used as the basis for specifying the minimum version of node that can be used to run embark, and that's what is checked by `bin/embark`. Some changes have been introduced, e.g. in `lib/core/config` and `lib/utils/solidity/remapImports` so that it's *not* implicitly assumed that `process.env.DAPP_PATH` / `fs.dappPath()` are the same as `process.cwd()`. There are probably several++ places where that assumption is still in effect, and we should work to identify and correct them. `embark reset` now deletes `embarkArtifacts/` within a dapp root, and `embarkArtifacts/` is git-ignored. `lib/core/env` adds all `node_modules` relative to `process.env.EMBARK_PATH` to `NODE_PATH` so that embark's modules can be resolved as expected whether embark's `node_modules` have been deduped or are installed in npm's flat "global style". `checkDependencies` has been inlined (see `lib/utils/checkDependencies`) and slightly modified to support dependencies that have been hoisted into a higher-up `node_modules`, e.g. as part of a yarn workspace. eslint has been disabled for that script to avoid more involved changes to it. `test_apps` is not in `packages/embark`; rather, there is `test_dapps` at the top-level of the monorepo. `test_dapps` is an embedded monorepo, and its `ci` / `qa` scripts `npm install` embark from freshly built tarballs of the packages in the outer monorepo and then use that installation to run `embark test` in the dapps. This should allow us to rapidly detect breakage related to auto-bumps in transitive dependencies. [filter options]: https://github.com/lerna/lerna/tree/master/core/filter-options [embark-readme]: https://github.com/embark-framework/embark/blob/build/lerna/packages/embark/README.md [fixed-locked]: https://github.com/lerna/lerna#fixedlocked-mode-default [independent]: https://github.com/lerna/lerna#independent-mode [npm-scripts]: https://docs.npmjs.com/misc/scripts [lerna publish]: https://github.com/lerna/lerna/tree/master/commands/publish [pub-pos]: https://github.com/lerna/lerna/tree/master/commands/publish#positionals [ver-pos]: https://github.com/lerna/lerna/tree/master/commands/version#positionals [lerna-json]: https://github.com/embark-framework/embark/blob/build/lerna/lerna.json#L11 [verdaccio]: https://www.npmjs.com/package/verdaccio [nohoist]: https://github.com/embark-framework/embark/blob/build/lerna/package.json#L52-L55 [restrictpath]: https://github.com/embark-framework/embark/blob/build/lerna/packages/embark/src/lib/core/fs.js#L9
d9b816f to
ed5f92f
Compare
|
Thanks for all the helpful feedback and compliments, team! I really appreciate your patience and support as this took shape in the New Year. Thanks especially to @emizzle and @PascalPrecht for the generous amounts of time they spent helping me sort some things out. |
TL;DR
yarn installin a fresh clone of the repo.yarn rebootwhen switching branches.When pulling in these changes, there may be untracked files at the root in all/some of:
They can be safely deleted since those paths are no longer in use at the root.
Many of the scripts in the top-level
package.jsonsupport Lerna's filter options. For example:yarn build --scope embarkbuild onlypackages/embark.yarn build --ignore embark-uibuild everything exceptpackages/embark-ui.Scoping scripts will be more useful when there are more packages in the monorepo and, for example,
yarn startdoesn't need to be invoked for all of them while working on just a few of them simultaneously, e.gembarkandembarkjs.It's also possible to
cdinto a particular package and run its scripts directly:Hot Topics & Questions
What should be done about the README for
packages/embark? Should the top-level README be duplicated in that package?Lerna is setup to use Fixed/Locked mode, and accordingly
packages/embark-uiis set to4.0.0-beta.0. The same will be true when adding embarkjs, swarm-api, etc. to the monorepo. Is this acceptable or do we want to use Independent mode?Scripts
If a package doesn't have a matching script,
lerna runskips it automatically. For example,packages/embark-uidoesn't have atypecheckscript.yarn buildRuns babel, webpack, etc. according to a package's
buildscript.yarn build:no-uiis a shortcut foryarn build --ignore embark-ui.yarn ciRuns a series of scripts relevant in a CI context according to a package's
ciscript. Forpackages/embarkthat'slint typecheck build test package.Also runs the
ciscript of the embeddedtest_dappsmonorepo.yarn cleanRuns rimraf, etc. according to a package's
cleanscript.yarn globalizeMakes the development embark available on the global PATH, either via symlink (Linux, macOS) or a shim script (Windows).
yarn lintRuns eslint, etc. according to a package's
lintscript.yarn packageInvokes
npm packaccording to a package'spackagescript.yarn qaVery similar to
ci, runs a series of scripts according to a package'sqascript. The big difference betweenciandqais that at the top-levelqafirst kicks offreboot:full.There is a
preqascript (invoked automatically), which is a bit of a wart. It makes sure thatembark resetcan be run successfully inpackages/embark/templates/*when therebootscript invokes theresetscript.The
qascript is invoked byyarn releasebefore the latter proceeds to invokelerna publish.yarn rebootInvokes the
resetscript and then doesyarn install.The
reboot:fullvariant invokesreset:fulland then doesyarn install.yarn releaseWorks in concert with lerna publish, which will prompt to verify the version before proceeding. Use
nto cancel instead ofctrl-caslerna publishhas been seen to occasionally misbehave when not exited cleanly (e.g. creating a tag when it shouldn't have).[bump]seepublishpositionals andversionpositionals; an exact version can also be specified.--preidprerelease identifier, e.g.beta; when doing a prerelease bump will default to whatever identifier is currently in use.--dist-tagregistry distribution tag, defaults tolatest.--messagecommit message format, defaults tochore(release): %v.--signindicates that the git commit and tag should be signed; not signed by default.--release-branchdefault ismaster; must match the current branch.--git-remotedefault isorigin.--registrydefault ishttps://registry.npmjs.org/per the top-levellerna.json.To release
4.0.0-beta.1asembark@next(assuming version is currently at4.0.0-beta.0) could do:For test releases (there is no longer a
--dry-runoption) verdaccio and a filesystem git remote can be used.Condensend instructions:
in another terminal:
in the first terminal:
yarn resetInvokes cleaning and resetting steps according to a package's
resetscript. The big difference betweencleanandresetis thatresetis intended to delete a package'snode_modules.The
reset:fullvariant deletes the monorepo's top-levelnode_modulesat the end. That shouldn't be necessary too often, e.g. in day-to-day work when switching branches, which is why there isreboot/resetvs.reboot:full/reset:full.Errors may be seen related to invocation of
embark resetif embark is not built, butresetwill still complete successfully.yarn startRuns babel, webpack, tsc, etc. (in parallel, in watch mode) according to a package's
startscript.yarn testRun mocha, etc. according to a package's
testscript.The
test:fullvariant runs a series of scripts:lint typecheck test test_dapps.yarn test_dappsRuns the
testscript of the embeddedtest_dappsmonorepo.The
test_dapps:ciandtest_dapps:qavariants run theciandqascripts of the embeddedtest_dappsmonorepo, respectively.yarn typecheckRuns tsc, etc. according to a package's
typecheckscript.Notes
npxis used in some of the top-level and package scripts to ensure the scripts can run even ifnode_modulesis missing."nohoist"specifies a couple of embark packages becauserestrictPathis interfering with access to modules that are located in a higher-upnode_modules.All dependencies in
packages/embark-uihave been madedevDependenciessince its production build is self-contained.packages/embark's existing CHANGELOG's formatting has been slightly adjusted to match the formatting that Lerna will use going forward (entries in the log haven't been modified).Lerna will generate a CHANGELOG at the top-level and in each package. Since we're transitioning to a monorepo, things may look a little wonky with respect to old entries in
packages/embark/CHANGELOG.mdand going forward we need to consider how scoping our commits corresponds to member-packages of the monorepo.In
packages/embark,testinvokesscripts/test, which starts a child process whereinprocess.env.DAPP_PATHis a temporary path that has all ofpackages/embark/dist/testcopied into it, so that paths to test helpers/fixtures don't need to be prefixed withdist/test/and so that a.embarkdirectory doesn't get written intopackages/embark.The
"engines"specified in top-level and packages'package.jsonreflect a node and npm pair that match (a source of confusion in the past). The pair was chosen according to the first post v5 npm that's bundled with node. A"runtime"key/object has been introduced inpackages/embark/package.jsonwhich is used as the basis for specifying the minimum version of node that can be used to run embark, and that's what is checked bybin/embark.Some changes have been introduced, e.g. in
lib/core/configandlib/utils/solidity/remapImportsso that it's not implicitly assumed thatprocess.env.DAPP_PATH/fs.dappPath()are the same asprocess.cwd(). There are probably several++ places where that assumption is still in effect, and we should work to identify and correct them.embark resetnow deletesembarkArtifacts/within a dapp root, andembarkArtifacts/is git-ignored.lib/core/envadds allnode_modulesrelative toprocess.env.EMBARK_PATHtoNODE_PATHso that embark's modules can be resolved as expected whether embark'snode_moduleshave been deduped or are installed in npm's flat "global style".checkDependencieshas been inlined (seelib/utils/checkDependencies) and slightly modified to support dependencies that have been hoisted into a higher-upnode_modules, e.g. as part of a yarn workspace. eslint has been disabled for that script to avoid more involved changes to it.test_appsis not inpackages/embark; rather, there istest_dappsat the top-level of the monorepo.test_dappsis an embedded monorepo, and itsci/qascriptsnpm installembark from freshly built tarballs of the packages in the outer monorepo and then use that installation to runembark testin the dapps. This should allow us to rapidly detect breakage related to auto-bumps in transitive dependencies.