comparison sat_frontends/jp/cmd_profile.py @ 3028:ab2696e34d29

Python 3 port: /!\ this is a huge commit /!\ starting from this commit, SàT is needs Python 3.6+ /!\ SàT maybe be instable or some feature may not work anymore, this will improve with time This patch port backend, bridge and frontends to Python 3. Roughly this has been done this way: - 2to3 tools has been applied (with python 3.7) - all references to python2 have been replaced with python3 (notably shebangs) - fixed files not handled by 2to3 (notably the shell script) - several manual fixes - fixed issues reported by Python 3 that where not handled in Python 2 - replaced "async" with "async_" when needed (it's a reserved word from Python 3.7) - replaced zope's "implements" with @implementer decorator - temporary hack to handle data pickled in database, as str or bytes may be returned, to be checked later - fixed hash comparison for password - removed some code which is not needed anymore with Python 3 - deactivated some code which needs to be checked (notably certificate validation) - tested with jp, fixed reported issues until some basic commands worked - ported Primitivus (after porting dependencies like urwid satext) - more manual fixes
author Goffi <goffi@goffi.org>
date Tue, 13 Aug 2019 19:08:41 +0200
parents 003b8b4b56a7
children fee60f17ebac
comparison
equal deleted inserted replaced
3027:ff5bcb12ae60 3028:ab2696e34d29
36 """Dummy command to use profile_session parent, i.e. to be able to connect without doing anything else""" 36 """Dummy command to use profile_session parent, i.e. to be able to connect without doing anything else"""
37 37
38 def __init__(self, host): 38 def __init__(self, host):
39 # it's weird to have a command named "connect" with need_connect=False, but it can be handy to be able 39 # it's weird to have a command named "connect" with need_connect=False, but it can be handy to be able
40 # to launch just the session, so some paradoxes don't hurt 40 # to launch just the session, so some paradoxes don't hurt
41 super(ProfileConnect, self).__init__(host, 'connect', need_connect=False, help=(u'connect a profile')) 41 super(ProfileConnect, self).__init__(host, 'connect', need_connect=False, help=('connect a profile'))
42 42
43 def add_parser_options(self): 43 def add_parser_options(self):
44 pass 44 pass
45 45
46 46
47 class ProfileDisconnect(base.CommandBase): 47 class ProfileDisconnect(base.CommandBase):
48 48
49 def __init__(self, host): 49 def __init__(self, host):
50 super(ProfileDisconnect, self).__init__(host, 'disconnect', need_connect=False, help=(u'disconnect a profile')) 50 super(ProfileDisconnect, self).__init__(host, 'disconnect', need_connect=False, help=('disconnect a profile'))
51 self.need_loop = True 51 self.need_loop = True
52 52
53 def add_parser_options(self): 53 def add_parser_options(self):
54 pass 54 pass
55 55
57 self.host.bridge.disconnect(self.args.profile, callback=self.host.quit) 57 self.host.bridge.disconnect(self.args.profile, callback=self.host.quit)
58 58
59 59
60 class ProfileDefault(base.CommandBase): 60 class ProfileDefault(base.CommandBase):
61 def __init__(self, host): 61 def __init__(self, host):
62 super(ProfileDefault, self).__init__(host, 'default', use_profile=False, help=(u'print default profile')) 62 super(ProfileDefault, self).__init__(host, 'default', use_profile=False, help=('print default profile'))
63 63
64 def add_parser_options(self): 64 def add_parser_options(self):
65 pass 65 pass
66 66
67 def start(self): 67 def start(self):
68 print self.host.bridge.profileNameGet('@DEFAULT@') 68 print(self.host.bridge.profileNameGet('@DEFAULT@'))
69 69
70 70
71 class ProfileDelete(base.CommandBase): 71 class ProfileDelete(base.CommandBase):
72 def __init__(self, host): 72 def __init__(self, host):
73 super(ProfileDelete, self).__init__(host, 'delete', use_profile=False, help=(u'delete a profile')) 73 super(ProfileDelete, self).__init__(host, 'delete', use_profile=False, help=('delete a profile'))
74 74
75 def add_parser_options(self): 75 def add_parser_options(self):
76 self.parser.add_argument('profile', type=str, help=PROFILE_HELP) 76 self.parser.add_argument('profile', type=str, help=PROFILE_HELP)
77 self.parser.add_argument('-f', '--force', action='store_true', help=_(u'delete profile without confirmation')) 77 self.parser.add_argument('-f', '--force', action='store_true', help=_('delete profile without confirmation'))
78 78
79 def start(self): 79 def start(self):
80 if self.args.profile not in self.host.bridge.profilesListGet(): 80 if self.args.profile not in self.host.bridge.profilesListGet():
81 log.error("Profile %s doesn't exist." % self.args.profile) 81 log.error("Profile %s doesn't exist." % self.args.profile)
82 self.host.quit(1) 82 self.host.quit(1)
83 if not self.args.force: 83 if not self.args.force:
84 message = u"Are you sure to delete profile [{}] ?".format(self.args.profile) 84 message = "Are you sure to delete profile [{}] ?".format(self.args.profile)
85 res = raw_input("{} (y/N)? ".format(message)) 85 res = input("{} (y/N)? ".format(message))
86 if res not in ("y", "Y"): 86 if res not in ("y", "Y"):
87 self.disp(_(u"Profile deletion cancelled")) 87 self.disp(_("Profile deletion cancelled"))
88 self.host.quit(2) 88 self.host.quit(2)
89 89
90 self.host.bridge.asyncDeleteProfile(self.args.profile, callback=lambda __: None) 90 self.host.bridge.asyncDeleteProfile(self.args.profile, callback=lambda __: None)
91 91
92 92
93 class ProfileInfo(base.CommandBase): 93 class ProfileInfo(base.CommandBase):
94 def __init__(self, host): 94 def __init__(self, host):
95 super(ProfileInfo, self).__init__(host, 'info', need_connect=False, help=_(u'get information about a profile')) 95 super(ProfileInfo, self).__init__(host, 'info', need_connect=False, help=_('get information about a profile'))
96 self.need_loop = True 96 self.need_loop = True
97 self.to_show = [(_(u"jid"), "Connection", "JabberID"),] 97 self.to_show = [(_("jid"), "Connection", "JabberID"),]
98 self.largest = max([len(item[0]) for item in self.to_show]) 98 self.largest = max([len(item[0]) for item in self.to_show])
99 99
100 100
101 def add_parser_options(self): 101 def add_parser_options(self):
102 self.parser.add_argument('--show-password', action='store_true', help=_(u'show the XMPP password IN CLEAR TEXT')) 102 self.parser.add_argument('--show-password', action='store_true', help=_('show the XMPP password IN CLEAR TEXT'))
103 103
104 def showNextValue(self, label=None, category=None, value=None): 104 def showNextValue(self, label=None, category=None, value=None):
105 """Show next value from self.to_show and quit on last one""" 105 """Show next value from self.to_show and quit on last one"""
106 if label is not None: 106 if label is not None:
107 print((u"{label:<"+unicode(self.largest+2)+"}{value}").format(label=label+": ", value=value)) 107 print((("{label:<"+str(self.largest+2)+"}{value}").format(label=label+": ", value=value)))
108 try: 108 try:
109 label, category, name = self.to_show.pop(0) 109 label, category, name = self.to_show.pop(0)
110 except IndexError: 110 except IndexError:
111 self.host.quit() 111 self.host.quit()
112 else: 112 else:
113 self.host.bridge.asyncGetParamA(name, category, profile_key=self.host.profile, 113 self.host.bridge.asyncGetParamA(name, category, profile_key=self.host.profile,
114 callback=lambda value: self.showNextValue(label, category, value)) 114 callback=lambda value: self.showNextValue(label, category, value))
115 115
116 def start(self): 116 def start(self):
117 if self.args.show_password: 117 if self.args.show_password:
118 self.to_show.append((_(u"XMPP password"), "Connection", "Password")) 118 self.to_show.append((_("XMPP password"), "Connection", "Password"))
119 self.showNextValue() 119 self.showNextValue()
120 120
121 121
122 class ProfileList(base.CommandBase): 122 class ProfileList(base.CommandBase):
123 def __init__(self, host): 123 def __init__(self, host):
124 super(ProfileList, self).__init__(host, 'list', use_profile=False, use_output='list', help=(u'list profiles')) 124 super(ProfileList, self).__init__(host, 'list', use_profile=False, use_output='list', help=('list profiles'))
125 125
126 def add_parser_options(self): 126 def add_parser_options(self):
127 group = self.parser.add_mutually_exclusive_group() 127 group = self.parser.add_mutually_exclusive_group()
128 group.add_argument('-c', '--clients', action='store_true', help=_(u'get clients profiles only')) 128 group.add_argument('-c', '--clients', action='store_true', help=_('get clients profiles only'))
129 group.add_argument('-C', '--components', action='store_true', help=(u'get components profiles only')) 129 group.add_argument('-C', '--components', action='store_true', help=('get components profiles only'))
130 130
131 131
132 def start(self): 132 def start(self):
133 if self.args.clients: 133 if self.args.clients:
134 clients, components = True, False 134 clients, components = True, False
139 self.output(self.host.bridge.profilesListGet(clients, components)) 139 self.output(self.host.bridge.profilesListGet(clients, components))
140 140
141 141
142 class ProfileCreate(base.CommandBase): 142 class ProfileCreate(base.CommandBase):
143 def __init__(self, host): 143 def __init__(self, host):
144 super(ProfileCreate, self).__init__(host, 'create', use_profile=False, help=(u'create a new profile')) 144 super(ProfileCreate, self).__init__(host, 'create', use_profile=False, help=('create a new profile'))
145 self.need_loop = True 145 self.need_loop = True
146 146
147 def add_parser_options(self): 147 def add_parser_options(self):
148 self.parser.add_argument('profile', type=str, help=_(u'the name of the profile')) 148 self.parser.add_argument('profile', type=str, help=_('the name of the profile'))
149 self.parser.add_argument('-p', '--password', type=str, default='', help=_(u'the password of the profile')) 149 self.parser.add_argument('-p', '--password', type=str, default='', help=_('the password of the profile'))
150 self.parser.add_argument('-j', '--jid', type=str, help=_(u'the jid of the profile')) 150 self.parser.add_argument('-j', '--jid', type=str, help=_('the jid of the profile'))
151 self.parser.add_argument('-x', '--xmpp-password', type=str, help=_(u'the password of the XMPP account (use profile password if not specified)'), 151 self.parser.add_argument('-x', '--xmpp-password', type=str, help=_('the password of the XMPP account (use profile password if not specified)'),
152 metavar='PASSWORD') 152 metavar='PASSWORD')
153 self.parser.add_argument('-C', '--component', type=base.unicode_decoder, default='', 153 self.parser.add_argument('-C', '--component', default='',
154 help=_(u'set to component import name (entry point) if this is a component')) 154 help=_('set to component import name (entry point) if this is a component'))
155 155
156 def _session_started(self, __): 156 def _session_started(self, __):
157 if self.args.jid: 157 if self.args.jid:
158 self.host.bridge.setParam("JabberID", self.args.jid, "Connection", profile_key=self.args.profile) 158 self.host.bridge.setParam("JabberID", self.args.jid, "Connection", profile_key=self.args.profile)
159 xmpp_pwd = self.args.password or self.args.xmpp_password 159 xmpp_pwd = self.args.password or self.args.xmpp_password
170 log.error("Profile %s already exists." % self.args.profile) 170 log.error("Profile %s already exists." % self.args.profile)
171 self.host.quit(1) 171 self.host.quit(1)
172 self.host.bridge.profileCreate(self.args.profile, self.args.password, self.args.component, 172 self.host.bridge.profileCreate(self.args.profile, self.args.password, self.args.component,
173 callback=self._profile_created, 173 callback=self._profile_created,
174 errback=partial(self.errback, 174 errback=partial(self.errback,
175 msg=_(u"can't create profile: {}"), 175 msg=_("can't create profile: {}"),
176 exit_code=C.EXIT_BRIDGE_ERRBACK)) 176 exit_code=C.EXIT_BRIDGE_ERRBACK))
177 177
178 178
179 class ProfileModify(base.CommandBase): 179 class ProfileModify(base.CommandBase):
180 def __init__(self, host): 180 def __init__(self, host):
181 super(ProfileModify, self).__init__(host, 'modify', need_connect=False, help=_(u'modify an existing profile')) 181 super(ProfileModify, self).__init__(host, 'modify', need_connect=False, help=_('modify an existing profile'))
182 182
183 def add_parser_options(self): 183 def add_parser_options(self):
184 profile_pwd_group = self.parser.add_mutually_exclusive_group() 184 profile_pwd_group = self.parser.add_mutually_exclusive_group()
185 profile_pwd_group.add_argument('-w', '--password', type=base.unicode_decoder, help=_(u'change the password of the profile')) 185 profile_pwd_group.add_argument('-w', '--password', help=_('change the password of the profile'))
186 profile_pwd_group.add_argument('--disable-password', action='store_true', help=_(u'disable profile password (dangerous!)')) 186 profile_pwd_group.add_argument('--disable-password', action='store_true', help=_('disable profile password (dangerous!)'))
187 self.parser.add_argument('-j', '--jid', type=base.unicode_decoder, help=_(u'the jid of the profile')) 187 self.parser.add_argument('-j', '--jid', help=_('the jid of the profile'))
188 self.parser.add_argument('-x', '--xmpp-password', type=base.unicode_decoder, help=_(u'change the password of the XMPP account'), 188 self.parser.add_argument('-x', '--xmpp-password', help=_('change the password of the XMPP account'),
189 metavar='PASSWORD') 189 metavar='PASSWORD')
190 self.parser.add_argument('-D', '--default', action='store_true', help=_(u'set as default profile')) 190 self.parser.add_argument('-D', '--default', action='store_true', help=_('set as default profile'))
191 191
192 def start(self): 192 def start(self):
193 if self.args.disable_password: 193 if self.args.disable_password:
194 self.args.password = '' 194 self.args.password = ''
195 if self.args.password is not None: 195 if self.args.password is not None:
204 204
205 class Profile(base.CommandBase): 205 class Profile(base.CommandBase):
206 subcommands = (ProfileConnect, ProfileDisconnect, ProfileCreate, ProfileDefault, ProfileDelete, ProfileInfo, ProfileList, ProfileModify) 206 subcommands = (ProfileConnect, ProfileDisconnect, ProfileCreate, ProfileDefault, ProfileDelete, ProfileInfo, ProfileList, ProfileModify)
207 207
208 def __init__(self, host): 208 def __init__(self, host):
209 super(Profile, self).__init__(host, 'profile', use_profile=False, help=_(u'profile commands')) 209 super(Profile, self).__init__(host, 'profile', use_profile=False, help=_('profile commands'))