Daniel Brötzmann pushed to branch master at gajim / gajim

Commits:

2 changed files:

Changes:

  • gajim/common/file_props.py
    ... ... @@ -17,48 +17,54 @@
    17 17
     True
    
    18 18
     """
    
    19 19
     
    
    20
    -from typing import Any  # pylint: disable=unused-import
    
    21
    -from typing import ClassVar  # pylint: disable=unused-import
    
    22
    -from typing import Dict  # pylint: disable=unused-import
    
    23
    -from typing import Tuple  # pylint: disable=unused-import
    
    20
    +from __future__ import annotations
    
    21
    +
    
    22
    +from typing import Callable
    
    23
    +from typing import Literal
    
    24
    +from typing import Optional
    
    25
    +from typing import ClassVar
    
    24 26
     
    
    25 27
     
    
    26 28
     class FilesProp:
    
    27
    -    _files_props = {}  # type: ClassVar[Dict[Tuple[str, str], Any]]
    
    29
    +    _files_props: ClassVar[dict[tuple[str, str], FileProp]] = {}
    
    28 30
     
    
    29 31
         def __init__(self):
    
    30 32
             raise Exception('this class should not be instantiated')
    
    31 33
     
    
    32 34
         @classmethod
    
    33
    -    def getNewFileProp(cls, account, sid):
    
    35
    +    def getNewFileProp(cls, account: str, sid: str) -> FileProp:
    
    34 36
             fp = FileProp(account, sid)
    
    35 37
             cls.setFileProp(fp, account, sid)
    
    36 38
             return fp
    
    37 39
     
    
    38 40
         @classmethod
    
    39
    -    def getFileProp(cls, account, sid):
    
    40
    -        return cls._files_props.get(account, sid)
    
    41
    +    def getFileProp(cls, account: str, sid: str) -> Optional[FileProp]:
    
    42
    +        return cls._files_props.get((account, sid))
    
    41 43
     
    
    42 44
         @classmethod
    
    43
    -    def getFilePropByAccount(cls, account):
    
    45
    +    def getFilePropByAccount(cls, account: str) -> list[FileProp]:
    
    44 46
             # Returns a list of file_props in one account
    
    45
    -        file_props = []
    
    47
    +        file_props: list[FileProp] = []
    
    46 48
             for account_, sid in cls._files_props:
    
    47 49
                 if account_ == account:
    
    48 50
                     file_props.append(cls._files_props[account, sid])
    
    49 51
             return file_props
    
    50 52
     
    
    51 53
         @classmethod
    
    52
    -    def getFilePropByType(cls, type_, sid):
    
    54
    +    def getFilePropByType(cls,
    
    55
    +                          type_: Literal['r', 's'],
    
    56
    +                          sid: str
    
    57
    +                          ) -> Optional[FileProp]:
    
    53 58
             # This method should be deleted. Getting fileprop by type and sid is not
    
    54 59
             # unique enough. More than one fileprop might have the same type and sid
    
    55 60
             files_prop = cls.getAllFileProp()
    
    56 61
             for fp in files_prop:
    
    57 62
                 if fp.type_ == type_ and fp.sid == sid:
    
    58 63
                     return fp
    
    64
    +        return None
    
    59 65
     
    
    60 66
         @classmethod
    
    61
    -    def getFilePropBySid(cls, sid):
    
    67
    +    def getFilePropBySid(cls, sid: str) -> Optional[FileProp]:
    
    62 68
             # This method should be deleted. It is kept to make things compatible
    
    63 69
             # This method should be replaced and instead get the file_props by
    
    64 70
             # account and sid
    
    ... ... @@ -66,99 +72,98 @@ def getFilePropBySid(cls, sid):
    66 72
             for fp in files_prop:
    
    67 73
                 if fp.sid == sid:
    
    68 74
                     return fp
    
    75
    +        return None
    
    69 76
     
    
    70 77
         @classmethod
    
    71
    -    def getFilePropByTransportSid(cls, account, sid):
    
    78
    +    def getFilePropByTransportSid(cls,
    
    79
    +                                  account: str,
    
    80
    +                                  sid: str
    
    81
    +                                  ) -> Optional[FileProp]:
    
    72 82
             files_prop = cls.getAllFileProp()
    
    73 83
             for fp in files_prop:
    
    74 84
                 if fp.account == account and fp.transport_sid == sid:
    
    75 85
                     return fp
    
    86
    +        return None
    
    76 87
     
    
    77 88
         @classmethod
    
    78
    -    def getAllFileProp(cls):
    
    89
    +    def getAllFileProp(cls) -> list[FileProp]:
    
    79 90
             return list(cls._files_props.values())
    
    80 91
     
    
    81 92
         @classmethod
    
    82
    -    def setFileProp(cls, fp, account, sid):
    
    93
    +    def setFileProp(cls, fp: FileProp, account: str, sid: str) -> None:
    
    83 94
             cls._files_props[account, sid] = fp
    
    84 95
     
    
    85 96
         @classmethod
    
    86
    -    def deleteFileProp(cls, file_prop):
    
    97
    +    def deleteFileProp(cls, file_prop: FileProp) -> None:
    
    87 98
             files_props = cls._files_props
    
    88
    -        a = s = None
    
    99
    +        acc = sid_ = None
    
    89 100
             for key in files_props:
    
    90 101
                 account, sid = key
    
    91 102
                 fp = files_props[account, sid]
    
    92 103
                 if fp is file_prop:
    
    93
    -                a = account
    
    94
    -                s = sid
    
    95
    -        if a is not None and s is not None:
    
    96
    -            del files_props[a, s]
    
    104
    +                acc = account
    
    105
    +                sid_ = sid
    
    106
    +        if acc is not None and sid_ is not None:
    
    107
    +            del files_props[acc, sid_]
    
    97 108
     
    
    98 109
     
    
    99 110
     class FileProp:
    
    100
    -
    
    101
    -    def __init__(self, account, sid):
    
    102
    -        # Do not instantiate this class directly. Call FilesProp.getNeFileProp
    
    103
    -        # instead
    
    111
    +    def __init__(self, account: str, sid: str) -> None:
    
    112
    +        # Do not instantiate this class directly!
    
    113
    +        # Call FilesProp.getNeFileProp instead
    
    104 114
             self.streamhosts = []
    
    105
    -        self.transfered_size = []
    
    106
    -        self.started = False
    
    107
    -        self.completed = False
    
    108
    -        self.paused = False
    
    109
    -        self.stalled = False
    
    110
    -        self.connected = False
    
    111
    -        self.stopped = False
    
    112
    -        self.is_a_proxy = False
    
    115
    +        self.transfered_size: list[int] = []
    
    116
    +        self.started: bool = False
    
    117
    +        self.completed: bool = False
    
    118
    +        self.paused: bool = False
    
    119
    +        self.stalled: bool = False
    
    120
    +        self.connected: bool = False
    
    121
    +        self.stopped: bool = False
    
    122
    +        self.is_a_proxy: bool = False
    
    113 123
             self.proxyhost = None
    
    114 124
             self.proxy_sender = None
    
    115 125
             self.proxy_receiver = None
    
    116 126
             self.streamhost_used = None
    
    117
    -        # method callback called in case of transfer failure
    
    118
    -        self.failure_cb = None
    
    119
    -        # method callback called when disconnecting
    
    127
    +        self.failure_cb: Optional[Callable[[str], None]] = None
    
    120 128
             self.disconnect_cb = None
    
    121
    -        self.continue_cb = None
    
    122
    -        self.sha_str = None
    
    129
    +        self.continue_cb: Optional[Callable[..., None]] = None
    
    130
    +        self.sha_str: Optional[str] = None
    
    123 131
             # transfer type: 's' for sending and 'r' for receiving
    
    124
    -        self.type_ = None
    
    125
    -        self.error = None
    
    126
    -        # Elapsed time of the file transfer
    
    127
    -        self.elapsed_time = 0
    
    128
    -        self.last_time = None
    
    129
    -        self.received_len = None
    
    130
    -        # full file path
    
    131
    -        self.file_name = None
    
    132
    -        self.name = None
    
    133
    -        self.date = None
    
    134
    -        self.desc = None
    
    135
    -        self.offset = None
    
    136
    -        self.sender = None
    
    137
    -        self.receiver = None
    
    138
    -        self.tt_account = None
    
    139
    -        self.size = None
    
    132
    +        self.type_: Optional[Literal['r', 's']] = None
    
    133
    +        self.error: Optional[int] = None
    
    134
    +        self.elapsed_time: float = 0  # Elapsed time of the file transfer
    
    135
    +        self.last_time: Optional[float] = None
    
    136
    +        self.received_len: Optional[int] = None
    
    137
    +        self.file_name: Optional[str] = None  # full file path
    
    138
    +        self.name: Optional[str] = None
    
    139
    +        self.date: Optional[str] = None
    
    140
    +        self.desc: Optional[str] = None
    
    141
    +        self.offset: Optional[int] = None
    
    142
    +        self.sender: Optional[str] = None
    
    143
    +        self.receiver: Optional[str] = None
    
    144
    +        self.tt_account: Optional[str] = None
    
    145
    +        self.size: Optional[int] = None
    
    140 146
             self._sid = sid
    
    141
    -        self.transport_sid = None
    
    147
    +        self.transport_sid: Optional[str] = None
    
    142 148
             self.account = account
    
    143
    -        self.mime_type = None
    
    144
    -        self.algo = None
    
    145
    -        self.direction = None
    
    146
    -        self.syn_id = None
    
    147
    -        self.seq = None
    
    148
    -        self.hash_ = None
    
    149
    -        self.fd = None
    
    150
    -        self.startexmpp = None
    
    149
    +        self.mime_type: Optional[str] = None
    
    150
    +        self.algo: Optional[str] = None
    
    151
    +        self.direction: Optional[Literal['<', '>']] = None
    
    152
    +        self.syn_id: Optional[str] = None
    
    153
    +        self.seq: Optional[int] = None
    
    154
    +        self.hash_: Optional[str] = None
    
    155
    +        self.fd: Optional[int] = None
    
    151 156
             # Type of the session, if it is 'jingle' or 'si'
    
    152
    -        self.session_type = None
    
    153
    -        self.request_id = None
    
    157
    +        self.session_type: Optional[str] = None
    
    158
    +        self.request_id: Optional[str] = None
    
    154 159
             self.proxyhosts = None
    
    155 160
             self.dstaddr = None
    
    156 161
     
    
    157
    -    def getsid(self):
    
    162
    +    def getsid(self) -> str:
    
    158 163
             # Getter of the property sid
    
    159 164
             return self._sid
    
    160 165
     
    
    161
    -    def setsid(self, value):
    
    166
    +    def setsid(self, value: str) -> None:
    
    162 167
             # The sid value will change
    
    163 168
             # we need to change the in _files_props key as well
    
    164 169
             del FilesProp._files_props[self.account, self._sid]
    

  • gajim/gtk/tooltips.py
    ... ... @@ -44,6 +44,7 @@
    44 44
     from gajim.common.const import PEPEventType
    
    45 45
     from gajim.common.i18n import Q_
    
    46 46
     from gajim.common.i18n import _
    
    47
    +from gajim.common.file_props import FileProp
    
    47 48
     
    
    48 49
     from .avatar import get_show_circle
    
    49 50
     from .builder import get_builder
    
    ... ... @@ -120,7 +121,7 @@ def _populate_grid(self, contact: types.GroupchatParticipant) -> None:
    120 121
             app.plugin_manager.gui_extension_point(
    
    121 122
                 'gc_tooltip_populate', self, contact, self._ui.tooltip_grid)
    
    122 123
     
    
    123
    -    def destroy(self):
    
    124
    +    def destroy(self) -> None:
    
    124 125
             self._ui.tooltip_grid.destroy()
    
    125 126
     
    
    126 127
     
    
    ... ... @@ -262,7 +263,7 @@ def _append_pep_info(self, contact: types.BareContact) -> None:
    262 263
                 self._ui.location.show()
    
    263 264
                 self._ui.location_label.show()
    
    264 265
     
    
    265
    -    def destroy(self):
    
    266
    +    def destroy(self) -> None:
    
    266 267
             self.clear_tooltip()
    
    267 268
     
    
    268 269
     
    
    ... ... @@ -279,52 +280,54 @@ def clear_tooltip(self) -> None:
    279 280
             self.sid = None
    
    280 281
             self.widget = None
    
    281 282
     
    
    282
    -    def get_tooltip(self, file_props, sid) -> tuple[bool, Gtk.Widget]:
    
    283
    +    def get_tooltip(self,
    
    284
    +                    file_prop: FileProp,
    
    285
    +                    sid: str
    
    286
    +                    ) -> tuple[bool, Gtk.Widget]:
    
    283 287
             if self.sid == sid:
    
    288
    +            assert self.widget is not None
    
    284 289
                 return True, self.widget
    
    285 290
     
    
    286
    -        self.widget = self._create_tooltip(file_props, sid)
    
    291
    +        self.widget = self._create_tooltip(file_prop, sid)
    
    287 292
             self.sid = sid
    
    288 293
             return False, self.widget
    
    289 294
     
    
    290
    -    def _create_tooltip(self, file_props, _sid) -> None:
    
    291
    -        ft_grid = Gtk.Grid.new()
    
    295
    +    def _create_tooltip(self, file_prop: FileProp, _sid: str) -> Gtk.Grid:
    
    296
    +        ft_grid = Gtk.Grid(row_spacing=6, column_spacing=12)
    
    292 297
             ft_grid.insert_column(0)
    
    293
    -        ft_grid.set_row_spacing(6)
    
    294
    -        ft_grid.set_column_spacing(12)
    
    295 298
             current_row = 0
    
    296
    -        properties = []
    
    297
    -        name = file_props.name
    
    298
    -        if file_props.type_ == 'r':
    
    299
    -            file_name = os.path.split(file_props.file_name)[1]
    
    299
    +        properties: list[tuple[str, str]] = []
    
    300
    +        name = file_prop.name
    
    301
    +        if file_prop.type_ == 'r':
    
    302
    +            file_name = os.path.split(file_prop.file_name)[1]
    
    300 303
             else:
    
    301
    -            file_name = file_props.name
    
    304
    +            file_name = file_prop.name
    
    302 305
             properties.append((_('File Name: '),
    
    303 306
                                GLib.markup_escape_text(file_name)))
    
    304 307
     
    
    305
    -        client = app.get_client(file_props.tt_account)
    
    306
    -        if file_props.type_ == 'r':
    
    308
    +        client = app.get_client(file_prop.tt_account)
    
    309
    +        if file_prop.type_ == 'r':
    
    307 310
                 type_ = Q_('?Noun:Download')
    
    308 311
                 actor = _('Sender: ')
    
    309
    -            sender = JID.from_string(file_props.sender)
    
    312
    +            sender = JID.from_string(file_prop.sender)
    
    310 313
                 name = client.get_module('Contacts').get_contact(sender.bare).name
    
    311 314
             else:
    
    312 315
                 type_ = Q_('?Noun:Upload')
    
    313 316
                 actor = _('Recipient: ')
    
    314
    -            receiver = JID.from_string(file_props.receiver)
    
    317
    +            receiver = JID.from_string(file_prop.receiver)
    
    315 318
                 name = client.get_module('Contacts').get_contact(
    
    316 319
                     receiver.bare).name
    
    317 320
             properties.append((Q_('?transfer type:Type: '), type_))
    
    318 321
             properties.append((actor, GLib.markup_escape_text(name)))
    
    319 322
     
    
    320
    -        transfered_len = file_props.received_len
    
    323
    +        transfered_len = file_prop.received_len
    
    321 324
             if not transfered_len:
    
    322 325
                 transfered_len = 0
    
    323 326
             properties.append((Q_('?transfer status:Transferred: '),
    
    324 327
                                GLib.format_size_full(transfered_len, self.units)))
    
    325
    -        status = self._get_current_status(file_props)
    
    328
    +        status = self._get_current_status(file_prop)
    
    326 329
             properties.append((Q_('?transfer status:Status: '), status))
    
    327
    -        file_desc = file_props.desc or ''
    
    330
    +        file_desc = file_prop.desc or ''
    
    328 331
             properties.append((_('Description: '),
    
    329 332
                                GLib.markup_escape_text(file_desc)))
    
    330 333
     
    
    ... ... @@ -347,19 +350,19 @@ def _create_tooltip(self, file_props, _sid) -> None:
    347 350
             return ft_grid
    
    348 351
     
    
    349 352
         @staticmethod
    
    350
    -    def _get_current_status(file_props) -> None:
    
    351
    -        if file_props.stopped:
    
    353
    +    def _get_current_status(file_prop: FileProp) -> str:
    
    354
    +        if file_prop.stopped:
    
    352 355
                 return Q_('?transfer status:Aborted')
    
    353
    -        if file_props.completed:
    
    356
    +        if file_prop.completed:
    
    354 357
                 return Q_('?transfer status:Completed')
    
    355
    -        if file_props.paused:
    
    358
    +        if file_prop.paused:
    
    356 359
                 return Q_('?transfer status:Paused')
    
    357
    -        if file_props.stalled:
    
    360
    +        if file_prop.stalled:
    
    358 361
                 # stalled is not paused. it is like 'frozen' it stopped alone
    
    359 362
                 return Q_('?transfer status:Stalled')
    
    360 363
     
    
    361
    -        if file_props.connected:
    
    362
    -            if file_props.started:
    
    364
    +        if file_prop.connected:
    
    365
    +            if file_prop.started:
    
    363 366
                     return Q_('?transfer status:Transferring')
    
    364 367
                 return Q_('?transfer status:Not started')
    
    365 368
             return Q_('?transfer status:Not started')