/// <summary> /// Verifies that a header name matches name of the associate header, with MIME string comparison semantics. /// </summary> /// <param name="name">The header name to verify</param> /// <param name="header">The <see cref="Header"/> to verify against.</param> static void VerifyName(string name, Header header) { if (!MimeStandard.Equals(name, header.Name)) { throw new MimeException(MimeError.InvalidHeader); } }
static EncodedLine LineFromSegment(StringSegment segment, bool hasCRLF) { // // Skip any trailing white space. RFC 2045, Section 6.7, Rule #3 // Whitespace is defined as MimeStandard.IsWhiteSpace // int endAt = segment.Length - 1; for (; endAt >= 0; --endAt) { if (!MimeStandard.IsWhitespace(segment[endAt])) { break; } } StringSegment cleanSegment; if (endAt < 0) { cleanSegment = StringSegment.Null; } else { cleanSegment = new StringSegment(segment.Source, segment.StartIndex, segment.StartIndex + endAt); } return(new EncodedLine { Text = cleanSegment, HasCRLF = hasCRLF }); }
/// <summary> /// Returns all values for the given paramName /// </summary> /// <param name="paramName"></param> /// <returns></returns> public IEnumerable <string> GetValues(string paramName) { return( from nv in this where MimeStandard.Equals(nv.Key, paramName) select nv.Value ); }
/// <summary> /// Tests if this header is named the supplied <paramref name="name"/> /// </summary> /// <param name="name">The name to test this header's name against</param> /// <returns><c>true</c> if the names match by MIME string comparison rules</returns> public bool IsNamed(string name) { if (string.IsNullOrEmpty(name)) { return(false); } return(MimeStandard.Equals(this.Name, name)); }
/// <summary> /// Tests if this content type has the named parameter and parameter value. /// </summary> /// <param name="contentType">The content type to test</param> /// <param name="parameter">The parameter name to test</param> /// <param name="value">The parameter value to test</param> /// <returns><c>true</c> if the content type has the named parameter with the parameter value</returns> public static bool HasParameter(this ContentType contentType, string parameter, string value) { string paramValue = contentType.Parameters[parameter]; if (paramValue == null) { return(false); } return(MimeStandard.Equals(paramValue, value)); }
/// <summary> /// Tests if this entity has the named header with a value, using MIME-appropriate string comparison. /// </summary> /// <param name="name">The header name to test for.</param> /// <param name="value">The value to test</param> /// <returns><c>true</c> if the entity has the named header and the header has the appropriate value, <c>false</c> otherwise</returns> public bool HasHeader(string name, string value) { if (!this.HasHeaders) { return(false); } Header header = m_headers[name]; return(header != null && MimeStandard.Equals(header.Value, value)); }
/// <summary> /// Parses the ContentTransferEncoding header, if any. /// If no header specified, returns SevenBit, the default /// If transfer encoding not recognized, returns TransferEncoding.Unknown /// </summary> /// <returns>The transfer encoding for this Mime Entity</returns> public TransferEncoding GetTransferEncoding() { TransferEncoding encoding = TransferEncoding.SevenBit; string transferEncodingHeader = this.ContentTransferEncoding; if (!string.IsNullOrEmpty(transferEncodingHeader)) { encoding = MimeStandard.ToTransferEncoding(transferEncodingHeader); } return(encoding); }
/// <summary> /// Advances the start position of <paramref name="text"/> to the first non-whitespace position /// </summary> /// <param name="text">The <see cref="StringSegment"/> potentially containing initial whitepace</param> /// <returns>A <see cref="StringSegment"/> with no intial whitespace (possibly an empty segment if the <paramref name="text"/> was empty or all whitespace)</returns> public static StringSegment SkipWhitespace(StringSegment text) { CharReader reader = new CharReader(text); char ch; while ((ch = reader.Read()) != CharReader.EOF && MimeStandard.IsWhitespace(ch)) { // quick skip } return(new StringSegment(text.Source, reader.Position, text.EndIndex)); }
/// <summary> /// Parse each line in lines as a <see cref="Header"/>. /// </summary> /// <param name="lines">The lines to parse.</param> /// <returns>The parsed enumeration of <see cref="Header"/> instances.</returns> public static IEnumerable <Header> ReadHeaders(IEnumerable <StringSegment> lines) { if (lines == null) { throw new ArgumentNullException("lines"); } Header header = null; foreach (StringSegment line in lines) { if (line.IsEmpty) { if (header != null) { yield return(header); header = null; } // // Done with the header section. Onto the Body, so we're done // break; } if (MimeStandard.IsWhitespace(line[0])) { // Line folding. This line belongs to the current header if (header == null) { throw new MimeException(MimeError.InvalidHeader); } header.AppendSourceText(line); } else { if (header != null) { yield return(header); } header = new Header(line); } } if (header != null) { yield return(header); } }
/// <summary> /// Return the index of the first matching field /// </summary> /// <param name="field"></param> /// <returns>-1 if field not found. Else >= 0</returns> public int IndexOfFirst(KeyValuePair <string, string> field) { for (int i = 0, count = this.Count; i < count; ++i) { KeyValuePair <string, string> foundField = this[i]; if (MimeStandard.Equals(foundField.Key, field.Key) && MimeStandard.Equals(foundField.Value, field.Value) ) { return(i); } } return(-1); }
/// <summary> /// Returns the index of the first parameter with this name /// </summary> /// <param name="paramName"></param> /// <returns></returns> public int IndexOfFirst(string paramName) { if (string.IsNullOrEmpty(paramName)) { throw new ArgumentException("paramName"); } for (int i = 0, count = this.Count; i < count; ++i) { if (MimeStandard.Equals(this[i].Key, paramName)) { return(i); } } return(-1); }
/// <summary> /// Returns the index to a header name. See <see cref="HeaderCollection"/> for more details. /// </summary> /// <remarks> /// Headers are not case sensitive, so <c>myHeaders.IndexOf("content-type")</c> and /// <c>myHeaders.IndexOf("Content-Type")</c> /// will refer to the same header value. /// </remarks> /// <param name="name">The name of the header to get or set. See remarks.</param> /// <returns>The zero-based index of the named header or -1 if the header was not found.</returns> public int IndexOf(string name) { if (string.IsNullOrEmpty(name)) { throw new ArgumentException("name was null or empty", "name"); } for (int i = 0, count = Count; i < count; ++i) { if (MimeStandard.Equals(this[i].Name, name)) { return(i); } } return(-1); }
/// <summary> /// Tests if this header is named one of the supplied <paramref name="names"/> /// </summary> /// <param name="names">The names to test this header's name against</param> /// <returns><c>true</c> if this header matches one of the supplied names match by MIME string comparison rules</returns> public bool IsHeaderNameOneOf(string[] names) { if (names == null || names.Length == 0) { return(false); } string name = this.Name; for (int i = 0; i < names.Length; ++i) { if (MimeStandard.Equals(names[i], name)) { return(true); } } return(false); }
/// <summary> /// Tests if this content type is same one represented by the specified <paramref name="mediaType"/> /// </summary> /// <param name="contentType">This <see cref="ContentType"/></param> /// <param name="mediaType">The content type string to test against this instance.</param> /// <returns></returns> public static bool IsMediaType(this ContentType contentType, string mediaType) { return(MimeStandard.Equals(contentType.MediaType, mediaType)); }
/// <summary> /// Parses the supplied <paramref name="lines"/> into constituent <see cref="MimePart"/> instances /// </summary> /// <remarks> /// This is the main parser interface. The <see cref="MimePart"/> instances expected to be returned are <see cref="Header"/> (one for each header), and <see cref="Body"/> /// </remarks> /// <param name="lines">The enumeration of <see cref="StringSegment"/> lines to parse</param> /// <returns>An enumeration of the constituent <see cref="MimePart"/> instances parsed from the <paramref name="lines"/></returns> public static IEnumerable <MimePart> ReadMimeParts(IEnumerable <StringSegment> lines) { if (lines == null) { throw new ArgumentNullException("lines"); } MimePartType expectedPartType = MimePartType.Header; Header header = null; Body body = null; foreach (StringSegment line in lines) { switch (expectedPartType) { default: throw new MimeException(MimeError.Unexpected); case MimePartType.Header: if (line.IsEmpty) { if (header != null) { yield return(header); header = null; } yield return(new MimePart(MimePartType.HeaderBoundary, line)); // // Done with the header section. Onto the Body // expectedPartType = MimePartType.Body; break; } if (MimeStandard.IsWhitespace(line[0])) { // Line folding. This line belongs to the current header if (header == null) { throw new MimeException(MimeError.InvalidHeader); } header.AppendSourceText(line); break; } if (header != null) { yield return(header); } header = new Header(line); break; case MimePartType.Body: if (body == null) { body = new Body(line); } else { body.AppendSourceText(line); } break; } } if (header != null) { yield return(header); } if (body != null) { yield return(body); } }
/// <summary> /// Returns a string representation of <paramref name="encoding"/> compatable with the <c>micalg</c> parameter /// </summary> /// <param name="encoding">The <see cref="TransferEncoding"/> to stringify.</param> /// <returns>The string representation of the encoding compatable with the <c>Content-Transfer-Encoding</c> header</returns> public static string AsString(this TransferEncoding encoding) { return(MimeStandard.ToString(encoding)); }
/// <summary> /// Tests if this collection has the named header with a value, using MIME-appropriate string comparison. /// </summary> /// <param name="name">The header name to test for.</param> /// <param name="value">The value to test</param> /// <returns><c>true</c> if the collection has the named header and the header has the appropriate value, <c>false</c> otherwise</returns> public bool HasHeader(string name, string value) { Header header = this[name]; return(header != null && MimeStandard.Equals(header.Value, value)); }