1  <?php
  2  /* Copyright (c) 2012, Geert Bergman (geert@scrivo.nl)
  3   * All rights reserved.
  4   *
  5   * Redistribution and use in source and binary forms, with or without
  6   * modification, are permitted provided that the following conditions are met:
  7   *
  8   * 1. Redistributions of source code must retain the above copyright notice,
  9   *    this list of conditions and the following disclaimer.
 10   * 2. Redistributions in binary form must reproduce the above copyright notice,
 11   *    this list of conditions and the following disclaimer in the documentation
 12   *    and/or other materials provided with the distribution.
 13   * 3. Neither the name of "Scrivo" nor the names of its contributors may be
 14   *    used to endorse or promote products derived from this software without
 15   *    specific prior written permission.
 16   *
 17   * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
 18   * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 19   * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 20   * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
 21   * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 22   * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 23   * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 24   * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 25   * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 26   * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 27   * POSSIBILITY OF SUCH DAMAGE.
 28   *
 29   * $Id: IdLabel.php 866 2013-08-25 16:22:35Z geert $
 30   */
 31  
 32  /**
 33   * Implementation of the \Scrivo\IdLabel class.
 34   */
 35  
 36  namespace Scrivo;
 37  
 38  /**
 39   * Class to represent id-label pairs.
 40   *
 41   * Object id's can be labeled in Scrivo, these labels then can be used as
 42   * constants in the template code. For instance suppose that the contact page
 43   * in a site has id 12349 then this id can be labeled "CONTACT". When loading
 44   * the page the label can be used instead of the id, thus allowing for clearer
 45   * program code. For example:
 46   *
 47   * \Scrivo\CachedData::load($context, 12349);
 48   * vs
 49   * \Scrivo\CachedData::load($context, $context->labels->CONTACT);
 50   *
 51   * Also deletion of labeled objects is not allowed: defining a label means
 52   * that the object has a special function in a project, deleting is likely
 53   * to cause an inconsistent project state.
 54   *
 55   * You can retrieve a labelled id by referring to its label as a member of
 56   * of an IdLabel object. A Scrivo Context object contains an IdLabel object
 57   * with all labelled ids for the contexts instance.
 58   *
 59   * $cfg = new Scrivo\Config();
 60   * $context = new Scrivo\Context($cfg, \Scrivo\User::PRIMARY_ADMIN_ID);
 61   * \Scrivo\CachedData::load($context, $context->labels->CONTACT);
 62   *
 63   * You can add and delete values using the set member:
 64   *
 65   * // Set an id-label pair
 66   * $context->labels->set($context, 123, \Scrivo\String("CONTACT"));
 67   * // Update an id-label pair
 68   * $context->labels->set($context, 123, \Scrivo\String("CONTACT_B"));
 69   * // Delete an id-label pair
 70   * $context->labels->set($context, 123);
 71   */
 72  class IdLabel implements \Iterator {
 73  
 74      /**
 75       * Array that holds the id-label pairs.
 76       * @var int[string]
 77       */
 78      private $labels;
 79  
 80      /**
 81       * Create an IdLabel object, the object will contain all the id-label pairs
 82       * that are defined for the given instance.
 83       *
 84       * @param \Scrivo\Context $context A Scrivo context.
 85       */
 86      protected function __construct(Context $context) {
 87          try {
 88  
 89              $sth $context->connection->prepare(
 90                  "SELECT id, label FROM id_label WHERE instance_id = :instId");
 91              $context->connection->bindInstance($sth);
 92              $sth->execute();
 93              $this->labels = array();
 94              while ($rd $sth->fetch(\PDO::FETCH_ASSOC)) {
 95                  $this->labels[$rd["label"]] = intval($rd["id"]);
 96              }
 97  
 98          } catch(\PDOException $e) {
 99              throw new \Scrivo\ResourceException($e);
100          }
101      }
102  
103      /**
104       * Select the id label pairs for a given context.
105       *
106       * @param \Scrivo\Context $context A Scrivo context.
107       */
108      public static function select(\Scrivo\Context $context) {
109          \Scrivo\ArgumentCheck::assertArgs(func_get_args(), array(null), 0);
110  
111          // Try to retieve form cache
112          $obj null;
113          if (isset($context->cache["LABELS"])) {
114              // Set the page from cache and set the context.
115              $obj $context->cache["LABELS"];
116          } else {
117              // Load the page and set it in the cache.
118              $obj = new \Scrivo\IdLabel($context);
119              $context->cache["LABELS"] = $obj;
120          }
121          return $obj;
122      }
123  
124      /**
125       * Test if a particular label was set.
126       *
127       * @param string $label The label to test.
128       *
129       * @return boolean True if the label was set, false if not.
130       */
131      public function __isset($label) {
132          return isset($this->labels[$label]);
133      }
134  
135      /**
136       * Accessor method for id-label members.
137       *
138       * @param string $label The label to retrieve the object id for.
139       *
140       * @return int The object id for the label.
141       */
142      public function __get($label) {
143          if (!$this->__isset($label)) {
144              throw new \Scrivo\SystemException("Invalid id-label '$label'");
145          }
146          return $this->labels[$label];
147      }
148  
149      /**
150       * Set an id-label pair.
151       *
152       * Use this method to insert/update/delete an id-label pair in the database.
153       * To delete a value just ommit the $label parameter.
154       *
155       * @param \Scrivo\Context $context A valid Scrivo context.
156       * @param int $id An object id.
157       * @param \Scrivo\String $label A label for the object id.
158       *
159       * @throws ApplicationException If the given label is not unique.
160       */
161      static function set(
162              \Scrivo\Context $context$id, \Scrivo\String $label=null) {
163          try {
164              $context->checkPermission(\Scrivo\AccessController::WRITE_ACCESS);
165  
166              $l "";
167  
168              // Check the label for uniqueness, throw an app exception if not.
169              if ($label && $label != "") {
170                  $l preg_replace(array("/[^ _A-Z0-9]/u""/ /u"),
171                          array("""_"), $label->toUpperCase());
172  
173                  $sth $context->connection->prepare(
174                      "SELECT COUNT(*) FROM id_label
175                      WHERE instance_id = :instId AND id <> :id AND label = :label");
176                  $context->connection->bindInstance($sth);
177                  $sth->bindValue(":id"$id, \PDO::PARAM_INT);
178                  $sth->bindValue(":label"$l, \PDO::PARAM_INT);
179                  $sth->execute();
180                  if ($sth->fetchColumn(0) > 0) {
181                      throw new \Scrivo\ApplicationException("Label not unique",
182                          \Scrivo\StatusCodes::LABEL_NOT_UNIQUE);
183                  }
184              }
185  
186              // Delete the label for this id.
187              $sth $context->connection->prepare(
188                  "DELETE FROM id_label WHERE instance_id = :instId AND id = :id");
189              $context->connection->bindInstance($sth);
190              $sth->bindValue(":id"$id, \PDO::PARAM_INT);
191              $sth->execute();
192  
193              // Insert a the new label for the id if given.
194              if ($l != "") {
195                  $sth $context->connection->prepare(
196                      "INSERT INTO id_label (instance_id, id, label)
197                      VALUES (:instId, :id, :label)");
198                  $context->connection->bindInstance($sth);
199                  $sth->bindValue(":id"$id, \PDO::PARAM_INT);
200                  $sth->bindValue(":label"$l, \PDO::PARAM_STR);
201                  $sth->execute();
202              }
203  
204              // Clear cache.
205              unset($context->cache["LABELS"]);
206  
207          } catch(\PDOException $e) {
208              throw new \Scrivo\ResourceException($e);
209          }
210      }
211  
212      /**
213       * Rewind the labels array so iterating will start at the beginning again.
214       */
215      function rewind() {
216          reset($this->labels);
217      }
218  
219      /**
220       * Get the current label when iterating.
221       */
222      function current() {
223          return current($this->labels);
224      }
225  
226      /**
227       * Get the key of the current label when iterating.
228       */
229      function key() {
230          return key($this->labels);
231      }
232  
233      /**
234       * Get the next label when iterating.
235       */
236      function next() {
237          next($this->labels);
238      }
239  
240      /**
241       * Check if the current key is valid.
242       */
243      function valid() {
244          return key($this->labels) ? true false;
245      }
246  
247  }
248  
249  ?>

Documentation generated by phpDocumentor 2.0.0a12 and ScrivoDocumentor on August 29, 2013