Skip to content
This repository has been archived by the owner on Jan 19, 2022. It is now read-only.

Commit

Permalink
Merge pull request #23 from klrmn/env_api
Browse files Browse the repository at this point in the history
CRUD APIs for Profile, Category, and Element
Looks good to me!
  • Loading branch information
camd committed Mar 13, 2013
2 parents c98da16 + 483d5c4 commit 2893b95
Show file tree
Hide file tree
Showing 22 changed files with 751 additions and 603 deletions.
56 changes: 50 additions & 6 deletions docs/userguide/api/core.rst
Expand Up @@ -5,9 +5,6 @@ Product
-------

.. http:get:: /api/v1/product
.. http:post:: /api/v1/product
.. http:delete:: /api/v1/product/<id>
.. http:put:: /api/v1/product/<id>
Filtering
^^^^^^^^^
Expand All @@ -18,14 +15,39 @@ Filtering

GET /api/v1/product/?format=json&name=Firefox

.. http:get:: /api/v1/product/<id>
.. http:post:: /api/v1/product
Required Fields
^^^^^^^^^^^^^^^

:name: A string Product name.
:productversions: A list of at least one Product Version.

Optional Fields
^^^^^^^^^^^^^^^

:description: A string description.

.. http:delete:: /api/v1/product/<id>
.. note::

Deleting a Product will delete all of it's child objects.

.. http:put:: /api/v1/product/<id>
.. note::

ProductVersions are displayed in the GET results. They may be added to
or changed by a POST request, but a POST to Product will not delete
any ProductVersion.


Product Version
---------------

.. http:get:: /api/v1/productversion
.. http:post:: /api/v1/productversion
.. http:delete:: /api/v1/productversion/<id>
.. http:put:: /api/v1/productversion/<id>
Filtering
^^^^^^^^^
Expand All @@ -42,3 +64,25 @@ Filtering

GET /api/v1/productversion/?format=json&version=10
GET /api/v1/productversion/?format=json&product__name=Firefox

.. http:get:: /api/v1/productversion/<id>
.. http:post:: /api/v1/productversion
Required Fields
^^^^^^^^^^^^^^^

:version: A string ProductVersion name.
:product: A resource uri of the parent Product.

Optional Fields
^^^^^^^^^^^^^^^

:codename: A string codename.

.. http:delete:: /api/v1/productversion/<id>
.. http:put:: /api/v1/productversion/<id>
.. note::

The Product of an existing ProductVersion may not be changed.
71 changes: 71 additions & 0 deletions docs/userguide/api/environments.rst
@@ -1,6 +1,77 @@
Environment API
===============

Profile
-------

.. http:get:: /api/v1/profile
Filtering
^^^^^^^^^

:name: The ``name`` of the Profile to filter on.

.. http:get:: /api/v1/profile/<id>
.. http:post:: /api/v1/profile
Required Fields
^^^^^^^^^^^^^^^

:name: A string Profile name.

.. http:delete:: /api/v1/profile/<id>
.. http:put:: /api/v1/profile/<id>
Category
--------

.. http:get:: /api/v1/category
Filtering
^^^^^^^^^

:name: The ``name`` of the Category to filter on.

.. http:get:: /api/v1/category/<id>
.. http:post:: /api/v1/category
Required Fields
^^^^^^^^^^^^^^^

:name: A string Category name.

.. http:delete:: /api/v1/category/<id>
.. http:put:: /api/v1/category/<id>
Element
-------

.. http:get:: /api/v1/element/
Filtering
^^^^^^^^^

:name: The ``name`` of the Element to filter on.
:category: The ``id`` of the Category to filter on.
:category__name: The ``name`` of the Category to filter on.

.. http:get:: /api/v1/element/<id>
.. http:post:: /api/v1/element
Required Fields
^^^^^^^^^^^^^^^

:name: A string Element name.
:category: A resource uri to the parent Category.

.. http:delete:: /api/v1/element/<id>
.. http:put:: /api/v1/element/<id>
.. note::

The Category of an existing Element may not be changed.

Environment
-----------

Expand Down
35 changes: 27 additions & 8 deletions docs/userguide/api/tags.rst
@@ -1,23 +1,42 @@
Tags API
=============
========

Tag
--------
---

.. http:get:: /api/v1/tag
.. http:post:: /api/v1/suite
.. http:delete:: /api/v1/suite/<id>
.. http:put:: /api/v1/suite/<id>
Filtering
^^^^^^^^^

:name: The name of the tag.
:product: The id of the product.
:product__name: The name of the product
:name: The Tag ``name`` to filter on.
:product: The Product ``id`` to filter on.
:product__name: The Product ``name`` to filter on.

**Example request**:

.. sourcecode:: http

GET /api/v1/tag/?format=json

.. http:get:: /api/v1/tag/<id>
.. http:post:: /api/v1/suite
Required Fields
^^^^^^^^^^^^^^^

:name: A string name for the Tag.
:product: A resource uri to a Product.

Optional Fields
^^^^^^^^^^^^^^^

:description: A string description for the Tag.

.. http:delete:: /api/v1/suite/<id>
.. http:put:: /api/v1/suite/<id>
.. note::

The Tag's Product may not be changed unless the tag is not in use, the
product is being set to None, or the product matches the existing cases."
29 changes: 29 additions & 0 deletions moztrap/model/core/api.py
Expand Up @@ -59,6 +59,35 @@ def model(self):
return ProductVersion


@property
def read_create_fields(self):
"""product is read-only"""
return ["product"]


def obj_update(self, bundle, request=None, **kwargs):
"""Avoid concurrency error caused by the setting of latest_version"""
bundle = self.check_read_create(bundle)

try:
# use grandparent rather than parent
bundle = super(MTResource, self).obj_update(
bundle=bundle, request=request, **kwargs)

# update the cc_version
bundle.obj.cc_version = self.model.objects.get(
id=bundle.obj.id).cc_version

# specify the user
bundle.obj.save(user=request.user)

except Exception: # pragma: no cover
logger.exception("error updating %s", bundle) # pragma: no cover
raise # pragma: no cover

return bundle



class ProductResource(MTResource):
"""
Expand Down
87 changes: 75 additions & 12 deletions moztrap/model/environments/api.py
@@ -1,28 +1,91 @@
from tastypie import fields
from tastypie.resources import ModelResource, ALL
from tastypie.resources import ModelResource, ALL, ALL_WITH_RELATIONS
from ..mtapi import MTResource, MTAuthorization

from .models import Environment, Element, Category
from .models import Profile, Environment, Element, Category



class CategoryResource(ModelResource):
"""Return a list of environment categories."""
class EnvironmentAuthorization(MTAuthorization):
"""Atypically named permission."""

class Meta:
@property
def permission(self):
"""This permission should be checked by is_authorized."""
return "environments.manage_environments"



class ProfileResource(MTResource):
"""Create, Read, Update, and Delete capabilities for Profile."""

class Meta(MTResource.Meta):
queryset = Profile.objects.all()
fields = ["id", "name"]
authorization = EnvironmentAuthorization()
ordering = ["id", "name"]
filtering = {
"name": ALL,
}

@property
def model(self):
"""Model class related to this resource."""
return Profile



class CategoryResource(MTResource):
"""Create, Read, Update and Delete capabilities for Category."""

elements = fields.ToManyField(
"moztrap.model.environments.api.ElementResource",
"elements",
full=True,
readonly=True
)

class Meta(MTResource.Meta):
queryset = Category.objects.all()
list_allowed_methods = ['get']
fields = ["id", "name"]
authorization = EnvironmentAuthorization()
ordering = ["id", "name"]
filtering = {
"name": ALL,
}

@property
def model(self):
"""Model class related to this resource."""
return Category

class ElementResource(ModelResource):
"""Return a list of environment elements."""

category = fields.ForeignKey(CategoryResource, "category", full=True)

class Meta:
class ElementResource(MTResource):
"""Create, Read, Update and Delete capabilities for Element."""

category = fields.ForeignKey(CategoryResource, "category")

class Meta(MTResource.Meta):
queryset = Element.objects.all()
list_allowed_methods = ['get']
fields = ["id", "name"]
fields = ["id", "name", "category"]
authorization = EnvironmentAuthorization()
filtering = {
"category": ALL_WITH_RELATIONS,
"name": ALL,
}
ordering = ["id", "name"]


@property
def model(self):
"""Model class related to this resource."""
return Element

@property
def read_create_fields(self):
"""List of fields that are required for create but read-only for update."""
return ["category"]



Expand Down

0 comments on commit 2893b95

Please sign in to comment.