diff --git a/arkindex/documents/api/elements.py b/arkindex/documents/api/elements.py
index aa9215a3ce7140946cfeeaed6d880bf728810e9c..fe62bc6b63b110b112a051d06c5ec50714fba0f4 100644
--- a/arkindex/documents/api/elements.py
+++ b/arkindex/documents/api/elements.py
@@ -23,6 +23,7 @@ from django.db.models import (
 from django.db.models.functions import Cast
 from django.shortcuts import get_object_or_404
 from django.utils.functional import cached_property
+from drf_spectacular.types import OpenApiTypes
 from drf_spectacular.utils import (
     OpenApiParameter,
     PolymorphicProxySerializer,
@@ -325,6 +326,12 @@ class ElementsListAutoSchema(AutoSchema):
                     type=UUID,
                     required=False,
                 ),
+                OpenApiParameter(
+                    'creator_email',
+                    description='Restrict to elements created by the user with the specified email address.',
+                    type=OpenApiTypes.EMAIL,
+                    required=False,
+                ),
                 OpenApiParameter(
                     'classification_confidence',
                     description='Restrict to elements having a classification with the given confidence. '
@@ -798,6 +805,9 @@ class ElementsListBase(CorpusACLMixin, DestroyModelMixin, ListAPIView):
         if 'name' in self.clean_params:
             filters &= Q(name__icontains=self.clean_params['name'])
 
+        if 'creator_email' in self.clean_params:
+            filters &= Q(creator__email=self.clean_params['creator_email'])
+
         if 'rotation_angle' in self.clean_params:
             try:
                 rotation_angle = int(self.clean_params['rotation_angle'])
diff --git a/arkindex/documents/tests/test_children_elements.py b/arkindex/documents/tests/test_children_elements.py
index 67ed18a55e40346cc83ebefd91cb8f6cffb907dc..784450ed643910da0fc8c15de4ae16f950f1a372 100644
--- a/arkindex/documents/tests/test_children_elements.py
+++ b/arkindex/documents/tests/test_children_elements.py
@@ -8,6 +8,7 @@ from arkindex.documents.models import Element, EntityType, MetaType, Transcripti
 from arkindex.process.models import WorkerRun, WorkerVersion
 from arkindex.project.aws import S3FileStatus
 from arkindex.project.tests import FixtureAPITestCase
+from arkindex.users.models import User
 
 
 class TestChildrenElements(FixtureAPITestCase):
@@ -688,6 +689,54 @@ class TestChildrenElements(FixtureAPITestCase):
             ]
         )
 
+    def test_children_filter_creator_email(self):
+        element_type = self.corpus.types.first()
+        user2 = User.objects.get(email='user2@user.fr')
+        test_element = self.corpus.elements.create(type=element_type, name='Test Element', creator=user2)
+        test_element.add_parent(self.vol)
+
+        with self.assertNumQueries(4):
+            response = self.client.get(
+                reverse('api:elements-children', kwargs={'pk': str(self.vol.id)}),
+                data={
+                    'creator_email': 'user2@user.fr'
+                }
+            )
+            self.assertEqual(response.status_code, status.HTTP_200_OK)
+        self.assertEqual(len(response.json()['results']), 1)
+        self.assertEqual(response.json()['results'][0]['name'], 'Test Element')
+
+    def test_children_filter_creator_email_case_insensitive(self):
+        element_type = self.corpus.types.first()
+        user2 = User.objects.get(email='user2@user.fr')
+        test_element = self.corpus.elements.create(type=element_type, name='Test Element', creator=user2)
+        test_element.add_parent(self.vol)
+
+        with self.assertNumQueries(4):
+            response = self.client.get(
+                reverse('api:elements-children', kwargs={'pk': str(self.vol.id)}),
+                data={
+                    'creator_email': 'USEr2@user.fr'
+                }
+            )
+            self.assertEqual(response.status_code, status.HTTP_200_OK)
+        self.assertEqual(len(response.json()['results']), 1)
+        self.assertEqual(response.json()['results'][0]['name'], 'Test Element')
+
+    def test_children_filter_creator_email_does_not_exist(self):
+        """
+        If there is no user with the given email, there is no error but no results are returned
+        """
+        with self.assertNumQueries(2):
+            response = self.client.get(
+                reverse('api:elements-children', kwargs={'pk': str(self.vol.id)}),
+                data={
+                    'creator_email': 'ohno@user.fr'
+                }
+            )
+            self.assertEqual(response.status_code, status.HTTP_200_OK)
+        self.assertEqual(len(response.json()['results']), 0)
+
     def test_children_filter_rotation_angle(self):
         element_type = self.corpus.types.first()
         not_rotated = self.corpus.elements.create(type=element_type, name='not rotated')
diff --git a/arkindex/documents/tests/test_corpus_elements.py b/arkindex/documents/tests/test_corpus_elements.py
index 0102b204f340355fbbcd9ecafa21b1bf3026d96b..00b7b45401b57fdb3a2d400aacedd12cb921b140 100644
--- a/arkindex/documents/tests/test_corpus_elements.py
+++ b/arkindex/documents/tests/test_corpus_elements.py
@@ -5,9 +5,10 @@ import sqlparse
 from django.urls import reverse
 from rest_framework import status
 
-from arkindex.documents.models import Corpus, Element, EntityType, MetaData, MetaType, Transcription
+from arkindex.documents.models import Corpus, Element, ElementType, EntityType, MetaData, MetaType, Transcription
 from arkindex.process.models import WorkerVersion
 from arkindex.project.tests import FixtureAPITestCase
+from arkindex.users.models import User
 
 
 class TestListElements(FixtureAPITestCase):
@@ -136,6 +137,50 @@ class TestListElements(FixtureAPITestCase):
         for result in results:
             self.assertIn(nameSelected, result['name'])
 
+    def test_list_elements_filter_creator_email(self):
+        page_type = ElementType.objects.get(corpus=self.corpus, slug='page')
+        user2 = User.objects.get(email='user2@user.fr')
+        self.corpus.elements.create(type=page_type, name='Test Element', creator=user2)
+        mail = 'user2@user.fr'
+        with self.assertNumQueries(4):
+            response = self.client.get(
+                reverse('api:corpus-elements', kwargs={'corpus': self.corpus.id}),
+                data={'creator_email': mail}
+            )
+        self.assertEqual(response.status_code, status.HTTP_200_OK)
+        results = response.json()['results']
+        self.assertEqual(len(results), 1)
+        self.assertEqual(results[0]['name'], 'Test Element')
+
+    def test_list_elements_filter_creator_email_case_insensitive(self):
+        page_type = ElementType.objects.get(corpus=self.corpus, slug='page')
+        user2 = User.objects.get(email='user2@user.fr')
+        self.corpus.elements.create(type=page_type, name='Test Element', creator=user2)
+        mail = 'UsER2@user.fr'
+        with self.assertNumQueries(4):
+            response = self.client.get(
+                reverse('api:corpus-elements', kwargs={'corpus': self.corpus.id}),
+                data={'creator_email': mail}
+            )
+        self.assertEqual(response.status_code, status.HTTP_200_OK)
+        results = response.json()['results']
+        self.assertEqual(len(results), 1)
+        self.assertEqual(results[0]['name'], 'Test Element')
+
+    def test_list_elements_filter_creator_email_does_not_exist(self):
+        """
+        If there is no user with the given email, there is no error but no results are returned
+        """
+        mail = 'ohno@user.fr'
+        with self.assertNumQueries(2):
+            response = self.client.get(
+                reverse('api:corpus-elements', kwargs={'corpus': self.corpus.id}),
+                data={'creator_email': mail}
+            )
+        self.assertEqual(response.status_code, status.HTTP_200_OK)
+        results = response.json()['results']
+        self.assertEqual(len(results), 0)
+
     def test_list_elements_corpus_uuid4(self):
         """
         Ensure the corpus filter allows any UUID, not just version 4 UUIDs.
diff --git a/arkindex/documents/tests/test_parents_elements.py b/arkindex/documents/tests/test_parents_elements.py
index f07e4a0119708d1dfe72aaffd83b0c0113341f3c..96d2e98a1cb5f74d9e6042d06afa99fab32a46f5 100644
--- a/arkindex/documents/tests/test_parents_elements.py
+++ b/arkindex/documents/tests/test_parents_elements.py
@@ -7,6 +7,7 @@ from rest_framework import status
 from arkindex.documents.models import Corpus, Element, EntityType, MetaType
 from arkindex.process.models import WorkerVersion
 from arkindex.project.tests import FixtureAPITestCase
+from arkindex.users.models import User
 
 
 class TestParentsElements(FixtureAPITestCase):
@@ -397,6 +398,54 @@ class TestParentsElements(FixtureAPITestCase):
                     expected_elements
                 )
 
+    def test_parents_filter_creator_email(self):
+        element_type = self.corpus.types.first()
+        user2 = User.objects.get(email='user2@user.fr')
+        parent_element = self.corpus.elements.create(type=element_type, name='Test Element', creator=user2)
+        self.page.add_parent(parent_element)
+
+        with self.assertNumQueries(4):
+            response = self.client.get(
+                reverse('api:elements-parents', kwargs={'pk': str(self.page.id)}),
+                data={
+                    'creator_email': 'user2@user.fr'
+                }
+            )
+            self.assertEqual(response.status_code, status.HTTP_200_OK)
+        self.assertEqual(len(response.json()['results']), 1)
+        self.assertEqual(response.json()['results'][0]['name'], 'Test Element')
+
+    def test_parents_filter_creator_email_case_insensitive(self):
+        element_type = self.corpus.types.first()
+        user2 = User.objects.get(email='user2@user.fr')
+        parent_element = self.corpus.elements.create(type=element_type, name='Test Element', creator=user2)
+        self.page.add_parent(parent_element)
+
+        with self.assertNumQueries(4):
+            response = self.client.get(
+                reverse('api:elements-parents', kwargs={'pk': str(self.page.id)}),
+                data={
+                    'creator_email': 'USEr2@user.fr'
+                }
+            )
+            self.assertEqual(response.status_code, status.HTTP_200_OK)
+        self.assertEqual(len(response.json()['results']), 1)
+        self.assertEqual(response.json()['results'][0]['name'], 'Test Element')
+
+    def test_parents_filter_creator_email_does_not_exist(self):
+        """
+        If there is no user with the given email, there is no error but no results are returned
+        """
+        with self.assertNumQueries(2):
+            response = self.client.get(
+                reverse('api:elements-parents', kwargs={'pk': str(self.page.id)}),
+                data={
+                    'creator_email': 'ohno@user.fr'
+                }
+            )
+            self.assertEqual(response.status_code, status.HTTP_200_OK)
+        self.assertEqual(len(response.json()['results']), 0)
+
     def test_parents_invalid_order(self):
         cases = [
             ({'order': 'blah', 'order_direction': 'asc'}, {'order': ['Unknown sorting field']}),