diff --git a/src/Entity.jl b/src/Entity.jl
index 419187468566f37e8403d452dd04425311677b82..a507886ecab1a358f19286ffda9c6a7d0cd855a0 100644
--- a/src/Entity.jl
+++ b/src/Entity.jl
@@ -198,7 +198,7 @@ mutable struct _DataType
     wrapped_datatype::Ptr{Cvoid}
     _deletable::Bool
 
-    function _DatatType(managed_by_julia::Bool = false)
+    function _DataType(managed_by_julia::Bool = false)
 
         datatype = new()
         datatype._deletable = false
@@ -470,12 +470,12 @@ function create_parent(; name::AbstractString = "", id::AbstractString = "")
 end
 
 """
-    function create_atomic_datatype(name::AbstractString)
+    function create_atomic_datatype(name::CaosDB.Constants.DATATYPE._DATATYPE)
 
 Create and return a DataType object with an atomic datatype specified by the
 `name`.
 """
-function create_atomic_datatype(name::AbstractString)
+function create_atomic_datatype(name::CaosDB.Constants.DATATYPE._DATATYPE)
 
     datatype = Ref{_DataType}(_DataType(true))
 
@@ -484,7 +484,7 @@ function create_atomic_datatype(name::AbstractString)
         Cint,
         (Ref{_DataType}, Cstring),
         datatype,
-        name,
+        string(name),
     )
 
     CaosDB.Exceptions.evaluate_return_code(err_code)
@@ -516,12 +516,12 @@ function create_reference_datatype(name::AbstractString)
 end
 
 """
-    function create_atomic_list_datatype(name::AbstractString)
+    function create_atomic_list_datatype(name::CaosDB.Constants.DATATYPE._DATATYPE)
 
 Create and return a DataType object which is a list of atomics specified by
 `name`.
 """
-function create_atomic_list_datatype(name::AbstractString)
+function create_atomic_list_datatype(name::CaosDB.Constants.DATATYPE._DATATYPE)
 
     datatype = Ref{_DataType}(_DataType(true))
 
@@ -530,7 +530,7 @@ function create_atomic_list_datatype(name::AbstractString)
         Cint,
         (Ref{_DataType}, Cstring),
         datatype,
-        name,
+        string(name),
     )
 
     CaosDB.Exceptions.evaluate_return_code(err_code)
@@ -539,12 +539,12 @@ function create_atomic_list_datatype(name::AbstractString)
 end
 
 """
-    function create_list_of_reference_datatype(name::AbstractString)
+    function create_reference_list_datatype(name::AbstractString)
 
 Create and return a DataType object which is a list of references specified by
 `name`.
 """
-function create_list_of_reference_datatype(name::AbstractString)
+function create_reference_list_datatype(name::AbstractString)
 
     datatype = Ref{_DataType}(_DataType(true))
 
@@ -893,33 +893,99 @@ function get_description(message::Ref{_Message})
     return unsafe_string(out[])
 end
 
-# TODO(henrik, daniel) Is this the best way to return name, is_ref,
-# and is_list to the users? Should we split it up?
+"""
+    function _get_datatype(datatype::Ref{_DataType})
+
+Return a tuple that contains the name of the `datatype`, and its collection type
+(`nothing` in case of a scalar datatype).
+"""
+function _get_datatype(datatype::Ref{_DataType})
+
+    name = Ref{Ptr{UInt8}}(Ptr{UInt8}())
+    err_code = ccall(
+        (:caosdb_entity_datatype_get_datatype_name, CaosDB.library_name),
+        Cint,
+        (Ref{_DataType}, Ref{Ptr{UInt8}}),
+        datatype,
+        name,
+    )
+    CaosDB.Exceptions.evaluate_return_code(err_code)
+    name = unsafe_string(name[])
+
+    is_a = Ref{Bool}(false)
+    err_code = ccall(
+        (:caosdb_entity_datatype_is_atomic, CaosDB.library_name),
+        Cint,
+        (Ref{_DataType}, Ref{Bool}),
+        datatype,
+        is_a,
+    )
+    CaosDB.Exceptions.evaluate_return_code(err_code)
+    if is_a[]
+        return getproperty(CaosDB.Constants.DATATYPE, Symbol(name)), nothing
+    end
+
+    err_code = ccall(
+        (:caosdb_entity_datatype_is_reference, CaosDB.library_name),
+        Cint,
+        (Ref{_DataType}, Ref{Bool}),
+        datatype,
+        is_a,
+    )
+    CaosDB.Exceptions.evaluate_return_code(err_code)
+    if is_a[]
+        return name, nothing
+    end
+
+    err_code = ccall(
+        (:caosdb_entity_datatype_is_list_of_atomic, CaosDB.library_name),
+        Cint,
+        (Ref{_DataType}, Ref{Bool}),
+        datatype,
+        is_a,
+    )
+    CaosDB.Exceptions.evaluate_return_code(err_code)
+    if is_a[]
+        return getproperty(CaosDB.Constants.DATATYPE, Symbol(name)),
+        CaosDB.Constants.COLLECTION.LIST
+    end
+
+    err_code = ccall(
+        (:caosdb_entity_datatype_is_list_of_reference, CaosDB.library_name),
+        Cint,
+        (Ref{_DataType}, Ref{Bool}),
+        datatype,
+        is_a,
+    )
+    CaosDB.Exceptions.evaluate_return_code(err_code)
+    if is_a[]
+        return name, CaosDB.Constants.COLLECTION.LIST
+    end
+
+    throw(CaosDB.Exceptions.ClientException("Unkown datatype"))
+
+end
+
 """
     function get_datatype(entity::Ref{_Entity})
 
-Return a tuple that contains the name of the datatype of the given
-`entity`, whether it is a reference, and whether it is a list.
+Return a tuple that contains the name of the datatype of the given `entity`, and
+its collection type (`nothing` in case of a scalar datatype).
 """
 function get_datatype(entity::Ref{_Entity})
 
-    out = Ref{Ptr{UInt8}}(Ptr{UInt8}())
-    is_ref = Ref{Bool}(false)
-    is_list = Ref{Bool}(false)
-
+    out = Ref{_DataType}(_DataType())
     err_code = ccall(
         (:caosdb_entity_entity_get_datatype, CaosDB.library_name),
         Cint,
-        (Ref{_Entity}, Ref{Ptr{UInt8}}, Ref{Bool}, Ref{Bool}),
+        (Ref{_Entity}, Ref{_DataType}),
         entity,
         out,
-        is_ref,
-        is_list,
     )
 
     CaosDB.Exceptions.evaluate_return_code(err_code)
 
-    return unsafe_string(out[]), is_ref[], is_list[]
+    return _get_datatype(out)
 end
 
 """
@@ -930,23 +996,18 @@ Return a tuple that contains the name of the datatype of the given
 """
 function get_datatype(property::Ref{_Property})
 
-    out = Ref{Ptr{UInt8}}(Ptr{UInt8}())
-    is_ref = Ref{Bool}(false)
-    is_list = Ref{Bool}(false)
-
+    out = Ref{_DataType}(_DataType())
     err_code = ccall(
         (:caosdb_entity_property_get_datatype, CaosDB.library_name),
         Cint,
-        (Ref{_Property}, Ref{Ptr{UInt8}}, Ref{Bool}, Ref{Bool}),
+        (Ref{_Property}, Ref{_DataType}),
         property,
         out,
-        is_ref,
-        is_list,
     )
 
     CaosDB.Exceptions.evaluate_return_code(err_code)
 
-    return unsafe_string(out[]), is_ref[], is_list[]
+    return _get_datatype(out)
 end
 
 """
@@ -1862,28 +1923,22 @@ function set_description(entity::Ref{_Entity}, description::AbstractString)
     CaosDB.Exceptions.evaluate_return_code(err_code)
 end
 
-# TODO(henrik, daniel) Convenience functions for lists and references,
-# too?
 """
     function set_datatype(
         entity::Ref{_Entity},
-        datatype::AbstractString;
-        is_list::Bool = false,
-        is_reference::Bool = false,
+        datatype::AbstractString,
+        collection::Union{CaosDB.Constants.COLLECTION._COLLECTION, Nothing}
     )
 
-Set the datatype of the given `entity` object to the given `datatype`
-name. Only possible if the role of the entity is "PROPERTY". Specify
-whether it is a reference or a list with the optional `is_list` and
-`is_reference` keyword arguments. If the datatype is not a reference,
-it is checked against the Atomic Datatypes known to CaosDB and an
-exception is thrown if it is not known.
+Set the datatype of the given `entity` object to a reference to the given
+`datatype` name. Only possible if the role of the entity is "PROPERTY". Specify
+whether the datatype is a list by specifying a `collection`. If none is given, a
+scalar datatype is set.
 """
 function set_datatype(
     entity::Ref{_Entity},
-    datatype::AbstractString;
-    is_list::Bool = false,
-    is_reference::Bool = false,
+    datatype::AbstractString,
+    collection::Union{CaosDB.Constants.COLLECTION._COLLECTION,Nothing} = nothing,
 )
 
     if get_role(entity) != CaosDB.Constants.ROLE.PROPERTY
@@ -1894,54 +1949,161 @@ function set_datatype(
         )
     end
 
+    if collection == nothing
+        dtype_ref = create_reference_datatype(datatype)
+    elseif collection == CaosDB.Constants.COLLECTION.LIST
+        dtype_ref = create_reference_list_datatype(datatype)
+    else
+        throw(ArgumentError("Unkown datatype: $datatype"))
+    end
+
     err_code = ccall(
         (:caosdb_entity_entity_set_datatype, CaosDB.library_name),
         Cint,
-        (Ref{_Entity}, Cstring, Bool, Bool),
+        (Ref{_Entity}, Ref{_DataType}),
         entity,
-        datatype,
-        is_reference,
-        is_list,
+        dtype_ref,
+    )
+
+    CaosDB.Exceptions.evaluate_return_code(err_code)
+end
+
+"""
+    function set_datatype(
+        entity::Ref{_Entity},
+        datatype::CaosDB.Constants.DATATYPE._DATATYPE,
+        collection::Union{CaosDB.Constants.COLLECTION._COLLECTION, Nothing}
+    )
+
+Set the datatype of the given `entity` object to a reference to the given atomic
+`datatype`. Only possible if the role of the entity is "PROPERTY". Specify
+whether the datatype is a list by specifying a `collection`. If none is given, a
+scalar datatype is set.
+"""
+function set_datatype(
+    entity::Ref{_Entity},
+    datatype::CaosDB.Constants.DATATYPE._DATATYPE,
+    collection::Union{CaosDB.Constants.COLLECTION._COLLECTION,Nothing} = nothing,
+)
+
+    if get_role(entity) != CaosDB.Constants.ROLE.PROPERTY
+        throw(
+            CaosDB.Exceptions.ClientException(
+                "Only entities with role PROPERTY can be assigned a datatype.",
+            ),
+        )
+    end
+
+    if collection == nothing
+        dtype_ref = create_atomic_datatype(datatype)
+    elseif collection == CaosDB.Constants.COLLECTION.LIST
+        dtype_ref = create_atomic_list_datatype(datatype)
+    else
+        throw(ArgumentError("Unkown datatype: $datatype"))
+    end
+
+    err_code = ccall(
+        (:caosdb_entity_entity_set_datatype, CaosDB.library_name),
+        Cint,
+        (Ref{_Entity}, Ref{_DataType}),
+        entity,
+        dtype_ref,
     )
 
     CaosDB.Exceptions.evaluate_return_code(err_code)
 end
 
+"""
+    function set_datatype(entity::Ref{_Entity}, datatype::Tuple{Any, Any})
+
+Convenience wrapper for the `set_datatype` functions s.th. expressions like
+`set_datatype(entity_a, get_datatype(entity_b))` work.
+"""
+function set_datatype(entity::Ref{_Entity}, datatype::Tuple{Any,Any})
+    set_datatype(entity, datatype[1], datatype[2])
+end
 
 """
     function set_datatype(
         property::Ref{_Property},
-        datatype::AbstractString;
-        is_list::Bool = false,
-        is_reference::Bool = false,
+        datatype::AbstractString,
+        collection::Union{CaosDB.Constants.COLLECTION._COLLECTION, Nothing}
     )
 
-Set the datatype of the given `property` object to the given
-`datatype` name. Specify whether it is a reference or a list with the
-optional `is_list` and `is_reference` keyword arguments. If the
-datatype is not a reference, it is checked against the Atomic
-Datatypes known to CaosDB and an exception is thrown if it is not
-known.
+Set the datatype of the given `property` object to a reference to the given
+`datatype` name. Specify whether the datatype is a list by specifying a
+`collection`. If none is given, a scalar datatype is set.
 """
 function set_datatype(
     property::Ref{_Property},
-    datatype::AbstractString;
-    is_list::Bool = false,
-    is_reference::Bool = false,
+    datatype::AbstractString,
+    collection::Union{CaosDB.Constants.COLLECTION._COLLECTION,Nothing} = nothing,
 )
+    if collection == nothing
+        dtype_ref = create_reference_datatype(datatype)
+    elseif collection == CaosDB.Constants.COLLECTION.LIST
+        dtype_ref = create_reference_list_datatype(datatype)
+    else
+        throw(ArgumentError("Unkown datatype: $datatype"))
+    end
+
     err_code = ccall(
         (:caosdb_entity_property_set_datatype, CaosDB.library_name),
         Cint,
-        (Ref{_Property}, Cstring, Bool, Bool),
+        (Ref{_Property}, Ref{_DataType}),
         property,
-        datatype,
-        is_reference,
-        is_list,
+        dtype_ref,
+    )
+
+    CaosDB.Exceptions.evaluate_return_code(err_code)
+end
+
+"""
+    function set_datatype(
+        property::Ref{_Property},
+        datatype::CaosDB.Constants.DATATYPE._DATATYPE,
+        collection::Union{CaosDB.Constants.COLLECTION._COLLECTION, Nothing}
+    )
+
+Set the datatype of the given `property` object to a reference to the given
+atomic `datatype`. Specify whether the datatype is a list by specifying a
+`collection`. If none is given, a scalar datatype is set.
+"""
+function set_datatype(
+    property::Ref{_Property},
+    datatype::CaosDB.Constants.DATATYPE._DATATYPE,
+    collection::Union{CaosDB.Constants.COLLECTION._COLLECTION,Nothing} = nothing,
+)
+
+    if collection == nothing
+        dtype_ref = create_atomic_datatype(datatype)
+    elseif collection == CaosDB.Constants.COLLECTION.LIST
+        dtype_ref = create_atomic_list_datatype(datatype)
+    else
+        throw(ArgumentError("Unkown datatype: $datatype"))
+    end
+
+    err_code = ccall(
+        (:caosdb_entity_property_set_datatype, CaosDB.library_name),
+        Cint,
+        (Ref{_Property}, Ref{_DataType}),
+        property,
+        dtype_ref,
     )
 
     CaosDB.Exceptions.evaluate_return_code(err_code)
 end
 
+"""
+    function set_datatype(property::Ref{_Property}, datatype::Tuple{Any, Any})
+
+Convenience wrapper for the `set_datatype` functions s.th. expressions like
+`set_datatype(property_a, get_datatype(property_b))` work.
+"""
+function set_datatype(property::Ref{_Property}, datatype::Tuple{Any,Any})
+    set_datatype(property, datatype[1], datatype[2])
+end
+
 """
     function set_unit(entity::Ref{_Entity}, unit::AbstractString)
 
@@ -1959,7 +2121,6 @@ function set_unit(entity::Ref{_Entity}, unit::AbstractString)
     CaosDB.Exceptions.evaluate_return_code(err_code)
 end
 
-
 """
     function set_unit(property::Ref{_Property}, unit::AbstractString)