diff --git a/MAINTAINING.md b/MAINTAINING.md index 1d8fa4381e..84d9854c61 100644 --- a/MAINTAINING.md +++ b/MAINTAINING.md @@ -18,7 +18,7 @@ style board to track and prioritize issues. ## Merging a pull request -Please, make sure: +Please, make sure: - Travis build is green - At least one collaborator (other than you) approves the PR @@ -84,3 +84,38 @@ guidelines are followed. If it is discovered that we have pushed a release in violation of semver, than a patch release reverting the offending change should be pushed as soon as possible to correct the error. The offending change can then be re-applied and released with the proper version bump. + +## Live releasing the documentation + +The documentation release script does a similar job to the release script except +that it doesn't publish to npm. It will auto tag the current branch with +a pre "docs" tag, and will push to documentation repository. + +For a given tag (lets say `0.22.1`) the first docs tag would be `0.22.1-docs.0`. +In order to tags to be incremental and in order to include all the previous docs +changes, make sure that if a docs tags exists for the current release, +that you start from that tag. + +To live patch the documentation in between release follow these steps + +0. Find the latest documentation release. + - Check the latest release tag (lets say `v0.22.1`). + - Look for a docs-release tag for that version ex: `v0.22.1-docs.X` + - If one exists, check-it-out. If not checkout the latest release tag. + - *Note: Checkout the tag and not master directly because some live + documentation changes on master that could related to new components + or updates for the upcoming release* +0. Create a new branch from there (for example `git checkout -b docs/v0.22.1`) +0. Cherry-pick the commits you want to include in the live update +`git cherry-pick ...` +0. Use the release-docs script to push and tag to the documentation repository. + +*Note: The branch name you checkout to cherry-picked the commit is not enforced. +Though keeping similar names ex: `docs/` helps finding the branch +easily.* + +Example usage of release-docs script: + +```bash +$ ./tools/release-docs +``` diff --git a/tools/release-docs b/tools/release-docs new file mode 100644 index 0000000000..298236d61a --- /dev/null +++ b/tools/release-docs @@ -0,0 +1,8 @@ +#!/usr/bin/env node +/* eslint no-var: 0 */ +require('../register-babel'); +var path = require('path'); +var nodeModulesBin = path.resolve(__dirname, '../node_modules/.bin'); +process.env.PATH = nodeModulesBin + ':' + process.env.PATH; +require('./release-docs-scripts/release-docs'); + diff --git a/tools/release-docs-scripts/release-docs.js b/tools/release-docs-scripts/release-docs.js new file mode 100644 index 0000000000..e5fe3cc71a --- /dev/null +++ b/tools/release-docs-scripts/release-docs.js @@ -0,0 +1,48 @@ +/* eslint no-process-exit: 0 */ + +import 'colors'; +import { exec } from 'child-process-promise'; + +import preConditions from '../release-scripts/pre-conditions'; +import versionBump from '../release-scripts/version-bump'; +import repoRelease from '../release-scripts/repo-release'; +import tag from '../release-scripts/tag'; +import { lint } from '../release-scripts/test'; + +import { repoRoot, docsRoot, docsRepo, tmpDocsRepo } from '../release-scripts/constants'; + +let version; + +const versionBumpOptions = { + preid: 'docs' +}; + +preConditions() + .then(lint) + .then(versionBump(repoRoot, versionBumpOptions)) + .then(v => { version = v; }) + .then(() => { + return exec('npm run docs-build') + .catch(err => { + console.log('Docs-build failed, reverting version bump'.red); + return exec('git reset HEAD .') + .then(() => exec('git checkout package.json')) + .then(() => console.log('Version bump reverted'.red)) + .then(() => { + throw err; + }); + }); + }) + .then(() => exec(`git commit -m "Release v${version}"`)) + .then(() => Promise.all([ + tag(version), + repoRelease(docsRepo, docsRoot, tmpDocsRepo, version) + ])) + .then(() => console.log('Version '.cyan + `v${version}`.green + ' released!'.cyan)) + .catch(err => { + if (!err.__handled) { + console.error(err.message.red); + } + + process.exit(1); + }); diff --git a/tools/release-scripts/constants.js b/tools/release-scripts/constants.js new file mode 100644 index 0000000000..24f94934ef --- /dev/null +++ b/tools/release-scripts/constants.js @@ -0,0 +1,18 @@ +import path from 'path'; + +const repoRoot = path.resolve(__dirname, '../../'); + +const bowerRepo = 'git@github.com:react-bootstrap/react-bootstrap-bower.git'; +const docsRepo = 'git@github.com:react-bootstrap/react-bootstrap.github.io.git'; + +const bowerRoot = path.join(repoRoot, 'amd/'); +const docsRoot = path.join(repoRoot, 'docs-built/'); + +const tmpBowerRepo = path.join(repoRoot, 'tmp-bower-repo'); +const tmpDocsRepo = path.join(repoRoot, 'tmp-docs-repo'); + +export { + repoRoot, + bowerRepo, bowerRoot, tmpBowerRepo, + docsRoot, docsRepo, tmpDocsRepo, +}; diff --git a/tools/release-scripts/release.js b/tools/release-scripts/release.js index 413f47376a..e0af96db59 100644 --- a/tools/release-scripts/release.js +++ b/tools/release-scripts/release.js @@ -1,6 +1,4 @@ /* eslint no-process-exit: 0 */ - -import path from 'path'; import yargs from 'yargs'; import { exec } from 'child-process-promise'; @@ -12,6 +10,8 @@ import tagAndPublish from './tag-and-publish'; import test from './test'; import build from '../build'; +import { repoRoot, bowerRepo, bowerRoot, tmpBowerRepo, docsRoot, docsRepo, tmpDocsRepo } from './constants'; + const yargsConf = yargs .usage('Usage: $0 [--preid ]') .example('$0 minor --preid beta', 'Release with minor version bump with pre-release tag') @@ -30,16 +30,6 @@ const yargsConf = yargs const argv = yargsConf.argv; let version; -const repoRoot = path.resolve(__dirname, '../../'); - -const bowerRepo = 'git@github.com:react-bootstrap/react-bootstrap-bower.git'; -const docsRepo = 'git@github.com:react-bootstrap/react-bootstrap.github.io.git'; - -const bowerRoot = path.join(repoRoot, 'amd/'); -const docsRoot = path.join(repoRoot, 'docs-built/'); - -const tmpBowerRepo = path.join(repoRoot, 'tmp-bower-repo'); -const tmpDocsRepo = path.join(repoRoot, 'tmp-docs-repo'); const versionBumpOptions = { preid: argv.preid, diff --git a/tools/release-scripts/tag-and-publish.js b/tools/release-scripts/tag-and-publish.js index bdee1f8672..adbd5e14b3 100644 --- a/tools/release-scripts/tag-and-publish.js +++ b/tools/release-scripts/tag-and-publish.js @@ -1,11 +1,10 @@ import { exec } from 'child-process-promise'; +import tag from './tag'; export default (version) => { console.log('Releasing: '.cyan + 'npm module'.green); - return exec(`git tag -a --message=v${version} v${version}`) - .then(() => exec(`git push`)) - .then(() => exec(`git push --tags`)) + return tag() .then(() => exec('npm publish')) .then(() => console.log('Released: '.cyan + 'npm module'.green)); }; diff --git a/tools/release-scripts/tag.js b/tools/release-scripts/tag.js new file mode 100644 index 0000000000..40c58cfc30 --- /dev/null +++ b/tools/release-scripts/tag.js @@ -0,0 +1,10 @@ +import { exec } from 'child-process-promise'; + +export default (version) => { + console.log('Tagging: '.cyan + `v${version}`.green); + + return exec(`git tag -a --message=v${version} v${version}`) + .then(() => exec(`git push`)) + .then(() => exec(`git push --tags`)) + .then(() => console.log('Tagged: '.cyan + `v${version}`.green)); +}; diff --git a/tools/release-scripts/test.js b/tools/release-scripts/test.js index 393d58a025..d681b4bfa8 100644 --- a/tools/release-scripts/test.js +++ b/tools/release-scripts/test.js @@ -15,9 +15,14 @@ function lint() { .then(() => console.log('Completed: '.cyan + 'eslint'.green)); } -export default function testAndLint() { +function testAndLint() { return Promise.all([ test(), lint() ]); } + +export { + testAndLint as default, + lint +};