diff options
author | Wyatt Hepler <hepler@google.com> | 2020-09-25 08:14:20 -0700 |
---|---|---|
committer | Wyatt Hepler <hepler@google.com> | 2020-09-25 23:08:32 +0000 |
commit | de4bb2391a5e791b57735d1cee321265c113bd05 (patch) | |
tree | 73cd6558eab744b7b71a5b05eca7ebd434abb3e1 /pw_status/py | |
parent | 352fcbcf6131cc1aff40303554cb18ffe8ee2133 (diff) | |
download | pigweed-de4bb2391a5e791b57735d1cee321265c113bd05.tar.gz |
pw_status: Tool for migrating Status constants
update_style.py updates Status and StatusWithSize uses from Status::CODE
to Status::Code() style.
Change-Id: I81102b3e524c6a123845d2ee152310a7a2991f3d
Reviewed-on: https://pigweed-review.googlesource.com/c/pigweed/pigweed/+/19000
Reviewed-by: Keir Mierle <keir@google.com>
Diffstat (limited to 'pw_status/py')
-rwxr-xr-x | pw_status/py/pw_status/update_style.py | 108 |
1 files changed, 108 insertions, 0 deletions
diff --git a/pw_status/py/pw_status/update_style.py b/pw_status/py/pw_status/update_style.py new file mode 100755 index 000000000..d7b642ebf --- /dev/null +++ b/pw_status/py/pw_status/update_style.py @@ -0,0 +1,108 @@ +#!/usr/bin/env python3 +# Copyright 2020 The Pigweed Authors +# +# Licensed under the Apache License, Version 2.0 (the "License"); you may not +# use this file except in compliance with the License. You may obtain a copy of +# the License at +# +# https://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations under +# the License. +"""Decodes and detokenizes Base64-encoded strings in serial output. + +The output is printed or saved to a file. Input is not supported. +""" + +import argparse +from pathlib import Path +import re +import sys +from typing import Iterable + +from pw_presubmit import git_repo + +_REMAP = { + 'OK': 'Ok', + 'CANCELLED': 'Cancelled', + 'UNKNOWN': 'Unknown', + 'INVALID_ARGUMENT': 'InvalidArgument', + 'DEADLINE_EXCEEDED': 'DeadlineExceeded', + 'NOT_FOUND': 'NotFound', + 'ALREADY_EXISTS': 'AlreadyExists', + 'PERMISSION_DENIED': 'PermissionDenied', + 'UNAUTHENTICATED': 'Unauthenticated', + 'RESOURCE_EXHAUSTED': 'ResourceExhausted', + 'FAILED_PRECONDITION': 'FailedPrecondition', + 'ABORTED': 'Aborted', + 'OUT_OF_RANGE': 'OutOfRange', + 'UNIMPLEMENTED': 'Unimplemented', + 'INTERNAL': 'Internal', + 'UNAVAILABLE': 'Unavailable', + 'DATA_LOSS': 'DataLoss', +} + + +def _remap_status_with_size(match) -> str: + return f'StatusWithSize::{_REMAP[match.group(1)]}(' + + +def _remap_codes(match) -> str: + return f'{match.group(1)}::{_REMAP[match.group(2)]}()' + + +_CODES = '|'.join(_REMAP.keys()) + +_STATUS_WITH_SIZE_CTOR = re.compile( + fr'\bStatusWithSize\(Status::({_CODES}),\s*') +_STATUS = re.compile(fr'\b(Status|StatusWithSize)::({_CODES})(?!")\b') + + +def _parse_args(): + """Parses and return command line arguments.""" + + parser = argparse.ArgumentParser(description=__doc__) + parser.add_argument('paths', + nargs='*', + type=Path, + help='Paths to repositories') + return parser.parse_args() + + +def update_status(paths: Iterable[Path]) -> None: + if not paths: + paths = [Path.cwd()] + + for path in paths: + if git_repo.has_uncommitted_changes(path): + raise RuntimeError('There are pending changes in the Git repo!') + + updated = 0 + + for file in git_repo.list_files(pathspecs=('*.h', '*.cc', '*.cpp'), + repo_path=path): + orig = file.read_text() + + # Replace StatusAWithSize constructor + text = _STATUS_WITH_SIZE_CTOR.sub(_remap_status_with_size, orig) + + # Replace Status and StatusAWithSize + text = _STATUS.sub(_remap_codes, text) + + if orig != text: + updated += 1 + file.write_text(text) + + print('Updated', updated, 'files.') + print('Manually inspect the changes! This script is not perfect.') + + +def main(): + return update_status(**vars(_parse_args())) + + +if __name__ == '__main__': + sys.exit(main()) |