1#!/usr/bin/env python 2 3# This Source Code Form is subject to the terms of the Mozilla Public 4# License, v. 2.0. If a copy of the MPL was not distributed with this file, 5# You can obtain one at http://mozilla.org/MPL/2.0/. 6 7""" 8Creates and/or modifies a Firefox profile. 9The profile can be modified by passing in addons to install or preferences to set. 10If no profile is specified, a new profile is created and the path of the 11resulting profile is printed. 12""" 13from __future__ import absolute_import, print_function 14 15import sys 16from optparse import OptionParser 17from .prefs import Preferences 18from .profile import FirefoxProfile 19from .profile import Profile 20 21__all__ = ['MozProfileCLI', 'cli'] 22 23 24class MozProfileCLI(object): 25 """The Command Line Interface for ``mozprofile``.""" 26 27 module = 'mozprofile' 28 profile_class = Profile 29 30 def __init__(self, args=sys.argv[1:], add_options=None): 31 self.parser = OptionParser(description=__doc__) 32 self.add_options(self.parser) 33 if add_options: 34 add_options(self.parser) 35 (self.options, self.args) = self.parser.parse_args(args) 36 37 def add_options(self, parser): 38 39 parser.add_option("-p", "--profile", dest="profile", 40 help="The path to the profile to operate on. " 41 "If none, creates a new profile in temp directory") 42 parser.add_option("-a", "--addon", dest="addons", 43 action="append", default=[], 44 help="Addon paths to install. Can be a filepath, " 45 "a directory containing addons, or a url") 46 parser.add_option("--addon-manifests", dest="addon_manifests", 47 action="append", 48 help="An addon manifest to install") 49 parser.add_option("--pref", dest="prefs", 50 action='append', default=[], 51 help="A preference to set. " 52 "Must be a key-value pair separated by a ':'") 53 parser.add_option("--preferences", dest="prefs_files", 54 action='append', default=[], 55 metavar="FILE", 56 help="read preferences from a JSON or INI file. " 57 "For INI, use 'file.ini:section' to specify a particular section.") 58 59 def profile_args(self): 60 """arguments to instantiate the profile class""" 61 return dict(profile=self.options.profile, 62 addons=self.options.addons, 63 addon_manifests=self.options.addon_manifests, 64 preferences=self.preferences()) 65 66 def preferences(self): 67 """profile preferences""" 68 69 # object to hold preferences 70 prefs = Preferences() 71 72 # add preferences files 73 for prefs_file in self.options.prefs_files: 74 prefs.add_file(prefs_file) 75 76 # change CLI preferences into 2-tuples 77 separator = ':' 78 cli_prefs = [] 79 for pref in self.options.prefs: 80 if separator not in pref: 81 self.parser.error("Preference must be a key-value pair separated by " 82 "a ':' (You gave: %s)" % pref) 83 cli_prefs.append(pref.split(separator, 1)) 84 85 # string preferences 86 prefs.add(cli_prefs, cast=True) 87 88 return prefs() 89 90 def profile(self, restore=False): 91 """create the profile""" 92 93 kwargs = self.profile_args() 94 kwargs['restore'] = restore 95 return self.profile_class(**kwargs) 96 97 98def cli(args=sys.argv[1:]): 99 """ Handles the command line arguments for ``mozprofile`` via ``sys.argv``""" 100 101 # add a view method for this cli method only 102 def add_options(parser): 103 parser.add_option('--view', dest='view', 104 action='store_true', default=False, 105 help="view summary of profile following invocation") 106 parser.add_option('--firefox', dest='firefox_profile', 107 action='store_true', default=False, 108 help="use FirefoxProfile defaults") 109 110 # process the command line 111 cli = MozProfileCLI(args, add_options) 112 113 if cli.args: 114 cli.parser.error("Program doesn't support positional arguments.") 115 116 if cli.options.firefox_profile: 117 cli.profile_class = FirefoxProfile 118 119 # create the profile 120 profile = cli.profile() 121 122 if cli.options.view: 123 # view the profile, if specified 124 print(profile.summary()) 125 return 126 127 # if no profile was passed in print the newly created profile 128 if not cli.options.profile: 129 print(profile.profile) 130 131 132if __name__ == '__main__': 133 cli() 134