tor-browser

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

create_venv.py (6448B)


      1 #!/usr/bin/env python3
      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
      4 # file, You can obtain one at http://mozilla.org/MPL/2.0/.
      5 
      6 """
      7 This scripts sets up a virtualenv and installs TPS into it.
      8 It's probably best to specify a path NOT inside the repo, otherwise
      9 all the virtualenv files will show up in e.g. hg status.
     10 """
     11 
     12 import optparse
     13 import os
     14 import subprocess
     15 import sys
     16 import venv
     17 
     18 here = os.path.dirname(os.path.abspath(__file__))
     19 usage_message = """
     20 ***********************************************************************
     21 
     22 To run TPS, activate the virtualenv using:
     23    source {TARGET}/{BIN_NAME}
     24 
     25 To change your TPS config, please edit the file:
     26    {TARGET}/config.json
     27 
     28 To execute tps use:
     29    runtps --binary=/path/to/firefox
     30 
     31 See runtps --help for all options
     32 
     33 ***********************************************************************
     34 """
     35 
     36 if sys.platform == "win32":
     37    bin_name = os.path.join("Scripts", "activate.bat")
     38    python_env = os.path.join("Scripts", "python.exe")
     39 else:
     40    bin_name = os.path.join("bin", "activate")
     41    python_env = os.path.join("bin", "python")
     42 
     43 
     44 def setup_virtualenv(target):
     45    print("Creating new virtual environment:", os.path.abspath(target))
     46    # system_site_packages=True so we have access to setuptools.
     47    venv.create(target, system_site_packages=True)
     48 
     49 
     50 def update_configfile(source, target, replacements):
     51    lines = []
     52 
     53    with open(source) as config:
     54        for line in config:
     55            for source_string, target_string in replacements.items():
     56                if target_string:
     57                    line = line.replace(source_string, target_string)
     58            lines.append(line)
     59 
     60    with open(target, "w") as config:
     61        for line in lines:
     62            config.write(line)
     63 
     64 
     65 def main():
     66    parser = optparse.OptionParser("Usage: %prog [options] path_to_venv")
     67    parser.add_option(
     68        "--keep-config",
     69        dest="keep_config",
     70        action="store_true",
     71        help="Keep the existing config file.",
     72    )
     73    parser.add_option(
     74        "--password",
     75        type="string",
     76        dest="password",
     77        metavar="FX_ACCOUNT_PASSWORD",
     78        default=None,
     79        help="The Firefox Account password.",
     80    )
     81    parser.add_option(
     82        "-p",
     83        "--python",
     84        type="string",
     85        dest="python",
     86        metavar="PYTHON_BIN",
     87        default=None,
     88        help="The Python interpreter to use.",
     89    )
     90    parser.add_option(
     91        "--sync-passphrase",
     92        type="string",
     93        dest="sync_passphrase",
     94        metavar="SYNC_ACCOUNT_PASSPHRASE",
     95        default=None,
     96        help="The old Firefox Sync account passphrase.",
     97    )
     98    parser.add_option(
     99        "--sync-password",
    100        type="string",
    101        dest="sync_password",
    102        metavar="SYNC_ACCOUNT_PASSWORD",
    103        default=None,
    104        help="The old Firefox Sync account password.",
    105    )
    106    parser.add_option(
    107        "--sync-username",
    108        type="string",
    109        dest="sync_username",
    110        metavar="SYNC_ACCOUNT_USERNAME",
    111        default=None,
    112        help="The old Firefox Sync account username.",
    113    )
    114    parser.add_option(
    115        "--username",
    116        type="string",
    117        dest="username",
    118        metavar="FX_ACCOUNT_USERNAME",
    119        default=None,
    120        help="The Firefox Account username.",
    121    )
    122 
    123    (options, args) = parser.parse_args(args=None, values=None)
    124 
    125    if len(args) != 1:
    126        parser.error("Path to the environment has to be specified")
    127    target = args[0]
    128    assert target
    129 
    130    setup_virtualenv(target)
    131 
    132    # Activate tps environment
    133    activate(target)
    134 
    135    # Install TPS in environment
    136    subprocess.check_call([
    137        os.path.join(target, python_env),
    138        os.path.join(here, "setup.py"),
    139        "install",
    140    ])
    141 
    142    # Get the path to tests and extensions directory by checking check where
    143    # the tests and extensions directories are located
    144    sync_dir = os.path.abspath(os.path.join(here, "..", "..", "services", "sync"))
    145    if os.path.exists(sync_dir):
    146        testdir = os.path.join(sync_dir, "tests", "tps")
    147        extdir = os.path.join(sync_dir, "tps", "extensions")
    148    else:
    149        testdir = os.path.join(here, "tests")
    150        extdir = os.path.join(here, "extensions")
    151 
    152    if not options.keep_config:
    153        update_configfile(
    154            os.path.join(here, "config", "config.json.in"),
    155            os.path.join(target, "config.json"),
    156            replacements={
    157                "__TESTDIR__": testdir.replace("\\", "/"),
    158                "__EXTENSIONDIR__": extdir.replace("\\", "/"),
    159                "__FX_ACCOUNT_USERNAME__": options.username,
    160                "__FX_ACCOUNT_PASSWORD__": options.password,
    161                "__SYNC_ACCOUNT_USERNAME__": options.sync_username,
    162                "__SYNC_ACCOUNT_PASSWORD__": options.sync_password,
    163                "__SYNC_ACCOUNT_PASSPHRASE__": options.sync_passphrase,
    164            },
    165        )
    166 
    167        if not (options.username and options.password):
    168            print("\nFirefox Account credentials not specified.")
    169        if not (options.sync_username and options.sync_password and options.passphrase):
    170            print("\nFirefox Sync account credentials not specified.")
    171 
    172    # Print the user instructions
    173    print(usage_message.format(TARGET=target, BIN_NAME=bin_name))
    174 
    175 
    176 def activate(target):
    177    # This is a lightly modified copy of `activate_this.py`, which existed when
    178    # venv was an external package, but doesn't come with the builtin venv support.
    179    old_os_path = os.environ.get("PATH", "")
    180    os.environ["PATH"] = (
    181        os.path.dirname(os.path.abspath(__file__)) + os.pathsep + old_os_path
    182    )
    183    base = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
    184    if sys.platform == "win32":
    185        site_packages = os.path.join(base, "Lib", "site-packages")
    186    else:
    187        site_packages = os.path.join(
    188            base, "lib", "python%s" % sys.version[:3], "site-packages"
    189        )
    190    prev_sys_path = list(sys.path)
    191    import site
    192 
    193    site.addsitedir(site_packages)
    194    sys.real_prefix = sys.prefix
    195    sys.prefix = base
    196    # Move the added items to the front of the path:
    197    new_sys_path = []
    198    for item in list(sys.path):
    199        if item not in prev_sys_path:
    200            new_sys_path.append(item)
    201            sys.path.remove(item)
    202    sys.path[:0] = new_sys_path
    203 
    204 
    205 if __name__ == "__main__":
    206    main()