1 | #!/usr/bin/env node
|
2 | 'use strict';
|
3 |
|
4 | /*
|
5 | * This script generates the template a changelog by comparing a current version
|
6 | * with master. Run this, copy what's logged into the `CHANGELOG.md` and update
|
7 | * the top section based on the changes listed in "Community Contributions"
|
8 | *
|
9 | * Usage:
|
10 | *
|
11 | * bin/changelog
|
12 | */
|
13 |
|
14 | var EOL = require('os').EOL;
|
15 | var RSVP = require('rsvp');
|
16 | var Promise = RSVP.Promise;
|
17 | var GitHubApi = require('github');
|
18 | var execSync = require('child_process').execSync;
|
19 |
|
20 | var github = new GitHubApi({version: '3.0.0'});
|
21 | var compareCommits = RSVP.denodeify(github.repos.compareCommits);
|
22 | var currentVersion = process.env.PRIOR_VERSION;
|
23 | var head = process.env.HEAD || 'master';
|
24 |
|
25 | compareCommits({
|
26 | user: 'ember-data',
|
27 | repo: 'active-model-adapter',
|
28 | base: currentVersion,
|
29 | head: head
|
30 | })
|
31 | .then(processPages)
|
32 | .then(console.log)
|
33 | .catch(function(err) {
|
34 | console.error(err);
|
35 | })
|
36 |
|
37 | function getCommitMessage(commitInfo) {
|
38 | var message = commitInfo.commit.message;
|
39 |
|
40 | if (message.indexOf('cherry picked from commit') > -1) {
|
41 | var cherryPickRegex = /cherry picked from commit ([a-z0-9]+)/;
|
42 | var originalCommit = cherryPickRegex.exec(message)[1]
|
43 |
|
44 | try {
|
45 | // command from http://stackoverflow.com/questions/8475448/find-merge-commit-which-include-a-specific-commit
|
46 | message = execSync('commit=$((git rev-list ' + originalCommit + '..origin/master --ancestry-path | cat -n; git rev-list ' + originalCommit + '..origin/master --first-parent | cat -n) | sort -k2 | uniq -f1 -d | sort -n | tail -1 | cut -f2) && git show --format="%s\n\n%b" $commit', { encoding: 'utf8' });
|
47 | } catch(e) { }
|
48 | }
|
49 |
|
50 | return message;
|
51 | }
|
52 |
|
53 | function processPages(res) {
|
54 | var contributions = res.commits.filter(function(commitInfo) {
|
55 | var message = commitInfo.commit.message;
|
56 |
|
57 | return message.indexOf('Merge pull request #') > -1 || message.indexOf('cherry picked from') > -1;
|
58 | }).map(function(commitInfo) {
|
59 | var message = getCommitMessage(commitInfo);
|
60 | var match = message.match(/#(\d+) from (.*)\//);
|
61 | var result = {
|
62 | sha: commitInfo.sha
|
63 | };
|
64 |
|
65 | if (match) {
|
66 | var numAndAuthor = match.slice(1, 3);
|
67 |
|
68 | result.number =numAndAuthor[0];
|
69 | result.title = message.split('\n\n')[1];
|
70 | } else {
|
71 | result.title = message.split('\n\n')[0];
|
72 | }
|
73 |
|
74 | return result;
|
75 | }).sort(function(a, b) {
|
76 | return a.number > b.number;
|
77 | }).map(function(pr) {
|
78 | var title = pr.title;
|
79 | var link;
|
80 | if (pr.number) {
|
81 | link = '[#' + pr.number + ']' + '(https://github.com/ember-data/active-model-adapter/pull/' + pr.number + ')';
|
82 | } else {
|
83 | link = '[' + pr.sha.slice(0, 8) + '](https://github.com/ember-data/active-model-adapter/commit/' + pr.sha + ')';
|
84 | }
|
85 |
|
86 | return '- ' + link + ' ' + title;
|
87 | }).join('\n');
|
88 |
|
89 | if (github.hasNextPage(res)) {
|
90 | return github.getNextPage(res)
|
91 | .then(function(nextPage) {
|
92 | contributions += processPages(nextPage);
|
93 | });
|
94 | } else {
|
95 | return RSVP.resolve(contributions);
|
96 | }
|
97 | }
|