Overview

Packages

  • CONTENIDO
  • Core
    • Authentication
    • Backend
    • Cache
    • CEC
    • Chain
    • ContentType
    • Database
    • Debug
    • Exception
    • Frontend
      • Search
      • URI
      • Util
    • GenericDB
      • Model
    • GUI
      • HTML
    • I18N
    • LayoutHandler
    • Log
    • Security
    • Session
    • Util
    • Validation
    • Versioning
    • XML
  • Module
    • ContentRssCreator
    • ContentSitemapHtml
    • ContentSitemapXml
    • ContentUserForum
    • NavigationTop
    • ScriptCookieDirective
  • mpAutoloaderClassMap
  • None
  • Plugin
    • ContentAllocation
    • CronjobOverview
    • FormAssistant
    • FrontendLogic
    • FrontendUsers
    • Linkchecker
    • ModRewrite
    • Newsletter
    • Repository
      • FrontendNavigation
      • KeywordDensity
    • SearchSolr
    • SmartyWrapper
    • UrlShortener
    • UserForum
    • Workflow
  • PluginManager
  • Setup
    • Form
    • GUI
    • Helper
      • Environment
      • Filesystem
      • MySQL
      • PHP
    • UpgradeJob
  • Smarty
    • Cacher
    • Compiler
    • Config
    • Debug
    • PluginsBlock
    • PluginsFilter
    • PluginsFunction
    • PluginsInternal
    • PluginsModifier
    • PluginsModifierCompiler
    • PluginsShared
    • Security
    • Template
    • TemplateResources
  • Swift
    • ByteStream
    • CharacterStream
    • Encoder
    • Events
    • KeyCache
    • Mailer
    • Mime
    • Plugins
    • Transport

Classes

  • Swift_FailoverTransport
  • Swift_LoadBalancedTransport
  • Swift_MailTransport
  • Swift_Plugins_Loggers_ArrayLogger
  • Swift_Plugins_Loggers_EchoLogger
  • Swift_SendmailTransport
  • Swift_SmtpTransport
  • Swift_Transport_AbstractSmtpTransport
  • Swift_Transport_Esmtp_Auth_CramMd5Authenticator
  • Swift_Transport_Esmtp_Auth_LoginAuthenticator
  • Swift_Transport_Esmtp_Auth_PlainAuthenticator
  • Swift_Transport_Esmtp_AuthHandler
  • Swift_Transport_EsmtpTransport
  • Swift_Transport_FailoverTransport
  • Swift_Transport_LoadBalancedTransport
  • Swift_Transport_MailTransport
  • Swift_Transport_SendmailTransport
  • Swift_Transport_SimpleMailInvoker
  • Swift_Transport_StreamBuffer

Interfaces

  • Swift_Plugins_Logger
  • Swift_Plugins_Pop_Pop3Exception
  • Swift_Transport
  • Swift_Transport_Esmtp_Authenticator
  • Swift_Transport_EsmtpHandler
  • Swift_Transport_IoBuffer
  • Swift_Transport_MailInvoker
  • Swift_Transport_SmtpAgent
  • Swift_TransportException
  • Overview
  • Package
  • Function
  • Todo
  • Download
  1: <?php
  2: 
  3: /*
  4:  * This file is part of SwiftMailer.
  5:  * (c) 2004-2009 Chris Corbyn
  6:  *
  7:  * For the full copyright and license information, please view the LICENSE
  8:  * file that was distributed with this source code.
  9:  */
 10: 
 11: /**
 12:  * An abstract base MIME Header.
 13:  * @package Swift
 14:  * @subpackage Mime
 15:  * @author Chris Corbyn
 16:  */
 17: abstract class Swift_Mime_Headers_AbstractHeader implements Swift_Mime_Header
 18: {
 19:     /**
 20:      * The name of this Header.
 21:      * @var string
 22:      * @access private
 23:      */
 24:     private $_name;
 25: 
 26:     /**
 27:      * The Grammar used for this Header.
 28:      * @var Swift_Mime_Grammar
 29:      * @access private
 30:      */
 31:     private $_grammar;
 32: 
 33:     /**
 34:      * The Encoder used to encode this Header.
 35:      * @var Swift_Encoder
 36:      * @access private
 37:      */
 38:     private $_encoder;
 39: 
 40:     /**
 41:      * The maximum length of a line in the header.
 42:      * @var int
 43:      * @access private
 44:      */
 45:     private $_lineLength = 78;
 46: 
 47:     /**
 48:      * The language used in this Header.
 49:      * @var string
 50:      */
 51:     private $_lang;
 52: 
 53:     /**
 54:      * The character set of the text in this Header.
 55:      * @var string
 56:      * @access private
 57:      */
 58:     private $_charset = 'utf-8';
 59: 
 60:     /**
 61:      * The value of this Header, cached.
 62:      * @var string
 63:      * @access private
 64:      */
 65:     private $_cachedValue = null;
 66: 
 67:     /**
 68:      * Creates a new Header.
 69:      * @param Swift_Mime_Grammar $grammar
 70:      */
 71:     public function __construct(Swift_Mime_Grammar $grammar)
 72:     {
 73:         $this->setGrammar($grammar);
 74:     }
 75: 
 76:     /**
 77:      * Set the character set used in this Header.
 78:      * @param string $charset
 79:      */
 80:     public function setCharset($charset)
 81:     {
 82:         $this->clearCachedValueIf($charset != $this->_charset);
 83:         $this->_charset = $charset;
 84:         if (isset($this->_encoder)) {
 85:             $this->_encoder->charsetChanged($charset);
 86:         }
 87:     }
 88: 
 89:     /**
 90:      * Get the character set used in this Header.
 91:      * @return string
 92:      */
 93:     public function getCharset()
 94:     {
 95:         return $this->_charset;
 96:     }
 97: 
 98:     /**
 99:      * Set the language used in this Header.
100:      * For example, for US English, 'en-us'.
101:      * This can be unspecified.
102:      * @param string $lang
103:      */
104:     public function setLanguage($lang)
105:     {
106:         $this->clearCachedValueIf($this->_lang != $lang);
107:         $this->_lang = $lang;
108:     }
109: 
110:     /**
111:      * Get the language used in this Header.
112:      * @return string
113:      */
114:     public function getLanguage()
115:     {
116:         return $this->_lang;
117:     }
118: 
119:     /**
120:      * Set the encoder used for encoding the header.
121:      * @param Swift_Mime_HeaderEncoder $encoder
122:      */
123:     public function setEncoder(Swift_Mime_HeaderEncoder $encoder)
124:     {
125:         $this->_encoder = $encoder;
126:         $this->setCachedValue(null);
127:     }
128: 
129:     /**
130:      * Get the encoder used for encoding this Header.
131:      * @return Swift_Mime_HeaderEncoder
132:      */
133:     public function getEncoder()
134:     {
135:         return $this->_encoder;
136:     }
137: 
138:     /**
139:      * Set the grammar used for the header.
140:      * @param Swift_Mime_Grammar $grammar
141:      */
142:     public function setGrammar(Swift_Mime_Grammar $grammar)
143:     {
144:         $this->_grammar = $grammar;
145:         $this->setCachedValue(null);
146:     }
147: 
148:     /**
149:      * Get the grammar used for this Header.
150:      * @return Swift_Mime_Grammar
151:      */
152:     public function getGrammar()
153:     {
154:         return $this->_grammar;
155:     }
156: 
157:     /**
158:      * Get the name of this header (e.g. charset).
159:      * @return string
160:      */
161:     public function getFieldName()
162:     {
163:         return $this->_name;
164:     }
165: 
166:     /**
167:      * Set the maximum length of lines in the header (excluding EOL).
168:      * @param int $lineLength
169:      */
170:     public function setMaxLineLength($lineLength)
171:     {
172:         $this->clearCachedValueIf($this->_lineLength != $lineLength);
173:         $this->_lineLength = $lineLength;
174:     }
175: 
176:     /**
177:      * Get the maximum permitted length of lines in this Header.
178:      * @return int
179:      */
180:     public function getMaxLineLength()
181:     {
182:         return $this->_lineLength;
183:     }
184: 
185:     /**
186:      * Get this Header rendered as a RFC 2822 compliant string.
187:      * @return string
188:      * @throws Swift_RfcComplianceException
189:      */
190:     public function toString()
191:     {
192:         return $this->_tokensToString($this->toTokens());
193:     }
194: 
195:     /**
196:      * Returns a string representation of this object.
197:      *
198:      * @return string
199:      *
200:      * @see toString()
201:      */
202:     public function __toString()
203:     {
204:         return $this->toString();
205:     }
206: 
207:     // -- Points of extension
208: 
209:     /**
210:      * Set the name of this Header field.
211:      * @param string $name
212:      * @access protected
213:      */
214:     protected function setFieldName($name)
215:     {
216:         $this->_name = $name;
217:     }
218: 
219:     /**
220:      * Produces a compliant, formatted RFC 2822 'phrase' based on the string given.
221:      * @param  Swift_Mime_Header        $header
222:      * @param  string                   $string  as displayed
223:      * @param  string                   $charset of the text
224:      * @param  Swift_Mime_HeaderEncoder $encoder
225:      * @param  boolean                  $shorten the first line to make remove for header name
226:      * @return string
227:      */
228:     protected function createPhrase(Swift_Mime_Header $header, $string, $charset, Swift_Mime_HeaderEncoder $encoder = null, $shorten = false)
229:     {
230:         //Treat token as exactly what was given
231:         $phraseStr = $string;
232:         //If it's not valid
233:         if (!preg_match('/^' . $this->getGrammar()->getDefinition('phrase') . '$/D', $phraseStr)) {
234:             // .. but it is just ascii text, try escaping some characters
235:             // and make it a quoted-string
236:             if (preg_match('/^' . $this->getGrammar()->getDefinition('text') . '*$/D', $phraseStr)) {
237:                 $phraseStr = $this->getGrammar()->escapeSpecials(
238:                     $phraseStr, array('"'), $this->getGrammar()->getSpecials()
239:                     );
240:                 $phraseStr = '"' . $phraseStr . '"';
241:             } else { // ... otherwise it needs encoding
242:                 //Determine space remaining on line if first line
243:                 if ($shorten) {
244:                     $usedLength = strlen($header->getFieldName() . ': ');
245:                 } else {
246:                     $usedLength = 0;
247:                 }
248:                 $phraseStr = $this->encodeWords($header, $string, $usedLength);
249:             }
250:         }
251: 
252:         return $phraseStr;
253:     }
254: 
255:     /**
256:      * Encode needed word tokens within a string of input.
257:      * @param  string $input
258:      * @param  string $usedLength, optional
259:      * @return string
260:      */
261:     protected function encodeWords(Swift_Mime_Header $header, $input, $usedLength = -1)
262:     {
263:         $value = '';
264: 
265:         $tokens = $this->getEncodableWordTokens($input);
266: 
267:         foreach ($tokens as $token) {
268:             //See RFC 2822, Sect 2.2 (really 2.2 ??)
269:             if ($this->tokenNeedsEncoding($token)) {
270:                 //Don't encode starting WSP
271:                 $firstChar = substr($token, 0, 1);
272:                 switch ($firstChar) {
273:                     case ' ':
274:                     case "\t":
275:                         $value .= $firstChar;
276:                         $token = substr($token, 1);
277:                 }
278: 
279:                 if (-1 == $usedLength) {
280:                     $usedLength = strlen($header->getFieldName() . ': ') + strlen($value);
281:                 }
282:                 $value .= $this->getTokenAsEncodedWord($token, $usedLength);
283: 
284:                 $header->setMaxLineLength(76); //Forefully override
285:             } else {
286:                 $value .= $token;
287:             }
288:         }
289: 
290:         return $value;
291:     }
292: 
293:     /**
294:      * Test if a token needs to be encoded or not.
295:      * @param  string  $token
296:      * @return boolean
297:      */
298:     protected function tokenNeedsEncoding($token)
299:     {
300:         return preg_match('~[\x00-\x08\x10-\x19\x7F-\xFF\r\n]~', $token);
301:     }
302: 
303:     /**
304:      * Splits a string into tokens in blocks of words which can be encoded quickly.
305:      * @param  string   $string
306:      * @return string[]
307:      */
308:     protected function getEncodableWordTokens($string)
309:     {
310:         $tokens = array();
311: 
312:         $encodedToken = '';
313:         //Split at all whitespace boundaries
314:         foreach (preg_split('~(?=[\t ])~', $string) as $token) {
315:             if ($this->tokenNeedsEncoding($token)) {
316:                 $encodedToken .= $token;
317:             } else {
318:                 if (strlen($encodedToken) > 0) {
319:                     $tokens[] = $encodedToken;
320:                     $encodedToken = '';
321:                 }
322:                 $tokens[] = $token;
323:             }
324:         }
325:         if (strlen($encodedToken)) {
326:             $tokens[] = $encodedToken;
327:         }
328: 
329:         return $tokens;
330:     }
331: 
332:     /**
333:      * Get a token as an encoded word for safe insertion into headers.
334:      * @param  string $token            to encode
335:      * @param  int    $firstLineOffset, optional
336:      * @return string
337:      */
338:     protected function getTokenAsEncodedWord($token, $firstLineOffset = 0)
339:     {
340:         //Adjust $firstLineOffset to account for space needed for syntax
341:         $charsetDecl = $this->_charset;
342:         if (isset($this->_lang)) {
343:             $charsetDecl .= '*' . $this->_lang;
344:         }
345:         $encodingWrapperLength = strlen(
346:             '=?' . $charsetDecl . '?' . $this->_encoder->getName() . '??='
347:             );
348: 
349:         if ($firstLineOffset >= 75) { //Does this logic need to be here?
350:             $firstLineOffset = 0;
351:         }
352: 
353:         $encodedTextLines = explode("\r\n",
354:             $this->_encoder->encodeString(
355:                 $token, $firstLineOffset, 75 - $encodingWrapperLength, $this->_charset
356:                 )
357:         );
358: 
359:         if (strtolower($this->_charset) !== 'iso-2022-jp') { // special encoding for iso-2022-jp using mb_encode_mimeheader
360:             foreach ($encodedTextLines as $lineNum => $line) {
361:                 $encodedTextLines[$lineNum] = '=?' . $charsetDecl .
362:                     '?' . $this->_encoder->getName() .
363:                     '?' . $line . '?=';
364:             }
365:         }
366: 
367:         return implode("\r\n ", $encodedTextLines);
368:     }
369: 
370:     /**
371:      * Generates tokens from the given string which include CRLF as individual tokens.
372:      * @param  string   $token
373:      * @return string[]
374:      * @access protected
375:      */
376:     protected function generateTokenLines($token)
377:     {
378:         return preg_split('~(\r\n)~', $token, -1, PREG_SPLIT_DELIM_CAPTURE);
379:     }
380: 
381:     /**
382:      * Set a value into the cache.
383:      * @param string $value
384:      * @access protected
385:      */
386:     protected function setCachedValue($value)
387:     {
388:         $this->_cachedValue = $value;
389:     }
390: 
391:     /**
392:      * Get the value in the cache.
393:      * @return string
394:      * @access protected
395:      */
396:     protected function getCachedValue()
397:     {
398:         return $this->_cachedValue;
399:     }
400: 
401:     /**
402:      * Clear the cached value if $condition is met.
403:      * @param boolean $condition
404:      * @access protected
405:      */
406:     protected function clearCachedValueIf($condition)
407:     {
408:         if ($condition) {
409:             $this->setCachedValue(null);
410:         }
411:     }
412: 
413:     // -- Private methods
414: 
415:     /**
416:      * Generate a list of all tokens in the final header.
417:      * @param  string $string The string to tokenize
418:      * @return array  An array of tokens as strings
419:      * @access protected
420:      */
421:     protected function toTokens($string = null)
422:     {
423:         if (is_null($string)) {
424:             $string = $this->getFieldBody();
425:         }
426: 
427:         $tokens = array();
428: 
429:         //Generate atoms; split at all invisible boundaries followed by WSP
430:         foreach (preg_split('~(?=[ \t])~', $string) as $token) {
431:             $tokens = array_merge($tokens, $this->generateTokenLines($token));
432:         }
433: 
434:         return $tokens;
435:     }
436: 
437:     /**
438:      * Takes an array of tokens which appear in the header and turns them into
439:      * an RFC 2822 compliant string, adding FWSP where needed.
440:      * @param  string[] $tokens
441:      * @return string
442:      * @access private
443:      */
444:     private function _tokensToString(array $tokens)
445:     {
446:         $lineCount = 0;
447:         $headerLines = array();
448:         $headerLines[] = $this->_name . ': ';
449:         $currentLine =& $headerLines[$lineCount++];
450: 
451:         //Build all tokens back into compliant header
452:         foreach ($tokens as $i => $token) {
453:             //Line longer than specified maximum or token was just a new line
454:             if (("\r\n" == $token) ||
455:                 ($i > 0 && strlen($currentLine . $token) > $this->_lineLength)
456:                 && 0 < strlen($currentLine))
457:             {
458:                 $headerLines[] = '';
459:                 $currentLine =& $headerLines[$lineCount++];
460:             }
461: 
462:             //Append token to the line
463:             if ("\r\n" != $token) {
464:                 $currentLine .= $token;
465:             }
466:         }
467: 
468:         //Implode with FWS (RFC 2822, 2.2.3)
469:         return implode("\r\n", $headerLines) . "\r\n";
470:     }
471: }
472: 
CMS CONTENIDO 4.9.7 API documentation generated by ApiGen