tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

configtest.py (5476B)


      1 #!/usr/bin/env python
      2 # This Source Code Form is subject to the terms of the Mozilla Public
      3 # License, v. 2.0. If a copy of the MPL was not distributed with this file,
      4 # You can obtain one at http://mozilla.org/MPL/2.0/.
      5 """configtest.py
      6 
      7 Verify the .json and .py files in the configs/ directory are well-formed.
      8 Further tests to verify validity would be desirable.
      9 
     10 This is also a good example script to look at to understand mozharness.
     11 """
     12 
     13 import os
     14 import pprint
     15 import sys
     16 
     17 try:
     18    import simplejson as json
     19 except ImportError:
     20    import json
     21 
     22 sys.path.insert(1, os.path.dirname(sys.path[0]))
     23 
     24 from mozharness.base.script import BaseScript
     25 
     26 
     27 # ConfigTest {{{1
     28 class ConfigTest(BaseScript):
     29    config_options = [
     30        [
     31            [
     32                "--test-file",
     33            ],
     34            {
     35                "action": "extend",
     36                "dest": "test_files",
     37                "help": "Specify which config files to test",
     38            },
     39        ]
     40    ]
     41 
     42    def __init__(self, require_config_file=False):
     43        self.config_files = []
     44        BaseScript.__init__(
     45            self,
     46            config_options=self.config_options,
     47            all_actions=[
     48                "list-config-files",
     49                "test-json-configs",
     50                "test-python-configs",
     51                "summary",
     52            ],
     53            default_actions=[
     54                "test-json-configs",
     55                "test-python-configs",
     56                "summary",
     57            ],
     58            require_config_file=require_config_file,
     59        )
     60 
     61    def query_config_files(self):
     62        """This query method, much like others, caches its runtime
     63        settings in self.VAR so we don't have to figure out config_files
     64        multiple times.
     65        """
     66        if self.config_files:
     67            return self.config_files
     68        c = self.config
     69        if "test_files" in c:
     70            self.config_files = c["test_files"]
     71            return self.config_files
     72        self.debug(
     73            "No --test-file(s) specified; defaulting to crawling the configs/ directory."
     74        )
     75        config_files = []
     76        for root, dirs, files in os.walk(os.path.join(sys.path[0], "..", "configs")):
     77            for name in files:
     78                # Hardcode =P
     79                if name.endswith(".json") or name.endswith(".py"):
     80                    if not name.startswith("test_malformed"):
     81                        config_files.append(os.path.join(root, name))
     82        self.config_files = config_files
     83        return self.config_files
     84 
     85    def list_config_files(self):
     86        """Non-default action that is mainly here to demonstrate how
     87        non-default actions work in a mozharness script.
     88        """
     89        config_files = self.query_config_files()
     90        for config_file in config_files:
     91            self.info(config_file)
     92 
     93    def test_json_configs(self):
     94        """Currently only "is this well-formed json?" """
     95        config_files = self.query_config_files()
     96        filecount = [0, 0]
     97        for config_file in config_files:
     98            if config_file.endswith(".json"):
     99                filecount[0] += 1
    100                self.info("Testing %s." % config_file)
    101                contents = self.read_from_file(config_file, verbose=False)
    102                try:
    103                    json.loads(contents)
    104                except ValueError:
    105                    self.add_summary("%s is invalid json." % config_file, level="error")
    106                    self.error(pprint.pformat(sys.exc_info()[1]))
    107                else:
    108                    self.info("Good.")
    109                    filecount[1] += 1
    110        if filecount[0]:
    111            self.add_summary(
    112                "%d of %d json config files were good." % (filecount[1], filecount[0])
    113            )
    114        else:
    115            self.add_summary("No json config files to test.")
    116 
    117    def test_python_configs(self):
    118        """Currently only "will this give me a config dictionary?" """
    119        config_files = self.query_config_files()
    120        filecount = [0, 0]
    121        for config_file in config_files:
    122            if config_file.endswith(".py"):
    123                filecount[0] += 1
    124                self.info("Testing %s." % config_file)
    125                global_dict = {}
    126                local_dict = {}
    127                try:
    128                    with open(config_file) as f:
    129                        exec(f.read(), global_dict, local_dict)
    130                except Exception:
    131                    self.add_summary(
    132                        "%s is invalid python." % config_file, level="error"
    133                    )
    134                    self.error(pprint.pformat(sys.exc_info()[1]))
    135                else:
    136                    if "config" in local_dict and isinstance(
    137                        local_dict["config"], dict
    138                    ):
    139                        self.info("Good.")
    140                        filecount[1] += 1
    141                    else:
    142                        self.add_summary(
    143                            "%s is valid python, "
    144                            "but doesn't create a config dictionary." % config_file,
    145                            level="error",
    146                        )
    147        if filecount[0]:
    148            self.add_summary(
    149                "%d of %d python config files were good." % (filecount[1], filecount[0])
    150            )
    151        else:
    152            self.add_summary("No python config files to test.")
    153 
    154 
    155 # __main__ {{{1
    156 if __name__ == "__main__":
    157    config_test = ConfigTest()
    158    config_test.run_and_exit()