Projet

Général

Profil

0001-misc-add-tenant-support-to-shell-management-command-.patch

Frédéric Péters, 25 avril 2020 15:35

Télécharger (6,46 ko)

Voir les différences:

Subject: [PATCH] misc: add tenant support to shell management command,
 deprecate old ctl (#42099)

 tests/test_ctl.py                    |  5 ++
 wcs/ctl/management/commands/shell.py | 31 ++++++++++
 wcs/ctl/shell.py                     | 88 ++--------------------------
 3 files changed, 40 insertions(+), 84 deletions(-)
 create mode 100644 wcs/ctl/management/commands/shell.py
tests/test_ctl.py
399 399
    site_zip_path = os.path.join(os.path.dirname(__file__), 'missing_file.zip')
400 400
    with pytest.raises(CommandError, match='missing file:'):
401 401
        call_command('import_site', '--domain=example.net', site_zip_path)
402

  
403

  
404
def test_shell():
405
    with pytest.raises(CommandError):
406
        call_command('shell')  # missing tenant name
wcs/ctl/management/commands/shell.py
1
# w.c.s. - web application for online forms
2
# Copyright (C) 2005-2020  Entr'ouvert
3
#
4
# This program is free software; you can redistribute it and/or modify
5
# it under the terms of the GNU General Public License as published by
6
# the Free Software Foundation; either version 2 of the License, or
7
# (at your option) any later version.
8
#
9
# This program is distributed in the hope that it will be useful,
10
# but WITHOUT ANY WARRANTY; without even the implied warranty of
11
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
# GNU General Public License for more details.
13
#
14
# You should have received a copy of the GNU General Public License
15
# along with this program; if not, see <http://www.gnu.org/licenses/>.
16

  
17
from django.core.management.commands import shell
18
from . import TenantCommand
19

  
20

  
21
class Command(shell.Command, TenantCommand):
22
    help = '''Run a shell in tenant context'''
23

  
24
    def add_arguments(self, parser):
25
        parser.add_argument('-d', '--domain', '--vhost', metavar='DOMAIN', required=True)
26
        super(Command, self).add_arguments(parser)
27

  
28
    def handle(self, *args, **options):
29
        domain = options.pop('domain')
30
        self.init_tenant_publisher(domain, register_tld_names=False)
31
        return shell.Command().handle(*args, **options)
wcs/ctl/shell.py
19 19
#
20 20
# [1]: file django/core/management/commands/shell.py
21 21

  
22
from __future__ import print_function
22
import sys
23 23

  
24
import os.path
25

  
26
from ..qommon.ctl import Command, make_option
24
from ..qommon.ctl import Command
27 25

  
28 26

  
29 27
class CmdShell(Command):
30
    '''Launch a shell and initialize a publisher on a given host'''
31

  
28
    '''(obsolete) Launch a shell and initialize a publisher on a given host'''
32 29
    name = 'shell'
33
    def __init__(self):
34
        Command.__init__(self, [
35
                make_option('--plain', action='store_true',
36
                            dest='plain', default=False) ])
37 30

  
38 31
    def execute(self, base_options, sub_options, args):
39
        from .. import publisher
40
        self.config.remove_option('main', 'error_log')
41
        publisher.WcsPublisher.configure(self.config)
42
        publisher = publisher.WcsPublisher.create_publisher(
43
                register_tld_names=False)
44
        publisher.app_dir = os.path.join(publisher.APP_DIR, args[0])
45
        if not os.path.exists(publisher.app_dir):
46
            print('Application directory %r does not exist.' % publisher.app_dir)
47
            raise SystemExit(1)
48
        publisher.set_config()
49
        try:
50
            if sub_options.plain:
51
                # Don't bother loading IPython, because the user wants plain Python.
52
                raise ImportError
53
            self.run_shell()
54
        except ImportError:
55
            import code
56
            # Set up a dictionary to serve as the environment for the shell, so
57
            # that tab completion works on objects that are imported at runtime.
58
            # See ticket 5082.
59
            imported_objects = {}
60
            try: # Try activating rlcompleter, because it's handy.
61
                import readline
62
            except ImportError:
63
                pass
64
            else:
65
                # We don't have to wrap the following import in a 'try', because
66
                # we already know 'readline' was imported successfully.
67
                import rlcompleter
68
                readline.set_completer(rlcompleter.Completer(imported_objects).complete)
69
                readline.parse_and_bind("tab:complete")
70

  
71
            # We want to honor both $PYTHONSTARTUP and .pythonrc.py, so follow system
72
            # conventions and get $PYTHONSTARTUP first then .pythonrc.py.
73
            if not sub_options.plain:
74
                for pythonrc in (os.environ.get("PYTHONSTARTUP"),
75
                                 os.path.expanduser('~/.pythonrc.py')):
76
                    if pythonrc and os.path.isfile(pythonrc):
77
                        try:
78
                            with open(pythonrc) as handle:
79
                                exec(compile(handle.read(), pythonrc, 'exec'))
80
                        except NameError:
81
                            pass
82
            code.interact(local=imported_objects)
83

  
84
    shells = [ 'ipython', 'bpython' ]
85

  
86
    def ipython(self):
87
        try:
88
            from IPython import embed
89
            embed()
90
        except ImportError:
91
            # IPython < 0.11
92
            # Explicitly pass an empty list as arguments, because otherwise
93
            # IPython would use sys.argv from this script.
94
            try:
95
                from IPython.Shell import IPShell
96
                shell = IPShell(argv=[])
97
                shell.mainloop()
98
            except ImportError:
99
                # IPython not found at all, raise ImportError
100
                raise
101

  
102
    def bpython(self):
103
        import bpython
104
        bpython.embed()
105

  
106
    def run_shell(self):
107
        for shell in self.shells:
108
            try:
109
                return getattr(self, shell)()
110
            except ImportError:
111
                pass
112
        raise ImportError
32
        print('Error: use wcs-manage shell command', file=sys.stderr)
113 33

  
114 34
CmdShell.register()
115
-