diff --git a/CHANGELOG.md b/CHANGELOG.md
index 1c8a144dc939f3a58d1f9346929ad5e32d62d213..a407cd214ba120392df9330811984abb09df7b2d 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -17,6 +17,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
 
 ### Changed ###
 
+* Updated error-handling tutorial in documentation to reflect the new
+  error classes
+
 ### Deprecated ###
 
 ### Removed ###
@@ -28,20 +31,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
 
 ## [0.5.1] - 2021-02-12 ##
 
-### Added ###
-
-### Changed ###
-
-### Deprecated ###
-
-### Removed ###
-
 ### Fixed ###
 
 * #43 - Error with `execute_query` when server doesn't support query caching.
 
-### Security ###
-
 ## [0.5.0] - 2021-02-11 ##
 
 ### Added ###
@@ -74,18 +67,12 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
   `QueryNotUniqueError` if no or more than one possible candidate is
   found, respectively.
 
-### Deprecated ###
-
 ### Removed ###
 
 * Dynamic exception type `EntityMultiError`. 
 * `get_something` functions from all error object in `exceptions.py`
 * `AmbiguityException`
 
-### Fixed ###
-
-### Security ###
-
 ## [0.4.1] - 2021-02-10 ##
 
 ### Added ###
@@ -95,18 +82,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
   entity.
 * Automated documentation builds: `make doc`
 
-### Changed ###
-
-### Deprecated ###
-
-### Removed ###
-
 ### Fixed ###
 
 * deepcopy of `_Messages` objects
 
-### Security ###
-
 ## [0.4.0] - 2020-07-17##
 
 ### Added ###
diff --git a/README_SETUP.md b/README_SETUP.md
index 9deadefb27e2a93377bafc59242eacc26057b414..30e53ac1c65763fb52b711a215f682c01d2e570e 100644
--- a/README_SETUP.md
+++ b/README_SETUP.md
@@ -84,7 +84,7 @@ Typically, you need to change at least the `url` and `username` fields as requir
 you do not know what to put there, but for the demo instances https://demo.indiscale.com, `username=admin`
 and `password=caosdb` should work).
 
-### Authentication ##
+### Authentication ###
 
 The default configuration (that your are asked for your password when ever a connection is created
 can be changed by setting `password_method`:
@@ -109,7 +109,7 @@ The following illustrates the recommended options:
 #password_method=keyring
 ```
 
-### SSL Certificate ##
+### SSL Certificate ###
 In some cases (especially if you are testing CaosDB) you might need to supply 
 an SSL certificate to allow SSL encryption.
 
@@ -118,7 +118,7 @@ an SSL certificate to allow SSL encryption.
 cacert=/path/to/caosdb.ca.pem
 ```
 
-### Further Settings ##
+### Further Settings ###
 As mentioned above, a complete list of options can be found in the 
 [pycaosdb.ini file](https://gitlab.com/caosdb/caosdb-pylib/-/blob/main/examples/pycaosdb.ini) in 
 the examples folder of the source code.
@@ -138,7 +138,7 @@ Out[2]: Connection to CaosDB with 501 Records.
 Note: This setup will ask you for your password whenever a new connection is created. If you do not
 like this, check out the "Authentication" section in the [configuration documentation](configuration.md).
 
-Now would be a good time to continue with the [tutorials](tutorials.html).
+Now would be a good time to continue with the [tutorials](tutorials/index).
 
 ## Run Unit Tests
 tox
@@ -147,15 +147,15 @@ tox
 
 autopep8 -i -r ./
 
-## Documentation #
+## Documentation ##
 
 Build documentation in `build/` with `make doc`.
 
-### Requirements ##
+### Requirements ###
 
 - `sphinx`
 - `sphinx-autoapi`
 - `recommonmark`
 
-### Troubleshooting ##
+### Troubleshooting ###
 If the client is to be executed directly from the `/src` folder, an initial `.\setup.py install --user` must be called.
diff --git a/examples/set_permissions.py b/examples/set_permissions.py
index 3d9012959fb036705ef9b086af35489238360c14..8162b11bfefb41b1bcdbc74b8e314f99a61d1a4e 100755
--- a/examples/set_permissions.py
+++ b/examples/set_permissions.py
@@ -25,8 +25,8 @@
 
 As a result, only a specific user or group may access it.
 
-This script assumes that the user specified in the 
-pycaosdb.ini configuration can create new entities.
+This script assumes that the user specified in the pycaosdb.ini
+configuration can create new entities.
 
 """
 
@@ -206,7 +206,8 @@ def create_test_entities():
     After calling this function, there will be a RecordType "Human Food" with the corresponding Records
     "Bread", "Tomatoes", and "Twinkies" inserted in the database.
     """
-    rt = db.RecordType(name="Human Food", description="Food that can be eaten only by humans").insert()
+    rt = db.RecordType(
+        name="Human Food", description="Food that can be eaten only by humans").insert()
     food = ("Bread", "Tomatoes", "Twinkies")
 
     cont = db.Container()
diff --git a/src/doc/Makefile b/src/doc/Makefile
index 9841c6618a33ef3148389650d15130e25ec25247..8b533626f6665fa2a3491ea5d319b58740c05299 100644
--- a/src/doc/Makefile
+++ b/src/doc/Makefile
@@ -45,4 +45,4 @@ doc-help:
 	@$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)
 
 apidoc:
-	@$(SPHINXAPIDOC) -o _apidoc $(PY_BASEDIR)
+	@$(SPHINXAPIDOC) -o _apidoc $(PY_BASEDIR) --separate
diff --git a/src/doc/conf.py b/src/doc/conf.py
index 8a3f5b6c273a3b770e853d255d56a80f5b8b12e2..a2bb79dcf0e8730e46c00603ea5380666f2f9b85 100644
--- a/src/doc/conf.py
+++ b/src/doc/conf.py
@@ -27,9 +27,9 @@ copyright = '2020, IndiScale GmbH'
 author = 'Daniel Hornung'
 
 # The short X.Y version
-version = '0.4.0'
+version = '0.5.1'
 # The full version, including alpha/beta/rc tags
-release = '0.4.0-rc'
+release = '0.5.1-rc'
 
 
 # -- General configuration ---------------------------------------------------
@@ -43,6 +43,7 @@ release = '0.4.0-rc'
 # ones.
 extensions = [
     'sphinx.ext.autodoc',
+    'sphinx.ext.autosectionlabel',
     'sphinx.ext.intersphinx',
     'sphinx.ext.napoleon',     # For Google style docstrings
     "recommonmark",            # For markdown files.
diff --git a/src/doc/index.rst b/src/doc/index.rst
index 76a2f88f6d31dd9b5f17995b6d54ccc63eb33631..bd29c6c56acf5c173e94ae6471a6aeba56ea4b93 100644
--- a/src/doc/index.rst
+++ b/src/doc/index.rst
@@ -12,12 +12,12 @@ Welcome to PyCaosDB's documentation!
    Concepts <concepts>
    Configuration <configuration>
    Administration <administration>
-   API documentation<_apidoc/modules>
+   API documentation<_apidoc/caosdb>
 
 This is the documentation for the Python client library for CaosDB, ``PyCaosDB``.
 
-This documentation helps you to :doc:`get started<getting_started>`, explains the most important
-:doc:`concepts<concepts>` and offers a range of :doc:`tutorials<tutorials>`.
+This documentation helps you to :doc:`get started<README_SETUP>`, explains the most important
+:doc:`concepts<concepts>` and offers a range of :doc:`tutorials<tutorials/index>`.
 
 
 Indices and tables
diff --git a/src/doc/tutorials/errors.rst b/src/doc/tutorials/errors.rst
index ba386dc31baad1021f01d53b2b12a2623d8278ad..37c53c9b527a0435f9f24ae6c6e71687e73eb963 100644
--- a/src/doc/tutorials/errors.rst
+++ b/src/doc/tutorials/errors.rst
@@ -1,53 +1,176 @@
 
 Error Handling
---------------
+==============
 
-HeartDBException
-~~~~~~~~~~~~~~~~
+In case of erroneous transactions, connection problems and a lot of
+other cases, PyCaosDB may raise specific errors in order to pinpoint
+the problem as precisely as possible. Some of these errors a
+representations of errors in the CaosDB server, others stem from
+problems that occurred on the client side.
+
+The errors and exceptions are ordered hierarchically form the most
+general exceptions to specific transaction or connection problems. The
+most important error types and the hierarchy will be explained in the
+following. For more information on specific error types, see also the
+:doc:`source code<../_apidoc/caosdb.exceptions>`.
+
+.. note::
+
+   Starting from PyCaosDB 0.5, the error handling has changed
+   significantly. New error classes have been introduced and the
+   behavior of ``TransactionError`` and ``EntityError`` has been
+   re-worked. In the following, only the "new" errors are
+   discussed. Please refer to the documentation of PyCaosDB 0.4.1 and
+   earlier for the old error handling.
+
+CaosDBException
+----------------
+
+``CaosDBException`` is the most generic exception and all other error classes inherit
+from this one. Because of its generality, it doesn't tell you much
+except that some component of PyCaosDB raised an exception. If you
+want to catch all possible CaosDB errors, this is the class to use.
 
 TransactionError
-~~~~~~~~~~~~~~~~
+----------------
 
 Every transaction (calling ``insert``, ``update``, ``retrieve``, or
 ``delete`` on a container or an entity) may finish with errors. They
 indicate, for instance, that an entity does not exist or that you need
 to specify a data type for your property and much more. If and only if
 one or more errors occur during a transaction a ``TransactionError``
-will be raised by the transaction method. The ``TransactionError`` class
-is a container for all errors which occur during a transaction. It can
-help you to find the crucial problems with your transaction by two
-important methods: \* ``get_errors()`` which returns a list of instances
-of ``EntityError``. \* ``get_entities()`` which returns a list of
-entities in the transaction container which are erroneous.
-
-Additionally, ``print(transaction_error`` prints a tree-like
+will be raised by the transaction method. The ``TransactionError``
+class is a container for all errors which occur during a
+transaction. It usually contains one or more :ref:`entity
+errors<EntityError>` which you can inspect in order to learn why the
+transaction failed. For this inspection, there are some helpful
+attributes and methods provided by the ``TransactionError``:
+
+* ``entities``: a list of all entities that directly caused at least one error
+  in this transaction.
+
+* ``errors``: a list of all ``EntityError`` objects that directly caused the
+  transaction to fail.
+
+* ``all_entities``, ``all_errors``: sets of all entities and errors
+  that, directly or indirectly, caused either this ``TransactionError`` or any of the
+  ``EntityError`` objects it contains.
+
+* ``has_error(error_t)``: Check whether an error of type ``error_t``
+  occurred during the transaction.
+
+Additionally, ``print(transaction_error)`` prints a tree-like
 representation of all errors regarding the transaction in question.
 
 EntityError
-~~~~~~~~~~~
+-----------
 
-An ``EntityError`` represents a single error that has been returned by
-the server. You might call \* ``get_entity()`` which returns the entity
-which caused the error. \* ``get_description()`` which returns a
-description of the error. \* ``get_code()`` which returns the error code
-(if specified) or 0 (if not).
+An ``EntityError`` specifies the entity and the error proper that
+caused a transaction to fail. It is never raised on its own but is
+contained in a ``TransactionError`` (which may or may not contain
+other ``EntityError`` objects) which is then raised. ``EntityError``
+has several :ref:`subclasses<Special Errors>` that further specify the
+error that occurred.
 
-In fact, the ``EntityError`` class is a subclass of
-``TransactionError``. So, it inherits the ``get_entities()``. Unless
-overridden by subclasses of ``EntityError``, it return a list with only
-one item—the entity which caused this error. Similarly, unless
-overridden by subclasses, the ``get_errors()`` method returns a list
-with only one item—``[self]``.
+The ``EntityError`` class is in fact a subclass of
+``TransactionError``. Thus, it has the same methods and attributes as
+the ``TransactionError`` explained
+:ref:`above<TransactionError>`. This is important in case of an
+``EntityError`` that was caused by other faulty entities (e.g., broken
+parents or properties). In that case these problematic entities and
+errors can again be inspected by visiting the ``entities`` and
+``errors`` lists as above.
 
 Special Errors
 ~~~~~~~~~~~~~~
 
-Subclasses of ``EntityError`` for special purposes: \*
-``EntityDoesNotExistError`` \* ``EntityHasNoDataTypeError`` \*
-``UniqueNamesError`` \* ``UnqualifiedParentsError`` - overrides
-``get_entities()``: returns all parent entities with errors. - overrides
-``get_errors()``: returns a list of EntityErrors which have been caused
-by parent entities. \* ``UnqualifiedPropertiesError`` - overrides
-``get_entities()``: returns all properties with errors. - overrides
-``get_errors()``: returns a list of EntityErrors which have been caused
-by properties.
+Subclasses of ``EntityError`` for special purposes:
+
+* ``EntityDoesNotExistError``
+
+* ``EntityHasNoDataTypeError``
+
+* ``UniqueNamesError``
+
+* ``UnqualifiedParentsError``
+
+* ``UnqualifiedPropertiesError``
+
+* ``ConsistencyError``
+
+* ``AuthorizationError``
+
+* ``AmbiguousEntityError``
+
+BadQueryError
+-------------
+
+A ``BadQueryError`` is raised when a query could not be processed by
+the server. In contrast to a ``TransactionError`` it is not
+necessarily caused by problematic entities or
+containers. ``BadQueryError`` has the two important subclasses
+``EmptyUniqueQueryError`` and ``QueryNotUniqueError`` for queries with
+``unique=True`` which found no or ambiguous entities, respectively.
+
+HTTP Errors
+-----------
+
+An ``HTTPClientError`` or an ``HTTPServerError`` is raised in case of
+http(s) connection problems caused by the Python client or the CaosDB
+server, respectively. There are the following subclasses of
+``HTTPClientError`` that are used to specify the connection problem:
+
+* ``HTTPURITooLongError``: The URI of the request was too long to be
+  processed by the server.
+
+* ``HTTPForbiddenError``: You're not allowed to access this resource.
+
+* ``HTTPResourceNotFoundError``: The requested resource doesn't exist.
+
+Other Errors
+------------
+
+There are further subclasses of ``CaosDBException`` that are raised in
+case of faulty configurations or other problems. They should be rather
+self-explanatory from their names; see the :doc:`source code<../_apidoc/caosdb.exceptions>`
+for further information.
+
+* ``ConfigurationError``
+
+* ``LoginFailedError``
+
+* ``MismatchingEntitiesError``
+
+* ``ServerConfigurationException``
+
+Examples
+--------
+
+.. code-block:: python3
+
+   import caosdb as db
+
+   def link_and_insert(entity, linked, link=True):
+     """Link the ENTITY to LINKED and insert it."""
+     if link:
+       entity.add_property(db.Property(name="link", value=linked))
+     try:
+       entity.insert()
+     except db.TransactionError as tre:
+       # Unique names problem may be worked around by using another name
+       if tre.has_error(db.UniqueNamesError):
+         for ent_error in tre.errors:
+           if (isinstance(ent_error, db.UniqueNamesError)
+               and entity in ent_error.entities):
+             entity.name = entity.name + "_new"  # Try again with new name.
+             link_and_insert(entity, linked, link=False)
+             break
+       # Unqualified properties will be handled by the caller
+       elif tre.has_error(db.UnqualifiedPropertiesError):
+         for ent_error in tre.errors:
+           if (isinstance(ent_error, db.UnqualifiedPropertiesError_
+               and entity in ent_error.entities):
+             raise RuntimeError("One of the properties was unqualified: " + str(ent_error))
+       # Other problems are not covered by this tutorial
+       else:
+         raise NotImplementedError("Unhandled TransactionError: " + str(tre))
diff --git a/src/doc/tutorials/first_steps.rst b/src/doc/tutorials/first_steps.rst
index 3eb804776960ba93acb9baf78824f0cf8a06e1f7..34b96bbeca416107fb34feb4707b9ef46fc49fe7 100644
--- a/src/doc/tutorials/first_steps.rst
+++ b/src/doc/tutorials/first_steps.rst
@@ -2,14 +2,15 @@ First Steps
 ===========
 
 You should have a working connection to a CaosDB instance now. If not, please check out the 
-:doc:`Getting Started secton</getting_started>`.
+:doc:`Getting Started secton</README_SETUP>`.
 
 If you are not yet familiar with Records, RecordTypes and Properties used in CaosDB,
-please check out the respective part in the `Web Interface Tutorial`_. 
-You should also know the basics of the CaosDB Query Language (a tutorial is here_).
+please check out the respective part in the `Web Interface tutorial`_.
+You should also know the basics of the CaosDB Query Language (a tutorial is
+`here <https://docs.indiscale.com/caosdb-webui/tutorials/query.html>`_).
 
-We recommend that you connect to the demo instance in order to try out the following
-examples. You can do this with
+We recommend that you connect to the `demo instance`_ (hosted by `Indiscale`_) in order to try out
+the following examples. You can do this with
 
 >>> import caosdb as db
 >>> _ = db.configure_connection(
@@ -19,7 +20,7 @@ examples. You can do this with
 ...    password="caosdb")
 
 or by using corresponding settings in the configuration file
-(see :doc:`Getting Started secton</getting_started>`.). 
+(see :doc:`Getting Started secton</README_SETUP>`.).
 However, you can also translate the examples to the data model that you have at hand.
 
 Let's start with a simple query.
@@ -124,9 +125,6 @@ the result Records and their properties.
 The next tutorial shows how to make some meaningful use of this.
 
 
-
-.. _here: https://gitlabio.something
 .. _`demo instance`: https://demo.indiscale.com
 .. _`IndiScale`: https://indiscale.com
-.. _`Web Interface Tutorial`: https://caosdb.gitlab.io/caosdb-webui/tutorials/model.html
-.. _here: https://caosdb.gitlab.io/caosdb-webui/tutorials/cql.html
+.. _`Web Interface tutorial`: https://docs.indiscale.com/caosdb-webui/tutorials/first_steps.html