Skip to content

Commit f56ec95

Browse files
authored
Fix hierarchy of headers a few pages in the documentation (#9909)
1 parent 8d4c2d0 commit f56ec95

28 files changed

+497
-516
lines changed

docs/api-guide/authentication.md

Lines changed: 29 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,6 @@ source:
33
- authentication.py
44
---
55

6-
# Authentication
7-
86
> Auth needs to be pluggable.
97
>
108
> — Jacob Kaplan-Moss, ["REST worst practices"][cite]
@@ -104,9 +102,9 @@ If you are deploying to Apache, and using any non-session based authentication,
104102

105103
---
106104

107-
# API Reference
105+
## API Reference
108106

109-
## BasicAuthentication
107+
### BasicAuthentication
110108

111109
This authentication scheme uses [HTTP Basic Authentication][basicauth], signed against a user's username and password. Basic authentication is generally only appropriate for testing.
112110

@@ -122,7 +120,7 @@ Unauthenticated responses that are denied permission will result in an `HTTP 401
122120
!!! note
123121
If you use `BasicAuthentication` in production you must ensure that your API is only available over `https`. You should also ensure that your API clients will always re-request the username and password at login, and will never store those details to persistent storage.
124122

125-
## TokenAuthentication
123+
### TokenAuthentication
126124

127125
!!! note
128126
The token authentication provided by Django REST framework is a fairly simple implementation.
@@ -171,9 +169,9 @@ The `curl` command line tool may be useful for testing token authenticated APIs.
171169
!!! note
172170
If you use `TokenAuthentication` in production you must ensure that your API is only available over `https`.
173171

174-
### Generating Tokens
172+
#### Generating Tokens
175173

176-
#### By using signals
174+
##### By using signals
177175

178176
If you want every user to have an automatically generated Token, you can simply catch the User's `post_save` signal.
179177

@@ -197,7 +195,7 @@ If you've already created some users, you can generate tokens for all existing u
197195
for user in User.objects.all():
198196
Token.objects.get_or_create(user=user)
199197

200-
#### By exposing an api endpoint
198+
##### By exposing an api endpoint
201199

202200
When using `TokenAuthentication`, you may want to provide a mechanism for clients to obtain a token given the username and password. REST framework provides a built-in view to provide this behavior. To use it, add the `obtain_auth_token` view to your URLconf:
203201

@@ -246,7 +244,7 @@ And in your `urls.py`:
246244
]
247245

248246

249-
#### With Django admin
247+
##### With Django admin
250248

251249
It is also possible to create Tokens manually through the admin interface. In case you are using a large user base, we recommend that you monkey patch the `TokenAdmin` class to customize it to your needs, more specifically by declaring the `user` field as `raw_field`.
252250

@@ -257,7 +255,7 @@ It is also possible to create Tokens manually through the admin interface. In ca
257255
TokenAdmin.raw_id_fields = ['user']
258256

259257

260-
#### Using Django manage.py command
258+
##### Using Django manage.py command
261259

262260
Since version 3.6.4 it's possible to generate a user token using the following command:
263261

@@ -272,7 +270,7 @@ In case you want to regenerate the token (for example if it has been compromised
272270
./manage.py drf_create_token -r <username>
273271

274272

275-
## SessionAuthentication
273+
### SessionAuthentication
276274

277275
This authentication scheme uses Django's default session backend for authentication. Session authentication is appropriate for AJAX clients that are running in the same session context as your website.
278276

@@ -291,7 +289,7 @@ If you're using an AJAX-style API with SessionAuthentication, you'll need to mak
291289
CSRF validation in REST framework works slightly differently from standard Django due to the need to support both session and non-session based authentication to the same views. This means that only authenticated requests require CSRF tokens, and anonymous requests may be sent without CSRF tokens. This behavior is not suitable for login views, which should always have CSRF validation applied.
292290

293291

294-
## RemoteUserAuthentication
292+
### RemoteUserAuthentication
295293

296294
This authentication scheme allows you to delegate authentication to your web server, which sets the `REMOTE_USER`
297295
environment variable.
@@ -312,7 +310,7 @@ Consult your web server's documentation for information about configuring an aut
312310
* [NGINX (Restricting Access)](https://docs.nginx.com/nginx/admin-guide/security-controls/configuring-http-basic-authentication/)
313311

314312

315-
# Custom authentication
313+
## Custom authentication
316314

317315
To implement a custom authentication scheme, subclass `BaseAuthentication` and override the `.authenticate(self, request)` method. The method should return a two-tuple of `(user, auth)` if authentication succeeds, or `None` otherwise.
318316

@@ -330,7 +328,7 @@ If the `.authenticate_header()` method is not overridden, the authentication sch
330328
!!! note
331329
When your custom authenticator is invoked by the request object's `.user` or `.auth` properties, you may see an `AttributeError` re-raised as a `WrappedAttributeError`. This is necessary to prevent the original exception from being suppressed by the outer property access. Python will not recognize that the `AttributeError` originates from your custom authenticator and will instead assume that the request object does not have a `.user` or `.auth` property. These errors should be fixed or otherwise handled by your authenticator.
332330

333-
## Example
331+
### Example
334332

335333
The following example will authenticate any incoming request as the user given by the username in a custom request header named 'X-USERNAME'.
336334

@@ -353,19 +351,19 @@ The following example will authenticate any incoming request as the user given b
353351

354352
---
355353

356-
# Third party packages
354+
## Third party packages
357355

358356
The following third-party packages are also available.
359357

360-
## django-rest-knox
358+
### django-rest-knox
361359

362360
[Django-rest-knox][django-rest-knox] library provides models and views to handle token-based authentication in a more secure and extensible way than the built-in TokenAuthentication scheme - with Single Page Applications and Mobile clients in mind. It provides per-client tokens, and views to generate them when provided some other authentication (usually basic authentication), to delete the token (providing a server enforced logout) and to delete all tokens (logs out all clients that a user is logged into).
363361

364-
## Django OAuth Toolkit
362+
### Django OAuth Toolkit
365363

366364
The [Django OAuth Toolkit][django-oauth-toolkit] package provides OAuth 2.0 support and works with Python 3.4+. The package is maintained by [jazzband][jazzband] and uses the excellent [OAuthLib][oauthlib]. The package is well documented, and well supported and is currently our **recommended package for OAuth 2.0 support**.
367365

368-
### Installation & configuration
366+
#### Installation & configuration
369367

370368
Install using `pip`.
371369

@@ -386,42 +384,42 @@ Add the package to your `INSTALLED_APPS` and modify your REST framework settings
386384

387385
For more details see the [Django REST framework - Getting started][django-oauth-toolkit-getting-started] documentation.
388386

389-
## Django REST framework OAuth
387+
### Django REST framework OAuth
390388

391389
The [Django REST framework OAuth][django-rest-framework-oauth] package provides both OAuth1 and OAuth2 support for REST framework.
392390

393391
This package was previously included directly in the REST framework but is now supported and maintained as a third-party package.
394392

395-
### Installation & configuration
393+
#### Installation & configuration
396394

397395
Install the package using `pip`.
398396

399397
pip install djangorestframework-oauth
400398

401399
For details on configuration and usage see the Django REST framework OAuth documentation for [authentication][django-rest-framework-oauth-authentication] and [permissions][django-rest-framework-oauth-permissions].
402400

403-
## JSON Web Token Authentication
401+
### JSON Web Token Authentication
404402

405403
JSON Web Token is a fairly new standard which can be used for token-based authentication. Unlike the built-in TokenAuthentication scheme, JWT Authentication doesn't need to use a database to validate a token. A package for JWT authentication is [djangorestframework-simplejwt][djangorestframework-simplejwt] which provides some features as well as a pluggable token blacklist app.
406404

407-
## Hawk HTTP Authentication
405+
### Hawk HTTP Authentication
408406

409407
The [HawkREST][hawkrest] library builds on the [Mohawk][mohawk] library to let you work with [Hawk][hawk] signed requests and responses in your API. [Hawk][hawk] lets two parties securely communicate with each other using messages signed by a shared key. It is based on [HTTP MAC access authentication][mac] (which was based on parts of [OAuth 1.0][oauth-1.0a]).
410408

411-
## HTTP Signature Authentication
409+
### HTTP Signature Authentication
412410

413411
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] (outdated) package which provides an easy-to-use HTTP Signature Authentication mechanism. You can use the updated fork version of [djangorestframework-httpsignature][djangorestframework-httpsignature], which is [drf-httpsig][drf-httpsig].
414412

415-
## Djoser
413+
### Djoser
416414

417415
[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 uses token-based authentication. This is a ready to use REST implementation of the Django authentication system.
418416

419-
## DRF Auth Kit
417+
### DRF Auth Kit
420418

421419
[DRF Auth Kit][drf-auth-kit] library provides a modern REST authentication solution with JWT cookies, social login, multi-factor authentication, and comprehensive user management. The package offers full type safety, automatic OpenAPI schema generation with DRF Spectacular. It supports multiple authentication types (JWT, DRF Token, or Custom) and includes built-in internationalization for 50+ languages.
422420

423421

424-
## django-rest-auth / dj-rest-auth
422+
### django-rest-auth / dj-rest-auth
425423

426424
This library provides a set of REST API endpoints for registration, authentication (including social media authentication), password reset, retrieve and update user details, etc. By having these API endpoints, your client apps such as AngularJS, iOS, Android, and others can communicate to your Django backend site independently via REST APIs for user management.
427425

@@ -431,25 +429,25 @@ There are currently two forks of this project.
431429
* [Django-rest-auth][django-rest-auth] is the original project, [but is not currently receiving updates](https://github.com/Tivix/django-rest-auth/issues/568).
432430
* [Dj-rest-auth][dj-rest-auth] is a newer fork of the project.
433431

434-
## drf-social-oauth2
432+
### drf-social-oauth2
435433

436434
[Drf-social-oauth2][drf-social-oauth2] is a framework that helps you authenticate with major social oauth2 vendors, such as Facebook, Google, Twitter, Orcid, etc. It generates tokens in a JWTed way with an easy setup.
437435

438-
## drfpasswordless
436+
### drfpasswordless
439437

440438
[drfpasswordless][drfpasswordless] adds (Medium, Square Cash inspired) passwordless support to Django REST Framework's TokenAuthentication scheme. Users log in and sign up with a token sent to a contact point like an email address or a mobile number.
441439

442-
## django-rest-authemail
440+
### django-rest-authemail
443441

444442
[django-rest-authemail][django-rest-authemail] provides a RESTful API interface for user signup and authentication. Email addresses are used for authentication, rather than usernames. API endpoints are available for signup, signup email verification, login, logout, password reset, password reset verification, email change, email change verification, password change, and user detail. A fully functional example project and detailed instructions are included.
445443

446-
## Django-Rest-Durin
444+
### Django-Rest-Durin
447445

448446
[Django-Rest-Durin][django-rest-durin] is built with the idea to have one library that does token auth for multiple Web/CLI/Mobile API clients via one interface but allows different token configuration for each API Client that consumes the API. It provides support for multiple tokens per user via custom models, views, permissions that work with Django-Rest-Framework. The token expiration time can be different per API client and is customizable via the Django Admin Interface.
449447

450448
More information can be found in the [Documentation](https://django-rest-durin.readthedocs.io/en/latest/index.html).
451449

452-
## django-pyoidc
450+
### django-pyoidc
453451

454452
[django_pyoidc][django-pyoidc] adds support for OpenID Connect (OIDC) authentication. This allows you to delegate user management to an Identity Provider, which can be used to implement Single-Sign-On (SSO). It provides support for most uses-cases, such as customizing how token info are mapped to user models, using OIDC audiences for access control, etc.
455453

docs/api-guide/content-negotiation.md

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,6 @@ source:
33
- negotiation.py
44
---
55

6-
# Content negotiation
7-
86
> HTTP has provisions for several mechanisms for "content negotiation" - the process of selecting the best representation for a given response when there are multiple representations available.
97
>
108
> &mdash; [RFC 2616][cite], Fielding et al.
@@ -40,7 +38,7 @@ For more information on the `HTTP Accept` header, see [RFC 2616][accept-header]
4038

4139
This is a valid approach as the HTTP spec deliberately underspecifies how a server should weight server-based preferences against client-based preferences.
4240

43-
# Custom content negotiation
41+
## Custom content negotiation
4442

4543
It's unlikely that you'll want to provide a custom content negotiation scheme for REST framework, but you can do so if needed. To implement a custom content negotiation scheme override `BaseContentNegotiation`.
4644

@@ -50,7 +48,7 @@ The `select_parser()` method should return one of the parser instances from the
5048

5149
The `select_renderer()` method should return a two-tuple of (renderer instance, media type), or raise a `NotAcceptable` exception.
5250

53-
## Example
51+
### Example
5452

5553
The following is a custom content negotiation class which ignores the client
5654
request when selecting the appropriate parser or renderer.
@@ -70,7 +68,7 @@ request when selecting the appropriate parser or renderer.
7068
"""
7169
return (renderers[0], renderers[0].media_type)
7270

73-
## Setting the content negotiation
71+
### Setting the content negotiation
7472

7573
The default content negotiation class may be set globally, using the `DEFAULT_CONTENT_NEGOTIATION_CLASS` setting. For example, the following settings would use our example `IgnoreClientContentNegotiation` class.
7674

docs/api-guide/exceptions.md

Lines changed: 17 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -93,9 +93,9 @@ Note that the exception handler will only be called for responses generated by r
9393

9494
---
9595

96-
# API Reference
96+
## API Reference
9797

98-
## APIException
98+
### APIException
9999

100100
**Signature:** `APIException()`
101101

@@ -143,79 +143,79 @@ dictionary of items:
143143
>>> print(exc.get_full_details())
144144
{"name":{"message":"This field is required.","code":"required"},"age":{"message":"A valid integer is required.","code":"invalid"}}
145145

146-
## ParseError
146+
### ParseError
147147

148148
**Signature:** `ParseError(detail=None, code=None)`
149149

150150
Raised if the request contains malformed data when accessing `request.data`.
151151

152152
By default this exception results in a response with the HTTP status code "400 Bad Request".
153153

154-
## AuthenticationFailed
154+
### AuthenticationFailed
155155

156156
**Signature:** `AuthenticationFailed(detail=None, code=None)`
157157

158158
Raised when an incoming request includes incorrect authentication.
159159

160160
By default this exception results in a response with the HTTP status code "401 Unauthenticated", but it may also result in a "403 Forbidden" response, depending on the authentication scheme in use. See the [authentication documentation][authentication] for more details.
161161

162-
## NotAuthenticated
162+
### NotAuthenticated
163163

164164
**Signature:** `NotAuthenticated(detail=None, code=None)`
165165

166166
Raised when an unauthenticated request fails the permission checks.
167167

168168
By default this exception results in a response with the HTTP status code "401 Unauthenticated", but it may also result in a "403 Forbidden" response, depending on the authentication scheme in use. See the [authentication documentation][authentication] for more details.
169169

170-
## PermissionDenied
170+
### PermissionDenied
171171

172172
**Signature:** `PermissionDenied(detail=None, code=None)`
173173

174174
Raised when an authenticated request fails the permission checks.
175175

176176
By default this exception results in a response with the HTTP status code "403 Forbidden".
177177

178-
## NotFound
178+
### NotFound
179179

180180
**Signature:** `NotFound(detail=None, code=None)`
181181

182182
Raised when a resource does not exist at the given URL. This exception is equivalent to the standard `Http404` Django exception.
183183

184184
By default this exception results in a response with the HTTP status code "404 Not Found".
185185

186-
## MethodNotAllowed
186+
### MethodNotAllowed
187187

188188
**Signature:** `MethodNotAllowed(method, detail=None, code=None)`
189189

190190
Raised when an incoming request occurs that does not map to a handler method on the view.
191191

192192
By default this exception results in a response with the HTTP status code "405 Method Not Allowed".
193193

194-
## NotAcceptable
194+
### NotAcceptable
195195

196196
**Signature:** `NotAcceptable(detail=None, code=None)`
197197

198198
Raised when an incoming request occurs with an `Accept` header that cannot be satisfied by any of the available renderers.
199199

200200
By default this exception results in a response with the HTTP status code "406 Not Acceptable".
201201

202-
## UnsupportedMediaType
202+
### UnsupportedMediaType
203203

204204
**Signature:** `UnsupportedMediaType(media_type, detail=None, code=None)`
205205

206206
Raised if there are no parsers that can handle the content type of the request data when accessing `request.data`.
207207

208208
By default this exception results in a response with the HTTP status code "415 Unsupported Media Type".
209209

210-
## Throttled
210+
### Throttled
211211

212212
**Signature:** `Throttled(wait=None, detail=None, code=None)`
213213

214214
Raised when an incoming request fails the throttling checks.
215215

216216
By default this exception results in a response with the HTTP status code "429 Too Many Requests".
217217

218-
## ValidationError
218+
### ValidationError
219219

220220
**Signature:** `ValidationError(detail=None, code=None)`
221221

@@ -235,35 +235,35 @@ By default this exception results in a response with the HTTP status code "400 B
235235

236236
---
237237

238-
# Generic Error Views
238+
## Generic Error Views
239239

240240
Django REST Framework provides two error views suitable for providing generic JSON `500` Server Error and
241241
`400` Bad Request responses. (Django's default error views provide HTML responses, which may not be appropriate for an
242242
API-only application.)
243243

244244
Use these as per [Django's Customizing error views documentation][django-custom-error-views].
245245

246-
## `rest_framework.exceptions.server_error`
246+
### `rest_framework.exceptions.server_error`
247247

248248
Returns a response with status code `500` and `application/json` content type.
249249

250250
Set as `handler500`:
251251

252252
handler500 = 'rest_framework.exceptions.server_error'
253253

254-
## `rest_framework.exceptions.bad_request`
254+
### `rest_framework.exceptions.bad_request`
255255

256256
Returns a response with status code `400` and `application/json` content type.
257257

258258
Set as `handler400`:
259259

260260
handler400 = 'rest_framework.exceptions.bad_request'
261261

262-
# Third party packages
262+
## Third party packages
263263

264264
The following third-party packages are also available.
265265

266-
## DRF Standardized Errors
266+
### DRF Standardized Errors
267267

268268
The [drf-standardized-errors][drf-standardized-errors] package provides an exception handler that generates the same format for all 4xx and 5xx responses. It is a drop-in replacement for the default exception handler and allows customizing the error response format without rewriting the whole exception handler. The standardized error response format is easier to document and easier to handle by API consumers.
269269

0 commit comments

Comments
 (0)