Passed
Pull Request — master (#171)
by Zaahid
07:22 queued 03:34
created

ParserMimePartProxy::isParentBoundaryFound()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 1
c 1
b 0
f 0
dl 0
loc 3
ccs 2
cts 2
cp 1
rs 10
cc 1
nc 1
nop 0
crap 1
1
<?php
2
/**
3
 * This file is part of the ZBateson\MailMimeParser project.
4
 *
5
 * @license http://opensource.org/licenses/bsd-license.php BSD
6
 */
7
namespace ZBateson\MailMimeParser\Parser\Proxy;
8
9
use ZBateson\MailMimeParser\Header\HeaderConsts;
10
use ZBateson\MailMimeParser\Message\IMessagePart;
11
12
/**
13
 * A bi-directional parser-to-part proxy for MimeParser and IMimeParts.
14
 *
15
 * @author Zaahid Bateson
16
 */
17
class ParserMimePartProxy extends ParserPartProxy
18
{
19
    /**
20
     * @var boolean set to true once the end boundary of the currently-parsed
21
     *      part is found.
22
     */
23
    protected $endBoundaryFound = false;
24
25
    /**
26
     * @var boolean set to true once a boundary belonging to this parent's part
27
     *      is found.
28
     */
29
    protected $parentBoundaryFound = false;
30
31
    /**
32
     * @var bool|null|string FALSE if not queried for in the content-type
33
     *      header of this part, NULL if the current part does not have a
34
     *      boundary, and otherwise contains the value of the boundary parameter
35
     *      of the content-type header if the part contains one.
36
     */
37
    protected $mimeBoundary = false;
38
39
    /**
40
     * @var bool true once all children of this part have been parsed.
41
     */
42
    protected $allChildrenParsed = false;
43
44
    /**
45
     * @var ParserPartProxy[] Parsed children used as a 'first-in-first-out'
46
     *      stack as children are parsed.
47
     */
48
    protected $children = [];
49
50
    /**
51
     * @var ParserPartProxy Reference to the last child added to this part.
52
     */
53
    protected $lastAddedChild = null;
54
55
    /**
56
     * Ensures that the last child added to this part is fully parsed (content
57
     * and children).
58
     */
59 106
    protected function ensureLastChildParsed()
60
    {
61 106
        if ($this->lastAddedChild !== null) {
62 76
            $this->lastAddedChild->parseAll();
63
        }
64 106
    }
65
66
    /**
67
     * Parses the next child of this part and adds it to the 'stack' of
68
     * children.
69
     */
70 106
    protected function parseNextChild()
71
    {
72 106
        if ($this->allChildrenParsed) {
73 19
            return;
74
        }
75 106
        $this->parseContent();
76 106
        $this->ensureLastChildParsed();
77 106
        $next = $this->parser->parseNextChild($this);
78 106
        if ($next !== null) {
79 76
            array_push($this->children, $next);
80 76
            $this->lastAddedChild = $next;
81
        } else {
82 106
            $this->allChildrenParsed = true;
83
        }
84 106
    }
85
86
    /**
87
     * Returns the next child part if one exists, popping it from the internal
88
     * 'stack' of children, attempting to parse a new one if the stack is empty,
89
     * and returning null if there are no more children.
90
     *
91
     * @return IMessagePart|null the child part.
92
     */
93 104
    public function popNextChild()
94
    {
95 104
        if (empty($this->children)) {
96 104
            $this->parseNextChild();
97
        }
98 104
        $proxy = array_shift($this->children);
99 104
        return ($proxy !== null) ? $proxy->getPart() : null;
100
    }
101
102
    /**
103
     * Parses all content and children for this part.
104
     */
105 104
    public function parseAll()
106
    {
107 104
        $this->parseContent();
108 104
        while (!$this->allChildrenParsed) {
109 26
            $this->parseNextChild();
110
        }
111 104
    }
112
113
    /**
114
     * Returns a ParameterHeader representing the parsed Content-Type header for
115
     * this part.
116
     *
117
     * @return \ZBateson\MailMimeParser\Header\ParameterHeader
118
     */
119 78
    public function getContentType()
120
    {
121 78
        return $this->getHeaderContainer()->get(HeaderConsts::CONTENT_TYPE);
122
    }
123
124
    /**
125
     * Returns the parsed boundary parameter of the Content-Type header if set
126
     * for a multipart message part.
127
     *
128
     * @return string
129
     */
130 77
    public function getMimeBoundary()
131
    {
132 77
        if ($this->mimeBoundary === false) {
133 77
            $this->mimeBoundary = null;
134 77
            $contentType = $this->getContentType();
135 77
            if ($contentType !== null) {
136 75
                $this->mimeBoundary = $contentType->getValueFor('boundary');
137
            }
138
        }
139 77
        return $this->mimeBoundary;
140
    }
141
142
    /**
143
     * Returns true if the passed $line of read input matches this part's mime
144
     * boundary, or any of its parent's mime boundaries for a multipart message.
145
     *
146
     * If the passed $line is the ending boundary for the current part,
147
     * $this->isEndBoundaryFound will return true after.
148
     *
149
     * @param string $line
150
     * @return bool
151
     */
152 75
    public function setEndBoundaryFound($line)
153
    {
154 75
        $boundary = $this->getMimeBoundary();
155 75
        if ($this->getParent() !== null && $this->getParent()->setEndBoundaryFound($line)) {
0 ignored issues
show
Bug introduced by
The method setEndBoundaryFound() does not exist on ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy. It seems like you code against a sub-type of ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy such as ZBateson\MailMimeParser\...oxy\ParserMimePartProxy. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

155
        if ($this->getParent() !== null && $this->getParent()->/** @scrutinizer ignore-call */ setEndBoundaryFound($line)) {
Loading history...
156 73
            $this->parentBoundaryFound = true;
157 73
            return true;
158 75
        } elseif ($boundary !== null) {
0 ignored issues
show
introduced by
The condition $boundary !== null is always true.
Loading history...
159 73
            if ($line === "--$boundary--") {
160 73
                $this->endBoundaryFound = true;
161 73
                return true;
162 73
            } elseif ($line === "--$boundary") {
163 73
                return true;
164
            }
165
        }
166 37
        return false;
167
    }
168
169
    /**
170
     * Returns true if the parser passed an input line to setEndBoundary that
171
     * matches a parent's mime boundary, and the following input belongs to a
172
     * new part under its parent.
173
     *
174
     * @return bool
175
     */
176 102
    public function isParentBoundaryFound()
177
    {
178 102
        return ($this->parentBoundaryFound);
179
    }
180
181
    /**
182
     * Returns true if an end boundary was found for this part.
183
     *
184
     * @return bool
185
     */
186 75
    public function isEndBoundaryFound()
187
    {
188 75
        return ($this->endBoundaryFound);
189
    }
190
191
    /**
192
     * Called once EOF is reached while reading content.  The method sets the
193
     * flag used by isParentBoundaryFound() to true on this part and all parent
194
     * parts.
195
     */
196 96
    public function setEof()
197
    {
198 96
        $this->parentBoundaryFound = true;
199 96
        if ($this->getParent() !== null) {
200 65
            $this->getParent()->setEof();
0 ignored issues
show
Bug introduced by
The method setEof() does not exist on ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy. It seems like you code against a sub-type of ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy such as ZBateson\MailMimeParser\...oxy\ParserMimePartProxy. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

200
            $this->getParent()->/** @scrutinizer ignore-call */ setEof();
Loading history...
201
        }
202 96
    }
203
204
    /**
205
     * Sets the length of the last line ending read by MimeParser (e.g. 2 for
206
     * '\r\n', or 1 for '\n').
207
     *
208
     * The line ending may not belong specifically to this part, so
209
     * ParserMimePartProxy simply calls setLastLineEndingLength on its parent,
210
     * which must eventually reach a ParserMessageProxy which actually stores
211
     * the length.
212
     *
213
     * @param int $length
214
     */
215 73
    public function setLastLineEndingLength($length)
216
    {
217 73
        $this->getParent()->setLastLineEndingLength($length);
0 ignored issues
show
Bug introduced by
The method setLastLineEndingLength() does not exist on ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy. It seems like you code against a sub-type of ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy such as ZBateson\MailMimeParser\...oxy\ParserMimePartProxy. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

217
        $this->getParent()->/** @scrutinizer ignore-call */ setLastLineEndingLength($length);
Loading history...
218 73
    }
219
220
    /**
221
     * Returns the length of the last line ending read by MimeParser (e.g. 2 for
222
     * '\r\n', or 1 for '\n').
223
     *
224
     * The line ending may not belong specifically to this part, so
225
     * ParserMimePartProxy simply calls getLastLineEndingLength on its parent,
226
     * which must eventually reach a ParserMessageProxy which actually keeps
227
     * the length and returns it.
228
     *
229
     * @return int the length of the last line ending read
230
     */
231 73
    public function getLastLineEndingLength()
232
    {
233 73
        return $this->getParent()->getLastLineEndingLength();
0 ignored issues
show
Bug introduced by
The method getLastLineEndingLength() does not exist on ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy. It seems like you code against a sub-type of ZBateson\MailMimeParser\...r\Proxy\ParserPartProxy such as ZBateson\MailMimeParser\...oxy\ParserMimePartProxy. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

233
        return $this->getParent()->/** @scrutinizer ignore-call */ getLastLineEndingLength();
Loading history...
234
    }
235
}
236