| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | <?php | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | require_once('attachment.class.php'); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | /** | 
					
						
							|  |  |  |  * Fast Mime Mail parser Class using PHP's MailParse Extension | 
					
						
							|  |  |  |  * @author gabe@fijiwebdesign.com | 
					
						
							|  |  |  |  * @url http://www.fijiwebdesign.com/ | 
					
						
							|  |  |  |  * @license http://creativecommons.org/licenses/by-sa/3.0/us/ | 
					
						
							|  |  |  |  * @version $Id$ | 
					
						
							|  |  |  |  */ | 
					
						
							|  |  |  | class MimeMailParser { | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * PHP MimeParser Resource ID | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public $resource; | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * A file pointer to email | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public $stream; | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * A text of an email | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public $data; | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Stream Resources for Attachments | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public $attachment_streams; | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Inialize some stuff | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 	 * @return | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	 */ | 
					
						
							|  |  |  | 	public function __construct() { | 
					
						
							|  |  |  | 		$this->attachment_streams = array(); | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Free the held resouces | 
					
						
							|  |  |  | 	 * @return void | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function __destruct() { | 
					
						
							|  |  |  | 		// clear the email file resource
 | 
					
						
							|  |  |  | 		if (is_resource($this->stream)) { | 
					
						
							|  |  |  | 			fclose($this->stream); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		// clear the MailParse resource
 | 
					
						
							|  |  |  | 		if (is_resource($this->resource)) { | 
					
						
							|  |  |  | 			mailparse_msg_free($this->resource); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		// remove attachment resources
 | 
					
						
							|  |  |  | 		foreach($this->attachment_streams as $stream) { | 
					
						
							|  |  |  | 			fclose($stream); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Set the file path we use to get the email text | 
					
						
							|  |  |  | 	 * @return Object MimeMailParser Instance | 
					
						
							|  |  |  | 	 * @param $mail_path Object | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function setPath($path) { | 
					
						
							|  |  |  | 		// should parse message incrementally from file
 | 
					
						
							|  |  |  | 		$this->resource = mailparse_msg_parse_file($path); | 
					
						
							|  |  |  | 		$this->stream = fopen($path, 'r'); | 
					
						
							|  |  |  | 		$this->parse(); | 
					
						
							|  |  |  | 		return $this; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Set the Stream resource we use to get the email text | 
					
						
							|  |  |  | 	 * @return Object MimeMailParser Instance | 
					
						
							|  |  |  | 	 * @param $stream Resource | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function setStream($stream) { | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 		// streams have to be cached to file first
 | 
					
						
							|  |  |  | 		if (get_resource_type($stream) == 'stream') { | 
					
						
							|  |  |  | 			$tmp_fp = tmpfile(); | 
					
						
							|  |  |  | 			if ($tmp_fp) { | 
					
						
							|  |  |  | 				while(!feof($stream)) { | 
					
						
							|  |  |  | 					fwrite($tmp_fp, fread($stream, 2028)); | 
					
						
							|  |  |  | 				} | 
					
						
							|  |  |  | 				fseek($tmp_fp, 0); | 
					
						
							|  |  |  | 				$this->stream =& $tmp_fp; | 
					
						
							|  |  |  | 			} else { | 
					
						
							|  |  |  | 				throw new Exception('Could not create temporary files for attachments. Your tmp directory may be unwritable by PHP.'); | 
					
						
							|  |  |  | 				return false; | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 			fclose($stream); | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			$this->stream = $stream; | 
					
						
							|  |  |  | 		} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 		$this->resource = mailparse_msg_create(); | 
					
						
							|  |  |  | 		// parses the message incrementally low memory usage but slower
 | 
					
						
							|  |  |  | 		while(!feof($this->stream)) { | 
					
						
							|  |  |  | 			mailparse_msg_parse($this->resource, fread($this->stream, 2082)); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		$this->parse(); | 
					
						
							|  |  |  | 		return $this; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Set the email text | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 	 * @return Object MimeMailParser Instance | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	 * @param $data String | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function setText($data) { | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 	// NOTE: This has been modified for Phabricator. If the input data does not
 | 
					
						
							|  |  |  | 	// end in a newline, Mailparse fails to include the last line in the mail
 | 
					
						
							|  |  |  | 	// body. This happens somewhere deep, deep inside the mailparse extension,
 | 
					
						
							|  |  |  | 	// so adding a newline here seems like the most straightforward fix.
 | 
					
						
							|  |  |  | 	if (!preg_match('/\n\z/', $data)) { | 
					
						
							|  |  |  | 	  $data = $data."\n"; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2015-04-21 09:49:40 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 		$this->resource = mailparse_msg_create(); | 
					
						
							|  |  |  | 		// does not parse incrementally, fast memory hog might explode
 | 
					
						
							|  |  |  | 		mailparse_msg_parse($this->resource, $data); | 
					
						
							|  |  |  | 		$this->data = $data; | 
					
						
							|  |  |  | 		$this->parse(); | 
					
						
							|  |  |  | 		return $this; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Parse the Message into parts | 
					
						
							|  |  |  | 	 * @return void | 
					
						
							|  |  |  | 	 * @private | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function parse() { | 
					
						
							|  |  |  | 		$structure = mailparse_msg_get_structure($this->resource); | 
					
						
							|  |  |  | 		$this->parts = array(); | 
					
						
							|  |  |  | 		foreach($structure as $part_id) { | 
					
						
							|  |  |  | 			$part = mailparse_msg_get_part($this->resource, $part_id); | 
					
						
							|  |  |  | 			$this->parts[$part_id] = mailparse_msg_get_part_data($part); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the Email Headers | 
					
						
							|  |  |  | 	 * @return Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function getHeaders() { | 
					
						
							|  |  |  | 		if (isset($this->parts[1])) { | 
					
						
							|  |  |  | 			return $this->getPartHeaders($this->parts[1]); | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('MimeMailParser::setPath() or MimeMailParser::setText() must be called before retrieving email headers.'); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return false; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the raw Email Headers | 
					
						
							|  |  |  | 	 * @return string | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function getHeadersRaw() { | 
					
						
							|  |  |  | 		if (isset($this->parts[1])) { | 
					
						
							|  |  |  | 			return $this->getPartHeaderRaw($this->parts[1]); | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('MimeMailParser::setPath() or MimeMailParser::setText() must be called before retrieving email headers.'); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return false; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve a specific Email Header | 
					
						
							|  |  |  | 	 * @return String | 
					
						
							|  |  |  | 	 * @param $name String Header name | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function getHeader($name) { | 
					
						
							|  |  |  | 		if (isset($this->parts[1])) { | 
					
						
							|  |  |  | 			$headers = $this->getPartHeaders($this->parts[1]); | 
					
						
							|  |  |  | 			if (isset($headers[$name])) { | 
					
						
							|  |  |  | 				return $headers[$name]; | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('MimeMailParser::setPath() or MimeMailParser::setText() must be called before retrieving email headers.'); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return false; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Returns the email message body in the specified format | 
					
						
							|  |  |  | 	 * @return Mixed String Body or False if not found | 
					
						
							|  |  |  | 	 * @param $type Object[optional] | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function getMessageBody($type = 'text') { | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	  // NOTE: This function has been modified for Phabricator. The default
 | 
					
						
							|  |  |  | 	  // implementation returns the last matching part, which throws away text
 | 
					
						
							|  |  |  | 	  // for many emails. Instead, we concatenate all matching parts. See
 | 
					
						
							|  |  |  | 	  // issue 22 for discussion:
 | 
					
						
							|  |  |  | 	  // http://code.google.com/p/php-mime-mail-parser/issues/detail?id=22
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 		$body = false; | 
					
						
							|  |  |  | 		$mime_types = array( | 
					
						
							|  |  |  | 			'text'=> 'text/plain', | 
					
						
							|  |  |  | 			'html'=> 'text/html' | 
					
						
							|  |  |  | 		); | 
					
						
							|  |  |  | 		if (in_array($type, array_keys($mime_types))) { | 
					
						
							|  |  |  | 			foreach($this->parts as $part) { | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 			$disposition = $this->getPartContentDisposition($part); | 
					
						
							|  |  |  | 			if ($disposition == 'attachment') { | 
					
						
							|  |  |  | 			  // text/plain parts with "Content-Disposition: attachment" are
 | 
					
						
							|  |  |  | 			  // attachments, not part of the text body.
 | 
					
						
							|  |  |  | 			  continue; | 
					
						
							|  |  |  | 			} | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 				if ($this->getPartContentType($part) == $mime_types[$type]) { | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 		  $headers = $this->getPartHeaders($part); | 
					
						
							|  |  |  | 		  // Concatenate all the matching parts into the body text. For example,
 | 
					
						
							|  |  |  | 		  // if a user sends a message with some text, then an image, and then
 | 
					
						
							|  |  |  | 		  // some more text, the text body of the email gets split over several
 | 
					
						
							|  |  |  | 		  // attachments.
 | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 					$body .= $this->decode( | 
					
						
							|  |  |  | 					  $this->getPartBody($part), | 
					
						
							|  |  |  | 					  array_key_exists('content-transfer-encoding', $headers) | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 						? $headers['content-transfer-encoding'] | 
					
						
							|  |  |  | 						: ''); | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 				} | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('Invalid type specified for MimeMailParser::getMessageBody. "type" can either be text or html.'); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return $body; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	/** | 
					
						
							|  |  |  | 	 * get the headers for the message body part. | 
					
						
							|  |  |  | 	 * @return Array | 
					
						
							|  |  |  | 	 * @param $type Object[optional] | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function getMessageBodyHeaders($type = 'text') { | 
					
						
							|  |  |  | 		$headers = false; | 
					
						
							|  |  |  | 		$mime_types = array( | 
					
						
							|  |  |  | 			'text'=> 'text/plain', | 
					
						
							|  |  |  | 			'html'=> 'text/html' | 
					
						
							|  |  |  | 		); | 
					
						
							|  |  |  | 		if (in_array($type, array_keys($mime_types))) { | 
					
						
							|  |  |  | 			foreach($this->parts as $part) { | 
					
						
							|  |  |  | 				if ($this->getPartContentType($part) == $mime_types[$type]) { | 
					
						
							|  |  |  | 					$headers = $this->getPartHeaders($part); | 
					
						
							|  |  |  | 				} | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('Invalid type specified for MimeMailParser::getMessageBody. "type" can either be text or html.'); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return $headers; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	/** | 
					
						
							|  |  |  | 	 * Returns the attachments contents in order of appearance | 
					
						
							|  |  |  | 	 * @return Array | 
					
						
							|  |  |  | 	 * @param $type Object[optional] | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	public function getAttachments() { | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  |     // NOTE: This has been modified for Phabricator. Some mail clients do not
 | 
					
						
							|  |  |  |     // send attachments with "Content-Disposition" headers.
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 		$attachments = array(); | 
					
						
							|  |  |  | 		$dispositions = array("attachment","inline"); | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 		$non_attachment_types = array("text/plain", "text/html"); | 
					
						
							|  |  |  | 		$nonameIter = 0; | 
					
						
							|  |  |  | 		foreach ($this->parts as $part) { | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 			$disposition = $this->getPartContentDisposition($part); | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 			$filename = 'noname'; | 
					
						
							|  |  |  | 			if (isset($part['disposition-filename'])) { | 
					
						
							|  |  |  | 				$filename = $part['disposition-filename']; | 
					
						
							|  |  |  | 			} elseif (isset($part['content-name'])) { | 
					
						
							|  |  |  | 				// if we have no disposition but we have a content-name, it's a valid attachment.
 | 
					
						
							|  |  |  | 				// we simulate the presence of an attachment disposition with a disposition filename
 | 
					
						
							|  |  |  | 				$filename = $part['content-name']; | 
					
						
							|  |  |  | 				$disposition = 'attachment'; | 
					
						
							|  |  |  | 			} elseif (!in_array($part['content-type'], $non_attachment_types, true) | 
					
						
							|  |  |  | 				&& substr($part['content-type'], 0, 10) !== 'multipart/' | 
					
						
							|  |  |  | 				) { | 
					
						
							|  |  |  | 				// if we cannot get it with getMessageBody, we assume it is an attachment
 | 
					
						
							|  |  |  | 				$disposition = 'attachment'; | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 			if (in_array($disposition, $dispositions) && isset($filename) === true) { | 
					
						
							|  |  |  | 				if ($filename == 'noname') { | 
					
						
							|  |  |  | 					$nonameIter++; | 
					
						
							|  |  |  | 					$filename = 'noname'.$nonameIter; | 
					
						
							|  |  |  | 				} | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 				$attachments[] = new MimeMailParser_attachment( | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 					$filename, | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 					$this->getPartContentType($part), | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 					$this->getAttachmentStream($part), | 
					
						
							|  |  |  | 					$disposition, | 
					
						
							|  |  |  | 					$this->getPartHeaders($part) | 
					
						
							|  |  |  | 				); | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return $attachments; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Return the Headers for a MIME part | 
					
						
							|  |  |  | 	 * @return Array | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartHeaders($part) { | 
					
						
							|  |  |  | 		if (isset($part['headers'])) { | 
					
						
							|  |  |  | 			return $part['headers']; | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return false; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Return a Specific Header for a MIME part | 
					
						
							|  |  |  | 	 * @return Array | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 * @param $header String Header Name | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartHeader($part, $header) { | 
					
						
							|  |  |  | 		if (isset($part['headers'][$header])) { | 
					
						
							|  |  |  | 			return $part['headers'][$header]; | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return false; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Return the ContentType of the MIME part | 
					
						
							|  |  |  | 	 * @return String | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartContentType($part) { | 
					
						
							|  |  |  | 		if (isset($part['content-type'])) { | 
					
						
							|  |  |  | 			return $part['content-type']; | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return false; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Return the Content Disposition | 
					
						
							|  |  |  | 	 * @return String | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartContentDisposition($part) { | 
					
						
							|  |  |  | 		if (isset($part['content-disposition'])) { | 
					
						
							|  |  |  | 			return $part['content-disposition']; | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return false; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the raw Header of a MIME part | 
					
						
							|  |  |  | 	 * @return String | 
					
						
							|  |  |  | 	 * @param $part Object | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartHeaderRaw(&$part) { | 
					
						
							|  |  |  | 		$header = ''; | 
					
						
							|  |  |  | 		if ($this->stream) { | 
					
						
							|  |  |  | 			$header = $this->getPartHeaderFromFile($part); | 
					
						
							|  |  |  | 		} else if ($this->data) { | 
					
						
							|  |  |  | 			$header = $this->getPartHeaderFromText($part); | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('MimeMailParser::setPath() or MimeMailParser::setText() must be called before retrieving email parts.'); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return $header; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the Body of a MIME part | 
					
						
							|  |  |  | 	 * @return String | 
					
						
							|  |  |  | 	 * @param $part Object | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartBody(&$part) { | 
					
						
							|  |  |  | 		$body = ''; | 
					
						
							|  |  |  | 		if ($this->stream) { | 
					
						
							|  |  |  | 			$body = $this->getPartBodyFromFile($part); | 
					
						
							|  |  |  | 		} else if ($this->data) { | 
					
						
							|  |  |  | 			$body = $this->getPartBodyFromText($part); | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('MimeMailParser::setPath() or MimeMailParser::setText() must be called before retrieving email parts.'); | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return $body; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the Header from a MIME part from file | 
					
						
							|  |  |  | 	 * @return String Mime Header Part | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartHeaderFromFile(&$part) { | 
					
						
							|  |  |  | 		$start = $part['starting-pos']; | 
					
						
							|  |  |  | 		$end = $part['starting-pos-body']; | 
					
						
							|  |  |  | 		fseek($this->stream, $start, SEEK_SET); | 
					
						
							|  |  |  | 		$header = fread($this->stream, $end-$start); | 
					
						
							|  |  |  | 		return $header; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the Body from a MIME part from file | 
					
						
							|  |  |  | 	 * @return String Mime Body Part | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartBodyFromFile(&$part) { | 
					
						
							|  |  |  | 		$start = $part['starting-pos-body']; | 
					
						
							|  |  |  | 		$end = $part['ending-pos-body']; | 
					
						
							|  |  |  | 		fseek($this->stream, $start, SEEK_SET); | 
					
						
							|  |  |  | 		$body = fread($this->stream, $end-$start); | 
					
						
							|  |  |  | 		return $body; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the Header from a MIME part from text | 
					
						
							|  |  |  | 	 * @return String Mime Header Part | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartHeaderFromText(&$part) { | 
					
						
							|  |  |  | 		$start = $part['starting-pos']; | 
					
						
							|  |  |  | 		$end = $part['starting-pos-body']; | 
					
						
							|  |  |  | 		$header = substr($this->data, $start, $end-$start); | 
					
						
							|  |  |  | 		return $header; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	/** | 
					
						
							|  |  |  | 	 * Retrieve the Body from a MIME part from text | 
					
						
							|  |  |  | 	 * @return String Mime Body Part | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getPartBodyFromText(&$part) { | 
					
						
							|  |  |  | 		$start = $part['starting-pos-body']; | 
					
						
							|  |  |  | 		$end = $part['ending-pos-body']; | 
					
						
							|  |  |  | 		$body = substr($this->data, $start, $end-$start); | 
					
						
							|  |  |  | 		return $body; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Read the attachment Body and save temporary file resource | 
					
						
							|  |  |  | 	 * @return String Mime Body Part | 
					
						
							|  |  |  | 	 * @param $part Array | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function getAttachmentStream(&$part) { | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 		$temp_fp = tmpfile(); | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 		array_key_exists('content-transfer-encoding', $part['headers']) ? $encoding = $part['headers']['content-transfer-encoding'] : $encoding = ''; | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 
 | 
					
						
							|  |  |  | 		if ($temp_fp) { | 
					
						
							|  |  |  | 			if ($this->stream) { | 
					
						
							|  |  |  | 				$start = $part['starting-pos-body']; | 
					
						
							|  |  |  | 				$end = $part['ending-pos-body']; | 
					
						
							|  |  |  | 				fseek($this->stream, $start, SEEK_SET); | 
					
						
							|  |  |  | 				$len = $end-$start; | 
					
						
							|  |  |  | 				$written = 0; | 
					
						
							|  |  |  | 				$write = 2028; | 
					
						
							|  |  |  | 				$body = ''; | 
					
						
							|  |  |  | 				while($written < $len) { | 
					
						
							|  |  |  | 					if (($written+$write < $len )) { | 
					
						
							|  |  |  | 						$write = $len - $written; | 
					
						
							|  |  |  | 					} | 
					
						
							|  |  |  | 					$part = fread($this->stream, $write); | 
					
						
							|  |  |  | 					fwrite($temp_fp, $this->decode($part, $encoding)); | 
					
						
							|  |  |  | 					$written += $write; | 
					
						
							|  |  |  | 				} | 
					
						
							|  |  |  | 			} else if ($this->data) { | 
					
						
							|  |  |  | 				$attachment = $this->decode($this->getPartBodyFromText($part), $encoding); | 
					
						
							|  |  |  | 				fwrite($temp_fp, $attachment, strlen($attachment)); | 
					
						
							|  |  |  | 			} | 
					
						
							|  |  |  | 			fseek($temp_fp, 0, SEEK_SET); | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			throw new Exception('Could not create temporary files for attachments. Your tmp directory may be unwritable by PHP.'); | 
					
						
							|  |  |  | 			return false; | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 		return $temp_fp; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-06-12 21:09:55 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-09-21 15:02:45 -07:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * Decode the string depending on encoding type. | 
					
						
							|  |  |  | 	 * @return String the decoded string. | 
					
						
							|  |  |  | 	 * @param $encodedString	The string in its original encoded state. | 
					
						
							|  |  |  | 	 * @param $encodingType		The encoding type from the Content-Transfer-Encoding header of the part. | 
					
						
							|  |  |  | 	 */ | 
					
						
							|  |  |  | 	private function decode($encodedString, $encodingType) { | 
					
						
							|  |  |  | 		if (strtolower($encodingType) == 'base64') { | 
					
						
							|  |  |  | 			return base64_decode($encodedString); | 
					
						
							|  |  |  | 		} else if (strtolower($encodingType) == 'quoted-printable') { | 
					
						
							|  |  |  | 			 return quoted_printable_decode($encodedString); | 
					
						
							|  |  |  | 		} else { | 
					
						
							|  |  |  | 			return $encodedString; | 
					
						
							|  |  |  | 		} | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-05-04 23:09:42 -07:00
										 |  |  | 
 | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | ?>
 |