OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, 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 part of dart.io; | 5 part of dart.io; |
6 | 6 |
7 class _HttpHeaders implements HttpHeaders { | 7 class _HttpHeaders implements HttpHeaders { |
8 _HttpHeaders(String this.protocolVersion) | 8 _HttpHeaders(String this.protocolVersion) |
9 : _headers = new Map<String, List<String>>(); | 9 : _headers = new Map<String, List<String>>(); |
10 | 10 |
(...skipping 457 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
468 final String protocolVersion; | 468 final String protocolVersion; |
469 String _host; | 469 String _host; |
470 int _port; | 470 int _port; |
471 } | 471 } |
472 | 472 |
473 | 473 |
474 class _HeaderValue implements HeaderValue { | 474 class _HeaderValue implements HeaderValue { |
475 String _value; | 475 String _value; |
476 Map<String, String> _parameters; | 476 Map<String, String> _parameters; |
477 | 477 |
478 _HeaderValue([String this._value = "", this._parameters]); | 478 _HeaderValue([String this._value = "", Map<String, String> parameters]) { |
| 479 if (parameters != null) { |
| 480 _parameters = |
| 481 new _UnmodifiableMap(new Map<String, String>.from(parameters)); |
| 482 } |
| 483 } |
479 | 484 |
480 static _HeaderValue parse(String value, {parameterSeparator: ";"}) { | 485 static _HeaderValue parse(String value, {parameterSeparator: ";"}) { |
481 // Parse the string. | 486 // Parse the string. |
482 var result = new _HeaderValue(); | 487 var result = new _HeaderValue(); |
483 result._parse(value, parameterSeparator); | 488 result._parse(value, parameterSeparator); |
484 return result; | 489 return result; |
485 } | 490 } |
486 | 491 |
487 String get value => _value; | 492 String get value => _value; |
488 | 493 |
| 494 void _ensureParameters() { |
| 495 if (_parameters == null) { |
| 496 _parameters = new _UnmodifiableMap(new Map<String, String>()); |
| 497 } |
| 498 } |
| 499 |
489 Map<String, String> get parameters { | 500 Map<String, String> get parameters { |
490 if (_parameters == null) _parameters = new Map<String, String>(); | 501 _ensureParameters(); |
491 return _parameters; | 502 return _parameters; |
492 } | 503 } |
493 | 504 |
494 String toString() { | 505 String toString() { |
495 StringBuffer sb = new StringBuffer(); | 506 StringBuffer sb = new StringBuffer(); |
496 sb.write(_value); | 507 sb.write(_value); |
497 if (parameters != null && parameters.length > 0) { | 508 if (parameters != null && parameters.length > 0) { |
498 _parameters.forEach((String name, String value) { | 509 _parameters.forEach((String name, String value) { |
499 sb.write("; "); | 510 sb.write("; "); |
500 sb.write(name); | 511 sb.write(name); |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
533 throw new HttpException("Failed to parse header value"); | 544 throw new HttpException("Failed to parse header value"); |
534 } | 545 } |
535 index++; | 546 index++; |
536 } | 547 } |
537 | 548 |
538 void maybeExpect(String expected) { | 549 void maybeExpect(String expected) { |
539 if (s[index] == expected) index++; | 550 if (s[index] == expected) index++; |
540 } | 551 } |
541 | 552 |
542 void parseParameters() { | 553 void parseParameters() { |
543 _parameters = new Map<String, String>(); | 554 var parameters = new Map<String, String>(); |
| 555 _parameters = new _UnmodifiableMap(parameters); |
544 | 556 |
545 String parseParameterName() { | 557 String parseParameterName() { |
546 int start = index; | 558 int start = index; |
547 while (!done()) { | 559 while (!done()) { |
548 if (s[index] == " " || s[index] == "\t" || s[index] == "=") break; | 560 if (s[index] == " " || s[index] == "\t" || s[index] == "=") break; |
549 index++; | 561 index++; |
550 } | 562 } |
551 return s.substring(start, index).toLowerCase(); | 563 return s.substring(start, index).toLowerCase(); |
552 } | 564 } |
553 | 565 |
(...skipping 23 matching lines...) Expand all Loading... |
577 } | 589 } |
578 | 590 |
579 while (!done()) { | 591 while (!done()) { |
580 skipWS(); | 592 skipWS(); |
581 if (done()) return; | 593 if (done()) return; |
582 String name = parseParameterName(); | 594 String name = parseParameterName(); |
583 skipWS(); | 595 skipWS(); |
584 expect("="); | 596 expect("="); |
585 skipWS(); | 597 skipWS(); |
586 String value = parseParameterValue(); | 598 String value = parseParameterValue(); |
587 _parameters[name] = value; | 599 parameters[name] = value; |
588 skipWS(); | 600 skipWS(); |
589 if (done()) return; | 601 if (done()) return; |
590 expect(parameterSeparator); | 602 expect(parameterSeparator); |
591 } | 603 } |
592 } | 604 } |
593 | 605 |
594 skipWS(); | 606 skipWS(); |
595 _value = parseValue(); | 607 _value = parseValue(); |
596 skipWS(); | 608 skipWS(); |
597 if (done()) return; | 609 if (done()) return; |
598 maybeExpect(parameterSeparator); | 610 maybeExpect(parameterSeparator); |
599 parseParameters(); | 611 parseParameters(); |
600 } | 612 } |
601 } | 613 } |
602 | 614 |
603 | 615 |
604 class _ContentType extends _HeaderValue implements ContentType { | 616 class _ContentType extends _HeaderValue implements ContentType { |
605 String _primaryType = ""; | 617 String _primaryType = ""; |
606 String _subType = ""; | 618 String _subType = ""; |
607 | 619 |
608 _ContentType(String primaryType, | 620 _ContentType(String primaryType, |
609 String subType, | 621 String subType, |
610 String charset, | 622 String charset, |
611 Map<String, String> parameters) | 623 Map<String, String> parameters) |
612 : _primaryType = primaryType, _subType = subType, super("") { | 624 : _primaryType = primaryType, _subType = subType, super("") { |
613 if (_primaryType == null) _primaryType = ""; | 625 if (_primaryType == null) _primaryType = ""; |
614 if (_subType == null) _subType = ""; | 626 if (_subType == null) _subType = ""; |
615 _value = "$_primaryType/$_subType";; | 627 _value = "$_primaryType/$_subType"; |
616 if (parameters != null) { | 628 if (parameters != null) { |
| 629 _ensureParameters(); |
617 parameters.forEach((String key, String value) { | 630 parameters.forEach((String key, String value) { |
618 this.parameters[key.toLowerCase()] = value.toLowerCase(); | 631 this._parameters._map[key.toLowerCase()] = value.toLowerCase(); |
619 }); | 632 }); |
620 } | 633 } |
621 if (charset != null) { | 634 if (charset != null) { |
622 this.parameters["charset"] = charset.toLowerCase(); | 635 _ensureParameters(); |
| 636 this._parameters._map["charset"] = charset.toLowerCase(); |
623 } | 637 } |
624 } | 638 } |
625 | 639 |
626 _ContentType._(); | 640 _ContentType._(); |
627 | 641 |
628 static _ContentType parse(String value) { | 642 static _ContentType parse(String value) { |
629 var result = new _ContentType._(); | 643 var result = new _ContentType._(); |
630 result._parse(value, ";"); | 644 result._parse(value, ";"); |
631 int index = result._value.indexOf("/"); | 645 int index = result._value.indexOf("/"); |
632 if (index == -1 || index == (result._value.length - 1)) { | 646 if (index == -1 || index == (result._value.length - 1)) { |
633 result._primaryType = result._value.trim().toLowerCase(); | 647 result._primaryType = result._value.trim().toLowerCase(); |
634 result._subType = ""; | 648 result._subType = ""; |
635 } else { | 649 } else { |
636 result._primaryType = result._value.substring(0, index).trim().toLowerCase
(); | 650 result._primaryType = |
| 651 result._value.substring(0, index).trim().toLowerCase(); |
637 result._subType = result._value.substring(index + 1).trim().toLowerCase(); | 652 result._subType = result._value.substring(index + 1).trim().toLowerCase(); |
638 } | 653 } |
639 return result; | 654 return result; |
640 } | 655 } |
641 | 656 |
642 String get mimeType => '$primaryType/$subType'; | 657 String get mimeType => '$primaryType/$subType'; |
643 | 658 |
644 String get primaryType => _primaryType; | 659 String get primaryType => _primaryType; |
645 | 660 |
646 String get subType => _subType; | 661 String get subType => _subType; |
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
771 | 786 |
772 String name; | 787 String name; |
773 String value; | 788 String value; |
774 DateTime expires; | 789 DateTime expires; |
775 int maxAge; | 790 int maxAge; |
776 String domain; | 791 String domain; |
777 String path; | 792 String path; |
778 bool httpOnly = false; | 793 bool httpOnly = false; |
779 bool secure = false; | 794 bool secure = false; |
780 } | 795 } |
| 796 |
| 797 |
| 798 class _UnmodifiableMap<K, V> implements Map<K, V> { |
| 799 final Map _map; |
| 800 const _UnmodifiableMap(this._map); |
| 801 |
| 802 bool containsValue(Object value) => _map.containsValue(value); |
| 803 bool containsKey(Object key) => _map.containsKey(key); |
| 804 V operator [](Object key) => _map[key]; |
| 805 void operator []=(K key, V value) { |
| 806 throw new UnsupportedError("Cannot modify an unmodifiable map"); |
| 807 } |
| 808 V putIfAbsent(K key, V ifAbsent()) { |
| 809 throw new UnsupportedError("Cannot modify an unmodifiable map"); |
| 810 } |
| 811 addAll(Map other) { |
| 812 throw new UnsupportedError("Cannot modify an unmodifiable map"); |
| 813 } |
| 814 V remove(Object key) { |
| 815 throw new UnsupportedError("Cannot modify an unmodifiable map"); |
| 816 } |
| 817 void clear() { |
| 818 throw new UnsupportedError("Cannot modify an unmodifiable map"); |
| 819 } |
| 820 void forEach(void f(K key, V value)) => _map.forEach(f); |
| 821 Iterable<K> get keys => _map.keys; |
| 822 Iterable<V> get values => _map.values; |
| 823 int get length => _map.length; |
| 824 bool get isEmpty => _map.isEmpty; |
| 825 bool get isNotEmpty => _map.isNotEmpty; |
| 826 } |
OLD | NEW |