ItemFactory.php
Go to the documentation of this file.
00001 <?PHP 00002 00003 # 00004 # FILE: ItemFactory.php 00005 # 00006 # NOTES: 00007 # - for a derived class to use the temp methods the item record in the 00008 # database must include "DateLastModified" and "LastModifiedById" 00009 # fields, and the item object must include a "Delete()" method 00010 # 00011 # Copyright 2007-2010 Edward Almasy and Internet Scout 00012 # http://scout.wisc.edu 00013 # 00014 00015 class ItemFactory { 00016 00017 # ---- PUBLIC INTERFACE -------------------------------------------------- 00018 00019 # object constructor 00020 function ItemFactory($ItemClassName, $ItemTableName, $ItemIdFieldName, 00021 $ItemNameFieldName = NULL, $FieldId = NULL, $OrderOpsAllowed = FALSE) 00022 { 00023 # save item access names 00024 $this->ItemClassName = $ItemClassName; 00025 $this->ItemTableName = $ItemTableName; 00026 $this->ItemIdFieldName = $ItemIdFieldName; 00027 $this->ItemNameFieldName = $ItemNameFieldName; 00028 00029 # save field ID (if specified) 00030 if ($FieldId !== NULL) { $this->FieldId = intval($FieldId); } 00031 00032 # save flag indicating whether item type allows ordering operations 00033 $this->OrderOpsAllowed = $OrderOpsAllowed; 00034 if ($OrderOpsAllowed) 00035 { 00036 $this->OrderList = new DoublyLinkedItemList( 00037 $ItemTableName, $ItemIdFieldName); 00038 $this->SetOrderOpsCondition(NULL); 00039 } 00040 00041 # grab our own database handle 00042 $this->DB = new Database(); 00043 00044 # assume everything will be okay 00045 $this->ErrorStatus = 0; 00046 } 00047 00048 # return current error status 00049 function Status() { return $this->ErrorStatus; } 00050 00051 # get ID of currently edited item 00052 function GetCurrentEditedItemId() 00053 { 00054 # if ID available in session variable 00055 global $Session; 00056 if ($EditedIds = $Session->Get($this->ItemClassName."EditedIds")) 00057 { 00058 # look up value in session variable 00059 $ItemId = $EditedIds[0]; 00060 } 00061 else 00062 { 00063 # attempt to look up last temp item ID 00064 $ItemId = $this->GetLastTempItemId(); 00065 00066 # store it in session variable 00067 $EditedIds = array($ItemId); 00068 $Session->RegisterVariable($this->ItemClassName."EditedIds", $EditedIds); 00069 } 00070 00071 # return ID (if any) to caller 00072 return $ItemId; 00073 } 00074 00075 # set ID of currently edited item 00076 function SetCurrentEditedItemId($NewId) 00077 { 00078 # if edited ID array already stored for session 00079 global $Session; 00080 if ($EditedIds = $Session->Get($this->ItemClassName."EditedIds")) 00081 { 00082 # prepend new value to array 00083 array_unshift($EditedIds, $NewId); 00084 } 00085 else 00086 { 00087 # start with fresh array 00088 $EditedIds = array($NewId); 00089 } 00090 00091 # save in session variable 00092 $Session->RegisterVariable($this->ItemClassName."EditedIds", $EditedIds); 00093 } 00094 00095 # clear currently edited item ID 00096 function ClearCurrentEditedItemId() 00097 { 00098 # if edited item IDs available in a session variable 00099 global $Session; 00100 $SessionVarName = $this->ItemClassName."EditedIds"; 00101 if ($EditedIds = $Session->Get($SessionVarName)) 00102 { 00103 # remove current item from edited item ID array 00104 array_shift($EditedIds); 00105 00106 # if no further edited items 00107 if (count($EditedIds) < 1) 00108 { 00109 # destroy session variable 00110 $Session->UnregisterVariable($SessionVarName); 00111 } 00112 else 00113 { 00114 # save new shorter edited item ID array to session variable 00115 $Session->RegisterVariable($SessionVarName, $EditedIds); 00116 } 00117 } 00118 } 00119 00120 # clear currently edited item ID and item 00121 function ClearCurrentEditedItem() 00122 { 00123 # if current edited item is temp item 00124 $CurrentEditedItemId = $this->GetCurrentEditedItemId(); 00125 if ($CurrentEditedItemId < 0) 00126 { 00127 # delete temp item from DB 00128 $this->DB->Query("DELETE FROM ".$this->ItemTableName 00129 ." WHERE ".$this->ItemIdFieldName." = ".$CurrentEditedItemId); 00130 } 00131 00132 # clear current edited item ID 00133 $this->ClearCurrentEditedItemId(); 00134 } 00135 00136 # clear out any temp items more than one week old 00137 function CleanOutStaleTempItems() 00138 { 00139 # load array of stale items 00140 $this->DB->Query("SELECT ".$this->ItemIdFieldName." FROM ".$this->ItemTableName 00141 ." WHERE ".$this->ItemIdFieldName." < 0" 00142 ." AND DateLastModified < DATE_SUB(NOW(), INTERVAL 7 DAY)"); 00143 $ItemIds = $this->DB->FetchColumn($this->ItemIdFieldName); 00144 00145 # delete stale items 00146 foreach ($ItemIds as $ItemId) 00147 { 00148 $Item = new $this->ItemClassName($ItemId); 00149 $Item->Delete(); 00150 } 00151 } 00152 00153 # retrieve most recent temp item ID based on user ID 00154 # (returns NULL if no temp item found for that user ID) 00155 function GetLastTempItemId() 00156 { 00157 # retrieve ID of most recently modified temp item for this user 00158 global $User; 00159 $ItemId = $this->DB->Query("SELECT ".$this->ItemIdFieldName." FROM ".$this->ItemTableName 00160 ." WHERE LastModifiedById = '".$User->Get("UserId")."'" 00161 ." AND ".$this->ItemIdFieldName." < 0" 00162 ." ORDER BY ".$this->ItemIdFieldName." ASC" 00163 ." LIMIT 1", 00164 $this->ItemIdFieldName); 00165 00166 # return item to caller (or NULL if none found) 00167 return $ItemId; 00168 } 00169 00170 # return next item ID 00171 function GetNextItemId() 00172 { 00173 # if no highest item ID found 00174 $HighestItemId = $this->GetHighestItemId(); 00175 if ($HighestItemId <= 0) 00176 { 00177 # start with item ID 1 00178 $ItemId = 1; 00179 } 00180 else 00181 { 00182 # else use next ID available after highest 00183 $ItemId = $HighestItemId + 1; 00184 } 00185 00186 # return next ID to caller 00187 return $ItemId; 00188 } 00189 00190 # return highest item ID ($Condition should not include "WHERE") 00191 function GetHighestItemId($Condition = NULL, $IncludeTempItems = FALSE) 00192 { 00193 # if temp items are supposed to be included 00194 if ($IncludeTempItems) 00195 { 00196 # condition is only as supplied 00197 $ConditionString = ($Condition == NULL) ? "" : " WHERE ".$Condition; 00198 } 00199 else 00200 { 00201 # condition is non-negative IDs plus supplied condition 00202 $ConditionString = " WHERE ".$this->ItemIdFieldName." >= 0" 00203 .(($Condition == NULL) ? "" : " AND ".$Condition); 00204 } 00205 00206 # return highest item ID to caller 00207 return $this->DB->Query("SELECT ".$this->ItemIdFieldName 00208 ." FROM ".$this->ItemTableName 00209 .$ConditionString 00210 ." ORDER BY ".$this->ItemIdFieldName 00211 ." DESC LIMIT 1", 00212 $this->ItemIdFieldName); 00213 } 00214 00215 # return next temp item ID 00216 function GetNextTempItemId() 00217 { 00218 $LowestItemId = $this->DB->Query("SELECT ".$this->ItemIdFieldName 00219 ." FROM ".$this->ItemTableName 00220 ." ORDER BY ".$this->ItemIdFieldName 00221 ." ASC LIMIT 1", 00222 $this->ItemIdFieldName); 00223 if ($LowestItemId > 0) 00224 { 00225 $ItemId = -1; 00226 } 00227 else 00228 { 00229 $ItemId = $LowestItemId - 1; 00230 } 00231 return $ItemId; 00232 } 00233 00234 # return count of items 00235 function GetItemCount($Condition = NULL, $IncludeTempItems = FALSE) 00236 { 00237 # if condition was supplied 00238 if ($Condition != NULL) 00239 { 00240 # use condition 00241 $ConditionString = " WHERE ".$Condition; 00242 } 00243 else 00244 { 00245 # if field ID is available 00246 if (isset($this->FieldId)) 00247 { 00248 # use condition for matching field ID 00249 $ConditionString = " WHERE FieldId = ".intval($this->FieldId); 00250 } 00251 else 00252 { 00253 # use no condition 00254 $ConditionString = ""; 00255 } 00256 } 00257 00258 # if temp items are to be excluded 00259 if (!$IncludeTempItems) 00260 { 00261 # if a condition was previously set 00262 if (strlen($ConditionString)) 00263 { 00264 # add in condition to exclude temp items 00265 $ConditionString .= " AND (".$this->ItemIdFieldName." >= 0)"; 00266 } 00267 else 00268 { 00269 # use condition to exclude temp items 00270 $ConditionString = " WHERE ".$this->ItemIdFieldName." >= 0"; 00271 } 00272 } 00273 00274 # retrieve item count 00275 $Count = $this->DB->Query("SELECT COUNT(*) AS RecordCount" 00276 ." FROM ".$this->ItemTableName 00277 .$ConditionString, 00278 "RecordCount"); 00279 00280 # return count to caller 00281 return $Count; 00282 } 00283 00284 # return array of item IDs ($Condition should not include "WHERE") 00285 function GetItemIds($Condition = NULL, $IncludeTempItems = FALSE) 00286 { 00287 # if temp items are supposed to be included 00288 if ($IncludeTempItems) 00289 { 00290 # condition is only as supplied 00291 $ConditionString = ($Condition == NULL) ? "" : " WHERE ".$Condition; 00292 } 00293 else 00294 { 00295 # condition is non-negative IDs plus supplied condition 00296 $ConditionString = " WHERE ".$this->ItemIdFieldName." >= 0" 00297 .(($Condition == NULL) ? "" : " AND ".$Condition); 00298 } 00299 00300 # get item IDs 00301 $this->DB->Query("SELECT ".$this->ItemIdFieldName 00302 ." FROM ".$this->ItemTableName 00303 .$ConditionString); 00304 $ItemIds = $this->DB->FetchColumn($this->ItemIdFieldName); 00305 00306 # return IDs to caller 00307 return $ItemIds; 00308 } 00309 00310 # return latest modification date ($Condition should not include "WHERE") 00311 function GetLatestModificationDate($Condition = NULL) 00312 { 00313 # return modification date for item most recently changed 00314 $ConditionString = ($Condition == NULL) ? "" : " WHERE ".$Condition; 00315 return $this->DB->Query("SELECT MAX(DateLastModified) AS LastChangeDate" 00316 ." FROM ".$this->ItemTableName.$ConditionString, 00317 "LastChangeDate"); 00318 } 00319 00320 # retrieve item by item ID 00321 function GetItem($ItemId) 00322 { 00323 return new $this->ItemClassName($ItemId); 00324 } 00325 00330 function ItemExists($ItemId) 00331 { 00332 return $this->DB->Query("SELECT COUNT(*) AS ItemCount" 00333 ." FROM ".$this->ItemTableName 00334 ." WHERE ".$this->ItemIdFieldName." = ".intval($ItemId), "ItemCount") 00335 > 0 ? TRUE : FALSE; 00336 } 00337 00338 # retrieve item by name 00339 function GetItemByName($Name, $IgnoreCase = FALSE) 00340 { 00341 # error out if this is an illegal operation for this item type 00342 if ($this->ItemNameFieldName == NULL) 00343 { 00344 exit("<br>ERROR: attempt to get item by name on item type" 00345 ."(".$this->ItemClassName.") that has no name field specified<br>\n"); 00346 } 00347 00348 # query database for item ID 00349 $Comparison = $IgnoreCase 00350 ? "LOWER(".$this->ItemNameFieldName.") = '" 00351 .addslashes(strtolower($Name))."'" 00352 : $this->ItemNameFieldName." = '" .addslashes($Name)."'"; 00353 $ItemId = $this->DB->Query("SELECT ".$this->ItemIdFieldName 00354 ." FROM ".$this->ItemTableName 00355 ." WHERE ".$Comparison 00356 .(isset($this->FieldId) 00357 ? " AND FieldId = ".$this->FieldId 00358 : ""), 00359 $this->ItemIdFieldName); 00360 00361 # if item ID was not found 00362 if ($ItemId === NULL) 00363 { 00364 # return NULL to caller 00365 $Item = NULL; 00366 } 00367 else 00368 { 00369 # generate new item object 00370 $Item = $this->GetItem($ItemId); 00371 } 00372 00373 # return new object to caller 00374 return $Item; 00375 } 00376 00382 function GetItemNames($SqlCondition = NULL) 00383 { 00384 # error out if this is an illegal operation for this item type 00385 if ($this->ItemNameFieldName == NULL) 00386 { 00387 exit("<br>ERROR: attempt to get array of item names on item type" 00388 ."(".$this->ItemClassName.") that has no name field specified<br>\n"); 00389 } 00390 00391 # query database for item names 00392 $Condition = ""; 00393 if ($this->FieldId || $SqlCondition) 00394 { 00395 $Condition = "WHERE "; 00396 if ($this->FieldId) 00397 $Condition .= "FieldId = ".intval($this->FieldId); 00398 if ($this->FieldId && $SqlCondition) 00399 $Condition .= " AND "; 00400 if ($SqlCondition) 00401 $Condition .= $SqlCondition; 00402 } 00403 $this->DB->Query("SELECT ".$this->ItemIdFieldName 00404 .", ".$this->ItemNameFieldName 00405 ." FROM ".$this->ItemTableName." " 00406 .$Condition 00407 ." ORDER BY ".$this->ItemNameFieldName); 00408 $Names = $this->DB->FetchColumn( 00409 $this->ItemNameFieldName, $this->ItemIdFieldName); 00410 00411 # return item names to caller 00412 return $Names; 00413 } 00414 00420 function GetItems($SqlCondition = NULL) 00421 { 00422 $Items = array(); 00423 $Names = $this->GetItemNames($SqlCondition); 00424 foreach ($Names as $Id => $Name) 00425 { 00426 $Items[$Id] = $this->GetItem($Id); 00427 } 00428 return $Items; 00429 } 00430 00440 function GetItemsAsOptionList( 00441 $OptionListName, $SelectedItemId = NULL, $SqlCondition = NULL) 00442 { 00443 # retrieve requested fields 00444 $ItemNames = $this->GetItemNames($SqlCondition); 00445 00446 # begin HTML option list 00447 $Html = "<select name=\"".htmlspecialchars($OptionListName)."\">\n"; 00448 $Html .= "<option value=\"-1\">--</option>\n"; 00449 00450 # for each metadata field 00451 foreach ($ItemNames as $Id => $Name) 00452 { 00453 # add entry for field to option list 00454 $Html .= "<option value=\"".$Id."\""; 00455 if ($Id == $SelectedItemId) { $Html .= " selected"; } 00456 $Html .= ">".htmlspecialchars($Name)."</option>\n"; 00457 } 00458 00459 # end HTML option list 00460 $Html .= "</select>\n"; 00461 00462 # return constructed HTML to caller 00463 return $Html; 00464 } 00471 function NameIsInUse($Name, $IgnoreCase = FALSE) 00472 { 00473 $Condition = $IgnoreCase 00474 ? "LOWER(".$this->ItemNameFieldName.")" 00475 ." = '".addslashes(strtolower($Name))."'" 00476 : $this->ItemNameFieldName." = '".addslashes($Name)."'"; 00477 $NameCount = $this->DB->Query("SELECT COUNT(*) AS RecordCount FROM " 00478 .$this->ItemTableName." WHERE ".$Condition, "RecordCount"); 00479 return ($NameCount > 0) ? TRUE : FALSE; 00480 } 00481 00482 # retrieve names of items matching search string (array index is IDs) 00483 # (NOTE: IncludeVariants parameter is NOT YET SUPPORTED!) 00484 function SearchForItemNames($SearchString, $NumberOfResults = 100, 00485 $IncludeVariants = FALSE, $UseBooleanMode = TRUE, $Offset=0) 00486 { 00487 # error out if this is an illegal operation for this item type 00488 if ($this->ItemNameFieldName == NULL) 00489 { 00490 exit("<br>ERROR: attempt to search for item names on item type" 00491 ."(".$this->ItemClassName.") that has no name field specified<br>\n"); 00492 } 00493 00494 # return no results if empty search string passed in 00495 if (!strlen(trim($SearchString))) { return array(); } 00496 00497 # construct SQL query 00498 $DB = new Database(); 00499 $QueryString = "SELECT ".$this->ItemIdFieldName.",".$this->ItemNameFieldName 00500 ." FROM ".$this->ItemTableName." WHERE"; 00501 if ($this->FieldId) 00502 { 00503 $QueryString .= " FieldId = ".$this->FieldId." AND"; 00504 } 00505 if ($UseBooleanMode) 00506 { 00507 $SearchString = preg_replace("/[)\(><]+/", "", $SearchString); 00508 $Words = preg_split("/[\s]+/", trim($SearchString)); 00509 $NewSearchString = ""; 00510 $InQuotedString = FALSE; 00511 $SqlVarObj = new MysqlSystemVariables($DB); 00512 $StopWordList = $SqlVarObj->GetStopWords(); 00513 $MinWordLen = $SqlVarObj->Get("ft_min_word_len"); 00514 foreach ($Words as $Word) 00515 { 00516 # remove any query-specific terms, punctuation, etc. 00517 $JustTheWord = preg_replace("/[^a-zA-Z-]/", "", $Word); 00518 00519 # require (boolean AND) certain words 00520 if ($InQuotedString == FALSE 00521 && !in_array($JustTheWord, $StopWordList) 00522 && strlen($JustTheWord) >= $MinWordLen 00523 && $Word{0} != "+" 00524 && $Word{0} != "-") 00525 { 00526 $NewSearchString .= "+"; 00527 } 00528 00529 if (preg_match("/^\"/", $Word)) { $InQuotedString = TRUE; } 00530 if (preg_match("/\"$/", $Word)) { $InQuotedString = FALSE; } 00531 $NewSearchString .= $Word." "; 00532 } 00533 00534 $QueryString .= " MATCH (".$this->ItemNameFieldName.")" 00535 ." AGAINST ('".addslashes(trim($NewSearchString))."'" 00536 ." IN BOOLEAN MODE)"; 00537 } 00538 else 00539 { 00540 $QueryString .= " MATCH (".$this->ItemNameFieldName.")" 00541 ." AGAINST ('".addslashes(trim($SearchString))."')"; 00542 } 00543 $QueryString .= " LIMIT ".intval($NumberOfResults)." OFFSET " 00544 .intval($Offset); 00545 00546 # perform query and retrieve names and IDs of items found by query 00547 $DB->Query($QueryString); 00548 $Names = $DB->FetchColumn($this->ItemNameFieldName, $this->ItemIdFieldName); 00549 00550 if ($UseBooleanMode) 00551 { 00552 foreach ($Words as $Word) 00553 { 00554 $TgtWord = preg_replace("/[^a-zA-Z]/", "", $Word); 00555 if ($Word{0} == "-" && strlen($TgtWord) < $MinWordLen) 00556 { 00557 $NewNames = array(); 00558 foreach ($Names as $Id => $Name) 00559 { 00560 if (! preg_match('/\b'.$TgtWord.'/i', $Name)) 00561 { 00562 $NewNames[$Id] = $Name; 00563 } 00564 } 00565 $Names = $NewNames; 00566 } 00567 } 00568 } 00569 00570 # return names to caller 00571 return $Names; 00572 } 00573 00574 # retrieve the count of names of items matching search string (array index 00575 # is IDs) (NOTE: IncludeVariants parameter is NOT YET SUPPORTED!) 00576 function GetCountForItemNames($SearchString, $IncludeVariants = FALSE, 00577 $UseBooleanMode = TRUE) 00578 { 00579 # return no results if empty search string passed in 00580 if (!strlen(trim($SearchString))) { return 0; } 00581 00582 # construct SQL query 00583 $DB = new Database(); 00584 $QueryString = "SELECT COUNT(*) as ItemCount FROM " 00585 .$this->ItemTableName." WHERE"; 00586 if ($this->FieldId) 00587 { 00588 $QueryString .= " FieldId = ".$this->FieldId." AND"; 00589 } 00590 if ($UseBooleanMode) 00591 { 00592 $SearchString = preg_replace("/[)\(><]+/", "", $SearchString); 00593 $Words = preg_split("/[\s]+/", trim($SearchString)); 00594 $NewSearchString = ""; 00595 $InQuotedString = FALSE; 00596 $SqlVarObj = new MysqlSystemVariables($DB); 00597 $StopWordList = $SqlVarObj->GetStopWords(); 00598 $MinWordLen = $SqlVarObj->Get("ft_min_word_len"); 00599 foreach ($Words as $Word) 00600 { 00601 # remove any query-specific terms, punctuation, etc. 00602 $JustTheWord = preg_replace("/[^a-zA-Z-]/", "", $Word); 00603 00604 # require (boolean AND) certain words 00605 if ($InQuotedString == FALSE 00606 && !in_array($JustTheWord, $StopWordList) 00607 && strlen($JustTheWord) >= $MinWordLen 00608 && $Word{0} != "+" 00609 && $Word{0} != "-") 00610 { 00611 $NewSearchString .= "+"; 00612 } 00613 00614 if (preg_match("/^\"/", $Word)) { $InQuotedString = TRUE; } 00615 if (preg_match("/\"$/", $Word)) { $InQuotedString = FALSE; } 00616 $NewSearchString .= $Word." "; 00617 } 00618 00619 $QueryString .= " MATCH (".$this->ItemNameFieldName.")" 00620 ." AGAINST ('".addslashes(trim($NewSearchString))."'" 00621 ." IN BOOLEAN MODE)"; 00622 } 00623 else 00624 { 00625 $QueryString .= " MATCH (".$this->ItemNameFieldName.")" 00626 ." AGAINST ('".addslashes(trim($SearchString))."')"; 00627 } 00628 00629 # perform query and retrieve names and IDs of items found by query 00630 $DB->Query($QueryString); 00631 return intval($DB->FetchField("ItemCount")); 00632 } 00633 00642 function AddItems($ItemNames, $Qualifier = NULL) 00643 { 00644 # for each supplied item name 00645 $ItemCount = 0; 00646 foreach ($ItemNames as $Name) 00647 { 00648 # if item does not exist with this name 00649 $Name = trim($Name); 00650 if ($this->GetItemByName($Name) === NULL) 00651 { 00652 # add item 00653 $NewItem = new $this->ItemClassName(NULL, $Name, $this->FieldId); 00654 $ItemCount++; 00655 00656 # assign qualifier to item if supplied 00657 if ($Qualifier !== NULL) 00658 { 00659 $NewItem->Qualifier($Qualifier); 00660 } 00661 } 00662 } 00663 00664 # return count of items added to caller 00665 return $ItemCount; 00666 } 00667 00668 # ---- order operations -------------------------------------------------- 00669 00670 # set SQL condition (added to WHERE clause) used to select items for ordering ops 00671 # (use NULL to clear any previous condition) 00672 function SetOrderOpsCondition($Condition) 00673 { 00674 # condition is non-negative IDs (non-temp items) plus supplied condition 00675 $NewCondition = $this->ItemIdFieldName." >= 0" 00676 .(($Condition) ? " AND ".$Condition : ""); 00677 $this->OrderList->SqlCondition($NewCondition); 00678 } 00679 00680 # insert/move item to before specified item 00681 function InsertBefore($SourceItemOrItemId, $TargetItemOrItemId) 00682 { 00683 # error out if ordering operations are not allowed for this item type 00684 if (!$this->OrderOpsAllowed) 00685 { 00686 exit("<br>ERROR: attempt to perform ordering operation" 00687 ." (InsertBefore()) on item type" 00688 ."(".$this->ItemClassName.") that does not support ordering<br>\n"); 00689 } 00690 00691 # insert/move item 00692 $this->OrderList->InsertBefore($SourceItemOrItemId, $TargetItemOrItemId); 00693 } 00694 00695 # insert/move item to after specified item 00696 function InsertAfter($SourceItemOrItemId, $TargetItemOrItemId) 00697 { 00698 # error out if ordering operations are not allowed for this item type 00699 if (!$this->OrderOpsAllowed) 00700 { 00701 exit("<br>ERROR: attempt to perform ordering operation" 00702 ." (InsertAfter()) on item type" 00703 ."(".$this->ItemClassName.") that does not support ordering<br>\n"); 00704 } 00705 00706 # insert/move item 00707 $this->OrderList->InsertAfter($SourceItemOrItemId, $TargetItemOrItemId); 00708 } 00709 00710 # add/move item to beginning of list 00711 function Prepend($ItemOrItemId) 00712 { 00713 # error out if ordering operations are not allowed for this item type 00714 if (!$this->OrderOpsAllowed) 00715 { 00716 exit("<br>ERROR: attempt to perform ordering operation" 00717 ." (Prepend()) on item type" 00718 ."(".$this->ItemClassName.") that does not support ordering<br>\n"); 00719 } 00720 00721 # prepend item 00722 $this->OrderList->Prepend($ItemOrItemId); 00723 } 00724 00725 # add/move item to end of list 00726 function Append($ItemOrItemId) 00727 { 00728 # error out if ordering operations are not allowed for this item type 00729 if (!$this->OrderOpsAllowed) 00730 { 00731 exit("<br>ERROR: attempt to perform ordering operation" 00732 ." (Append()) on item type" 00733 ."(".$this->ItemClassName.") that does not support ordering<br>\n"); 00734 } 00735 00736 # add/move item 00737 $this->OrderList->Append($ItemOrItemId); 00738 } 00739 00740 # retrieve list of item IDs in order 00741 function GetItemIdsInOrder($AddStrayItemsToOrder = TRUE) 00742 { 00743 # error out if ordering operations are not allowed for this item type 00744 if (!$this->OrderOpsAllowed) 00745 { 00746 exit("<br>ERROR: attempt to perform ordering operation" 00747 ." (GetItemIdsInOrder()) on item type" 00748 ."(".$this->ItemClassName.") that does not support ordering<br>\n"); 00749 } 00750 00751 # retrieve list of IDs 00752 return $this->OrderList->GetIds($AddStrayItemsToOrder); 00753 } 00754 00755 # remove item from existing order 00756 function RemoveItemFromOrder($ItemId) 00757 { 00758 # error out if ordering operations are not allowed for this item type 00759 if (!$this->OrderOpsAllowed) 00760 { 00761 exit("<br>ERROR: attempt to perform ordering operation" 00762 ." (RemoveItemFromOrder()) on item type" 00763 ."(".$this->ItemClassName.") that does not support ordering<br>\n"); 00764 } 00765 00766 # remove item 00767 $this->OrderList->Remove($ItemId); 00768 } 00769 00770 00771 # ---- PRIVATE INTERFACE ------------------------------------------------- 00772 00773 protected $DB; 00774 protected $FieldId; 00775 00776 private $ItemClassName; 00777 private $ItemTableName; 00778 private $ItemIdFieldName; 00779 private $ItemNameFieldName; 00780 private $ErrorStatus; 00781 private $OrderOpsAllowed; 00782 private $OrderList; 00783 00784 # get/set ordering values 00785 private function GetPreviousItemId($ItemId) 00786 { 00787 return $this->DB->Query("SELECT Previous".$this->ItemIdFieldName 00788 ." FROM ".$this->ItemTableName 00789 ." WHERE ".$this->ItemIdFieldName." = ".intval($ItemId), 00790 "Previous".$this->ItemIdFieldName); 00791 } 00792 private function GetNextItemIdInOrder($ItemId) 00793 { 00794 return $this->DB->Query("SELECT Next".$this->ItemIdFieldName 00795 ." FROM ".$this->ItemTableName 00796 ." WHERE ".$this->ItemIdFieldName." = ".intval($ItemId), 00797 "Next".$this->ItemIdFieldName); 00798 } 00799 private function SetPreviousItemId($ItemId, $NewValue) 00800 { 00801 $this->DB->Query("UPDATE ".$this->ItemTableName 00802 ." SET Previous".$this->ItemIdFieldName." = ".intval($NewValue) 00803 ." WHERE ".$this->ItemIdFieldName." = ".intval($ItemId)); 00804 } 00805 private function SetNextItemId($ItemId, $NewValue) 00806 { 00807 $this->DB->Query("UPDATE ".$this->ItemTableName 00808 ." SET Next".$this->ItemIdFieldName." = ".intval($NewValue) 00809 ." WHERE ".$this->ItemIdFieldName." = ".intval($ItemId)); 00810 } 00811 private function SetPreviousAndNextItemIds($ItemId, $NewPreviousId, $NewNextId) 00812 { 00813 $this->DB->Query("UPDATE ".$this->ItemTableName 00814 ." SET Previous".$this->ItemIdFieldName." = ".intval($NewPreviousId) 00815 .", Next".$this->ItemIdFieldName." = ".intval($NewNextId) 00816 ." WHERE ".$this->ItemIdFieldName." = ".intval($ItemId)); 00817 } 00818 } 00819 00820 ?>