diff --git a/gajim/atom_window.py b/gajim/atom_window.py
index 93ca8b0c1b337d7ef20e05301bf4cf7016b30f1e..5ab727fce82ece7126fc2c4b67b95c2f5c92fa28 100644
--- a/gajim/atom_window.py
+++ b/gajim/atom_window.py
@@ -17,6 +17,9 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
+from typing import List  # pylint: disable=unused-import
+from typing import Any  # pylint: disable=unused-import
+
 from gi.repository import Gdk
 from gi.repository import GLib
 
@@ -26,7 +29,7 @@ from gajim.common import i18n
 
 class AtomWindow:
     window = None
-    entries = []
+    entries = []  # type: List[Any]
 
     @classmethod
     def newAtomEntry(cls, entry):
diff --git a/gajim/chat_control.py b/gajim/chat_control.py
index ac8da8eb23749d9660af1505d83e8685e121c3c4..044ee53d5939f18130688226310819f5fd0b036b 100644
--- a/gajim/chat_control.py
+++ b/gajim/chat_control.py
@@ -23,12 +23,21 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
+from typing import ClassVar  # pylint: disable=unused-import
+from typing import Type  # pylint: disable=unused-import
+
 import os
 import time
+
 from gi.repository import Gtk
 from gi.repository import Gio
 from gi.repository import Pango
 from gi.repository import GLib
+from nbxmpp.protocol import NS_XHTML, NS_XHTML_IM, NS_FILE, NS_MUC
+from nbxmpp.protocol import NS_JINGLE_RTP_AUDIO, NS_JINGLE_RTP_VIDEO
+from nbxmpp.protocol import NS_JINGLE_ICE_UDP, NS_JINGLE_FILE_TRANSFER_5
+from nbxmpp.protocol import NS_CHATSTATES
+
 from gajim import gtkgui_helpers
 from gajim import gui_menu_builder
 from gajim import message_control
@@ -41,14 +50,11 @@ from gajim.common import helpers
 from gajim.common import ged
 from gajim.common import i18n
 from gajim.common.contacts import GC_Contact
-from nbxmpp.protocol import NS_XHTML, NS_XHTML_IM, NS_FILE, NS_MUC
-from nbxmpp.protocol import NS_JINGLE_RTP_AUDIO, NS_JINGLE_RTP_VIDEO
-from nbxmpp.protocol import NS_JINGLE_ICE_UDP, NS_JINGLE_FILE_TRANSFER_5
-from nbxmpp.protocol import NS_CHATSTATES
 from gajim.common.connection_handlers_events import MessageOutgoingEvent
 from gajim.common.const import AvatarSize, KindConstant
 
 from gajim.command_system.implementation.hosts import ChatCommands
+from gajim.command_system.framework import CommandHost  # pylint: disable=unused-import
 from gajim.chat_control_base import ChatControlBase
 
 ################################################################################
@@ -69,7 +75,7 @@ class ChatControl(ChatControlBase):
 
     # Set a command host to bound to. Every command given through a chat will be
     # processed with this command host.
-    COMMAND_HOST = ChatCommands
+    COMMAND_HOST = ChatCommands  # type: ClassVar[Type[CommandHost]]
 
     def __init__(self, parent_win, contact, acct, session, resource=None):
         ChatControlBase.__init__(self, self.TYPE_ID, parent_win,
diff --git a/gajim/common/app.py b/gajim/common/app.py
index eefed71d0f69b5aee5943a9da0d448bc23aa08ab..b8dd434a18efafff30370532d1e538697369c8dd 100644
--- a/gajim/common/app.py
+++ b/gajim/common/app.py
@@ -24,8 +24,11 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
+from typing import Any  # pylint: disable=unused-import
 from typing import Dict  # pylint: disable=unused-import
 from typing import List  # pylint: disable=unused-import
+from typing import Optional  # pylint: disable=unused-import
+from typing import cast
 
 import os
 import sys
@@ -44,21 +47,25 @@ from gajim.common import ged as ged_module
 from gajim.common.contacts import LegacyContactsAPI
 from gajim.common.events import Events
 from gajim.common.css_config import CSSConfig
+from gajim.common.types import NetworkEventsControllerT  # pylint: disable=unused-import
+from gajim.common.types import InterfaceT  # pylint: disable=unused-import
+from gajim.common.types import LoggerT  # pylint: disable=unused-import
+from gajim.common.types import ConnectionT  # pylint: disable=unused-import
 
-interface = None  # type: gajim.interface.Interface
+interface = cast(InterfaceT, None)
 thread_interface = lambda *args: None # Interface to run a thread and then a callback
 config = c_config.Config()
 version = gajim.__version__
-connections = {} # 'account name': 'account (connection.Connection) instance'
-avatar_cache = {}
+connections = {}  # type: Dict[str, ConnectionT]
+avatar_cache = {}  # type: Dict[str, Dict[str, Any]]
 ipython_window = None
 app = None  # Gtk.Application
 
 ged = ged_module.GlobalEventsDispatcher() # Global Events Dispatcher
-nec = None  # type: gajim.common.nec.NetworkEventsController
+nec = cast(NetworkEventsControllerT, None)
 plugin_manager = None # Plugins Manager
 
-logger = None  # type: gajim.common.logger.Logger
+logger = cast(LoggerT, None)
 
 # For backwards compatibility needed
 # some plugins use that
@@ -113,7 +120,7 @@ nicks = {}  # type: Dict[str, str]
 # to something else than offline
 # can also contain account/transport_jid to block notifications for contacts
 # from this transport
-block_signed_in_notifications = {}
+block_signed_in_notifications = {}  # type: Dict[str, bool]
 
  # type of each connection (ssl, tls, tcp, ...)
 con_types = {}  # type: Dict[str, Optional[str]]
@@ -153,10 +160,10 @@ gajim_common_features = [nbxmpp.NS_BYTESTREAM, nbxmpp.NS_SI, nbxmpp.NS_FILE,
     nbxmpp.NS_EME, 'urn:xmpp:avatar:metadata+notify']
 
 # Optional features gajim supports per account
-gajim_optional_features = {}
+gajim_optional_features = {}  # type: Dict[str, List[str]]
 
 # Capabilities hash per account
-caps_hash = {}
+caps_hash = {}  # type: Dict[str, List[str]]
 
 _dependencies = {
     'PYTHON-DBUS': False,
diff --git a/gajim/common/config.py b/gajim/common/config.py
index efe1237d51c5c6100e54c9bc23410953093a20b0..e17c769c2c3da182b16bbd3910311e5842c64089 100644
--- a/gajim/common/config.py
+++ b/gajim/common/config.py
@@ -27,6 +27,11 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
+from typing import Any  # pylint: disable=unused-import
+from typing import Dict  # pylint: disable=unused-import
+from typing import List  # pylint: disable=unused-import
+from typing import Tuple  # pylint: disable=unused-import
+
 import re
 from enum import IntEnum, unique
 
@@ -287,7 +292,7 @@ class Config:
         'use_keyring': [opt_bool, True, _('If true, Gajim will use the Systems Keyring to store account passwords.')],
         'pgp_encoding': [opt_str, '', _('Sets the encoding used by python-gnupg'), True],
         'remote_commands': [opt_bool, False, _('If true, Gajim will execute XEP-0146 Commands.')],
-    }, {})
+    }, {})  # type: Tuple[Dict[str, List[Any]], Dict[Any, Any]]
 
     __options_per_key = {
         'accounts': ({
@@ -436,7 +441,7 @@ class Config:
         'plugins': ({
             'active': [opt_bool, False, _('State whether plugins should be activated on startup (this is saved on Gajim exit). This option SHOULD NOT be used to (de)activate plug-ins. Use GUI instead.')],
         }, {}),
-    }
+    }  # type: Dict[str, Tuple[Dict[str, List[Any]], Dict[Any, Any]]]
 
     statusmsg_default = {
         _('Sleeping'): ['ZZZZzzzzzZZZZZ', 'inactive', 'sleeping', '', 'sleepy', ''],
diff --git a/gajim/common/const.py b/gajim/common/const.py
index 0ce7c118b582c82292961d4120cd234588fd0bb0..471a7345922b92989214bdc130db8698ff7349be 100644
--- a/gajim/common/const.py
+++ b/gajim/common/const.py
@@ -4,10 +4,10 @@ from collections import namedtuple
 from gajim.common.i18n import _
 
 Option = namedtuple('Option', 'kind label type value name callback data desc enabledif props')
-Option.__new__.__defaults__ = (None,) * len(Option._fields)
+Option.__new__.__defaults__ = (None,) * len(Option._fields)  # type: ignore
 
 DialogButton = namedtuple('DialogButton', 'text callback action')
-DialogButton.__new__.__defaults__ = (None, None)
+DialogButton.__new__.__defaults__ = (None, None)  # type: ignore
 
 
 @unique
diff --git a/gajim/common/file_props.py b/gajim/common/file_props.py
index 9cc6a9440879c79b1fdd08de0937f0b0b0a36163..deceedfb27c78cde8d73117a21a1c595fe114f92 100644
--- a/gajim/common/file_props.py
+++ b/gajim/common/file_props.py
@@ -17,8 +17,14 @@ Exception: this class should not be instatiated
 True
 """
 
+from typing import Any  # pylint: disable=unused-import
+from typing import ClassVar  # pylint: disable=unused-import
+from typing import Dict  # pylint: disable=unused-import
+from typing import Tuple  # pylint: disable=unused-import
+
+
 class FilesProp:
-    _files_props = {}
+    _files_props = {}  # type: ClassVar[Dict[Tuple[str, str], Any]]
 
     def __init__(self):
         raise Exception('this class should not be instantiated')
diff --git a/gajim/common/jingle_content.py b/gajim/common/jingle_content.py
index 39d8f7224dcd27dd09af7d8b976b22bd665283e6..92c1f3b4db6f324802d5f2dd0abbe49f9e3c64c4 100644
--- a/gajim/common/jingle_content.py
+++ b/gajim/common/jingle_content.py
@@ -16,14 +16,19 @@
 Handles Jingle contents (XEP 0166)
 """
 
+from typing import Any  # pylint: disable=unused-import
+from typing import Dict  # pylint: disable=unused-import
+
 import os
+
+import nbxmpp
+
 from gajim.common import app
 from gajim.common import configpaths
-import nbxmpp
 from gajim.common.jingle_xtls import SELF_SIGNED_CERTIFICATE
 from gajim.common.jingle_xtls import load_cert_file
 
-contents = {}
+contents = {}  # type: Dict[str, Any]
 
 def get_jingle_content(node):
     namespace = node.getNamespace()
diff --git a/gajim/common/jingle_transport.py b/gajim/common/jingle_transport.py
index fce1767d6ed35bdb7f3bd7c86f70ba25af843531..9d326df1502cdc7e11d09fa5356990c649a8dd52 100644
--- a/gajim/common/jingle_transport.py
+++ b/gajim/common/jingle_transport.py
@@ -16,16 +16,21 @@
 Handles Jingle Transports (currently only ICE-UDP)
 """
 
+from typing import Any  # pylint: disable=unused-import
+from typing import Dict  # pylint: disable=unused-import
+
 import logging
 import socket
 from enum import IntEnum, unique
+
 import nbxmpp
+
 from gajim.common import app
 
 log = logging.getLogger('gajim.c.jingle_transport')
 
 
-transports = {}
+transports = {}  # type: Dict[str, Any]
 
 def get_jingle_transport(node):
     namespace = node.getNamespace()
diff --git a/gajim/common/passwords.py b/gajim/common/passwords.py
index b1ccd1f6fcf1968dfb9c23b4dc452d4be6f6c2e8..fda112a24485d40df631e2cb556bd9e33009f8f8 100644
--- a/gajim/common/passwords.py
+++ b/gajim/common/passwords.py
@@ -28,10 +28,12 @@ __all__ = ['get_password', 'save_password']
 
 log = logging.getLogger('gajim.password')
 
-keyring = None
+
 try:
     import keyring
+    KEYRING_AVAILABLE = True
 except ImportError:
+    KEYRING_AVAILABLE = False
     log.debug('python-keyring missing, falling back to plaintext storage')
 
 
@@ -83,7 +85,7 @@ class PasswordStorageManager(PasswordStorage):
         """
         # TODO: handle disappearing backends
 
-        if app.config.get('use_keyring') and keyring:
+        if app.config.get('use_keyring') and KEYRING_AVAILABLE:
             self.secret = SecretPasswordStorage()
 
     def get_password(self, account_name):
diff --git a/gajim/common/pep.py b/gajim/common/pep.py
index fe9533226254d984c3a4fac02effecb1bf8a6504..f936fe3e9741afbaf76e4e603fdb156164857f5d 100644
--- a/gajim/common/pep.py
+++ b/gajim/common/pep.py
@@ -19,11 +19,14 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
+from typing import Any  # pylint: disable=unused-import
+from typing import List  # pylint: disable=unused-import
+
 import logging
-log = logging.getLogger('gajim.c.pep')
 
 from gajim.common import app
 
+log = logging.getLogger('gajim.c.pep')
 
 class AbstractPEP:
 
@@ -75,4 +78,4 @@ class AbstractPEP:
         pass
 
 
-SUPPORTED_PERSONAL_USER_EVENTS = []
+SUPPORTED_PERSONAL_USER_EVENTS = []  # type: List[Any]
diff --git a/gajim/common/rst_xhtml_generator.py b/gajim/common/rst_xhtml_generator.py
index d0fc86df4745d4c9104693d8894ac110d96868ca..e198aea222a11231bb087c4fdb784e96e99bb28a 100644
--- a/gajim/common/rst_xhtml_generator.py
+++ b/gajim/common/rst_xhtml_generator.py
@@ -18,11 +18,11 @@
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
 try:
-    from docutils import io
+    from docutils import io  # type: ignore
     from docutils.core import Publisher
     from docutils.parsers.rst import roles
-    from docutils import nodes, utils
-    from docutils.parsers.rst.roles import set_classes
+    from docutils import nodes, utils  # type: ignore
+    from docutils.parsers.rst.roles import set_classes  # type: ignore
 except ImportError:
     print("Requires docutils 0.4 for set_classes to be available")
     def create_xhtml(text):
diff --git a/gajim/common/socks5.py b/gajim/common/socks5.py
index bdc78a52826d1fd016e6534db140dda7e7fefc11..a37ce0e27164d7d8857924894a8b8d5b6aa6338b 100644
--- a/gajim/common/socks5.py
+++ b/gajim/common/socks5.py
@@ -799,7 +799,7 @@ class Socks5:
                 return self.file_props.received_len
         return None
 
-    def disconnect(self):
+    def disconnect(self, *args, **kwargs):
         """
         Close open descriptors and remover socket descr. from idleque
         """
diff --git a/gajim/common/types.py b/gajim/common/types.py
index 7d467add30842f4e800cc97a972428dbd017ab5a..5f9b6a6859e413359cd5b0114ad6ef3985943c47 100644
--- a/gajim/common/types.py
+++ b/gajim/common/types.py
@@ -33,6 +33,15 @@ if TYPE_CHECKING:
     from gajim.common.contacts import Contact
     from gajim.common.contacts import GC_Contact
     from gajim.common.nec import NetworkEvent
+    from gajim.common.nec import NetworkEventsController
+    from gajim.common.logger import Logger
+
+    from gajim.gui_interface import Interface
+
+
+NetworkEventsControllerT = Union['NetworkEventsController']
+InterfaceT = Union['Interface']
+LoggerT = Union['Logger']
 
 ConnectionT = Union['Connection', 'ConnectionZeroconf']
 ContactT = Union['Contact', 'GC_Contact']
diff --git a/gajim/common/zeroconf/client_zeroconf.py b/gajim/common/zeroconf/client_zeroconf.py
index 83e14c42d7cf1deead898e34674d8c5d8f19370d..6cc52a1a9e34e09d53d8c52b0377e9805964cafc 100644
--- a/gajim/common/zeroconf/client_zeroconf.py
+++ b/gajim/common/zeroconf/client_zeroconf.py
@@ -19,6 +19,7 @@ from gajim.common import app
 import nbxmpp
 from nbxmpp.idlequeue import IdleObject
 from nbxmpp import dispatcher_nb, simplexml
+from nbxmpp.plugin import PlugIn
 from nbxmpp.plugin import *
 from nbxmpp.transports_nb import DATA_RECEIVED, DATA_SENT, DATA_ERROR
 from gajim.common.zeroconf import zeroconf
diff --git a/gajim/common/zeroconf/zeroconf.py b/gajim/common/zeroconf/zeroconf.py
index ad479cd2650eb21add304d7cc9c0e4d53d517dc5..37d4e2fba24df3666e4b08f1b212091c8603a09d 100644
--- a/gajim/common/zeroconf/zeroconf.py
+++ b/gajim/common/zeroconf/zeroconf.py
@@ -14,8 +14,11 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim.  If not, see <http://www.gnu.org/licenses/>.
 
+from typing import Any  # pylint: disable=unused-import
+
 from enum import IntEnum, unique
 
+
 @unique
 class Constant(IntEnum):
     NAME = 0
@@ -54,7 +57,7 @@ def test_zeroconf():
 
 if test_avahi():
     from gajim.common.zeroconf import zeroconf_avahi
-    Zeroconf = zeroconf_avahi.Zeroconf
+    Zeroconf = zeroconf_avahi.Zeroconf  # type: Any
 elif test_bonjour():
     from gajim.common.zeroconf import zeroconf_bonjour
     Zeroconf = zeroconf_bonjour.Zeroconf
diff --git a/gajim/dialogs.py b/gajim/dialogs.py
index 1dc8977e599b4e1dfe43e4b7f798cff9677346b7..3c72b82a583f13594954b6c7a06aefe1c3756a1a 100644
--- a/gajim/dialogs.py
+++ b/gajim/dialogs.py
@@ -25,18 +25,22 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
-from gi.repository import Gtk
-from gi.repository import Gdk
-from gi.repository import GLib
+from typing import Dict  # pylint: disable=unused-import
+from typing import List  # pylint: disable=unused-import
+from typing import Tuple  # pylint: disable=unused-import
 
 import os
 import logging
+from random import randrange
+
+from gi.repository import Gtk
+from gi.repository import Gdk
+from gi.repository import GLib
 
 from gajim import gtkgui_helpers
 from gajim import vcard
 from gajim import dataforms_widget
 
-from random import randrange
 from gajim.common import ged
 from gajim.common.i18n import _
 from gajim.common.const import ACTIVITIES
@@ -1363,7 +1367,7 @@ class ProgressDialog:
 
 class TransformChatToMUC:
     # Keep a reference on windows so garbage collector don't restroy them
-    instances = []
+    instances = []  # type: List[TransformChatToMUC]
     def __init__(self, account, jids, preselected=None):
         """
         This window is used to trasform a one-to-one chat to a MUC. We do 2
@@ -1584,7 +1588,7 @@ class ResourceConflictDialog(TimeoutDialog, InputDialog):
 
 
 class VoIPCallReceivedDialog:
-    instances = {}
+    instances = {}   # type: Dict[Tuple[str, str], VoIPCallReceivedDialog]
     def __init__(self, account, contact_jid, sid, content_types):
         self.instances[(contact_jid, sid)] = self
         self.account = account
diff --git a/gajim/gtk/single_message.py b/gajim/gtk/single_message.py
index de579817727957776291bdc67fc788b6cbe81bbe..c48d5a0f6e0d75408a8329eb540772b1b9d15dff 100644
--- a/gajim/gtk/single_message.py
+++ b/gajim/gtk/single_message.py
@@ -12,6 +12,8 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
+from typing import List  # pylint: disable=unused-import
+
 from gi.repository import Gdk
 from gi.repository import GLib
 
@@ -40,7 +42,7 @@ class SingleMessageWindow:
     action argument which can be 'send' or 'receive'
     """
     # Keep a reference on windows so garbage collector don't restroy them
-    instances = []
+    instances = []  # type: List[SingleMessageWindow]
     def __init__(self, account, to='', action='', from_whom='', subject='',
             message='', resource='', session=None, form_node=None):
         self.instances.append(self)
diff --git a/gajim/gtkgui_helpers.py b/gajim/gtkgui_helpers.py
index 325eb1cf01a77f04fa2858cc8593a292fa91e037..f79285803caecb8deed88a94eb56f8c492908406 100644
--- a/gajim/gtkgui_helpers.py
+++ b/gajim/gtkgui_helpers.py
@@ -23,32 +23,34 @@
 # You should have received a copy of the GNU General Public License
 # along with Gajim. If not, see <http://www.gnu.org/licenses/>.
 
+import cairo
+import os
+import sys
+import math
+import logging
+from io import BytesIO
+import xml.etree.ElementTree as ET
 import xml.sax.saxutils
+from xml.sax import ContentHandler  # type: ignore
+
 from gi.repository import Gtk
 from gi.repository import Gdk
 from gi.repository import GdkPixbuf
 from gi.repository import GLib
 from gi.repository import Pango
-import cairo
-import os
-import sys
-import math
-import xml.etree.ElementTree as ET
 
 try:
     from PIL import Image
 except Exception:
     pass
-from io import BytesIO
-
-import logging
-log = logging.getLogger('gajim.gtkgui_helpers')
 
 from gajim.common import i18n
 from gajim.common import app
 from gajim.common import configpaths
 from gajim.common.const import PEPEventType, ACTIVITIES, MOODS
 
+log = logging.getLogger('gajim.gtkgui_helpers')
+
 gtk_icon_theme = Gtk.IconTheme.get_default()
 gtk_icon_theme.append_search_path(configpaths.get('ICONS'))
 
@@ -234,9 +236,9 @@ def scroll_to_end(widget):
     return False
 
 
-class ServersXMLHandler(xml.sax.ContentHandler):
+class ServersXMLHandler(ContentHandler):
     def __init__(self):
-        xml.sax.ContentHandler.__init__(self)
+        ContentHandler.__init__(self)
         self.servers = []
 
     def startElement(self, name, attributes):
diff --git a/gajim/roster_window.py b/gajim/roster_window.py
index 488f97222fbcd5b201ca547922854e2d73a9d20d..29fb4839c5cb60e8e14505cd140462783fa8cc6e 100644
--- a/gajim/roster_window.py
+++ b/gajim/roster_window.py
@@ -5643,7 +5643,7 @@ class RosterWindow:
 ###
 ################################################################################
 
-    def __init__(self, application: Gtk.Application):
+    def __init__(self, application):
         self.application = application
         self.filtering = False
         self.starting = False
diff --git a/mypy.ini b/mypy.ini
index d8b13d77798c85d239e42b2ea3e60d988ff616dc..7a8ff5766bdd0ff93040c5f65e9d34af0c67323f 100644
--- a/mypy.ini
+++ b/mypy.ini
@@ -1,5 +1,6 @@
 [mypy]
 python_version = 3.5
+warn_unused_configs = True
 disallow_incomplete_defs = True
 
 [mypy-nbxmpp.*]
@@ -61,3 +62,12 @@ ignore_missing_imports = True
 
 [mypy-docutils.*]
 ignore_missing_imports = True
+
+[mypy-IPython.*]
+ignore_missing_imports = True
+
+[mypy-traitlets.*]
+ignore_missing_imports = True
+
+[mypy-pygments.*]
+ignore_missing_imports = True
\ No newline at end of file