| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174 |
- <?php
- /*
- * File: Structure.php
- * Category: -
- * Author: M.Goldenbaum
- * Created: 17.09.20 20:38
- * Updated: -
- *
- * Description:
- * -
- */
- namespace Webklex\PHPIMAP;
- use Webklex\PHPIMAP\Exceptions\InvalidMessageDateException;
- use Webklex\PHPIMAP\Exceptions\MessageContentFetchingException;
- /**
- * Class Structure
- *
- * @package Webklex\PHPIMAP
- */
- class Structure {
- /**
- * Raw structure
- *
- * @var string $raw
- */
- public $raw = "";
- /**
- * @var Header $header
- */
- private $header = null;
- /**
- * Message type (if multipart or not)
- *
- * @var int $type
- */
- public $type = IMAP::MESSAGE_TYPE_TEXT;
- /**
- * All available parts
- *
- * @var Part[] $parts
- */
- public $parts = [];
- /**
- * Config holder
- *
- * @var array $config
- */
- protected $config = [];
- /**
- * Structure constructor.
- * @param $raw_structure
- * @param Header $header
- *
- * @throws MessageContentFetchingException
- * @throws InvalidMessageDateException
- */
- public function __construct($raw_structure, Header $header) {
- $this->raw = $raw_structure;
- $this->header = $header;
- $this->config = ClientManager::get('options');
- $this->parse();
- }
- /**
- * Parse the given raw structure
- *
- * @throws MessageContentFetchingException
- * @throws InvalidMessageDateException
- */
- protected function parse(){
- $this->findContentType();
- $this->parts = $this->find_parts();
- }
- /**
- * Determine the message content type
- */
- public function findContentType(){
- $content_type = $this->header->get("content_type");
- $content_type = (is_array($content_type)) ? implode(' ', $content_type) : $content_type;
- if(stripos($content_type, 'multipart') === 0) {
- $this->type = IMAP::MESSAGE_TYPE_MULTIPART;
- }else{
- $this->type = IMAP::MESSAGE_TYPE_TEXT;
- }
- }
- /**
- * Find all available headers and return the left over body segment
- * @var string $context
- * @var integer $part_number
- *
- * @return Part[]
- * @throws InvalidMessageDateException
- */
- private function parsePart($context, $part_number = 0){
- $body = $context;
- while (($pos = strpos($body, "\r\n")) > 0) {
- $body = substr($body, $pos + 2);
- }
- $headers = substr($context, 0, strlen($body) * -1);
- $body = substr($body, 0, -2);
- $headers = new Header($headers);
- if (($boundary = $headers->getBoundary()) !== null) {
- return $this->detectParts($boundary, $body, $part_number);
- }
- return [new Part($body, $headers, $part_number)];
- }
- /**
- * @param string $boundary
- * @param string $context
- * @param int $part_number
- *
- * @return array
- * @throws InvalidMessageDateException
- */
- private function detectParts($boundary, $context, $part_number = 0){
- $base_parts = explode( $boundary, $context);
- $final_parts = [];
- foreach($base_parts as $ctx) {
- $ctx = substr($ctx, 2);
- if ($ctx !== "--" && $ctx != "") {
- $parts = $this->parsePart($ctx, $part_number);
- foreach ($parts as $part) {
- $final_parts[] = $part;
- $part_number = $part->part_number;
- }
- $part_number++;
- }
- }
- return $final_parts;
- }
- /**
- * Find all available parts
- *
- * @return array
- * @throws MessageContentFetchingException
- * @throws InvalidMessageDateException
- */
- public function find_parts(){
- if($this->type === IMAP::MESSAGE_TYPE_MULTIPART) {
- if (($boundary = $this->header->getBoundary()) === null) {
- throw new MessageContentFetchingException("no content found", 0);
- }
- return $this->detectParts($boundary, $this->raw);
- }
- return [new Part($this->raw, $this->header)];
- }
- /**
- * Try to find a boundary if possible
- *
- * @return string|null
- * @Depricated since version 2.4.4
- */
- public function getBoundary(){
- return $this->header->getBoundary();
- }
- }
|