diff --git a/Makefile b/Makefile
index d81534bd53fe76e6244a998aa393a6a86f52ac69..c74b3a117a84b9996180961a9eba56cab4d9217e 100644
--- a/Makefile
+++ b/Makefile
@@ -51,3 +51,7 @@ autopep8:
 
 # Meta target to call the other targets.
 all: autopep8 test
+
+
+mypy:
+	mypy tests
diff --git a/tests/test_affiliation.py b/tests/test_affiliation.py
index 153e9db31f6ee74da4bb7fd3527638334404957b..1234a728919d1e1fa794a68fe33594afc513b83f 100644
--- a/tests/test_affiliation.py
+++ b/tests/test_affiliation.py
@@ -26,11 +26,19 @@
 @author: tf
 """
 import os
-import caosdb as db
-from nose.tools import nottest, assert_equal, assert_is_not_none
+import linkahead as db
+import pytest
 from pytest import raises
 
 
+def assert_equal(a, b):
+    assert a == b
+
+
+def assert_is_not_none(a):
+    assert a is not None
+
+
 def setup_module():
     f = open(file_path, "w")
     f.write("hello, world!")
@@ -218,7 +226,7 @@ def test_file_file_is_invalid():
     assert ee.msg == "Affiliation is not defined for this child-parent constellation."
 
 
-@nottest
+@pytest.mark.skip()
 def test_query_party_example():
     try:
         organisation = db.RecordType(name="Organisation").insert()
diff --git a/tests/test_data_model_leap.py b/tests/test_data_model_leap.py
index f8489c8b0bb4994517c4ba45874858fbb874874e..c7e12d1ede33b18e1397f807eb6447c5e3681f9d 100644
--- a/tests/test_data_model_leap.py
+++ b/tests/test_data_model_leap.py
@@ -25,11 +25,23 @@
 
 @author: fitschen
 """
-from nose.tools import assert_true, assert_equal, assert_is_not_none  # @UnresolvedImport
+
+
+def assert_equal(a, b):
+    assert a == b
+
+
+def assert_true(a):
+    assert a
+
+
+def assert_is_not_none(a):
+    assert a is not None
 
 
 def test_leap_datamodel():
-    import caosdb as h
+    import linkahead as h
+
     try:
         h.execute_query("FIND ENTITY WITH ID>100").delete()
     except BaseException:
diff --git a/tests/test_deletion.py b/tests/test_deletion.py
index bf449218765e49f994c69eaebff60c6673c0f867..2b795fd2907802df32ea29efe0100d444be80a47 100755
--- a/tests/test_deletion.py
+++ b/tests/test_deletion.py
@@ -26,9 +26,21 @@
 # Testcase fuer deletion
 # A. Schlemmer, 08/2014
 
-from nose.tools import with_setup, assert_false, assert_true, assert_raises, assert_equal
 
-import caosdb as h
+import linkahead as h
+import pytest
+
+
+def assert_false(a):
+    assert not a
+
+
+def assert_true(a):
+    assert a
+
+
+def assert_equal(a, b):
+    assert a == b
 
 
 def setup_module():
@@ -143,7 +155,9 @@ def test_deletion():
     assert cr2.id is not None
 
     c.extend([cr1, sr, d])
-    assert_raises(h.TransactionError, c.delete)
+    with pytest.raises(h.TransactionError):
+        c.delete()
+
     assert_true(c.has_errors())
     assert_equal(int(c.get_errors()[0].code), 12)
 
diff --git a/tests/test_file.py b/tests/test_file.py
index e8ff621e441411508452fa3bb23c3da48b0a2599..9072b2343055769c9ec9077d8b4a0787a00c1f4a 100644
--- a/tests/test_file.py
+++ b/tests/test_file.py
@@ -34,12 +34,27 @@ from sys import maxsize as maxint
 
 from lxml import etree
 from pytest import raises, mark
-from nose.tools import (assert_equal, assert_false, assert_is_not_none,
-                        assert_true)
-from caosdb import execute_query, get_config, get_connection
-from caosdb.common import models
-from caosdb.exceptions import EntityError, TransactionError
-from caosdb.utils.checkFileSystemConsistency import runCheck
+
+from linkahead import execute_query, get_config, get_connection
+from linkahead.common import models
+from linkahead.exceptions import EntityError, TransactionError
+from linkahead.utils.checkFileSystemConsistency import runCheck
+
+
+def assert_equal(a, b):
+    assert a == b
+
+
+def assert_false(a):
+    assert not a
+
+
+def assert_is_not_none(a):
+    assert a is not None
+
+
+def assert_true(a):
+    assert a
 
 
 def setup_module():
diff --git a/tests/test_list.py b/tests/test_list.py
index b2c246e092d9998e37b2c4fd12f2f18f26c4ae35..a569fd0ccdb3f1b2d09d1de62a1b4775937b2a92 100644
--- a/tests/test_list.py
+++ b/tests/test_list.py
@@ -26,13 +26,20 @@
 @author: tf
 """
 import os
-import caosdb as db
-from caosdb.exceptions import (TransactionError,
-                               UnqualifiedPropertiesError)
-from nose.tools import assert_true, assert_equal
+import linkahead as db
+from linkahead.exceptions import (TransactionError,
+                                  UnqualifiedPropertiesError)
 from pytest import raises
 
 
+def assert_equal(a, b):
+    assert a == b
+
+
+def assert_true(a):
+    assert a
+
+
 def setup_function(function):
     d = db.execute_query("FIND ENTITY WITH ID > 99")
     if len(d) > 0:
diff --git a/tests/test_manual.py b/tests/test_manual.py
index 1ba0b50dfb8d68c6c32ae82a4fe94b5e79f2d32a..0fbe09d7e8e7cc9daf74fc537b3fe1b70b3fa920 100644
--- a/tests/test_manual.py
+++ b/tests/test_manual.py
@@ -21,11 +21,24 @@
 #
 # ** end header
 #
-from caosdb import Record, RecordType, Property, Container, File, execute_query
+import pytest
+from linkahead import Record, RecordType, Property, Container, File, execute_query
 
-# @UnresolvedImport
-from nose.tools import assert_not_equal, assert_true, assert_is_not_none, assert_equal
-from nose.tools.nontrivial import nottest
+
+def assert_not_equal(a, b):
+    assert a != b
+
+
+def assert_true(a):
+    assert a
+
+
+def assert_is_not_none(a):
+    assert a is not None
+
+
+def assert_equal(a, b):
+    assert a == b
 
 
 def test_retrieve_shortcuts():
@@ -103,9 +116,9 @@ def test_references():
             pass
 
 
-@nottest
+@pytest.mark.skip()
 def test_name_overriding():
-    from caosdb import execute_query
+    from linkahead import execute_query
 
     try:
         # RecordType "Person"
diff --git a/tests/test_messages.py b/tests/test_messages.py
index 79430422d37000700454d1d70b97fbf353f733dc..ae0d157ea81ef4666b4046bc9e2a7abeb8cd09a4 100644
--- a/tests/test_messages.py
+++ b/tests/test_messages.py
@@ -26,7 +26,7 @@
 @author: Timm Fitschen
 """
 
-import caosdb as db
+import linkahead as db
 
 
 def test_messages_dict_behavior():
diff --git a/tests/test_name_properties.py b/tests/test_name_properties.py
index ad53e2050d9d7e514b72ad3f3df5be27603028cf..b2fff379bb70e297cafc2bbe8b97a85c54516bc7 100644
--- a/tests/test_name_properties.py
+++ b/tests/test_name_properties.py
@@ -26,9 +26,16 @@
 @author: tf
 """
 
-import caosdb as db
+import linkahead as db
 from pytest import raises, mark
-from nose.tools import assert_true, assert_equal
+
+
+def assert_true(a):
+    assert a
+
+
+def assert_equal(a, b):
+    assert a == b
 
 
 def setup_module():
diff --git a/tests/test_permissions.py b/tests/test_permissions.py
index fafc70db1a8fb97c63c2ba875e08f7eeb6768afa..7fffb273fc40bec37202d445c32330d2792188a5 100644
--- a/tests/test_permissions.py
+++ b/tests/test_permissions.py
@@ -27,15 +27,26 @@
 """
 
 from __future__ import absolute_import
-
-import caosdb as db
-from nose.tools import (assert_equal,
-                        assert_raises,
-                        assert_false,
-                        assert_is_none,
-                        assert_is_not_none)
 from pytest import raises, mark
 
+import linkahead as db
+
+
+def assert_equal(a, b):
+    assert a == b
+
+
+def assert_is_not_none(a):
+    assert a is not None
+
+
+def assert_false(a):
+    assert not a
+
+
+def assert_is_none(a):
+    assert a is None
+
 
 test_user = "test_user"
 test_role = "test_role"
diff --git a/tests/test_query_template.py b/tests/test_query_template.py
index b2bcab4c4d9001b02c3e426081deec99c9fc65a4..f78dc461a628654b67db4fc57554f58e1c047ecc 100644
--- a/tests/test_query_template.py
+++ b/tests/test_query_template.py
@@ -25,11 +25,22 @@
 
 @author: tf
 """
-import caosdb as db
-from nose.tools import assert_true, assert_equal, assert_is_not_none
+import linkahead as db
 from pytest import raises
 
 
+def assert_true(a):
+    assert a
+
+
+def assert_equal(a, b):
+    assert a == b
+
+
+def assert_is_not_none(a):
+    assert a is not None
+
+
 def setup_module():
     db.configure_connection()
     try:
@@ -342,12 +353,12 @@ def test_query_with_subquery_referenced_by():
             unique=True).name,
         "TestRecord")
 
-    assert_true(
+    assert_equal(
         db.execute_query(
             "FIND TestPerson WHICH IS REFERENCED BY TestPigExperiment AS A TestConductor",
             unique=True).name,
         "TestJohnDoe")
-    assert_true(
+    assert_equal(
         db.execute_query(
             "FIND TestPerson WHICH IS REFERENCED BY TestPigExperiment",
             unique=True).name,
diff --git a/tests/test_records.py b/tests/test_records.py
index 182375ba2495539025b47cb604f1acaed07adade..a9a08a4593662c95125574bccb94a7510fa071ae 100644
--- a/tests/test_records.py
+++ b/tests/test_records.py
@@ -23,11 +23,27 @@
 #
 from random import randint
 from sys import maxsize as maxint
-from nose.tools import nottest, assert_is_not_none, assert_equal, assert_true, assert_false
+import pytest
 from pytest import raises
-from caosdb import Record
-from caosdb.exceptions import CaosDBException
-import caosdb
+from linkahead import Record
+from linkahead.exceptions import CaosDBException
+import linkahead as caosdb
+
+
+def assert_is_not_none(a):
+    assert a is not None
+
+
+def assert_equal(a, b):
+    assert a == b
+
+
+def assert_true(a):
+    assert a
+
+
+def assert_false(a):
+    assert not a
 
 
 def teardown_function(function):
@@ -477,7 +493,7 @@ def test_property_doublette4():
             pass
 
 
-@nottest
+@pytest.mark.skip()
 def test_non_existent():
     rec = Record(id=466142163).retrieve(raise_exception_on_error=False)
 
diff --git a/tests/test_recordtypes.py b/tests/test_recordtypes.py
index 67c5b5a9c2c84ad0ea6095b4c3b2ac81922068a6..12ef99f9bef969a088cc45f1eed596cfafee72e6 100644
--- a/tests/test_recordtypes.py
+++ b/tests/test_recordtypes.py
@@ -22,11 +22,14 @@
 # ** end header
 #
 
-import caosdb
+import linkahead as caosdb
 
 
 def test_recordtypes():
-    from nose.tools import assert_is_not_none  # @UnresolvedImport
+
+    def assert_is_not_none(obj):
+        assert obj is not None
+
     from sys import hexversion
     from sys import maxsize as maxint  # @Reimport
     from random import randint
@@ -99,7 +102,15 @@ def test_recordtypes():
 
 
 def test_record_types_as_reference_properties():
-    from nose.tools import assert_is_not_none, assert_true, assert_equal  # @UnresolvedImport
+
+    def assert_is_not_none(obj):
+        assert obj is not None
+
+    def assert_true(obj):
+        assert obj is True
+
+    def assert_equal(obj1, obj2):
+        assert obj1 == obj2
 
     try:
         """recordtype without any property."""
diff --git a/tests/test_xmlparsing.py b/tests/test_xmlparsing.py
index 50fbbfc07d37aeda1982c7db5c2fc256826a027c..18a10dc95a4c3f6bde318b84a99ceff4b72c8fe4 100644
--- a/tests/test_xmlparsing.py
+++ b/tests/test_xmlparsing.py
@@ -31,13 +31,15 @@ import pytest
 @pytest.mark.local_server
 def test_parse_xml():
     from lxml import etree
-    from nose.tools import assert_equal  # @UnresolvedImport
-    from caosdb.common.models import File
-    from caosdb.common.models import parse_xml
-    from caosdb.common.models import Parent
-    from caosdb.common.models import Property
-    from caosdb.common.models import Message
-    from caosdb import INTEGER
+    from linkahead.common.models import File
+    from linkahead.common.models import parse_xml
+    from linkahead.common.models import Parent
+    from linkahead.common.models import Property
+    from linkahead.common.models import Message
+    from linkahead import INTEGER
+
+    def assert_equal(a, b):
+        assert a == b
 
     # define test file xml
     tmp_name = 'filename'
diff --git a/tox.ini b/tox.ini
index 9b25c55a6044d83d1d7eaec23b9e1d17d7e54396..ac89bf16138abefbea5b4cf172d6739e49f65f05 100644
--- a/tox.ini
+++ b/tox.ini
@@ -1,5 +1,5 @@
 [tox]
-envlist=py37, py38, py39, py310, py311
+envlist=py37, py38, py39, py310, py311, py312
 skip_missing_interpreters = true
 
 [pycodestyle]
@@ -12,12 +12,13 @@ max-line-length=100
 setenv = PASSWORD_STORE_DIR = {env:HOME}/.password-store
 passenv = PYCAOSDBINI
 deps=pytest
-    nose
     pytest-cov
     python-dateutil
+    setuptools
+    jsonschema
 commands_pre=pip install ../caosdb-pylib/
     python --version
-    python -c "import caosdb; print(caosdb.version.version)"
+    python -c "import linkahead; print(linkahead.version.version)"
 # Add "-x" to stop at first error.
 commands=pytest --cov=caosdb -vv {posargs}