Commit 493faf16 authored by Xinan Lin's avatar Xinan Lin Committed by LUCI CQ

Add new API to update files by gerrit module

The new API here could support users to update files to remote
repo without loading the source code to the bot.

BUG=1207955
TEST=train

Change-Id: I2970171bf5b58db0db41bab5a433fc6721b7b2aa
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/tools/depot_tools/+/3042407
Commit-Queue: Xinan Lin <linxinan@chromium.org>
Reviewed-by: 's avatarMichael Moss <mmoss@chromium.org>
Reviewed-by: 's avatarAndrii Shyshkalov <tandrii@google.com>
parent 1bd4ffa2
......@@ -355,7 +355,7 @@ revision map. This doesn't overwrite the revision if it was already set.
&emsp; **@use_mirror.setter**<br>&mdash; **def [use\_mirror](/recipes/recipe_modules/gclient/api.py#116)(self, val):**
### *recipe_modules* / [gerrit](/recipes/recipe_modules/gerrit)
[DEPS](/recipes/recipe_modules/gerrit/__init__.py#1): [recipe\_engine/context][recipe_engine/recipe_modules/context], [recipe\_engine/json][recipe_engine/recipe_modules/json], [recipe\_engine/path][recipe_engine/recipe_modules/path], [recipe\_engine/python][recipe_engine/recipe_modules/python], [recipe\_engine/raw\_io][recipe_engine/recipe_modules/raw_io], [recipe\_engine/step][recipe_engine/recipe_modules/step]
[DEPS](/recipes/recipe_modules/gerrit/__init__.py#1): [recipe\_engine/context][recipe_engine/recipe_modules/context], [recipe\_engine/file][recipe_engine/recipe_modules/file], [recipe\_engine/json][recipe_engine/recipe_modules/json], [recipe\_engine/path][recipe_engine/recipe_modules/path], [recipe\_engine/python][recipe_engine/recipe_modules/python], [recipe\_engine/raw\_io][recipe_engine/recipe_modules/raw_io], [recipe\_engine/step][recipe_engine/recipe_modules/step]
#### **class [GerritApi](/recipes/recipe_modules/gerrit/api.py#7)([RecipeApi][recipe_engine/wkt/RecipeApi]):**
......@@ -445,6 +445,22 @@ Returns:
https://gerrit-review.googlesource.com/Documentation/rest-api-changes.html#list-changes
&mdash; **def [move\_changes](/recipes/recipe_modules/gerrit/api.py#229)(self, host, project, from_branch, to_branch, step_test_data=None):**
&mdash; **def [update\_files](/recipes/recipe_modules/gerrit/api.py#253)(self, host, project, branch, new_contents_by_file_path, commit_msg, submit=False):**
Update a set of files by creating and submitting a Gerrit CL.
Args:
* host: URL of Gerrit host to name.
* project: Gerrit project name, e.g. chromium/src.
* branch: The branch to land the change, e.g. main
* new_contents_by_file_path: Dict of the new contents with file path as
the key.
* commit_msg: Description to add to the CL.
* submit: Should land this CL instantly.
Returns:
Integer change number.
### *recipe_modules* / [git](/recipes/recipe_modules/git)
[DEPS](/recipes/recipe_modules/git/__init__.py#1): [recipe\_engine/buildbucket][recipe_engine/recipe_modules/buildbucket], [recipe\_engine/context][recipe_engine/recipe_modules/context], [recipe\_engine/path][recipe_engine/recipe_modules/path], [recipe\_engine/platform][recipe_engine/recipe_modules/platform], [recipe\_engine/properties][recipe_engine/recipe_modules/properties], [recipe\_engine/python][recipe_engine/recipe_modules/python], [recipe\_engine/raw\_io][recipe_engine/recipe_modules/raw_io], [recipe\_engine/runtime][recipe_engine/recipe_modules/runtime], [recipe\_engine/step][recipe_engine/recipe_modules/step]
......
DEPS = [
'recipe_engine/context',
'recipe_engine/json',
'recipe_engine/path',
'recipe_engine/python',
'recipe_engine/raw_io',
'recipe_engine/step',
'recipe_engine/context',
'recipe_engine/file',
'recipe_engine/json',
'recipe_engine/path',
'recipe_engine/python',
'recipe_engine/raw_io',
'recipe_engine/step',
]
......@@ -249,3 +249,85 @@ class GerritApi(recipe_api.RecipeApi):
args,
step_test_data=step_test_data,
).json.output
def update_files(self,
host,
project,
branch,
new_contents_by_file_path,
commit_msg,
submit=False):
"""Update a set of files by creating and submitting a Gerrit CL.
Args:
* host: URL of Gerrit host to name.
* project: Gerrit project name, e.g. chromium/src.
* branch: The branch to land the change, e.g. main
* new_contents_by_file_path: Dict of the new contents with file path as
the key.
* commit_msg: Description to add to the CL.
* submit: Should land this CL instantly.
Returns:
Integer change number.
"""
assert len(new_contents_by_file_path
) > 0, 'The dict of file paths should not be empty.'
step_result = self('create change at (%s %s)' % (project, branch), [
'createchange',
'--host',
host,
'--project',
project,
'--branch',
branch,
'--subject',
commit_msg,
'--json_file',
self.m.json.output(),
])
change = int(step_result.json.output.get('_number'))
step_result.presentation.links['change %d' %
change] = '%s/#/q/%d' % (host, change)
with self.m.step.nest('update contents in CL %d' % change):
for path, content in new_contents_by_file_path.items():
_file = self.m.path.mkstemp()
self.m.file.write_raw('store the new content for %s' % path, _file,
content)
self('edit file %s' % path, [
'changeedit',
'--host',
host,
'--change',
change,
'--path',
path,
'--file',
_file,
])
self('publish edit', [
'publishchangeedit',
'--host',
host,
'--change',
change,
])
if submit:
self('set Bot-Commit+1 for change %d' % change, [
'setbotcommit',
'--host',
host,
'--change',
change,
])
self('submit change %d' % change, [
'submitchange',
'--host',
host,
'--change',
change,
])
return change
......@@ -106,6 +106,141 @@
"@@@STEP_LOG_END@json.output@@@"
]
},
{
"cmd": [
"vpython",
"-u",
"RECIPE_REPO[depot_tools]/gerrit_client.py",
"createchange",
"--host",
"https://chromium-review.googlesource.com",
"--project",
"v8/v8",
"--branch",
"main",
"--subject",
"Dummy CL.",
"--json_file",
"/path/to/tmp/json"
],
"env": {
"PATH": "<PATH>:RECIPE_REPO[depot_tools]"
},
"infra_step": true,
"name": "gerrit create change at (v8/v8 main)",
"~followup_annotations": [
"@@@STEP_LOG_LINE@json.output@{@@@",
"@@@STEP_LOG_LINE@json.output@ \"_number\": \"91827\", @@@",
"@@@STEP_LOG_LINE@json.output@ \"branch\": \"main\", @@@",
"@@@STEP_LOG_LINE@json.output@ \"change_id\": \"Ideadbeef\", @@@",
"@@@STEP_LOG_LINE@json.output@ \"created\": \"2017-01-30 13:11:20.000000000\", @@@",
"@@@STEP_LOG_LINE@json.output@ \"has_review_started\": false, @@@",
"@@@STEP_LOG_LINE@json.output@ \"project\": \"chromium/src\", @@@",
"@@@STEP_LOG_LINE@json.output@ \"status\": \"NEW\", @@@",
"@@@STEP_LOG_LINE@json.output@ \"subject\": \"Change title\"@@@",
"@@@STEP_LOG_LINE@json.output@}@@@",
"@@@STEP_LOG_END@json.output@@@",
"@@@STEP_LINK@change 91827@https://chromium-review.googlesource.com/#/q/91827@@@"
]
},
{
"cmd": [],
"name": "update contents in CL 91827"
},
{
"cmd": [
"vpython",
"-u",
"RECIPE_MODULE[recipe_engine::file]/resources/fileutil.py",
"--json-output",
"/path/to/tmp/json",
"copy",
"99.99.99.99",
"[CLEANUP]/tmp_tmp_1"
],
"infra_step": true,
"name": "update contents in CL 91827.store the new content for chrome/VERSION",
"~followup_annotations": [
"@@@STEP_NEST_LEVEL@1@@@",
"@@@STEP_LOG_LINE@tmp_tmp_1@99.99.99.99@@@",
"@@@STEP_LOG_END@tmp_tmp_1@@@"
]
},
{
"cmd": [
"vpython",
"-u",
"RECIPE_REPO[depot_tools]/gerrit_client.py",
"changeedit",
"--host",
"https://chromium-review.googlesource.com",
"--change",
"91827",
"--path",
"chrome/VERSION",
"--file",
"[CLEANUP]/tmp_tmp_1"
],
"env": {
"PATH": "<PATH>:RECIPE_REPO[depot_tools]"
},
"infra_step": true,
"name": "update contents in CL 91827.gerrit edit file chrome/VERSION",
"~followup_annotations": [
"@@@STEP_NEST_LEVEL@1@@@"
]
},
{
"cmd": [
"vpython",
"-u",
"RECIPE_REPO[depot_tools]/gerrit_client.py",
"publishchangeedit",
"--host",
"https://chromium-review.googlesource.com",
"--change",
"91827"
],
"env": {
"PATH": "<PATH>:RECIPE_REPO[depot_tools]"
},
"infra_step": true,
"name": "gerrit publish edit"
},
{
"cmd": [
"vpython",
"-u",
"RECIPE_REPO[depot_tools]/gerrit_client.py",
"setbotcommit",
"--host",
"https://chromium-review.googlesource.com",
"--change",
"91827"
],
"env": {
"PATH": "<PATH>:RECIPE_REPO[depot_tools]"
},
"infra_step": true,
"name": "gerrit set Bot-Commit+1 for change 91827"
},
{
"cmd": [
"vpython",
"-u",
"RECIPE_REPO[depot_tools]/gerrit_client.py",
"submitchange",
"--host",
"https://chromium-review.googlesource.com",
"--change",
"91827"
],
"env": {
"PATH": "<PATH>:RECIPE_REPO[depot_tools]"
},
"infra_step": true,
"name": "gerrit submit change 91827"
},
{
"cmd": [
"vpython",
......
......@@ -23,6 +23,13 @@ def RunSteps(api):
api.gerrit.move_changes(host, project, 'master', 'main')
change = api.gerrit.update_files(host,
project,
'main', {'chrome/VERSION': '99.99.99.99'},
'Dummy CL.',
submit=True)
assert change == 91827, change
# Query for changes in Chromium's CQ.
api.gerrit.get_changes(
host,
......@@ -65,15 +72,16 @@ def RunSteps(api):
def GenTests(api):
yield (
api.test('basic') +
api.step_data('gerrit create_gerrit_branch (v8/v8 test)',
api.gerrit.make_gerrit_create_branch_response_data()) +
api.step_data('gerrit get_gerrit_branch (v8/v8 master)',
api.gerrit.make_gerrit_get_branch_response_data()) +
api.step_data('gerrit move changes',
api.gerrit.get_move_change_response_data(branch='main')) +
api.step_data('gerrit relatedchanges',
api.gerrit.get_related_changes_response_data()) +
api.step_data('gerrit changes empty query',
api.gerrit.get_empty_changes_response_data()))
yield (api.test('basic') +
api.step_data('gerrit create_gerrit_branch (v8/v8 test)',
api.gerrit.make_gerrit_create_branch_response_data()) +
api.step_data('gerrit create change at (v8/v8 main)',
api.gerrit.update_files_response_data()) +
api.step_data('gerrit get_gerrit_branch (v8/v8 master)',
api.gerrit.make_gerrit_get_branch_response_data()) +
api.step_data('gerrit move changes',
api.gerrit.get_move_change_response_data(branch='main'))
+ api.step_data('gerrit relatedchanges',
api.gerrit.get_related_changes_response_data()) +
api.step_data('gerrit changes empty query',
api.gerrit.get_empty_changes_response_data()))
......@@ -79,6 +79,11 @@ class GerritTestApi(recipe_test_api.RecipeTestApi):
def get_one_change_response_data(self, **kwargs):
return self._make_gerrit_response_json([self._gerrit_change_data(**kwargs)])
def update_files_response_data(self, **kwargs):
data = self._gerrit_change_data(**kwargs)
data.pop('revisions')
return self._make_gerrit_response_json(data)
def get_empty_changes_response_data(self):
return self._make_gerrit_response_json([])
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment