This is an automated email from the ASF dual-hosted git repository. wangzx pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/incubator-echarts-bot.git
commit 1c1fd56a52728146cc01062e57c98df3c3f235fc Author: Ovilia <zwl.s...@gmail.com> AuthorDate: Wed Feb 20 20:16:20 2019 +0800 feat: update for new issue template --- index.js | 103 +++++++++++++++++++++++----------- src/coreCommitters.js | 4 +- src/issue.js | 150 ++++++++++---------------------------------------- src/text.js | 59 ++++++++++++++++++++ 4 files changed, 162 insertions(+), 154 deletions(-) diff --git a/index.js b/index.js index 338360d..847df80 100644 --- a/index.js +++ b/index.js @@ -1,55 +1,59 @@ const Issue = require('./src/issue'); const coreCommitters = require('./src/coreCommitters'); +const {PR_OPENED, PR_MERGED, PR_NOT_MERGED, LABEL_HOWTO, NOT_USING_TEMPLATE} = require('./src/text'); module.exports = app => { - app.on(['issues.opened', 'issues.edited'], async context => { + app.on(['issues.opened', 'issues.edited', 'issues.reopened'], async context => { const issue = new Issue(context); - if (!issue.isUsingTemplate()) { - // Close issue - const comment = context.github.issues.createComment(context.issue({ - body: issue.response - })); + // Ignore comment because it will commented when adding invalid label + const comment = issue.response === NOT_USING_TEMPLATE + ? Promise.resolve() + : commentIssue(context, issue.response); - const close = context.github.issues.edit(context.issue({ - state: 'closed' - })); + const addLabels = issue.addLabels.length + ? context.github.issues.addLabels(context.issue({ + labels: issue.addLabels + })) + : Promise.resolve(); - return Promise.all([comment, close]); + const removeLabels = issue.removeLabels.length + ? context.github.issues.addLabels(context.issue({ + labels: issue.removeLabels + })) + : Promise.resolve(); + + if (issue.isUsingTemplate()) { + return Promise.all([comment, addLabels, removeLabel]); } else { - const addLabels = issue.tags.length - ? context.github.issues.addLabels(context.issue({ - labels: issue.tags - })) - : Promise.resolve(); - - const removeLabel = getRemoveLabel( - context, - issue.isMeetAllRequires() - ? 'waiting-for-author' - : 'waiting-for-help' - ); + return Promise.all([comment, addLabels, removeLabels]); + } + }); - const comment = context.github.issues.createComment(context.issue({ - body: issue.response - })); + app.on('issues.labeled', async context => { + switch (context.payload.label.name) { + case 'invalid': + return Promise.all([commentIssue(context, NOT_USING_TEMPLATE), closeIssue(context)]); - return Promise.all([addLabels, removeLabel, comment]); + case 'howto': + return Promise.all([commentIssue(context, LABEL_HOWTO), closeIssue(context)]); } }); app.on('issue_comment.created', async context => { const commenter = context.payload.comment.user.login; - let removeLabel, addLabel; - if (coreCommitters.isCoreCommitter(commenter)) { + const isCommenterAuthor = commenter === context.payload.issue.user.login; + let removeLabel; + let addLabel; + if (coreCommitters.isCoreCommitter(commenter) && !isCommenterAuthor) { // New comment from core committers removeLabel = getRemoveLabel(context, 'waiting-for-help'); addLabel = context.github.issues.addLabels(context.issue({ labels: ['waiting-for-author'] })); } - else if (commenter === context.payload.issue.user.login) { + else if (isCommenterAuthor) { // New comment from issue author removeLabel = getRemoveLabel(context, 'waiting-for-author'); addLabel = context.github.issues.addLabels(context.issue({ @@ -58,6 +62,27 @@ module.exports = app => { } return Promise.all([removeLabel, addLabel]); }); + + // Pull Requests Not Tested Yet + // app.on(['pull_request.opened', 'pull_request.reopened'], async context => { + // console.log('pull request open'); + // const comment = context.github.issues.createComment(context.issue({ + // body: PR_OPENED + // })); + + // return Promise.all([comment]); + // }); + + // app.on(['pull_request.closed'], async context => { + // console.log('pull request close'); + // console.log(context.payload); + // const isMerged = context.payload['pull_request'].merged; + // const comment = context.github.issues.createComment(context.issue({ + // body: isMerged ? PR_MERGED : PR_NOT_MERGED + // })); + + // return Promise.all([comment]); + // }); } function getRemoveLabel(context, name) { @@ -67,8 +92,22 @@ function getRemoveLabel(context, name) { }) ).catch(err => { // Ignore error caused by not existing. - if (err.message !== 'Not Found') { - throw(err); - } + // if (err.message !== 'Not Found') { + // throw(err); + // } }); } + +function closeIssue(context) { + const closeIssue = context.github.issues.edit(context.issue({ + state: 'closed' + })); + return closeIssue; +} + +function commentIssue(context, commentText) { + const comment = context.github.issues.createComment(context.issue({ + body: commentText + })); + return comment; +} diff --git a/src/coreCommitters.js b/src/coreCommitters.js index 6d9cf9f..c13147e 100644 --- a/src/coreCommitters.js +++ b/src/coreCommitters.js @@ -14,6 +14,6 @@ function isCoreCommitter(user) { } module.exports = { - getCoreCommitters: getCoreCommitters, - isCoreCommitter: isCoreCommitter + getCoreCommitters, + isCoreCommitter }; diff --git a/src/issue.js b/src/issue.js index 73077ff..1d1d770 100644 --- a/src/issue.js +++ b/src/issue.js @@ -1,156 +1,66 @@ +const {NOT_USING_TEMPLATE, ISSUE_CREATED, ISSUE_UPDATED} = require('./text'); + class Issue { constructor(context) { this.context = context; this.issue = context.payload.issue; this.body = this.issue.body; + this.issueType = null; + this.addLabels = []; + this.removeLabels = []; if (this.isUsingTemplate()) { this.init(); } else { - this.response = `💔 Oops... Please follow the issue template to ask questions. - I'm going to close this issue, and please create a new issue and DO NOT DELETE ISSUE TEMPLATE.`; + this.response = NOT_USING_TEMPLATE; + this.addLabels.push('invalid'); } } init() { - this.isInEnglish = this._matches('I am using English in this issue'); - - this.issueType = 'others'; - if (this._matches('I have a question to ask about')) { - this.issueType = 'support'; - } - else if (this._matches('I have a bug to report')) { + if (this._contain('Steps to reproduce')) { this.issueType = 'bug'; } - else if (this._matches('I have a feature to request')) { + else if (this._contain('What problem does this feature solve')) { this.issueType = 'new-feature'; } - else if (this._matches('I have a feature to enhance')) { - this.issueType = 'enhancement'; - } - else if (this._matches('There\'s something wrong with the documents')) { - this.issueType = 'doc'; + else { + this.response = NOT_USING_TEMPLATE; + return; } - this.requiredReadDoc = this._matches('I have read the document'); - this.requiredSearch = this._matches('I have searched for similar issues'); - this.requiredLatest = this._matches('I have tried with the latest version'); - this.requiredIssueType = this._matches('issue type'); - this.requiredDesc = this._matches('one sentence description in issue details'); - this.requiredDemo = this._matches('demo if this is bug report') - || this.issueType !== 'bug' && this.issueType !== 'support'; - this.requiredVersion = this._matches('ECharts version'); - this._computeResponse(); - this._computeTags(); } isUsingTemplate() { - return this.body.indexOf('I have read the document') > -1; - } - - isMeetAllRequires() { - return this.requiredReadDoc && this.requiredSearch && this.requiredLatest - && this.requiredIssueType && this.requiredDesc - && this.requiredDemo && this.requiredVersion; + return this.body.indexOf('generated by echarts-issue-helper') > -1; } _computeResponse() { - let response = ''; - - if (this.isMeetAllRequires()) { - switch(this.context.payload.action) { - case 'opened': - response = 'Hi! We\'ve received your issue and the expected respond time is within one day for weekdays. Have a nice day! 🍵'; - break; - case 'edited': - response = 'Thanks for editing. Please wait for the community to reply. 🍻' - } - } - else { - response += 'Thanks for editing, but something doesn\'t seem to be right:\n❗️ **[Error]** Please '; - - if (!this.requiredReadDoc) { - response += 'read the [doc](https://echarts.apache.org/option.html) and [examples](https://ecomfe.github.io/echarts-examples/public/index.html)'; - } - else if (!this.requiredSearch) { - response += '**search issue list**'; - } - else if (!this.requiredLatest) { - response += 'try with the **lastest version** of ECharts'; - } - else if (!this.requiredIssueType) { - response += 'provide with **issue type**'; - } - else if (!this.requiredDesc) { - response += 'provide with **issue description**'; - } - else if (!this.requiredDemo) { - response += 'provide with a **demo** (place N/A for demo if your problem does not need one and check the tick of demo)'; - } - else if (!this.requiredVersion) { - response += 'provide with ECharts **version**'; - } - - response += ' first, and make sure everything is checked in the `REQUIRED FIELDS`.\nYou may edit this issue and I will check it again. 😃'; - } - - this.response = response; - } - - _computeTags() { - this.tags = []; - - if (this.isMeetAllRequires()) { - this.tags.push('waiting-for-help'); - } - else { - this.tags.push('waiting-for-author'); - } - - if (this.isInEnglish) { - this.tags.push('en'); + switch(this.context.payload.action) { + case 'opened': + case 'reopened': + this.response = ISSUE_CREATED; + break; + case 'edited': + this.response = ISSUE_UPDATED; + this.removeLabels.push('waiting-for-help'); + break; } - if (this.issueType !== 'others') { - this.tags.push(this.issueType); - } - - const topics = this._getTopics(); - for (let i = 0; i < topics.length; ++i) { - this.tags.push(topics[i]); - } - } - - _getTopics() { - if (this.topics) { - return this.topics; - } - else { - this.topics = []; - } + this.addLabels.push('waiting-for-help'); + this.addLabels.push('pending'); + this.addLabels.push(this.issueType); - const labels = { - 'Legend': 'legend', - 'Tooltip': 'tooltip', - 'Event': 'event', - 'Performance': 'performance', - 'SVG': 'SVG', - 'Map': 'map', - 'ECharts GL': 'gl', - 'Third-party': 'third-party' - }; - for (let label in labels) { - if (this._matches(label)) { - this.topics.push(labels[label]); - } + const isInEnglish = this._contain('This issue is in English'); + if (isInEnglish) { + this.addLabels.push('en'); } - return this.topics; } - _matches(text) { - return this.body.indexOf('- [x] Required: ' + text) > -1; + _contain(txt) { + return this.body.indexOf(txt) > -1; } } diff --git a/src/text.js b/src/text.js new file mode 100644 index 0000000..22df08d --- /dev/null +++ b/src/text.js @@ -0,0 +1,59 @@ +const NOT_USING_TEMPLATE = + `This issue is not created using [issue template](https://ecomfe.github.io/echarts-issue-helper/) so I'm going to close it. 🙊 +Sorry for this, but it helps saving our maintainers' time so that more developers get helped. +Feel free to create another issue using the issue template. + +这个 issue 未使用 [issue 模板](https://ecomfe.github.io/echarts-issue-helper/?lang=zh-cn) 创建,所以我将关闭此 issue。 +为此带来的麻烦我深表歉意,但是请理解这是为了节约社区维护者的时间,以更高效地服务社区的开发者群体。 +如果您愿意,可以请使用 issue 模板重新创建 issue。`; + +const ISSUE_CREATED = + `Hi! We\'ve received your issue and please be patient to get responded. 🎉 +The average response time is expected to be within one day for weekdays. + +In the meanwhile, please make sure that **you have posted enough image to demo your request**. You may also check out the [API](http://echarts.apache.org/api.html) and [chart option](http://echarts.apache.org/option.html) to get the answer. + +Have a nice day! 🍵`; + +const ISSUE_UPDATED = + `An update has been made to this issue. The maintainers are right on their way. 🚒`; + +const PR_OPENED = + `Thanks for your contribution! +@Ovilia Please check out this PR.`; + +const PR_MERGED = + `Congratulations! Your PR has been merged. Thanks for your contribution! 👍 + +Now you are one of the ECharts contributors. Since we joined the Apache group, you need to assign [ICLA](https://www.apache.org/licenses/icla.pdf) file if this is your first PR. +Please fill in the PDF and print it, then sign on it and send the scanned file to secret...@apache.org and oviliazhang at gmail.com with the title \`ICLA for incubator-echarts project\`. +This may be a little tricky, and sorry for the trouble. This is required for the first time your commit is merged in. If you refused, your commit will be backed off. + +You may send an email to dev-subscr...@echarts.apache.org to subscribe our developing discussion on mail list. +`; + +const PR_NOT_MERGED = `I'm sorry your PR didn't get merged. Don't get frustrated. Maybe next time. 😛` + +const LABEL_HOWTO = + `Sorry, but please ask *how-to* questions on [Stack Overflow](https://stackoverflow.com/questions/tagged/echarts). Here's why: + +Maintaining open source projects, especially popular ones, is [hard work](https://nolanlawson.com/2017/03/05/what-it-feels-like-to-be-an-open-source-maintainer/). As ECharts's user base has grown, we are getting more and more usage questions, bug reports, feature requests and pull requests every single day. + +As a free and open source project, ECharts also has limited maintainer bandwidth. That means the only way to ensure the project's sustainability is to: + +1. Prioritize more concrete work (bug fixes and new features); +2. Improve issue triaging efficiency. + +For (1), we have decided to use the GitHub issue lists exclusively for work that has well-defined, actionable goals. Questions and open ended discussions should be posted to mediums that are better suited for them. + +For (2), we have found that issues that do not provide proper information upfront usually results in terribly inefficient back-and-forth communication just to extract the basic information needed for actual triaging. This is exactly why we have created this app: to ensure that every issue is created with the necessary information, and to save time on both sides.` + +module.exports = { + NOT_USING_TEMPLATE, + ISSUE_CREATED, + ISSUE_UPDATED, + PR_OPENED, + LABEL_HOWTO, + PR_MERGED, + PR_NOT_MERGED +}; --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscr...@echarts.apache.org For additional commands, e-mail: commits-h...@echarts.apache.org