root / api / emitter.py @ ed66d976
History | View | Annotate | Download (1.8 kB)
1 | 00b4f1be | Faidon Liambotis | # vim: ts=4 sts=4 et ai sw=4 fileencoding=utf-8
|
---|---|---|---|
2 | 00b4f1be | Faidon Liambotis | #
|
3 | 00b4f1be | Faidon Liambotis | # Copyright © 2010 Greek Research and Technology Network
|
4 | 00b4f1be | Faidon Liambotis | #
|
5 | 00b4f1be | Faidon Liambotis | |
6 | 00b4f1be | Faidon Liambotis | from piston.resource import Resource as BaseResource |
7 | 00b4f1be | Faidon Liambotis | import re |
8 | 00b4f1be | Faidon Liambotis | |
9 | 00b4f1be | Faidon Liambotis | _accept_re = re.compile(r'([^\s;,]+)(?:[^,]*?;\s*q=(\d*(?:\.\d+)?))?')
|
10 | 00b4f1be | Faidon Liambotis | |
11 | 00b4f1be | Faidon Liambotis | def parse_accept_header(value): |
12 | 00b4f1be | Faidon Liambotis | """Parse an HTTP Accept header
|
13 | 00b4f1be | Faidon Liambotis |
|
14 | 00b4f1be | Faidon Liambotis | Returns an ordered by quality list of tuples (value, quality)
|
15 | 00b4f1be | Faidon Liambotis | """
|
16 | 00b4f1be | Faidon Liambotis | if not value: |
17 | 00b4f1be | Faidon Liambotis | return []
|
18 | 00b4f1be | Faidon Liambotis | |
19 | 00b4f1be | Faidon Liambotis | result = [] |
20 | 00b4f1be | Faidon Liambotis | for match in _accept_re.finditer(value): |
21 | 00b4f1be | Faidon Liambotis | quality = match.group(2)
|
22 | 00b4f1be | Faidon Liambotis | if not quality: |
23 | 00b4f1be | Faidon Liambotis | quality = 1
|
24 | 00b4f1be | Faidon Liambotis | else:
|
25 | 00b4f1be | Faidon Liambotis | quality = max(min(float(quality), 1), 0) |
26 | 00b4f1be | Faidon Liambotis | result.append((match.group(1), quality))
|
27 | 00b4f1be | Faidon Liambotis | |
28 | 00b4f1be | Faidon Liambotis | # sort by quality
|
29 | 00b4f1be | Faidon Liambotis | result.sort(key=lambda x: x[1]) |
30 | 00b4f1be | Faidon Liambotis | |
31 | 00b4f1be | Faidon Liambotis | return result
|
32 | 00b4f1be | Faidon Liambotis | |
33 | 00b4f1be | Faidon Liambotis | # XXX: works as intended but not used since piston's XMLEmitter doesn't output
|
34 | 00b4f1be | Faidon Liambotis | # XML according to our spec :(
|
35 | 00b4f1be | Faidon Liambotis | class Resource(BaseResource): |
36 | 00b4f1be | Faidon Liambotis | def determine_emitter(self, request, *args, **kwargs): |
37 | 00b4f1be | Faidon Liambotis | """
|
38 | 00b4f1be | Faidon Liambotis | Override default emitter policy to account for Accept header
|
39 | 00b4f1be | Faidon Liambotis |
|
40 | 00b4f1be | Faidon Liambotis | emitter_format (.json or .xml suffix in URL) always takes precedence.
|
41 | 00b4f1be | Faidon Liambotis |
|
42 | 00b4f1be | Faidon Liambotis | After that, the Accept header is checked; if both JSON and XML are
|
43 | 00b4f1be | Faidon Liambotis | equally preferred, use JSON.
|
44 | 00b4f1be | Faidon Liambotis |
|
45 | 00b4f1be | Faidon Liambotis | If none of the two were provided, then use JSON as per the
|
46 | 00b4f1be | Faidon Liambotis | specification.
|
47 | 00b4f1be | Faidon Liambotis | """
|
48 | 00b4f1be | Faidon Liambotis | |
49 | 00b4f1be | Faidon Liambotis | em = request.GET.get('format', 'xml') |
50 | 00b4f1be | Faidon Liambotis | if 'emitter_format' in kwargs: |
51 | 00b4f1be | Faidon Liambotis | em = kwargs.pop('emitter_format')
|
52 | 00b4f1be | Faidon Liambotis | elif 'HTTP_ACCEPT' in request.META: |
53 | 00b4f1be | Faidon Liambotis | accepts = parse_accept_header(request.META['HTTP_ACCEPT'])
|
54 | 00b4f1be | Faidon Liambotis | for content_type, quality in accepts: |
55 | 00b4f1be | Faidon Liambotis | if content_type == 'application/json': |
56 | 00b4f1be | Faidon Liambotis | break
|
57 | 00b4f1be | Faidon Liambotis | elif content_type == 'application/xml': |
58 | 00b4f1be | Faidon Liambotis | em = request.GET.get('format', 'xml') |
59 | 00b4f1be | Faidon Liambotis | break
|
60 | 00b4f1be | Faidon Liambotis | |
61 | 00b4f1be | Faidon Liambotis | return em |