diff options
| -rwxr-xr-x | docs/api-guide/authentication.md | 8 | ||||
| -rw-r--r-- | docs/topics/2.4-announcement.md | 4 | ||||
| -rw-r--r-- | docs/topics/contributing.md | 8 | ||||
| -rw-r--r-- | docs/topics/third-party-resources.md | 1 | ||||
| -rw-r--r-- | rest_framework/routers.py | 5 | ||||
| -rw-r--r-- | rest_framework/serializers.py | 6 | ||||
| -rw-r--r-- | tox.ini | 2 | 
7 files changed, 25 insertions, 9 deletions
| diff --git a/docs/api-guide/authentication.md b/docs/api-guide/authentication.md index 0ec5bad1..3a5156fd 100755 --- a/docs/api-guide/authentication.md +++ b/docs/api-guide/authentication.md @@ -168,12 +168,13 @@ The `curl` command line tool may be useful for testing token authenticated APIs.  If you want every user to have an automatically generated Token, you can simply catch the User's `post_save` signal. +    from django.conf import settings      from django.contrib.auth import get_user_model      from django.db.models.signals import post_save      from django.dispatch import receiver      from rest_framework.authtoken.models import Token -    @receiver(post_save, sender=get_user_model()) +    @receiver(post_save, sender=settings.AUTH_USER_MODEL)      def create_auth_token(sender, instance=None, created=False, **kwargs):          if created:              Token.objects.create(user=instance) @@ -415,6 +416,10 @@ The [HawkREST][hawkrest] library builds on the [Mohawk][mohawk] library to let y  HTTP Signature (currently a [IETF draft][http-signature-ietf-draft]) provides a way to achieve origin authentication and message integrity for HTTP messages. Similar to [Amazon's HTTP Signature scheme][amazon-http-signature], used by many of its services, it permits stateless, per-request authentication. [Elvio Toccalino][etoccalino] maintains the [djangorestframework-httpsignature][djangorestframework-httpsignature] package which provides an easy to use HTTP Signature Authentication mechanism. +## Djoser + +[Djoser][djoser] library provides a set of views to handle basic actions such as registration, login, logout, password reset and account activation. The package works with a custom user model and it uses token based authentication. This is a ready to use REST implementation of Django authentication system. +  [cite]: http://jacobian.org/writing/rest-worst-practices/  [http401]: http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html#sec10.4.2  [http403]: http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html#sec10.4.4 @@ -449,3 +454,4 @@ HTTP Signature (currently a [IETF draft][http-signature-ietf-draft]) provides a  [hawk]: https://github.com/hueniverse/hawk  [mohawk]: http://mohawk.readthedocs.org/en/latest/  [mac]: http://tools.ietf.org/html/draft-hammer-oauth-v2-mac-token-05 +[djoser]: https://github.com/sunscrapers/djoser diff --git a/docs/topics/2.4-announcement.md b/docs/topics/2.4-announcement.md index 09294b91..8e4f3bb2 100644 --- a/docs/topics/2.4-announcement.md +++ b/docs/topics/2.4-announcement.md @@ -164,8 +164,8 @@ Once again, many thanks to all the generous [backers and sponsors][kickstarter-s  [lts-releases]: https://docs.djangoproject.com/en/dev/internals/release-process/#long-term-support-lts-releases  [2-4-release-notes]: release-notes#240 -[view-name-and-description-settings]: ../api-guide/settings/#view-names-and-descriptions -[client-ip-identification]: ../api-guide/throttling/#how-clients-are-identified +[view-name-and-description-settings]: ../api-guide/settings#view-names-and-descriptions +[client-ip-identification]: ../api-guide/throttling#how-clients-are-identified  [2-3-announcement]: 2.3-announcement  [github-labels]: https://github.com/tomchristie/django-rest-framework/issues  [github-milestones]: https://github.com/tomchristie/django-rest-framework/milestones diff --git a/docs/topics/contributing.md b/docs/topics/contributing.md index 3400bc8f..4fafb1b1 100644 --- a/docs/topics/contributing.md +++ b/docs/topics/contributing.md @@ -210,7 +210,9 @@ We recommend the [`django-reusable-app`][django-reusable-app] template as a good  ## Linking to your package -Once your package is decently documented and available on PyPI open a pull request or issue, and we'll add a link to it from the main REST framework documentation. +Once your package is decently documented and available on PyPI open a pull request or issue, and we'll add a link to it from the main REST framework documentation. You can add your package under **Third party packages** of the API Guide section that best applies, like [Authentication][authentication] or [Permissions][permissions]. You can also link your package under the [Third Party Resources][third-party-resources] section. + +We also suggest adding it to the [REST Framework][rest-framework-grid] grid on Django Packages.  [cite]: http://www.w3.org/People/Berners-Lee/FAQ.html  [code-of-conduct]: https://www.djangoproject.com/conduct/ @@ -225,3 +227,7 @@ Once your package is decently documented and available on PyPI open a pull reque  [docs]: https://github.com/tomchristie/django-rest-framework/tree/master/docs  [mou]: http://mouapp.com/  [django-reusable-app]: https://github.com/dabapps/django-reusable-app +[authentication]: ../api-guide/authentication.md +[permissions]: ../api-guide/permissions.md +[third-party-resources]: third-party-resources.md +[rest-framework-grid]: https://www.djangopackages.com/grids/g/django-rest-framework/ diff --git a/docs/topics/third-party-resources.md b/docs/topics/third-party-resources.md index 1ca91742..0317dd64 100644 --- a/docs/topics/third-party-resources.md +++ b/docs/topics/third-party-resources.md @@ -16,6 +16,7 @@ To submit new content, [open an issue](https://github.com/tomchristie/django-res  * [djangorestframework-jwt](https://github.com/GetBlimp/django-rest-framework-jwt) - Provides JSON Web Token Authentication support.  * [hawkrest](https://github.com/kumar303/hawkrest) - Provides Hawk HTTP Authorization.  * [djangorestframework-httpsignature](https://github.com/etoccalino/django-rest-framework-httpsignature) - Provides an easy to use HTTP Signature Authentication mechanism. +* [djoser](https://github.com/sunscrapers/djoser) - Provides a set of views to handle basic actions such as registration, login, logout, password reset and account activation.  ### Permissions diff --git a/rest_framework/routers.py b/rest_framework/routers.py index f2d06211..169e6e8b 100644 --- a/rest_framework/routers.py +++ b/rest_framework/routers.py @@ -20,6 +20,7 @@ from collections import namedtuple  from django.conf.urls import patterns, url  from django.core.exceptions import ImproperlyConfigured  from django.core.urlresolvers import NoReverseMatch +from django.utils.datastructures import SortedDict  from rest_framework import views  from rest_framework.response import Response  from rest_framework.reverse import reverse @@ -277,7 +278,7 @@ class DefaultRouter(SimpleRouter):          """          Return a view to use as the API root.          """ -        api_root_dict = {} +        api_root_dict = SortedDict()          list_name = self.routes[0].name          for prefix, viewset, basename in self.registry:              api_root_dict[prefix] = list_name.format(basename=basename) @@ -286,7 +287,7 @@ class DefaultRouter(SimpleRouter):              _ignore_model_permissions = True              def get(self, request, *args, **kwargs): -                ret = {} +                ret = SortedDict()                  for key, url_name in api_root_dict.items():                      try:                          ret[key] = reverse( diff --git a/rest_framework/serializers.py b/rest_framework/serializers.py index b3db3582..d24cb99d 100644 --- a/rest_framework/serializers.py +++ b/rest_framework/serializers.py @@ -845,7 +845,7 @@ class ModelSerializer(Serializer):          }          if model_field: -            kwargs['required'] = not(model_field.null or model_field.blank) +            kwargs['required'] = not(model_field.null or model_field.blank) and model_field.editable              if model_field.help_text is not None:                  kwargs['help_text'] = model_field.help_text              if model_field.verbose_name is not None: @@ -868,7 +868,7 @@ class ModelSerializer(Serializer):          """          kwargs = {} -        if model_field.null or model_field.blank: +        if model_field.null or model_field.blank and model_field.editable:              kwargs['required'] = False          if isinstance(model_field, models.AutoField) or not model_field.editable: @@ -1126,7 +1126,7 @@ class HyperlinkedModelSerializer(ModelSerializer):          }          if model_field: -            kwargs['required'] = not(model_field.null or model_field.blank) +            kwargs['required'] = not(model_field.null or model_field.blank) and model_field.editable              if model_field.help_text is not None:                  kwargs['help_text'] = model_field.help_text              if model_field.verbose_name is not None: @@ -9,6 +9,8 @@ envlist =  [testenv]  commands = ./runtests.py --fast +setenv = +       PYTHONDONTWRITEBYTECODE=1  [testenv:flake8]  basepython = python2.7 | 
