aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohan Herland <johan@herland.net>2019-12-01 02:49:54 +0100
committerStephen Finucane <stephen@that.guru>2019-12-01 11:59:37 +0000
commitde36300a2f78c7d22e9f6879342b99ad1c4586b2 (patch)
treec220359922999185bd87f87a8c74eba28cb98f4d
parent79a3efb63a3ac2dea0382a4d6ec1b675a7b154c9 (diff)
downloadpatchwork-de36300a2f78c7d22e9f6879342b99ad1c4586b2.tar
patchwork-de36300a2f78c7d22e9f6879342b99ad1c4586b2.tar.gz
REST: Add 'actor' field to '/events' model
Signed-off-by: Johan Herland <johan@herland.net> Reviewed-by: Stephen Finucane <stephen@that.guru> Acked-by: Daniel Axtens <dja@axtens.net> Cc: Mauro Carvalho Chehab <mchehab+samsung@kernel.org> Closes: #73
-rw-r--r--docs/api/schemas/latest/patchwork.yaml7
-rw-r--r--docs/api/schemas/patchwork.j29
-rw-r--r--docs/api/schemas/v1.2/patchwork.yaml7
-rw-r--r--docs/usage/overview.rst3
-rw-r--r--patchwork/api/event.py10
-rw-r--r--patchwork/api/filters.py5
-rw-r--r--patchwork/tests/api/test_event.py29
7 files changed, 66 insertions, 4 deletions
diff --git a/docs/api/schemas/latest/patchwork.yaml b/docs/api/schemas/latest/patchwork.yaml
index 6c7564b..fc23cdb 100644
--- a/docs/api/schemas/latest/patchwork.yaml
+++ b/docs/api/schemas/latest/patchwork.yaml
@@ -1649,6 +1649,13 @@ components:
type: string
format: iso8601
readOnly: true
+ actor:
+ type: object
+ title: Actor
+ description: The user that caused/created this event.
+ readOnly: true
+ allOf:
+ - $ref: '#/components/schemas/UserEmbedded'
payload:
type: object
EventCoverCreated:
diff --git a/docs/api/schemas/patchwork.j2 b/docs/api/schemas/patchwork.j2
index e2c8a8c..85f3977 100644
--- a/docs/api/schemas/patchwork.j2
+++ b/docs/api/schemas/patchwork.j2
@@ -1679,6 +1679,15 @@ components:
type: string
format: iso8601
readOnly: true
+{% if version >= (1, 2) %}
+ actor:
+ type: object
+ title: Actor
+ description: The user that caused/created this event.
+ readOnly: true
+ allOf:
+ - $ref: '#/components/schemas/UserEmbedded'
+{% endif %}
payload:
type: object
EventCoverCreated:
diff --git a/docs/api/schemas/v1.2/patchwork.yaml b/docs/api/schemas/v1.2/patchwork.yaml
index 7dc9579..b4d1cf6 100644
--- a/docs/api/schemas/v1.2/patchwork.yaml
+++ b/docs/api/schemas/v1.2/patchwork.yaml
@@ -1649,6 +1649,13 @@ components:
type: string
format: iso8601
readOnly: true
+ actor:
+ type: object
+ title: Actor
+ description: The user that caused/created this event.
+ readOnly: true
+ allOf:
+ - $ref: '#/components/schemas/UserEmbedded'
payload:
type: object
EventCoverCreated:
diff --git a/docs/usage/overview.rst b/docs/usage/overview.rst
index e84e13d..273c792 100644
--- a/docs/usage/overview.rst
+++ b/docs/usage/overview.rst
@@ -228,6 +228,9 @@ properties:
``date``
When this event was created
+``actor``
+ The user, if any, that caused/created this event
+
``payload``
Additional information
diff --git a/patchwork/api/event.py b/patchwork/api/event.py
index e6d467d..e00ce05 100644
--- a/patchwork/api/event.py
+++ b/patchwork/api/event.py
@@ -23,6 +23,7 @@ from patchwork.models import Event
class EventSerializer(ModelSerializer):
project = ProjectSerializer(read_only=True)
+ actor = UserSerializer()
patch = PatchSerializer(read_only=True)
series = SeriesSerializer(read_only=True)
cover = CoverLetterSerializer(read_only=True)
@@ -50,7 +51,7 @@ class EventSerializer(ModelSerializer):
data = super(EventSerializer, self).to_representation(instance)
payload = OrderedDict()
kept_fields = self._category_map[instance.category] + [
- 'id', 'category', 'project', 'date']
+ 'id', 'category', 'project', 'date', 'actor']
for field in [x for x in data]:
if field not in kept_fields:
@@ -65,10 +66,13 @@ class EventSerializer(ModelSerializer):
class Meta:
model = Event
- fields = ('id', 'category', 'project', 'date', 'patch', 'series',
- 'cover', 'previous_state', 'current_state',
+ fields = ('id', 'category', 'project', 'date', 'actor', 'patch',
+ 'series', 'cover', 'previous_state', 'current_state',
'previous_delegate', 'current_delegate', 'created_check')
read_only_fields = fields
+ versioned_fields = {
+ '1.2': ('actor', ),
+ }
class EventList(ListAPIView):
diff --git a/patchwork/api/filters.py b/patchwork/api/filters.py
index 6b4d84c..60f1a36 100644
--- a/patchwork/api/filters.py
+++ b/patchwork/api/filters.py
@@ -236,7 +236,10 @@ class EventFilterSet(TimestampMixin, BaseFilterSet):
class Meta:
model = Event
- fields = ('project', 'category', 'series', 'patch', 'cover')
+ fields = ('project', 'category', 'series', 'patch', 'cover', 'actor')
+ versioned_fields = {
+ '1.2': ('actor', ),
+ }
class BundleFilterSet(BaseFilterSet):
diff --git a/patchwork/tests/api/test_event.py b/patchwork/tests/api/test_event.py
index bff8f40..c202a65 100644
--- a/patchwork/tests/api/test_event.py
+++ b/patchwork/tests/api/test_event.py
@@ -35,11 +35,16 @@ class TestEventAPI(utils.APITestCase):
def assertSerialized(self, event_obj, event_json):
self.assertEqual(event_obj.id, event_json['id'])
self.assertEqual(event_obj.category, event_json['category'])
+ if event_obj.actor is None:
+ self.assertIsNone(event_json['actor'])
# nested fields
self.assertEqual(event_obj.project.id,
event_json['project']['id'])
+ if event_obj.actor is not None:
+ self.assertEqual(event_obj.actor.id,
+ event_json['actor']['id'])
# TODO(stephenfin): Check other fields
@@ -66,10 +71,12 @@ class TestEventAPI(utils.APITestCase):
# check-created
create_check(patch=patch)
# patch-delegated, patch-state-changed
+ actor = create_maintainer(project=patch.project)
user = create_maintainer(project=patch.project)
state = create_state()
patch.delegate = user
patch.state = state
+ self.assertTrue(patch.is_editable(actor))
patch.save()
return Event.objects.all()
@@ -149,6 +156,28 @@ class TestEventAPI(utils.APITestCase):
resp = self.client.get(self.api_url(), {'series': 999999})
self.assertEqual(0, len(resp.data))
+ def test_list_filter_actor(self):
+ """Filter events by actor."""
+ events = self._create_events()
+
+ # The final two events (patch-delegated, patch-state-changed)
+ # have an actor set
+ actor = events[0].actor
+ resp = self.client.get(self.api_url(), {'actor': actor.pk})
+ self.assertEqual(2, len(resp.data))
+
+ resp = self.client.get(self.api_url(), {'actor': 'foo-bar'})
+ self.assertEqual(0, len(resp.data))
+
+ def test_list_filter_actor_version_1_1(self):
+ """Filter events by actor using API v1.1."""
+ events = self._create_events()
+
+ # we still see all the events since the actor field is ignored
+ resp = self.client.get(self.api_url(version='1.1'),
+ {'actor': 'foo-bar'})
+ self.assertEqual(len(events), len(resp.data))
+
def test_order_by_date_default(self):
"""Assert the default ordering is by date descending."""
self._create_events()