diff options
| author | David Greenaway <dgreenaway@google.com> | 2022-12-09 09:38:24 +1100 |
|---|---|---|
| committer | David Greenaway <dgreenaway@google.com> | 2022-12-12 22:19:57 +0000 |
| commit | d98f3935247818eb5f5ff2f3816d67c680915161 (patch) | |
| tree | e3bb555807e2d76f7ffe47ff9377278d3e7025a7 | |
| parent | 0324e43242ff078dfce70e80ce8e00d394f5ccdb (diff) | |
| download | git-repo-d98f3935247818eb5f5ff2f3816d67c680915161.tar.gz | |
upload: Allow user to configure unusual commit threshold
Add a per-remote option `uploadwarningthreshold` allowing the user to
override how many commits can be uploaded prior to a warning being
displayed.
Change-Id: Ia7e1b2c7de89a0bf9ca1c24cc83dc595b3667437
Reviewed-on: https://gerrit-review.googlesource.com/c/git-repo/+/354375
Tested-by: David Greenaway <dgreenaway@google.com>
Reviewed-by: Mike Frysinger <vapier@google.com>
| -rw-r--r-- | docs/internal-fs-layout.md | 35 | ||||
| -rw-r--r-- | subcmds/upload.py | 88 |
2 files changed, 79 insertions, 44 deletions
diff --git a/docs/internal-fs-layout.md b/docs/internal-fs-layout.md index a9bd1d26..8be61782 100644 --- a/docs/internal-fs-layout.md +++ b/docs/internal-fs-layout.md | |||
| @@ -222,23 +222,24 @@ The `[remote]` settings are automatically populated/updated from the manifest. | |||
| 222 | 222 | ||
| 223 | The `[branch]` settings are updated by `repo start` and `git branch`. | 223 | The `[branch]` settings are updated by `repo start` and `git branch`. |
| 224 | 224 | ||
| 225 | | Setting | Subcommands | Use/Meaning | | 225 | | Setting | Subcommands | Use/Meaning | |
| 226 | |-------------------------------|---------------|-------------| | 226 | |---------------------------------------|---------------|-------------| |
| 227 | | review.\<url\>.autocopy | upload | Automatically add to `--cc=<value>` | | 227 | | review.\<url\>.autocopy | upload | Automatically add to `--cc=<value>` | |
| 228 | | review.\<url\>.autoreviewer | upload | Automatically add to `--reviewers=<value>` | | 228 | | review.\<url\>.autoreviewer | upload | Automatically add to `--reviewers=<value>` | |
| 229 | | review.\<url\>.autoupload | upload | Automatically answer "yes" or "no" to all prompts | | 229 | | review.\<url\>.autoupload | upload | Automatically answer "yes" or "no" to all prompts | |
| 230 | | review.\<url\>.uploadhashtags | upload | Automatically add to `--hashtag=<value>` | | 230 | | review.\<url\>.uploadhashtags | upload | Automatically add to `--hashtag=<value>` | |
| 231 | | review.\<url\>.uploadlabels | upload | Automatically add to `--label=<value>` | | 231 | | review.\<url\>.uploadlabels | upload | Automatically add to `--label=<value>` | |
| 232 | | review.\<url\>.uploadnotify | upload | [Notify setting][upload-notify] to use | | 232 | | review.\<url\>.uploadnotify | upload | [Notify setting][upload-notify] to use | |
| 233 | | review.\<url\>.uploadtopic | upload | Default [topic] to use | | 233 | | review.\<url\>.uploadtopic | upload | Default [topic] to use | |
| 234 | | review.\<url\>.username | upload | Override username with `ssh://` review URIs | | 234 | | review.\<url\>.uploadwarningthreshold | upload | Warn when attempting to upload more than this many CLs | |
| 235 | | remote.\<remote\>.fetch | sync | Set of refs to fetch | | 235 | | review.\<url\>.username | upload | Override username with `ssh://` review URIs | |
| 236 | | remote.\<remote\>.projectname | \<network\> | The name of the project as it exists in Gerrit review | | 236 | | remote.\<remote\>.fetch | sync | Set of refs to fetch | |
| 237 | | remote.\<remote\>.pushurl | upload | The base URI for pushing CLs | | 237 | | remote.\<remote\>.projectname | \<network\> | The name of the project as it exists in Gerrit review | |
| 238 | | remote.\<remote\>.review | upload | The URI of the Gerrit review server | | 238 | | remote.\<remote\>.pushurl | upload | The base URI for pushing CLs | |
| 239 | | remote.\<remote\>.url | sync & upload | The URI of the git project to fetch | | 239 | | remote.\<remote\>.review | upload | The URI of the Gerrit review server | |
| 240 | | branch.\<branch\>.merge | sync & upload | The branch to merge & upload & track | | 240 | | remote.\<remote\>.url | sync & upload | The URI of the git project to fetch | |
| 241 | | branch.\<branch\>.remote | sync & upload | The remote to track | | 241 | | branch.\<branch\>.merge | sync & upload | The branch to merge & upload & track | |
| 242 | | branch.\<branch\>.remote | sync & upload | The remote to track | | ||
| 242 | 243 | ||
| 243 | ## ~/ dotconfig layout | 244 | ## ~/ dotconfig layout |
| 244 | 245 | ||
diff --git a/subcmds/upload.py b/subcmds/upload.py index 0ad3ce26..ceab6463 100644 --- a/subcmds/upload.py +++ b/subcmds/upload.py | |||
| @@ -17,6 +17,7 @@ import functools | |||
| 17 | import optparse | 17 | import optparse |
| 18 | import re | 18 | import re |
| 19 | import sys | 19 | import sys |
| 20 | from typing import List | ||
| 20 | 21 | ||
| 21 | from command import DEFAULT_LOCAL_JOBS, InteractiveCommand | 22 | from command import DEFAULT_LOCAL_JOBS, InteractiveCommand |
| 22 | from editor import Editor | 23 | from editor import Editor |
| @@ -24,21 +25,54 @@ from error import UploadError | |||
| 24 | from git_command import GitCommand | 25 | from git_command import GitCommand |
| 25 | from git_refs import R_HEADS | 26 | from git_refs import R_HEADS |
| 26 | from hooks import RepoHook | 27 | from hooks import RepoHook |
| 28 | from project import ReviewableBranch | ||
| 27 | 29 | ||
| 28 | 30 | ||
| 29 | UNUSUAL_COMMIT_THRESHOLD = 5 | 31 | _DEFAULT_UNUSUAL_COMMIT_THRESHOLD = 5 |
| 30 | 32 | ||
| 31 | 33 | ||
| 32 | def _ConfirmManyUploads(multiple_branches=False): | 34 | def _VerifyPendingCommits(branches: List[ReviewableBranch]) -> bool: |
| 33 | if multiple_branches: | 35 | """Perform basic safety checks on the given set of branches. |
| 34 | print('ATTENTION: One or more branches has an unusually high number ' | 36 | |
| 35 | 'of commits.') | 37 | Ensures that each branch does not have a "large" number of commits |
| 36 | else: | 38 | and, if so, prompts the user to confirm they want to proceed with |
| 37 | print('ATTENTION: You are uploading an unusually high number of commits.') | 39 | the upload. |
| 38 | print('YOU PROBABLY DO NOT MEAN TO DO THIS. (Did you rebase across ' | 40 | |
| 39 | 'branches?)') | 41 | Returns true if all branches pass the safety check or the user |
| 40 | answer = input("If you are sure you intend to do this, type 'yes': ").strip() | 42 | confirmed. Returns false if the upload should be aborted. |
| 41 | return answer == "yes" | 43 | """ |
| 44 | |||
| 45 | # Determine if any branch has a suspicious number of commits. | ||
| 46 | many_commits = False | ||
| 47 | for branch in branches: | ||
| 48 | # Get the user's unusual threshold for the branch. | ||
| 49 | # | ||
| 50 | # Each branch may be configured to have a different threshold. | ||
| 51 | remote = branch.project.GetBranch(branch.name).remote | ||
| 52 | key = f'review.{remote.review}.uploadwarningthreshold' | ||
| 53 | threshold = branch.project.config.GetInt(key) | ||
| 54 | if threshold is None: | ||
| 55 | threshold = _DEFAULT_UNUSUAL_COMMIT_THRESHOLD | ||
| 56 | |||
| 57 | # If the branch has more commits than the threshold, show a warning. | ||
| 58 | if len(branch.commits) > threshold: | ||
| 59 | many_commits = True | ||
| 60 | break | ||
| 61 | |||
| 62 | # If any branch has many commits, prompt the user. | ||
| 63 | if many_commits: | ||
| 64 | if len(branches) > 1: | ||
| 65 | print('ATTENTION: One or more branches has an unusually high number ' | ||
| 66 | 'of commits.') | ||
| 67 | else: | ||
| 68 | print('ATTENTION: You are uploading an unusually high number of commits.') | ||
| 69 | print('YOU PROBABLY DO NOT MEAN TO DO THIS. (Did you rebase across ' | ||
| 70 | 'branches?)') | ||
| 71 | answer = input( | ||
| 72 | "If you are sure you intend to do this, type 'yes': ").strip() | ||
| 73 | return answer == 'yes' | ||
| 74 | |||
| 75 | return True | ||
| 42 | 76 | ||
| 43 | 77 | ||
| 44 | def _die(fmt, *args): | 78 | def _die(fmt, *args): |
| @@ -149,6 +183,13 @@ review.URL.uploadnotify: | |||
| 149 | Control e-mail notifications when uploading. | 183 | Control e-mail notifications when uploading. |
| 150 | https://gerrit-review.googlesource.com/Documentation/user-upload.html#notify | 184 | https://gerrit-review.googlesource.com/Documentation/user-upload.html#notify |
| 151 | 185 | ||
| 186 | review.URL.uploadwarningthreshold: | ||
| 187 | |||
| 188 | Repo will warn you if you are attempting to upload a large number | ||
| 189 | of commits in one or more branches. By default, the threshold | ||
| 190 | is five commits. This option allows you to override the warning | ||
| 191 | threshold to a different value. | ||
| 192 | |||
| 152 | # References | 193 | # References |
| 153 | 194 | ||
| 154 | Gerrit Code Review: https://www.gerritcodereview.com/ | 195 | Gerrit Code Review: https://www.gerritcodereview.com/ |
| @@ -261,16 +302,15 @@ Gerrit Code Review: https://www.gerritcodereview.com/ | |||
| 261 | else: | 302 | else: |
| 262 | answer = sys.stdin.readline().strip().lower() | 303 | answer = sys.stdin.readline().strip().lower() |
| 263 | answer = answer in ('y', 'yes', '1', 'true', 't') | 304 | answer = answer in ('y', 'yes', '1', 'true', 't') |
| 305 | if not answer: | ||
| 306 | _die("upload aborted by user") | ||
| 264 | 307 | ||
| 265 | if not opt.yes and answer: | 308 | # Perform some basic safety checks prior to uploading. |
| 266 | if len(branch.commits) > UNUSUAL_COMMIT_THRESHOLD: | 309 | if not opt.yes and not _VerifyPendingCommits([branch]): |
| 267 | answer = _ConfirmManyUploads() | ||
| 268 | |||
| 269 | if answer: | ||
| 270 | self._UploadAndReport(opt, [branch], people) | ||
| 271 | else: | ||
| 272 | _die("upload aborted by user") | 310 | _die("upload aborted by user") |
| 273 | 311 | ||
| 312 | self._UploadAndReport(opt, [branch], people) | ||
| 313 | |||
| 274 | def _MultipleBranches(self, opt, pending, people): | 314 | def _MultipleBranches(self, opt, pending, people): |
| 275 | projects = {} | 315 | projects = {} |
| 276 | branches = {} | 316 | branches = {} |
| @@ -337,15 +377,9 @@ Gerrit Code Review: https://www.gerritcodereview.com/ | |||
| 337 | if not todo: | 377 | if not todo: |
| 338 | _die("nothing uncommented for upload") | 378 | _die("nothing uncommented for upload") |
| 339 | 379 | ||
| 340 | if not opt.yes: | 380 | # Perform some basic safety checks prior to uploading. |
| 341 | many_commits = False | 381 | if not opt.yes and not _VerifyPendingCommits(todo): |
| 342 | for branch in todo: | 382 | _die("upload aborted by user") |
| 343 | if len(branch.commits) > UNUSUAL_COMMIT_THRESHOLD: | ||
| 344 | many_commits = True | ||
| 345 | break | ||
| 346 | if many_commits: | ||
| 347 | if not _ConfirmManyUploads(multiple_branches=True): | ||
| 348 | _die("upload aborted by user") | ||
| 349 | 383 | ||
| 350 | self._UploadAndReport(opt, todo, people) | 384 | self._UploadAndReport(opt, todo, people) |
| 351 | 385 | ||
