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:  * This file contains the generic db item class.
  4:  *
  5:  * @package Core
  6:  * @subpackage GenericDB
  7:  * @version SVN Revision $Rev:$
  8:  *
  9:  * @author Timo Hummel
 10:  * @author Murat Purc <murat@purc.de>
 11:  * @copyright four for business AG <www.4fb.de>
 12:  * @license http://www.contenido.org/license/LIZENZ.txt
 13:  * @link http://www.4fb.de
 14:  * @link http://www.contenido.org
 15:  */
 16: 
 17: defined('CON_FRAMEWORK') || die('Illegal call: Missing framework initialization - request aborted.');
 18: 
 19: /**
 20:  * Class Item
 21:  * Abstract class for database based items.
 22:  *
 23:  * @package Core
 24:  * @subpackage GenericDB
 25:  */
 26: abstract class Item extends cItemBaseAbstract {
 27: 
 28:     /**
 29:      * Storage of the source table to use for the user informations
 30:      *
 31:      * @var array
 32:      */
 33:     public $values;
 34: 
 35:     /**
 36:      * Storage of the fields which were modified, where the keys are the
 37:      * fieldnames and the values just simple booleans.
 38:      *
 39:      * @var array
 40:      */
 41:     protected $modifiedValues;
 42: 
 43:     /**
 44:      * Stores the old primary key, just in case somebody wants to change it
 45:      *
 46:      * @var string
 47:      */
 48:     protected $oldPrimaryKey;
 49: 
 50:     /**
 51:      * List of funcion names of the filters used when data is stored to the db.
 52:      *
 53:      * @var array
 54:      */
 55:     protected $_arrInFilters = array(
 56:         'htmlspecialchars',
 57:         'addslashes'
 58:     );
 59: 
 60:     /**
 61:      * List of funcion names of the filtersused when data is retrieved from the
 62:      * db
 63:      *
 64:      * @var array
 65:      */
 66:     protected $_arrOutFilters = array(
 67:         'stripslashes',
 68:         'htmldecode'
 69:     );
 70: 
 71:     /**
 72:      * Class name of meta object
 73:      *
 74:      * @var string
 75:      */
 76:     protected $_metaObject;
 77: 
 78:     /**
 79:      * Last executed SQL statement
 80:      *
 81:      * @var string
 82:      */
 83:     protected $_lastSQL;
 84: 
 85:     /**
 86:      * Constructor function
 87:      *
 88:      * @param string $sTable The table to use as information source
 89:      * @param string $sPrimaryKey The primary key to use
 90:      * @param int $iLifetime
 91:      */
 92:     public function __construct($sTable, $sPrimaryKey) {
 93:         parent::__construct($sTable, $sPrimaryKey, get_parent_class($this));
 94:     }
 95: 
 96:     /**
 97:      * Resets class variables back to default
 98:      * This is handy in case a new item is tried to be loaded into this class instance.
 99:      */
100:     protected function _resetItem() {
101:         parent::_resetItem();
102: 
103:         // make sure not to reset filters because then default filters would always be used for loading
104:         $this->values = null;
105:         $this->modifiedValues = null;
106:         $this->_metaObject = null;
107:         $this->_lastSQL = null;
108:     }
109: 
110:     /**
111:      * Loads an item by colum/field from the database.
112:      *
113:      * @param string $sField Specifies the field
114:      * @param mixed $mValue Specifies the value
115:      * @param bool $bSafe Use inFilter or not
116:      * @throws cException if more than one item has been found matching the
117:      *         given arguments
118:      * @return bool True if the load was successful
119:      */
120:     public function loadBy($sField, $mValue, $bSafe = true) {
121:         // reset class variables back to default before loading
122:         $this->_resetItem();
123: 
124:         if ($bSafe) {
125:             $mValue = $this->_inFilter($mValue);
126:         }
127: 
128:         // check, if cache contains a matching entry
129:         $aRecordSet = NULL;
130:         if ($sField === $this->primaryKey) {
131:             $aRecordSet = $this->_oCache->getItem($mValue);
132:         } else {
133:             $aRecordSet = $this->_oCache->getItemByProperty($sField, $mValue);
134:         }
135: 
136:         if ($aRecordSet) {
137:             // entry in cache found, load entry from cache
138:             $this->loadByRecordSet($aRecordSet);
139:             return true;
140:         }
141: 
142:         // SQL-Statement to select by field
143:         $sql = "SELECT * FROM `%s` WHERE %s = '%s'";
144:         $sql = $this->db->prepare($sql, $this->table, $sField, $mValue);
145: 
146:         // Query the database
147:         $this->db->query($sql);
148: 
149:         $this->_lastSQL = $sql;
150: 
151:         if ($this->db->numRows() > 1) {
152:             $msg = "Tried to load a single line with field $sField and value $mValue from " . $this->table . " but found more than one row";
153:             throw new cException($msg);
154:         }
155: 
156:         // Advance to the next record, return false if nothing found
157:         if (!$this->db->nextRecord()) {
158:             return false;
159:         }
160: 
161:         $this->loadByRecordSet($this->db->toArray());
162:         $this->virgin = false;
163:         return true;
164:     }
165: 
166:     /**
167:      * Loads an item by colums/fields from the database.
168:      *
169:      * @param array $aAttributes associative array with field / value pairs
170:      * @param bool $bSafe Use inFilter or not
171:      * @throws cException if more than one item could be found matching the
172:      *         given arguments
173:      * @return bool True if the load was successful
174:      */
175:     public function loadByMany(array $aAttributes, $bSafe = true) {
176:         // reset class variables back to default before loading
177:         $this->_resetItem();
178: 
179:         if ($bSafe) {
180:             $aAttributes = $this->_inFilter($aAttributes);
181:         }
182: 
183:         // check, if cache contains a matching entry
184:         $aRecordSet = NULL;
185:         if (count($aAttributes) == 1 && isset($aAttributes[$this->primaryKey])) {
186:             $aRecordSet = $this->_oCache->getItem($aAttributes[$this->primaryKey]);
187:         } else {
188:             $aRecordSet = $this->_oCache->getItemByProperties($aAttributes);
189:         }
190: 
191:         if ($aRecordSet) {
192:             // entry in cache found, load entry from cache
193:             $this->loadByRecordSet($aRecordSet);
194:             return true;
195:         }
196: 
197:         // SQL-Statement to select by fields
198:         $sql = 'SELECT * FROM `:mytab` WHERE';
199:         foreach (array_keys($aAttributes) as $sKey) {
200:             // add quotes if key is a string
201:             if (is_string($sKey)) {
202:                 $sql .= " $sKey = ':$sKey' AND";
203:             } else {
204:                 $sql .= " $sKey = :$sKey AND";
205:             }
206:         }
207:         // strip the last " AND" token
208:         $sql = substr($sql, 0, strlen($sql) - 4);
209:         $sql = $this->db->prepare($sql, array_merge(array(
210:             'mytab' => $this->table
211:         ), $aAttributes));
212: 
213:         // Query the database
214:         $this->db->query($sql);
215: 
216:         $this->_lastSQL = $sql;
217: 
218:         if ($this->db->numRows() > 1) {
219:             $msg = 'Tried to load a single line with fields ' . print_r(array_keys($aAttributes), true) . ' and values ' . print_r(array_values($aAttributes), true) . ' from ' . $this->table . ' but found more than one row';
220:             throw new cException($msg);
221:         }
222: 
223:         // Advance to the next record, return false if nothing found
224:         if (!$this->db->nextRecord()) {
225:             return false;
226:         }
227: 
228:         $this->loadByRecordSet($this->db->toArray());
229:         $this->virgin = false;
230:         return true;
231:     }
232: 
233:     /**
234:      * Loads an item by passed where clause from the database.
235:      * This function is expensive, since it executes allways a query to the
236:      * database
237:      * to retrieve the primary key, even if the record set is aleady cached.
238:      * NOTE: Passed value has to be escaped before. This will not be done by
239:      * this function.
240:      *
241:      * @param string $sWhere The where clause like 'idart = 123 AND idlang = 1'
242:      * @throws cException if more than one item could be found matching the
243:      *         given where clause
244:      * @return bool True if the load was successful
245:      */
246:     protected function _loadByWhereClause($sWhere) {
247:         // SQL-Statement to select by whee clause
248:         $sql = "SELECT %s AS pk FROM `%s` WHERE " . (string) $sWhere;
249:         $sql = $this->db->prepare($sql, $this->primaryKey, $this->table);
250: 
251:         // Query the database
252:         $this->db->query($sql);
253: 
254:         $this->_lastSQL = $sql;
255: 
256:         if ($this->db->numRows() > 1) {
257:             $msg = "Tried to load a single line with where clause '" . $sWhere . "' from " . $this->table . " but found more than one row";
258:             throw new cException($msg);
259:         }
260: 
261:         // Advance to the next record, return false if nothing found
262:         if (!$this->db->nextRecord()) {
263:             return false;
264:         }
265: 
266:         $id = $this->db->f('pk');
267:         return $this->loadByPrimaryKey($id);
268:     }
269: 
270:     /**
271:      * Loads an item by ID from the database.
272:      *
273:      * @param string $mValue Specifies the primary key value
274:      * @return bool True if the load was successful
275:      */
276:     public function loadByPrimaryKey($mValue) {
277:         $bSuccess = $this->loadBy($this->primaryKey, $mValue);
278: 
279:         if ($bSuccess == true && method_exists($this, '_onLoad')) {
280:             $this->_onLoad();
281:         }
282: 
283:         return $bSuccess;
284:     }
285: 
286:     /**
287:      * Loads an item by it's recordset.
288:      *
289:      * @param array $aRecordSet The recordset of the item
290:      */
291:     public function loadByRecordSet(array $aRecordSet) {
292:         $this->values = $aRecordSet;
293:         $this->oldPrimaryKey = $this->values[$this->primaryKey];
294:         $this->virgin = false;
295:         $this->_oCache->addItem($this->oldPrimaryKey, $this->values);
296: 
297:         if (method_exists($this, '_onLoad')) {
298:             $this->_onLoad();
299:         }
300:     }
301: 
302:     /**
303:      * Checks if a the item is already loaded.
304:      *
305:      * @return bool
306:      */
307:     public function isLoaded() {
308:         return !$this->virgin;
309:     }
310: 
311:     /**
312:      * Function which is called whenever an item is loaded.
313:      * Inherited classes should override this function if desired.
314:      */
315:     protected function _onLoad() {
316:     }
317: 
318:     /**
319:      * Gets the value of a specific field.
320:      *
321:      * @param string $sField Specifies the field to retrieve
322:      * @param bool $bSafe Flag to run defined outFilter on passed value
323:      * @return mixed Value of the field
324:      */
325:     public function getField($sField, $bSafe = true) {
326:         if ($this->virgin == true) {
327:             $this->lasterror = 'No item loaded';
328:             return false;
329:         }
330: 
331:         if (true == $bSafe) {
332:             return $this->outFilter($this->values[$sField]);
333:         } else {
334:             return $this->values[$sField];
335:         }
336:     }
337: 
338:     /**
339:      * Wrapper for getField (less to type).
340:      *
341:      * @param string $sField Specifies the field to retrieve
342:      * @param bool $bSafe Flag to run defined outFilter on passed value
343:      * @return mixed Value of the field
344:      */
345:     public function get($sField, $bSafe = true) {
346:         return $this->getField($sField, $bSafe);
347:     }
348: 
349:     /**
350:      * Sets the value of a specific field.
351:      *
352:      * @param string $sField Field name
353:      * @param string $mValue Value to set
354:      * @param bool $bSafe Flag to run defined inFilter on passed value
355:      * @return bool
356:      */
357:     public function setField($sField, $mValue, $bSafe = true) {
358:         if ($this->virgin == true) {
359:             $this->lasterror = 'No item loaded';
360:             return false;
361:         }
362: 
363:         if ($sField == $this->primaryKey) {
364:             $this->oldPrimaryKey = $this->values[$sField];
365:         }
366: 
367:         // apply filter on value
368:         if (true == $bSafe) {
369:             $mValue = $this->_inFilter($mValue);
370:         }
371: 
372:         // flag as modified
373:         if ($this->values[$sField] != $mValue || strlen($this->values[$sField]) != strlen($mValue)) {
374:             $this->modifiedValues[$sField] = true;
375:         }
376: 
377:         // set new value
378:         $this->values[$sField] = $mValue;
379: 
380:         return true;
381:     }
382: 
383:     /**
384:      * Shortcut to setField.
385:      *
386:      * @param string $sField Field name
387:      * @param string $mValue Value to set
388:      * @param bool $bSafe Flag to run defined inFilter on passed value
389:      */
390:     public function set($sField, $mValue, $bSafe = true) {
391:         return $this->setField($sField, $mValue, $bSafe);
392:     }
393: 
394:     /**
395:      * Stores the loaded and modified item to the database.
396:      *
397:      * @return bool
398:      */
399:     public function store() {
400:         $this->_executeCallbacks(self::STORE_BEFORE, get_class($this), array(
401:             $this
402:         ));
403: 
404:         if ($this->virgin == true) {
405:             $this->lasterror = 'No item loaded';
406:             $this->_executeCallbacks(self::STORE_FAILURE, get_class($this), array(
407:                 $this
408:             ));
409:             return false;
410:         }
411: 
412:         $sql = 'UPDATE `' . $this->table . '` SET ';
413:         $first = true;
414: 
415:         if (!is_array($this->modifiedValues)) {
416:             $this->_executeCallbacks(self::STORE_SUCCESS, get_class($this), array(
417:                 $this
418:             ));
419:             return true;
420:         }
421: 
422:         foreach ($this->modifiedValues as $key => $bValue) {
423:             $value = $this->values[$key];
424:             if (is_string($value)) {
425:                 $value = $this->db->escape($value);
426:             }
427: 
428:             if ($first == true) {
429:                 $sql .= "`$key` = '" . $value . "'";
430:                 $first = false;
431:             } else {
432:                 $sql .= ", `$key` = '" . $value . "'";
433:             }
434:         }
435: 
436:         $sql .= " WHERE " . $this->primaryKey . " = '" . $this->oldPrimaryKey . "'";
437: 
438:         $this->db->query($sql);
439: 
440:         $this->_lastSQL = $sql;
441: 
442:         if ($this->db->affectedRows() > 0) {
443:             $this->_oCache->addItem($this->oldPrimaryKey, $this->values);
444:             $this->_executeCallbacks(self::STORE_SUCCESS, get_class($this), array(
445:                 $this
446:             ));
447:             return true;
448:         }
449: 
450:         $this->_executeCallbacks(self::STORE_FAILURE, get_class($this), array(
451:             $this
452:         ));
453:         return false;
454:     }
455: 
456:     /**
457:      * Returns current item data as an assoziative array.
458:      *
459:      * @return array false
460:      */
461:     public function toArray() {
462:         if ($this->virgin == true) {
463:             $this->lasterror = 'No item loaded';
464:             return false;
465:         }
466: 
467:         $aReturn = array();
468:         foreach ($this->values as $field => $value) {
469:             $aReturn[$field] = $this->getField($field);
470:         }
471:         return $aReturn;
472:     }
473: 
474:     /**
475:      * Returns current item data as an object.
476:      *
477:      * @return stdClass false
478:      */
479:     public function toObject() {
480:         $return = $this->toArray();
481:         return (false !== $return) ? (object) $return : $return;
482:     }
483: 
484:     /**
485:      * Sets a custom property.
486:      *
487:      * @param string $sType Specifies the type
488:      * @param string $sName Specifies the name
489:      * @param mixed $mValue Specifies the value
490:      * @param int $iClient Id of client to set property for
491:      * @return bool
492:      */
493:     public function setProperty($sType, $sName, $mValue, $iClient = 0) {
494:         // If this object wasn't loaded before, return false
495:         if ($this->virgin == true) {
496:             $this->lasterror = 'No item loaded';
497:             return false;
498:         }
499: 
500:         // Set the value
501:         $oProperties = $this->_getPropertiesCollectionInstance($iClient);
502:         $bResult = $oProperties->setValue($this->primaryKey, $this->get($this->primaryKey), $sType, $sName, $mValue);
503:         return $bResult;
504:     }
505: 
506:     /**
507:      * Returns a custom property.
508:      *
509:      * @param string $sType Specifies the type
510:      * @param string $sName Specifies the name
511:      * @param int $iClient Id of client to set property for
512:      * @return mixed Value of the given property or false
513:      */
514:     public function getProperty($sType, $sName, $iClient = 0) {
515:         // If this object wasn't loaded before, return false
516:         if ($this->virgin == true) {
517:             $this->lasterror = 'No item loaded';
518:             return false;
519:         }
520: 
521:         // Return the value
522:         $oProperties = $this->_getPropertiesCollectionInstance($iClient);
523:         $mValue = $oProperties->getValue($this->primaryKey, $this->get($this->primaryKey), $sType, $sName);
524:         return $mValue;
525:     }
526: 
527:     /**
528:      * Deletes a custom property.
529:      *
530:      * @param string $sType Specifies the type
531:      * @param string $sName Specifies the name
532:      * @param int $iClient Id of client to delete properties
533:      * @return bool
534:      */
535:     public function deleteProperty($sType, $sName, $iClient = 0) {
536:         // If this object wasn't loaded before, return false
537:         if ($this->virgin == true) {
538:             $this->lasterror = 'No item loaded';
539:             return false;
540:         }
541: 
542:         // Delete the value
543:         $oProperties = $this->_getPropertiesCollectionInstance($iClient);
544:         $bResult = $oProperties->deleteValue($this->primaryKey, $this->get($this->primaryKey), $sType, $sName);
545:         return $bResult;
546:     }
547: 
548:     /**
549:      * Deletes a custom property by its id.
550:      *
551:      * @param int $idprop Id of property
552:      * @return bool
553:      */
554:     public function deletePropertyById($idprop) {
555:         $oProperties = $this->_getPropertiesCollectionInstance();
556:         return $oProperties->delete($idprop);
557:     }
558: 
559:     ///**
560:     // * Deletes the current item
561:     // */
562:     // Method doesn't work, remove in future versions
563:     // function delete()
564:     // {
565:     // $this->_collectionInstance->delete($item->get($this->primaryKey));
566:     // }
567: 
568:     /**
569:      * Define the filter functions used when data is being stored or retrieved
570:      * from the database.
571:      *
572:      * Examples:
573:      * <pre>
574:      * $obj->setFilters(array('addslashes'), array('stripslashes'));
575:      * $obj->setFilters(array('htmlencode', 'addslashes'), array('stripslashes',
576:      * 'htmlencode'));
577:      * </pre>
578:      *
579:      * @param array $aInFilters Array with function names
580:      * @param array $aOutFilters Array with function names
581:      */
582:     public function setFilters($aInFilters = array(), $aOutFilters = array()) {
583:         $this->_arrInFilters = $aInFilters;
584:         $this->_arrOutFilters = $aOutFilters;
585:     }
586: 
587:     /**
588:      * Filters the passed data using the functions defines in the _arrInFilters
589:      * array.
590:      *
591:      * @param mixed $mData Data to filter
592:      * @return mixed Filtered data
593:      * @todo This method is used from public scope, but it should be protected
594:      * @see setFilters()
595:      */
596:     public function _inFilter($mData) {
597:         foreach ($this->_arrInFilters as $_function) {
598:             if (function_exists($_function)) {
599:                 if (is_array($mData)) {
600:                     foreach ($mData as $key => $value) {
601:                         $mData[$key] = $_function($value);
602:                     }
603:                 } else {
604:                     $mData = $_function($mData);
605:                 }
606:             }
607:         }
608:         return $mData;
609:     }
610: 
611:     /**
612:      * Filters the passed data using the functions defines in the _arrOutFilters
613:      * array.
614:      *
615:      *
616:      * @param mixed $mData Data to filter
617:      * @return mixed Filtered data
618:      * @see setFilters()
619:      */
620:     public function outFilter($mData) {
621:         foreach ($this->_arrOutFilters as $_function) {
622:             if (function_exists($_function)) {
623:                 if (is_array($mData)) {
624:                     foreach ($mData as $key => $value) {
625:                         $mData[$key] = $_function($value);
626:                     }
627:                 } else {
628:                     $mData = $_function($mData);
629:                 }
630:             }
631:         }
632:         return $mData;
633:     }
634: 
635:     /**
636:      * Set meta object class name.
637:      *
638:      * @param string $metaObject
639:      */
640:     protected function _setMetaObject($metaObject) {
641:         $this->_metaObject = $metaObject;
642:     }
643: 
644:     /**
645:      * Return meta object instance.
646:      * This object might be retrieved from a global cache ($_metaObjectCache).
647:      *
648:      * @return object
649:      */
650:     public function getMetaObject() {
651:         global $_metaObjectCache;
652: 
653:         if (!is_array($_metaObjectCache)) {
654:             $_metaObjectCache = array();
655:         }
656: 
657:         $sClassName = $this->_metaObject;
658:         $qclassname = strtolower($sClassName);
659: 
660:         if (array_key_exists($qclassname, $_metaObjectCache)) {
661:             if (is_object($_metaObjectCache[$qclassname])) {
662:                 if (strtolower(get_class($_metaObjectCache[$qclassname])) == $qclassname) {
663:                     $_metaObjectCache[$qclassname]->setPayloadObject($this);
664:                     return $_metaObjectCache[$qclassname];
665:                 }
666:             }
667:         }
668: 
669:         if (class_exists($sClassName)) {
670:             $_metaObjectCache[$qclassname] = new $sClassName($this);
671:             return $_metaObjectCache[$qclassname];
672:         }
673:     }
674: }
675: 
CMS CONTENIDO 4.9.7 API documentation generated by ApiGen