2 # Copyright 2020 The Pigweed Authors
4 # Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 # use this file except in compliance with the License. You may obtain a copy of
8 # https://www.apache.org/licenses/LICENSE-2.0
10 # Unless required by applicable law or agreed to in writing, software
11 # distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 # WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 # License for the specific language governing permissions and limitations under
15 """Updates pw::Status usages from Status::CODE to Status::Code() style.
17 Also updates StatusWithSize.
21 from pathlib import Path
24 from typing import Iterable
26 from pw_presubmit import git_repo
30 'CANCELLED': 'Cancelled',
32 'INVALID_ARGUMENT': 'InvalidArgument',
33 'DEADLINE_EXCEEDED': 'DeadlineExceeded',
34 'NOT_FOUND': 'NotFound',
35 'ALREADY_EXISTS': 'AlreadyExists',
36 'PERMISSION_DENIED': 'PermissionDenied',
37 'UNAUTHENTICATED': 'Unauthenticated',
38 'RESOURCE_EXHAUSTED': 'ResourceExhausted',
39 'FAILED_PRECONDITION': 'FailedPrecondition',
41 'OUT_OF_RANGE': 'OutOfRange',
42 'UNIMPLEMENTED': 'Unimplemented',
43 'INTERNAL': 'Internal',
44 'UNAVAILABLE': 'Unavailable',
45 'DATA_LOSS': 'DataLoss',
49 def _remap_status_with_size(match) -> str:
50 return f'StatusWithSize::{_REMAP[match.group(1)]}('
53 def _remap_codes(match) -> str:
54 return f'{match.group(1)}::{_REMAP[match.group(2)]}()'
57 _CODES = '|'.join(_REMAP.keys())
59 _STATUS_WITH_SIZE_CTOR = re.compile(
60 fr'\bStatusWithSize\(Status::({_CODES}),\s*')
61 _STATUS = re.compile(fr'\b(Status|StatusWithSize)::({_CODES})(?!")\b')
65 """Parses and return command line arguments."""
67 parser = argparse.ArgumentParser(description=__doc__)
68 parser.add_argument('paths',
71 help='Paths to repositories')
72 return parser.parse_args()
75 def update_status(paths: Iterable[Path]) -> None:
80 if git_repo.has_uncommitted_changes(path):
81 raise RuntimeError('There are pending changes in the Git repo!')
85 for file in git_repo.list_files(pathspecs=('*.h', '*.cc', '*.cpp'),
87 orig = file.read_text()
89 # Replace StatusAWithSize constructor
90 text = _STATUS_WITH_SIZE_CTOR.sub(_remap_status_with_size, orig)
92 # Replace Status and StatusAWithSize
93 text = _STATUS.sub(_remap_codes, text)
99 print('Updated', updated, 'files.')
100 print('Manually inspect the changes! This script is not perfect.')
104 return update_status(**vars(_parse_args()))
107 if __name__ == '__main__':