OLD | NEW |
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 library http_parser.media_type; | 5 library http_parser.media_type; |
6 | 6 |
7 import 'package:collection/collection.dart'; | 7 import 'package:collection/collection.dart'; |
8 import 'package:string_scanner/string_scanner.dart'; | 8 import 'package:string_scanner/string_scanner.dart'; |
9 | 9 |
| 10 import 'case_insensitive_map.dart'; |
10 import 'scan.dart'; | 11 import 'scan.dart'; |
11 import 'utils.dart'; | 12 import 'utils.dart'; |
12 | 13 |
13 /// A regular expression matching a character that needs to be backslash-escaped | 14 /// A regular expression matching a character that needs to be backslash-escaped |
14 /// in a quoted string. | 15 /// in a quoted string. |
15 final _escapedChar = new RegExp(r'["\x00-\x1F\x7F]'); | 16 final _escapedChar = new RegExp(r'["\x00-\x1F\x7F]'); |
16 | 17 |
17 /// A class representing an HTTP media type, as used in Accept and Content-Type | 18 /// A class representing an HTTP media type, as used in Accept and Content-Type |
18 /// headers. | 19 /// headers. |
19 /// | 20 /// |
20 /// This is immutable; new instances can be created based on an old instance by | 21 /// This is immutable; new instances can be created based on an old instance by |
21 /// calling [change]. | 22 /// calling [change]. |
22 class MediaType { | 23 class MediaType { |
23 /// The primary identifier of the MIME type. | 24 /// The primary identifier of the MIME type. |
| 25 /// |
| 26 /// This is always lowercase. |
24 final String type; | 27 final String type; |
25 | 28 |
26 /// The secondary identifier of the MIME type. | 29 /// The secondary identifier of the MIME type. |
| 30 /// |
| 31 /// This is always lowercase. |
27 final String subtype; | 32 final String subtype; |
28 | 33 |
29 /// The parameters to the media type. | 34 /// The parameters to the media type. |
30 /// | 35 /// |
31 /// This map is immutable. | 36 /// This map is immutable and the keys are case-insensitive. |
32 final Map<String, String> parameters; | 37 final Map<String, String> parameters; |
33 | 38 |
34 /// The media type's MIME type. | 39 /// The media type's MIME type. |
35 String get mimeType => "$type/$subtype"; | 40 String get mimeType => "$type/$subtype"; |
36 | 41 |
37 /// Parses a media type. | 42 /// Parses a media type. |
38 /// | 43 /// |
39 /// This will throw a FormatError if the media type is invalid. | 44 /// This will throw a FormatError if the media type is invalid. |
40 factory MediaType.parse(String mediaType) { | 45 factory MediaType.parse(String mediaType) { |
41 // This parsing is based on sections 3.6 and 3.7 of the HTTP spec: | 46 // This parsing is based on sections 3.6 and 3.7 of the HTTP spec: |
(...skipping 24 matching lines...) Expand all Loading... |
66 | 71 |
67 scanner.scan(whitespace); | 72 scanner.scan(whitespace); |
68 parameters[attribute] = value; | 73 parameters[attribute] = value; |
69 } | 74 } |
70 | 75 |
71 scanner.expectDone(); | 76 scanner.expectDone(); |
72 return new MediaType(type, subtype, parameters); | 77 return new MediaType(type, subtype, parameters); |
73 }); | 78 }); |
74 } | 79 } |
75 | 80 |
76 MediaType(this.type, this.subtype, [Map<String, String> parameters]) | 81 MediaType(String type, String subtype, [Map<String, String> parameters]) |
77 : this.parameters = new UnmodifiableMapView( | 82 : type = type.toLowerCase(), |
78 parameters == null ? {} : new Map.from(parameters)); | 83 subtype = subtype.toLowerCase(), |
| 84 parameters = new UnmodifiableMapView( |
| 85 parameters == null ? {} : new CaseInsensitiveMap.from(parameters)); |
79 | 86 |
80 /// Returns a copy of this [MediaType] with some fields altered. | 87 /// Returns a copy of this [MediaType] with some fields altered. |
81 /// | 88 /// |
82 /// [type] and [subtype] alter the corresponding fields. [mimeType] is parsed | 89 /// [type] and [subtype] alter the corresponding fields. [mimeType] is parsed |
83 /// and alters both the [type] and [subtype] fields; it cannot be passed along | 90 /// and alters both the [type] and [subtype] fields; it cannot be passed along |
84 /// with [type] or [subtype]. | 91 /// with [type] or [subtype]. |
85 /// | 92 /// |
86 /// [parameters] overwrites and adds to the corresponding field. If | 93 /// [parameters] overwrites and adds to the corresponding field. If |
87 /// [clearParameters] is passed, it replaces the corresponding field entirely | 94 /// [clearParameters] is passed, it replaces the corresponding field entirely |
88 /// instead. | 95 /// instead. |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
136 value.replaceAllMapped(_escapedChar, (match) => "\\" + match[0])) | 143 value.replaceAllMapped(_escapedChar, (match) => "\\" + match[0])) |
137 ..write('"'); | 144 ..write('"'); |
138 } else { | 145 } else { |
139 buffer.write(value); | 146 buffer.write(value); |
140 } | 147 } |
141 }); | 148 }); |
142 | 149 |
143 return buffer.toString(); | 150 return buffer.toString(); |
144 } | 151 } |
145 } | 152 } |
OLD | NEW |