| % submit_rule in the actual project (go, scratch, etc.) |
| % generates a list of labels and whether they are ok, needed, or can be ignored. |
| % Most repos don't define a specific submit_rule; the server uses gerrit:default_submit. |
| % |
| % submit_filter, defined below, is applied to the output of submit_rule to adjust it. |
| % The adjustments are: |
| % |
| % * do_not_review_filter: add a “rejected by Do-Not-Review label” |
| % if the commit message says DO NOT REVIEW. |
| % |
| % * do_not_submit_filter: add a “rejected by Do-Not-Submit label” |
| % if the commit message says DO NOT SUBMIT. |
| % |
| % * trust_filter: make sure that two different people have set |
| % either Code-Review+2 or Trust+1 on the commit. |
| % |
| % * self_review_filter: make sure that Code-Review+2 |
| % is from someone other than the author of the commit. |
| % |
| % Note that if you make any mistake in this file that causes |
| % a Prolog execution exception or makes submit_filter not succeed, |
| % the usual signal you get in Gerrit is that labels disappear from the UI for all CLs. |
| % Sometimes you get an internal error popup instead (syntax errors do this, for example). |
| |
| submit_filter(In, Out) :- |
| Gobot = user(5976), |
| In =.. [submit | A], |
| do_not_review_filter(Gobot, A, B), |
| do_not_submit_filter(Gobot, B, C), |
| trust_filter(Gobot, C, D), |
| self_review_filter(Gobot, D, E), |
| Out =.. [submit | E]. |
| |
| % We don't send email if the commit message says DO NOT REVIEW, |
| % so don't allow submit either. |
| % Case insensitive because the mail filter rules are. |
| do_not_review_filter(Gobot, In, Out) :- |
| gerrit:commit_message_matches('[Dd][Oo][ \t\r\n]+[Nn][Oo][Tt][ \t\r\n]+[Rr][Ee][Vv][Ii][Ee][Ww]'), |
| !, |
| gerrit:commit_author(Id), |
| Error = label('Do-Not-Review', reject(Id)), |
| Out = [Error | In]. |
| |
| do_not_review_filter(Gobot, In, Out) :- |
| Out = In. |
| |
| % Don't allow submit of DO NOT SUBMIT commit message either. |
| % Case insensitive because DO NOT REVIEW is. |
| do_not_submit_filter(Gobot, In, Out) :- |
| gerrit:commit_message_matches('[Dd][Oo][ \t\r\n]+[Nn][Oo][Tt][ \t\r\n]+[Ss][Uu][Bb][Mm][Ii][Tt]'), |
| !, |
| gerrit:commit_author(Id), |
| Error = label('Do-Not-Submit', reject(Id)), |
| Out = [Error | In]. |
| |
| do_not_submit_filter(Gobot, In, Out) :- |
| Out = In. |
| |
| % Check for two trusted author/reviewers, unless Self-Review-OK label set by project. |
| trust_filter(Gobot, In, Out) :- has_label('Self-Review-OK', In), !, Out = In. |
| trust_filter(Gobot, In, Out) :- trust2, !, Out = [label('Trusted', ok(Gobot)) | In]. |
| trust_filter(Gobot, In, Out) :- Out = [label('Untrusted', reject(Gobot)) | In]. |
| |
| trust2 :- trust(U1), trust(U2), U1 \= U2. |
| |
| trust(U) :- gerrit:commit_label(label('Code-Review', 2), U). |
| trust(U) :- gerrit:commit_label(label('Trust', 1), U). |
| |
| % Reject self-code-review, unless Self-Review-OK label set by project. |
| % |
| % NOTE: Projects (= repos) that allow self-code-review and that do not require Trust+2 |
| % (for example, the blog and proposal projects), can use this in rules.pl to set Self-Review-OK: |
| % |
| % submit_rule(S) :- |
| % Gobot = user(5976), |
| % gerrit:default_submit(R), |
| % R =.. [submit | A], |
| % self_review_ok(Gobot, A, B), |
| % S =.. [submit | B]. |
| % |
| % self_review_ok(Gobot, In, Out) :- Out = [label('Self-Review-OK', ok(Gobot)) | In]. |
| % |
| self_review_filter(Gobot, In, Out) :- has_label('Self-Review-OK', In), !, Out = In. |
| self_review_filter(Gobot, In, Out) :- self_review, !, Out = [label('Self-Review', reject(Gobot)) | In]. |
| self_review_filter(Gobot, In, Out) :- Out = In. |
| |
| self_review :- |
| gerrit:change_owner(Owner), |
| gerrit:commit_label(label('Code-Review', 2), Owner). |
| |
| % has_label checks whether the list contains the label L. |
| has_label(L, [label(L, _) | T]). |
| has_label(L, [_ | T]) :- has_label(L, T). |