From 466853e8da9ae51620407db03ceb892cd04b5f6e Mon Sep 17 00:00:00 2001 From: Amit Date: Tue, 9 Jan 2018 16:09:17 +0200 Subject: [PATCH 1/7] added manageWorkspaces field to consumer-bit-json --- src/consumer/bit-json/consumer-bit-json.js | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/src/consumer/bit-json/consumer-bit-json.js b/src/consumer/bit-json/consumer-bit-json.js index 4a9fc9c9674e..a4c90627836d 100644 --- a/src/consumer/bit-json/consumer-bit-json.js +++ b/src/consumer/bit-json/consumer-bit-json.js @@ -36,7 +36,8 @@ type consumerBitJsonProps = { packageManager?: 'npm' | 'yarn', packageManagerArgs?: string[], packageManagerProcessOptions?: Object, - useWorkspaces?: boolean + useWorkspaces?: boolean, + manageWorkspaces?: boolean }; export default class ConsumerBitJson extends AbstractBitJson { @@ -51,6 +52,7 @@ export default class ConsumerBitJson extends AbstractBitJson { packageManagerArgs: ?(string[]); // package manager client to use packageManagerProcessOptions: ?Object; // package manager process options useWorkspaces: boolean; // Enables integration with Yarn Workspaces + manageWorkspaces: boolean; // manage workspaces with yarn constructor({ impl, @@ -69,7 +71,8 @@ export default class ConsumerBitJson extends AbstractBitJson { packageManager = DEFAULT_PACKAGE_MANAGER, packageManagerArgs, packageManagerProcessOptions, - useWorkspaces = false + useWorkspaces = false, + manageWorkspaces = false }: consumerBitJsonProps) { super({ impl, spec, compiler, tester, dependencies, lang, bindingPrefix, extensions }); this.distTarget = distTarget; @@ -81,6 +84,7 @@ export default class ConsumerBitJson extends AbstractBitJson { this.packageManagerArgs = packageManagerArgs; this.packageManagerProcessOptions = packageManagerProcessOptions; this.useWorkspaces = useWorkspaces; + this.manageWorkspaces = manageWorkspaces; } toPlainObject() { @@ -92,7 +96,8 @@ export default class ConsumerBitJson extends AbstractBitJson { packageManager: this.packageManager, packageManagerArgs: this.packageManagerArgs, packageManagerProcessOptions: this.packageManagerProcessOptions, - useWorkspaces: this.useWorkspaces + useWorkspaces: this.useWorkspaces, + manageWorkspaces: this.manageWorkspaces }); if (this.distEntry || this.distTarget) { const dist = {}; @@ -145,7 +150,8 @@ export default class ConsumerBitJson extends AbstractBitJson { packageManager, packageManagerArgs, packageManagerProcessOptions, - useWorkspaces + useWorkspaces, + manageWorkspaces } = object; return new ConsumerBitJson({ @@ -164,6 +170,7 @@ export default class ConsumerBitJson extends AbstractBitJson { packageManagerArgs, packageManagerProcessOptions, useWorkspaces, + manageWorkspaces, distTarget: R.propOr(undefined, 'target', dist), distEntry: R.propOr(undefined, 'entry', dist) }); From ab9097f05d99ab74ebe54d88ae38cb6500ffa74a Mon Sep 17 00:00:00 2001 From: Amit Date: Wed, 10 Jan 2018 23:00:29 +0200 Subject: [PATCH 2/7] support yarn workspaces --- src/constants.js | 4 +++ src/consumer/bit-json/consumer-bit-json.js | 2 +- src/consumer/consumer.js | 33 +++++++++++++++++++++- 3 files changed, 37 insertions(+), 2 deletions(-) diff --git a/src/constants.js b/src/constants.js index e9b737f94672..07ee4182cd59 100644 --- a/src/constants.js +++ b/src/constants.js @@ -263,6 +263,10 @@ export const BIT_CACHE_DIRNAME = 'cache'; export const LATEST_TESTED_MARK = '*'; +export const BIT_DEPENDECIES_REGEX = '*/*/*'; + +export const YARN_WORKSPACES_REGEX = '*'; + export const SCOPE_JSON = 'scope.json'; export const DEFAULT_RESOLVER = () => ''; diff --git a/src/consumer/bit-json/consumer-bit-json.js b/src/consumer/bit-json/consumer-bit-json.js index a4c90627836d..b490b4b2a162 100644 --- a/src/consumer/bit-json/consumer-bit-json.js +++ b/src/consumer/bit-json/consumer-bit-json.js @@ -72,7 +72,7 @@ export default class ConsumerBitJson extends AbstractBitJson { packageManagerArgs, packageManagerProcessOptions, useWorkspaces = false, - manageWorkspaces = false + manageWorkspaces = true }: consumerBitJsonProps) { super({ impl, spec, compiler, tester, dependencies, lang, bindingPrefix, extensions }); this.distTarget = distTarget; diff --git a/src/consumer/consumer.js b/src/consumer/consumer.js index 5e823ff878dd..a8436cd6ffab 100644 --- a/src/consumer/consumer.js +++ b/src/consumer/consumer.js @@ -22,7 +22,10 @@ import { NODE_PATH_SEPARATOR, LATEST_BIT_VERSION, CFG_REGISTRY_DOMAIN_PREFIX, - DEFAULT_REGISTRY_DOMAIN_PREFIX + DEFAULT_REGISTRY_DOMAIN_PREFIX, + DEFAULT_SEPARATOR, + BIT_DEPENDECIES_REGEX, + YARN_WORKSPACES_REGEX } from '../constants'; import { Scope, ComponentWithDependencies } from '../scope'; import migratonManifest from './migrations/consumer-migrator-manifest'; @@ -480,6 +483,30 @@ export default class Consumer { }); } + /** + * Adds workspace array to package.json - only if user wants to work with yarn workspaces + */ + async addWorkspacesToPackageJson() { + const driver = await this.driver.getDriver(); + const PackageJson = driver.PackageJson; + const pkg = await PackageJson.load(this.getPath()); + const workSpaces = pkg.workspaces || []; + if (pkg) { + workSpaces.push(this.bitJson.dependenciesDirectory + BIT_DEPENDECIES_REGEX); + const formatedComponentsPath = format(this.bitJson.componentsDefaultDirectory, { + name: YARN_WORKSPACES_REGEX, + scope: YARN_WORKSPACES_REGEX, + namespace: YARN_WORKSPACES_REGEX + }); + const formatedRegexPath = formatedComponentsPath + .split(DEFAULT_SEPARATOR) + .map(part => (R.contains(YARN_WORKSPACES_REGEX, part) ? YARN_WORKSPACES_REGEX : part)) + .join(DEFAULT_SEPARATOR); + workSpaces.push(formatedRegexPath); + pkg.workspaces = R.uniq(workSpaces); + await pkg.write({ override: true }); + } + } /** * write the components into '/components' dir (or according to the bit.map) and its dependencies in the * '/components/.dependencies' dir. Both directories are configurable in bit.json @@ -603,6 +630,10 @@ export default class Consumer { } }); } + + // add workspaces if flag is true + if (this.bitJson.manageWorkspaces) await this.addWorkspacesToPackageJson(); + await bitMap.write(); if (installNpmPackages) await this.installNpmPackages(componentsWithDependencies, verbose); await this.addComponentsToRootPackageJson(writtenComponents, bitMap); From c1eff82fa2cf80937ebaf29364f31833c15a85fc Mon Sep 17 00:00:00 2001 From: Amit Date: Thu, 11 Jan 2018 18:18:29 +0200 Subject: [PATCH 3/7] support yarn workspaces --- src/constants.js | 2 +- src/consumer/consumer.js | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/constants.js b/src/constants.js index 07ee4182cd59..cb9d5bd911d5 100644 --- a/src/constants.js +++ b/src/constants.js @@ -263,7 +263,7 @@ export const BIT_CACHE_DIRNAME = 'cache'; export const LATEST_TESTED_MARK = '*'; -export const BIT_DEPENDECIES_REGEX = '*/*/*'; +export const BIT_DEPENDECIES_REGEX = '/*/*/*/*'; export const YARN_WORKSPACES_REGEX = '*'; diff --git a/src/consumer/consumer.js b/src/consumer/consumer.js index a8436cd6ffab..c3b655aee6ee 100644 --- a/src/consumer/consumer.js +++ b/src/consumer/consumer.js @@ -489,9 +489,9 @@ export default class Consumer { async addWorkspacesToPackageJson() { const driver = await this.driver.getDriver(); const PackageJson = driver.PackageJson; - const pkg = await PackageJson.load(this.getPath()); - const workSpaces = pkg.workspaces || []; + const pkg = await PackageJson.load(this.getPath(), false); if (pkg) { + const workSpaces = pkg.workspaces || []; workSpaces.push(this.bitJson.dependenciesDirectory + BIT_DEPENDECIES_REGEX); const formatedComponentsPath = format(this.bitJson.componentsDefaultDirectory, { name: YARN_WORKSPACES_REGEX, From 4338dea2e093c630a2db858ce4b026c7f5e8e608 Mon Sep 17 00:00:00 2001 From: Amit Date: Thu, 11 Jan 2018 18:20:26 +0200 Subject: [PATCH 4/7] bump bit-javascript --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index e0a163204bba..8d964fc8e9ff 100644 --- a/package.json +++ b/package.json @@ -34,7 +34,7 @@ "dependencies": { "array-difference": "^0.0.1", "babel-runtime": "^6.23.0", - "bit-javascript": "0.10.8-dev.10", + "bit-javascript": "0.10.8-dev.11", "buffer-from": "^0.1.1", "chalk": "^2.1.0", "chokidar": "^1.7.0", From f4c9a9c3a148370b2ade80de4b441138abed8da4 Mon Sep 17 00:00:00 2001 From: Amit Date: Thu, 11 Jan 2018 18:23:28 +0200 Subject: [PATCH 5/7] add tests to yarn workspaces --- e2e/commands/import.e2e.js | 54 +++++++++++++++++++++++++++++++++++--- e2e/e2e-helper.js | 18 +++++++++++++ 2 files changed, 69 insertions(+), 3 deletions(-) diff --git a/e2e/commands/import.e2e.js b/e2e/commands/import.e2e.js index 1ca88783f331..d833eea2e5bc 100644 --- a/e2e/commands/import.e2e.js +++ b/e2e/commands/import.e2e.js @@ -13,9 +13,9 @@ describe('bit import', function () { this.timeout(0); const helper = new Helper(); - after(() => { + /* after(() => { helper.destroyEnv(); - }); + }); */ const isTypeFixture = "module.exports = function isType() { return 'got is-type'; };"; const isStringFixture = @@ -1810,7 +1810,55 @@ describe('bit import', function () { }); }); }); - + describe('import component with dependencies with yarn workspaces', () => { + let dependencies; + before(() => { + helper.setNewLocalAndRemoteScopes(); + dependencies = path.join( + helper.localScopePath, + 'components', + '.dependencies', + 'global', + 'simple', + helper.remoteScope, + '0.0.1' + ); + helper.addNpmPackage('lodash.isboolean', '3.0.0'); + const simpleFixture = 'import a from "lodash.isboolean"; '; + helper.createFile('global', 'simple.js', simpleFixture); + helper.addComponentWithOptions('global/simple.js', { i: 'global/simple' }); + helper.commitComponent('simple'); + helper.exportComponent('simple'); + helper.addNpmPackage('lodash.isstring', '4.0.0'); + const withDepsFixture = 'import a from "./global/simple.js"; import c from "lodash.isstring"'; + helper.createFile('', 'with-deps.js', withDepsFixture); + helper.addComponentWithOptions('with-deps.js', { i: 'comp/with-deps' }); + helper.commitAllComponents(); + helper.exportComponent('comp/with-deps'); + helper.reInitLocalScope(); + helper.createPackageJson(); + helper.addRemoteScope(helper.remoteScopePath); + helper.changePackageManagerToYarn(); + helper.importComponent('comp/with-deps'); + }); + it('should install component dependencie as separate packages with yarn workspaces', () => { + expect(dependencies).to.be.a.directory('should not be empty').and.not.empty; + }); + it('Should contain yarn lock file', () => { + expect(path.join(helper.localScopePath, 'yarn.lock')).to.be.a.file('no yarn lock file'); + }); + it('should install global/simple package dependencies with yarn', () => { + expect(path.join(helper.localScopePath, 'node_modules')).to.be.a.directory('should not be empty').and.not.empty; + expect(path.join(helper.localScopePath, 'node_modules', 'lodash.isboolean')).to.be.a.directory( + 'should contain lodash.isboolean' + ).and.not.empty; + }); + it('should contain workspaces array in package.json and private true', () => { + const pkgJson = helper.readPackageJson(helper.localScopePath); + expect(pkgJson.workspaces).to.include('components/.dependencies/*/*/*/*', 'components/*/*'); + expect(pkgJson.private).to.be.true; + }); + }); describe.skip('Import compiler', () => { before(() => { helper.reInitLocalScope(); diff --git a/e2e/e2e-helper.js b/e2e/e2e-helper.js index 647f253829e3..29f81aa7056f 100644 --- a/e2e/e2e-helper.js +++ b/e2e/e2e-helper.js @@ -64,6 +64,24 @@ export default class Helper { return fs.readJSONSync(bitJsonPath) || {}; } + createPackageJson( + name: string = 'test', + version: string = '0.0.1', + packageJsonPath: string = path.join(this.localScopePath, 'package.json') + ) { + const packageJson = { name, version }; + fs.writeJSONSync(packageJsonPath, packageJson); + } + changePackageManagerToYarn( + withWorkspaces: boolean = true, + bitJsonPath: string = path.join(this.localScopePath, 'bit.json') + ) { + const bitJson = this.readBitJson(bitJsonPath); + bitJson.packageManager = 'yarn'; + bitJson.manageWorkspaces = withWorkspaces; + this.writeBitJson(bitJson); + } + readPackageJson(packageJsonFolder: string = this.localScopePath) { const packageJsonPath = path.join(packageJsonFolder, 'package.json'); return fs.readJSONSync(packageJsonPath) || {}; From 1099fcc6b90f3b4d87dcad9dbf358caed941105d Mon Sep 17 00:00:00 2001 From: Amit Date: Thu, 11 Jan 2018 18:28:54 +0200 Subject: [PATCH 6/7] add tests to yarn workspaces --- e2e/commands/import.e2e.js | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/e2e/commands/import.e2e.js b/e2e/commands/import.e2e.js index d833eea2e5bc..cdcda501e93a 100644 --- a/e2e/commands/import.e2e.js +++ b/e2e/commands/import.e2e.js @@ -1858,6 +1858,15 @@ describe('bit import', function () { expect(pkgJson.workspaces).to.include('components/.dependencies/*/*/*/*', 'components/*/*'); expect(pkgJson.private).to.be.true; }); + it('component dep should be install as npm package', () => { + const modulePath = path.join( + helper.localScopePath, + 'node_modules', + '@bit', + `${helper.remoteScope}.global.simple` + ); + expect(modulePath).to.be.a.directory('should contain component dep as npm package dep').and.not.empty; + }); }); describe.skip('Import compiler', () => { before(() => { From bdffe966f35880f6a6d4f23e6ab5c1a3f0ea17a7 Mon Sep 17 00:00:00 2001 From: Amit Date: Thu, 11 Jan 2018 19:03:46 +0200 Subject: [PATCH 7/7] re add delete after each test --- e2e/commands/import.e2e.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/e2e/commands/import.e2e.js b/e2e/commands/import.e2e.js index cdcda501e93a..56e2d193988a 100644 --- a/e2e/commands/import.e2e.js +++ b/e2e/commands/import.e2e.js @@ -13,9 +13,9 @@ describe('bit import', function () { this.timeout(0); const helper = new Helper(); - /* after(() => { + after(() => { helper.destroyEnv(); - }); */ + }); const isTypeFixture = "module.exports = function isType() { return 'got is-type'; };"; const isStringFixture =