Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 7fc87415 authored by Anushree Ganjam's avatar Anushree Ganjam Committed by Android (Google) Code Review
Browse files

Merge "Remove flag_check.py, we now have flag directive check in gerrit presubmit." into main

parents 1465beca 1649e6f3
Loading
Loading
Loading
Loading
+0 −3
Original line number Diff line number Diff line
@@ -29,8 +29,5 @@ hidden_api_txt_exclude_hook = ${REPO_ROOT}/frameworks/base/tools/hiddenapi/exclu

ktlint_hook = ${REPO_ROOT}/prebuilts/ktlint/ktlint.py --no-verify-format -f ${PREUPLOAD_FILES}

# This flag check hook runs only for "packages/SystemUI" subdirectory. If you want to include this check for other subdirectories, please modify flag_check.py.
flag_hook = ${REPO_ROOT}/frameworks/base/packages/SystemUI/flag_check.py --msg=${PREUPLOAD_COMMIT_MESSAGE} --files=${PREUPLOAD_FILES} --project=${REPO_PROJECT}

[Tool Paths]
ktfmt = ${REPO_ROOT}/external/ktfmt/ktfmt.sh

packages/SystemUI/flag_check.py

deleted100755 → 0
+0 −138
Original line number Diff line number Diff line
#! /usr/bin/env python3

import sys
import re
import argparse

# partially copied from tools/repohooks/rh/hooks.py

TEST_MSG = """Commit message is missing a "Flag:" line.  It must match one of the
following case-sensitive regex:

    %s

The Flag: stanza is regex matched and should describe whether your change is behind a flag or flags.
As a CL author, you'll have a consistent place to describe the risk of the proposed change by explicitly calling out the name of the flag.
For legacy flags use EXEMPT with your flag name.

Some examples below:

Flag: NONE Repohook Update
Flag: TEST_ONLY
Flag: EXEMPT resource only update
Flag: EXEMPT bugfix
Flag: EXEMPT refactor
Flag: com.android.launcher3.enable_twoline_allapps
Flag: com.google.android.apps.nexuslauncher.zero_state_web_data_loader

Check the git history for more examples. It's a regex matched field. See go/android-flag-directive for more details on various formats.
"""

def main():
    """Check the commit message for a 'Flag:' line."""
    parser = argparse.ArgumentParser(
        description='Check the commit message for a Flag: line.')
    parser.add_argument('--msg',
                        metavar='msg',
                        type=str,
                        nargs='?',
                        default='HEAD',
                        help='commit message to process.')
    parser.add_argument(
        '--files',
        metavar='files',
        nargs='?',
        default='',
        help=
        'PREUPLOAD_FILES in repo upload to determine whether the check should run for the files.')
    parser.add_argument(
        '--project',
        metavar='project',
        type=str,
        nargs='?',
        default='',
        help=
        'REPO_PROJECT in repo upload to determine whether the check should run for this project.')

    # Parse the arguments
    args = parser.parse_args()
    desc = args.msg
    files = args.files
    project = args.project

    if not should_run_path(project, files):
        return

    field = 'Flag'
    none = 'NONE'
    testOnly = 'TEST_ONLY'
    docsOnly = 'DOCS_ONLY'
    exempt = 'EXEMPT'
    justification = '<justification>'

    # Aconfig Flag name format = <packageName>.<flagName>
    # package name - Contains only lowercase alphabets + digits + '.' - Ex: com.android.launcher3
    # For now alphabets, digits, "_", "." characters are allowed in flag name.
    # Checks if there is "one dot" between packageName and flagName and not adding stricter format check
    #common_typos_disable
    flagName = '([a-zA-Z0-9.]+)([.]+)([a-zA-Z0-9_.]+)'

    # None and Exempt needs justification
    exemptRegex = fr'{exempt}\s*[a-zA-Z]+'
    noneRegex = fr'{none}\s*[a-zA-Z]+'
    #common_typos_enable

    readableRegexMsg = '\n\tFlag: '+none+' '+justification+'\n\tFlag: <packageName>.<flagName>\n\tFlag: ' +exempt+' '+justification+'\n\tFlag: '+testOnly+'\n\tFlag: '+docsOnly

    flagRegex = fr'^{field}: .*$'
    check_flag = re.compile(flagRegex) #Flag:

    # Ignore case for flag name format.
    flagNameRegex = fr'(?i)^{field}:\s*({noneRegex}|{flagName}|{testOnly}|{docsOnly}|{exemptRegex})\s*'
    check_flagName = re.compile(flagNameRegex) #Flag: <flag name format>

    flagError = False
    foundFlag = []
    # Check for multiple "Flag:" lines and all lines should match this format
    for line in desc.splitlines():
        if check_flag.match(line):
            if not check_flagName.match(line):
                flagError = True
                break
            foundFlag.append(line)

    # Throw error if
    # 1. No "Flag:" line is found
    # 2. "Flag:" doesn't follow right format.
    if (not foundFlag) or (flagError):
        error = TEST_MSG % (readableRegexMsg)
        print(error)
        sys.exit(1)

    sys.exit(0)


def should_run_path(project, files):
    """Returns a boolean if this check should run with these paths.
    If you want to check for a particular subdirectory under the path,
    add a check here, call should_run_files and check for a specific sub dir path in should_run_files.
    """
    if not project:
        return False
    if project == 'platform/frameworks/base':
        return should_run_files(files)
    # Default case, run for all other projects which calls this script.
    return True


def should_run_files(files):
    """Returns a boolean if this check should run with these files."""
    if not files:
        return False
    if 'packages/SystemUI' in files:
        return True
    return False


if __name__ == '__main__':
    main()