CookieHelper.cs 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Globalization;
  4. using System.Net;
  5. using System.Text;
  6. using System.Threading.Tasks;
  7. namespace SocketHttpListener.Net
  8. {
  9. public static class CookieHelper
  10. {
  11. internal static CookieCollection Parse(string value, bool response)
  12. {
  13. return response
  14. ? parseResponse(value)
  15. : null;
  16. }
  17. private static string[] splitCookieHeaderValue(string value)
  18. {
  19. return new List<string>(value.SplitHeaderValue(',', ';')).ToArray();
  20. }
  21. private static CookieCollection parseResponse(string value)
  22. {
  23. var cookies = new CookieCollection();
  24. Cookie cookie = null;
  25. var pairs = splitCookieHeaderValue(value);
  26. for (int i = 0; i < pairs.Length; i++)
  27. {
  28. var pair = pairs[i].Trim();
  29. if (pair.Length == 0)
  30. continue;
  31. if (pair.StartsWith("version", StringComparison.OrdinalIgnoreCase))
  32. {
  33. if (cookie != null)
  34. cookie.Version = Int32.Parse(pair.GetValueInternal("=").Trim('"'));
  35. }
  36. else if (pair.StartsWith("expires", StringComparison.OrdinalIgnoreCase))
  37. {
  38. var buffer = new StringBuilder(pair.GetValueInternal("="), 32);
  39. if (i < pairs.Length - 1)
  40. buffer.AppendFormat(", {0}", pairs[++i].Trim());
  41. DateTime expires;
  42. if (!DateTime.TryParseExact(
  43. buffer.ToString(),
  44. new[] { "ddd, dd'-'MMM'-'yyyy HH':'mm':'ss 'GMT'", "r" },
  45. new CultureInfo("en-US"),
  46. DateTimeStyles.AdjustToUniversal | DateTimeStyles.AssumeUniversal,
  47. out expires))
  48. expires = DateTime.Now;
  49. if (cookie != null && cookie.Expires == DateTime.MinValue)
  50. cookie.Expires = expires.ToLocalTime();
  51. }
  52. else if (pair.StartsWith("max-age", StringComparison.OrdinalIgnoreCase))
  53. {
  54. var max = Int32.Parse(pair.GetValueInternal("=").Trim('"'));
  55. var expires = DateTime.Now.AddSeconds((double)max);
  56. if (cookie != null)
  57. cookie.Expires = expires;
  58. }
  59. else if (pair.StartsWith("path", StringComparison.OrdinalIgnoreCase))
  60. {
  61. if (cookie != null)
  62. cookie.Path = pair.GetValueInternal("=");
  63. }
  64. else if (pair.StartsWith("domain", StringComparison.OrdinalIgnoreCase))
  65. {
  66. if (cookie != null)
  67. cookie.Domain = pair.GetValueInternal("=");
  68. }
  69. else if (pair.StartsWith("port", StringComparison.OrdinalIgnoreCase))
  70. {
  71. var port = pair.Equals("port", StringComparison.OrdinalIgnoreCase)
  72. ? "\"\""
  73. : pair.GetValueInternal("=");
  74. if (cookie != null)
  75. cookie.Port = port;
  76. }
  77. else if (pair.StartsWith("comment", StringComparison.OrdinalIgnoreCase))
  78. {
  79. if (cookie != null)
  80. cookie.Comment = pair.GetValueInternal("=").UrlDecode();
  81. }
  82. else if (pair.StartsWith("commenturl", StringComparison.OrdinalIgnoreCase))
  83. {
  84. if (cookie != null)
  85. cookie.CommentUri = pair.GetValueInternal("=").Trim('"').ToUri();
  86. }
  87. else if (pair.StartsWith("discard", StringComparison.OrdinalIgnoreCase))
  88. {
  89. if (cookie != null)
  90. cookie.Discard = true;
  91. }
  92. else if (pair.StartsWith("secure", StringComparison.OrdinalIgnoreCase))
  93. {
  94. if (cookie != null)
  95. cookie.Secure = true;
  96. }
  97. else if (pair.StartsWith("httponly", StringComparison.OrdinalIgnoreCase))
  98. {
  99. if (cookie != null)
  100. cookie.HttpOnly = true;
  101. }
  102. else
  103. {
  104. if (cookie != null)
  105. cookies.Add(cookie);
  106. string name;
  107. string val = String.Empty;
  108. var pos = pair.IndexOf('=');
  109. if (pos == -1)
  110. {
  111. name = pair;
  112. }
  113. else if (pos == pair.Length - 1)
  114. {
  115. name = pair.Substring(0, pos).TrimEnd(' ');
  116. }
  117. else
  118. {
  119. name = pair.Substring(0, pos).TrimEnd(' ');
  120. val = pair.Substring(pos + 1).TrimStart(' ');
  121. }
  122. cookie = new Cookie(name, val);
  123. }
  124. }
  125. if (cookie != null)
  126. cookies.Add(cookie);
  127. return cookies;
  128. }
  129. }
  130. }