Merge pull request #536 from taigaio/task/3538/add_tribe_git_field_to_user_stories

Task #3538: Add tribe_gig PickledObjectField attribute to UserStory model
remotes/origin/logger
David Barragán Merino 2015-12-09 12:07:45 +01:00
commit 97edb6e3fb
10 changed files with 84 additions and 19 deletions

View File

@ -11,6 +11,7 @@
- Improve login and forgot password: allow username or email case-insensitive if the query only
match with one user.
- Improve the django admin panel, now it is more usable and all the selector fields works properly.
- [API] Add tribe_gig field to user stories (improve integration between Taiga and Taiga Tribe).
- [API] Performance improvements for project stats.
- Lots of small and not so small bugfixes.

View File

@ -84,6 +84,19 @@ class PgArrayField(serializers.WritableField):
return data
class PickledObjectField(serializers.WritableField):
"""
PickledObjectField objects serializer.
"""
widget = widgets.Textarea
def to_native(self, obj):
return obj
def from_native(self, data):
return data
class TagsField(serializers.WritableField):
"""
Pickle objects serializer.

View File

@ -76,6 +76,23 @@ class ProjectViewSet(LikedResourceMixin, HistoryResourceMixin, ModelCrudViewSet)
return qs
def get_serializer_class(self):
if self.action == "list":
return self.list_serializer_class
elif self.action == "create":
return self.serializer_class
if self.action == "by_slug":
slug = self.request.QUERY_PARAMS.get("slug", None)
project = get_object_or_404(models.Project, slug=slug)
else:
project = self.get_object()
if permissions_service.is_project_owner(self.request.user, project):
return self.admin_serializer_class
return self.serializer_class
@detail_route(methods=["POST"])
def watch(self, request, pk=None):
project = self.get_object()
@ -105,23 +122,6 @@ class ProjectViewSet(LikedResourceMixin, HistoryResourceMixin, ModelCrudViewSet)
services.update_projects_order_in_bulk(data, "user_order", request.user)
return response.NoContent(data=None)
def get_serializer_class(self):
if self.action == "list":
return self.list_serializer_class
elif self.action == "create":
return self.serializer_class
if self.action == "by_slug":
slug = self.request.QUERY_PARAMS.get("slug", None)
project = get_object_or_404(models.Project, slug=slug)
else:
project = self.get_object()
if permissions_service.is_project_owner(self.request.user, project):
return self.admin_serializer_class
return self.serializer_class
@list_route(methods=["GET"])
def by_slug(self, request):
slug = request.QUERY_PARAMS.get("slug", None)

View File

@ -286,6 +286,7 @@ def userstory_freezer(us) -> dict:
"blocked_note": us.blocked_note,
"blocked_note_html": mdrender(us.project, us.blocked_note),
"custom_attributes": extract_user_story_custom_attributes(us),
"tribe_gig": us.tribe_gig,
}
return snapshot

View File

@ -9,7 +9,8 @@
"kanban_order",
"taskboard_order",
"us_order",
"custom_attributes"
"custom_attributes",
"tribe_gig",
] %}
{% for field_name, values in changed_fields.items() %}

View File

@ -9,7 +9,8 @@
"us_order",
"blocked_note_diff",
"blocked_note_html",
"custom_attributes"
"custom_attributes",
"tribe_gig",
] %}
{% for field_name, values in changed_fields.items() %}
{% if field_name not in excluded_fields %}

View File

@ -0,0 +1,20 @@
# -*- coding: utf-8 -*-
from __future__ import unicode_literals
from django.db import migrations, models
import picklefield.fields
class Migration(migrations.Migration):
dependencies = [
('userstories', '0010_remove_userstory_watchers'),
]
operations = [
migrations.AddField(
model_name='userstory',
name='tribe_gig',
field=picklefield.fields.PickledObjectField(editable=False, null=True, default=None, verbose_name='taiga tribe gig', blank=True),
),
]

View File

@ -21,6 +21,7 @@ from django.utils.translation import ugettext_lazy as _
from django.utils import timezone
from djorm_pgarray.fields import TextArrayField
from picklefield.fields import PickledObjectField
from taiga.base.tags import TaggedMixin
from taiga.projects.occ import OCCModelMixin
@ -101,6 +102,10 @@ class UserStory(OCCModelMixin, WatchedModelMixin, BlockedMixin, TaggedMixin, mod
related_name="generated_user_stories",
verbose_name=_("generated from issue"))
external_reference = TextArrayField(default=None, verbose_name=_("external reference"))
tribe_gig = PickledObjectField(null=True, blank=True, default=None,
verbose_name="taiga tribe gig")
_importing = None
class Meta:

View File

@ -17,6 +17,7 @@
from django.apps import apps
from taiga.base.api import serializers
from taiga.base.fields import TagsField
from taiga.base.fields import PickledObjectField
from taiga.base.fields import PgArrayField
from taiga.base.neighbors import NeighborsSerializerMixin
from taiga.base.utils import json
@ -60,6 +61,7 @@ class UserStorySerializer(WatchersValidator, VoteResourceSerializerMixin, Editab
status_extra_info = BasicUserStoryStatusSerializer(source="status", required=False, read_only=True)
assigned_to_extra_info = UserBasicInfoSerializer(source="assigned_to", required=False, read_only=True)
owner_extra_info = UserBasicInfoSerializer(source="owner", required=False, read_only=True)
tribe_gig = PickledObjectField(required=False)
class Meta:
model = models.UserStory

View File

@ -514,3 +514,24 @@ def test_update_userstory_remove_watchers(client):
assert response.data["watchers"] == []
watcher_ids = list(us.get_watchers().values_list("id", flat=True))
assert watcher_ids == []
def test_update_userstory_update_tribe_gig(client):
project = f.ProjectFactory.create()
us = f.UserStoryFactory.create(project=project, status__project=project, milestone__project=project)
f.MembershipFactory.create(project=us.project, user=us.owner, is_owner=True)
url = reverse("userstories-detail", kwargs={"pk": us.pk})
data = {
"tribe_gig": {
"id": 2,
"title": "This is a gig test title"
},
"version":1
}
client.login(user=us.owner)
response = client.json.patch(url, json.dumps(data))
assert response.status_code == 200
assert response.data["tribe_gig"] == data["tribe_gig"]