|
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124 |
- import os
- from subprocess import PIPE, Popen
-
- from django.apps import apps as installed_apps
- from django.utils.crypto import get_random_string
- from django.utils.encoding import DEFAULT_LOCALE_ENCODING
-
- from .base import CommandError, CommandParser
-
-
- def popen_wrapper(args, stdout_encoding='utf-8'):
- """
- Friendly wrapper around Popen.
-
- Return stdout output, stderr output, and OS status code.
- """
- try:
- p = Popen(args, shell=False, stdout=PIPE, stderr=PIPE, close_fds=os.name != 'nt')
- except OSError as err:
- raise CommandError('Error executing %s' % args[0]) from err
- output, errors = p.communicate()
- return (
- output.decode(stdout_encoding),
- errors.decode(DEFAULT_LOCALE_ENCODING, errors='replace'),
- p.returncode
- )
-
-
- def handle_extensions(extensions):
- """
- Organize multiple extensions that are separated with commas or passed by
- using --extension/-e multiple times.
-
- For example: running 'django-admin makemessages -e js,txt -e xhtml -a'
- would result in an extension list: ['.js', '.txt', '.xhtml']
-
- >>> handle_extensions(['.html', 'html,js,py,py,py,.py', 'py,.py'])
- {'.html', '.js', '.py'}
- >>> handle_extensions(['.html, txt,.tpl'])
- {'.html', '.tpl', '.txt'}
- """
- ext_list = []
- for ext in extensions:
- ext_list.extend(ext.replace(' ', '').split(','))
- for i, ext in enumerate(ext_list):
- if not ext.startswith('.'):
- ext_list[i] = '.%s' % ext_list[i]
- return set(ext_list)
-
-
- def find_command(cmd, path=None, pathext=None):
- if path is None:
- path = os.environ.get('PATH', '').split(os.pathsep)
- if isinstance(path, str):
- path = [path]
- # check if there are funny path extensions for executables, e.g. Windows
- if pathext is None:
- pathext = os.environ.get('PATHEXT', '.COM;.EXE;.BAT;.CMD').split(os.pathsep)
- # don't use extensions if the command ends with one of them
- for ext in pathext:
- if cmd.endswith(ext):
- pathext = ['']
- break
- # check if we find the command on PATH
- for p in path:
- f = os.path.join(p, cmd)
- if os.path.isfile(f):
- return f
- for ext in pathext:
- fext = f + ext
- if os.path.isfile(fext):
- return fext
- return None
-
-
- def get_random_secret_key():
- """
- Return a 50 character random string usable as a SECRET_KEY setting value.
- """
- chars = 'abcdefghijklmnopqrstuvwxyz0123456789!@#$%^&*(-_=+)'
- return get_random_string(50, chars)
-
-
- def parse_apps_and_model_labels(labels):
- """
- Parse a list of "app_label.ModelName" or "app_label" strings into actual
- objects and return a two-element tuple:
- (set of model classes, set of app_configs).
- Raise a CommandError if some specified models or apps don't exist.
- """
- apps = set()
- models = set()
-
- for label in labels:
- if '.' in label:
- try:
- model = installed_apps.get_model(label)
- except LookupError:
- raise CommandError('Unknown model: %s' % label)
- models.add(model)
- else:
- try:
- app_config = installed_apps.get_app_config(label)
- except LookupError as e:
- raise CommandError(str(e))
- apps.add(app_config)
-
- return models, apps
-
-
- def get_command_line_option(argv, option):
- """
- Return the value of a command line option (which should include leading
- dashes, e.g. '--testrunnner') from an argument list. Return None if the
- option wasn't passed or if the argument list couldn't be parsed.
- """
- parser = CommandParser(add_help=False, allow_abbrev=False)
- parser.add_argument(option, dest='value')
- try:
- options, _ = parser.parse_known_args(argv[2:])
- except CommandError:
- return None
- else:
- return options.value
|