CWIS Developer Documentation
SavedSearch.php
Go to the documentation of this file.
1 <?PHP
2 #
3 # FILE: SavedSearch.php
4 #
5 # NOTES:
6 # - the "$SearchGroups" values used herein contain a multi-dimentional
7 # array in the form of:
8 # $Criteria["MAIN"]["SearchStrings"][<field names>] = <value>
9 # for fields with a single value, and:
10 # $Criteria[<field ID>]["SearchStrings"][<field name>][] = <value>
11 # for fields with multiple values
12 #
13 #
14 # Part of the Collection Workflow Integration System (CWIS)
15 # Copyright 2011-2013 Edward Almasy and Internet Scout Research Group
16 # http://scout.wisc.edu/cwis/
17 #
18 
19 class SavedSearch {
20 
21  # ---- PUBLIC INTERFACE --------------------------------------------------
22 
23  # search frequency mnemonics
24  const SEARCHFREQ_NEVER = 0;
25  const SEARCHFREQ_HOURLY = 1;
26  const SEARCHFREQ_DAILY = 2;
27  const SEARCHFREQ_WEEKLY = 3;
29  const SEARCHFREQ_MONTHLY = 5;
31  const SEARCHFREQ_YEARLY = 7;
32 
33  # object constructor
34  function SavedSearch($SearchId, $SearchName = NULL, $UserId = NULL,
35  $Frequency = NULL, $SearchGroups = NULL)
36  {
37  # get our own database handle
38  $this->DB = new Database();
39 
40  # if search ID was provided
41  if ($SearchId !== NULL)
42  {
43  # save search ID
44  $this->SearchId = intval($SearchId);
45 
46  # initialize our local copies of data
47  $this->DB->Query("SELECT * FROM SavedSearches"
48  ." WHERE SearchId = '".$this->SearchId."'");
49  $this->Record = $this->DB->FetchRow();
50 
51  # update search details where provided
52  if ($SearchName) { $this->SearchName($SearchName); }
53  if ($UserId) { $this->UserId($UserId); }
54  if ($Frequency) { $this->Frequency($Frequency); }
55  }
56  else
57  {
58  # add new saved search to database
59  $this->DB->Query("INSERT INTO SavedSearches"
60  ." (SearchName, UserId, Frequency) VALUES ("
61  ."'".addslashes($SearchName)."', "
62  .intval($UserId).", "
63  .intval($Frequency).")");
64 
65  # retrieve and save ID of new search locally
66  $this->SearchId = $this->DB->LastInsertId();
67 
68  # save frequency and user ID locally
69  $this->Record["SearchName"] = $SearchName;
70  $this->Record["UserId"] = $UserId;
71  $this->Record["Frequency"] = $Frequency;
72 
73  #Add the correct search parameters if they are provided
74  #and save an initial set of matches
75  if($SearchGroups)
76  {
77  $SearchGroups = $this->SearchGroups($SearchGroups);
78  }
79  else
80  {
81  $SearchGroups = $this->SearchGroups();
82  }
83 
84  # add search group to contain our added conditions
85  $NextGroupIndex = count($SearchGroups);
86 
87  $EndUser = new CWUser(intval($this->UserId()));
88 
89  $RFactory = new ResourceFactory();
90 
91  # signal event to allow modification of search parameters
92  $SignalResult = $GLOBALS["AF"]->SignalEvent(
93  "EVENT_FIELDED_SEARCH", array(
94  "SearchGroups" => $SearchGroups,
95  "User" => $EndUser,
96  "SavedSearch" => $this));
97  $SearchGroups = $SignalResult["SearchGroups"];
98 
99  # perform search
100  if (!isset($SearchEngine)) { $SearchEngine = new SPTSearchEngine(); }
101  $SearchResults = $SearchEngine->GroupedSearch($SearchGroups, 0, PHP_INT_MAX);
102 
103  $NewItemIds = array_keys($SearchResults);
104 
105  #Only allow resources the user can view
106  $NewItemIds = $RFactory->FilterNonViewableResources($NewItemIds, $EndUser);
107 
108  # if search results were found
109  if (count($NewItemIds))
110  {
111  $this->SaveLastMatches($NewItemIds);
112  }
113  }
114 
115  }
116 
117  # get/set search parameters
118  function SearchGroups($NewSearchGroups = NULL)
119  {
120  $Schema = new MetadataSchema();
121 
122  # if new search parameters were supplied
123  if ($NewSearchGroups)
124  {
125  # remove existing entries for this search from the database
126  $this->DB->Query("DELETE FROM SavedSearchTextParameters WHERE SearchId = ".$this->SearchId);
127  $this->DB->Query("DELETE FROM SavedSearchIdParameters WHERE SearchId = ".$this->SearchId);
128 
129  # for each search group
130  foreach ($NewSearchGroups as $GroupIndex => $Group)
131  {
132  # if group holds single parameters
133  if ($GroupIndex == "MAIN")
134  {
135  # for each field within group
136  foreach ($Group["SearchStrings"] as $FieldName => $Value)
137  {
138  # convert value array to single value (if necessary)
139  if (is_array($Value))
140  {
141  $ConvertedValue = "";
142  foreach ($Value as $SingleValue)
143  {
144  $ConvertedValue .= $SingleValue." ";
145  }
146  $Value = trim($ConvertedValue);
147  }
148 
149  # add new text search parameter entry to database
150  if ($FieldName == "XXXKeywordXXX")
151  {
152  $FieldId = -101;
153  }
154  else
155  {
156  $Field = $Schema->GetFieldByName($FieldName);
157  $FieldId = $Field->Id();
158  }
159  $this->DB->Query("INSERT INTO SavedSearchTextParameters"
160  ." (SearchId, FieldId, SearchText) VALUES"
161  ." (".$this->SearchId.", ".$FieldId.", '".addslashes($Value)."')");
162  }
163  }
164  else
165  {
166  # convert value(s) as appropriate for field type
167  $FieldId = ($GroupIndex[0] == "X")
168  ? substr($GroupIndex, 1)
169  : $GroupIndex;
170  $Field = $Schema->GetField($FieldId);
171  $FieldName = $Field->Name();
172  $Values = SavedSearch::TranslateValues($Field, $Group["SearchStrings"][$FieldName], "SearchGroup to Database");
173 
174  # for each converted value
175  foreach ($Values as $Value)
176  {
177  # add new ID search parameter entry to database
178  $this->DB->Query("INSERT INTO SavedSearchIdParameters"
179  ." (SearchId, FieldId, SearchValueId) VALUES"
180  ." (".$this->SearchId.", ".$FieldId.", ".$Value.")");
181  }
182  }
183  }
184 
185  # save search parameters locally
186  $this->SearchGroups = $NewSearchGroups;
187  }
188  else
189  {
190  # if search groups not already read in
191  if (!isset($this->SearchGroups))
192  {
193  # for each text search parameter
194  $SearchGroups = array();
195  $this->DB->Query("SELECT * FROM SavedSearchTextParameters"
196  ." WHERE SearchId = ".$this->SearchId);
197  while ($Record = $this->DB->FetchRow())
198  {
199  # add parameter to search criteria
200  if ($Record["FieldId"] == -101)
201  {
202  $SearchGroups["MAIN"]["SearchStrings"]["XXXKeywordXXX"] =
203  $Record["SearchText"];
204  }
205  else
206  {
207  $Field = $Schema->GetField($Record["FieldId"]);
208  $SearchGroups["MAIN"]["SearchStrings"][$Field->Name()] =
209  $Record["SearchText"];
210  }
211  }
212 
213  # for each value ID search parameter
214  $this->DB->Query("SELECT * FROM SavedSearchIdParameters"
215  ." WHERE SearchId = ".$this->SearchId);
216  while ($Record = $this->DB->FetchRow())
217  {
218  # translate value based on field type
219  $FieldId = $Record["FieldId"];
220  if (!isset($Fields[$FieldId]))
221  {
222  $Fields[$FieldId] = $Schema->GetField($FieldId);
223  }
224  $Values = SavedSearch::TranslateValues($Fields[$FieldId],
225  $Record["SearchValueId"], "Database to SearchGroup");
226 
227  # add parameter to search criteria
228  foreach ($Values as $Value)
229  {
230  $SearchGroups[$FieldId]["SearchStrings"]
231  [$Fields[$FieldId]->Name()][] = $Value;
232  }
233  }
234 
235  # set appropriate logic in search parameters
236  foreach ($SearchGroups as $GroupIndex => $Group)
237  {
238  $SearchGroups[$GroupIndex]["Logic"] =
239  ($GroupIndex == "MAIN") ? SearchEngine::LOGIC_AND
241  }
242 
243  # save search parameters locally
244  $this->SearchGroups = $SearchGroups;
245  }
246  }
247 
248  # return search parameters to caller
249  return $this->SearchGroups;
250  }
251 
252  /*
253  * Get/set name of search.
254  * @param string $NewValue New name of search value.
255  * @return Current name of search value.
256  */
257  function SearchName($NewValue = DB_NOVALUE)
258  { return $this->UpdateValue("SearchName", $NewValue); }
259 
264  function Id() { return $this->SearchId; }
265 
271  function UserId($NewValue = DB_NOVALUE)
272  { return $this->UpdateValue("UserId", $NewValue); }
273 
279  function Frequency($NewValue = DB_NOVALUE)
280  { return $this->UpdateValue("Frequency", $NewValue); }
281 
282  # set date search was last run to current date/time
283  function UpdateDateLastRun()
284  {
285  $this->DB->Query("UPDATE SavedSearches SET DateLastRun = NOW() WHERE SearchId = ".$this->SearchId);
286  }
287 
288  # get/set date search was last run
289  function DateLastRun($NewValue = DB_NOVALUE)
290  { return $this->UpdateValue("DateLastRun", $NewValue); }
291 
296  function SaveLastMatches($ArrayofMatchingIds)
297  {
298  $NewValue = implode(",", $ArrayofMatchingIds);
299  $this->UpdateValue("LastMatchingIds", $NewValue);
300  }
301 
306  function LastMatches()
307  {
308  return explode(",", $this->DB->Query("SELECT LastMatchingIds FROM SavedSearches WHERE SearchId=".intval($this->SearchId), "LastMatchingIds"));
309  }
316  {
317  return self::TranslateSearchGroupsToUrlParameters($this->SearchGroups());
318  }
319 
357  static function TranslateSearchGroupsToUrlParameters($SearchGroups)
358  {
359  # assume that no parameters will be found
360  $UrlPortion = "";
361 
362  # for each group in parameters
363  $Schema = new MetadataSchema();
364  foreach ($SearchGroups as $GroupIndex => $Group)
365  {
366  # if group holds single parameters
367  if ($GroupIndex == "MAIN")
368  {
369  # for each field within group
370  foreach ($Group["SearchStrings"] as $FieldName => $Value)
371  {
372  # add segment to URL for this field
373  if ($FieldName == "XXXKeywordXXX")
374  {
375  $FieldId = "K";
376  }
377  else
378  {
379  $Field = $Schema->GetFieldByName($FieldName);
380  $FieldId = $Field->Id();
381  }
382  if (is_array($Value))
383  {
384  $UrlPortion .= "&F".$FieldId."=";
385  $ValueString = "";
386  foreach ($Value as $SingleValue)
387  {
388  $ValueString .= $SingleValue." ";
389  }
390  $UrlPortion .= urlencode(trim($ValueString));
391  }
392  else
393  {
394  $UrlPortion .= "&F".$FieldId."=".urlencode($Value);
395  }
396  }
397  }
398  else
399  {
400  # convert value based on field type
401  $FieldId = ($GroupIndex[0] == "X")
402  ? substr($GroupIndex, 1)
403  : $GroupIndex;
404  $Field = $Schema->GetField($FieldId);
405  $FieldName = $Field->Name();
406  $Values = SavedSearch::TranslateValues($Field,
407  $Group["SearchStrings"][$FieldName],
408  "SearchGroup to Database");
409 
410  # add values to URL
411  $FirstValue = TRUE;
412  foreach ($Values as $Value)
413  {
414  if ($FirstValue)
415  {
416  $FirstValue = FALSE;
417  $UrlPortion .= "&G".$FieldId."=".$Value;
418  }
419  else
420  {
421  $UrlPortion .= "-".$Value;
422  }
423  }
424  }
425  }
426 
427  # trim off any leading "&"
428  if (strlen($UrlPortion)) { $UrlPortion = substr($UrlPortion, 1); }
429 
430  # return URL portion to caller
431  return $UrlPortion;
432  }
433 
440  {
441  return self::TranslateSearchGroupsToUrlParameters($this->SearchGroups());
442  }
443 
450  static function TranslateSearchGroupsToUrlParameterArray($SearchGroups)
451  {
452  # assume that no parameters will be found
453  $UrlPortion = array();
454 
455  # for each group in parameters
456  $Schema = new MetadataSchema();
457  foreach ($SearchGroups as $GroupIndex => $Group)
458  {
459  # if group holds single parameters
460  if ($GroupIndex == "MAIN")
461  {
462  # for each field within group
463  foreach ($Group["SearchStrings"] as $FieldName => $Value)
464  {
465  # add segment to URL for this field
466  if ($FieldName == "XXXKeywordXXX")
467  {
468  $FieldId = "K";
469  }
470  else
471  {
472  $Field = $Schema->GetFieldByName($FieldName);
473  $FieldId = $Field->Id();
474  }
475  if (is_array($Value))
476  {
477  $ValueString = "";
478  foreach ($Value as $SingleValue)
479  {
480  $ValueString .= $SingleValue." ";
481  }
482 
483  $UrlPortion["F".$FieldId] = urlencode(trim($ValueString));
484  }
485  else
486  {
487  $UrlPortion["F".$FieldId] = urlencode($Value);
488  }
489  }
490  }
491  else
492  {
493  # convert value based on field type
494  $FieldId = ($GroupIndex[0] == "X")
495  ? substr($GroupIndex, 1)
496  : $GroupIndex;
497  $Field = $Schema->GetField($FieldId);
498  $FieldName = $Field->Name();
499  $Values = SavedSearch::TranslateValues($Field,
500  $Group["SearchStrings"][$FieldName],
501  "SearchGroup to Database");
502  $LeadChar = ($Group["Logic"] == SearchEngine::LOGIC_AND)
503  ? "H" : "G";
504 
505  # add values to URL
506  $FirstValue = TRUE;
507  foreach ($Values as $Value)
508  {
509  if ($FirstValue)
510  {
511  $FirstValue = FALSE;
512  $UrlPortion[$LeadChar.$FieldId] = $Value;
513  }
514  else
515  {
516  $UrlPortion[$LeadChar.$FieldId] .= "-".$Value;
517  }
518  }
519  }
520  }
521 
522  # return URL portion to caller
523  return $UrlPortion;
524  }
525 
526  # set search groups from URL (GET method) parameters
527  # (returns search group array)
528  static function TranslateUrlParametersToSearchGroups($GetVars)
529  {
530  # if URL segment was passed in instead of GET var array
531  if (is_string($GetVars))
532  {
533  $GetVars = ParseQueryString($GetVars);
534  }
535 
536  # start with empty list of parameters
537  $SearchGroups = array();
538 
539  $Schema = new MetadataSchema();
540  $AllFields = $Schema->GetFields(NULL, NULL, TRUE);
541 
542  foreach ($AllFields as $Field)
543  {
544  $FieldId = $Field->Id();
545  $FieldName = $Field->Name();
546 
547  # if URL included literal value for this field
548  if (isset($GetVars["F".$FieldId]))
549  {
550  # retrieve value and add to search parameters
551  $SearchGroups["MAIN"]["SearchStrings"][$FieldName] =
552  $GetVars["F".$FieldId];
553  }
554 
555  # if URL included group value for this field
556  if (isset($GetVars["G".$FieldId]))
557  {
558  # retrieve and parse out values
559  $Values = explode("-", $GetVars["G".$FieldId]);
560 
561  # translate values
562  $Values = SavedSearch::TranslateValues($Field, $Values,
563  "Database to SearchGroup");
564 
565  # add values to searchgroups
566  $SearchGroups[$FieldId]["SearchStrings"][$FieldName] = $Values;
567  }
568 
569  # if URL included group value for this field
570  if (isset($GetVars["H".$FieldId]))
571  {
572  # retrieve and parse out values
573  $Values = explode("-", $GetVars["H".$FieldId]);
574 
575  # translate values
576  $Values = SavedSearch::TranslateValues($Field, $Values,
577  "Database to SearchGroup");
578 
579  # add values to searchgroups
580  $SearchGroups["X".$FieldId]["SearchStrings"][$FieldName] = $Values;
581  }
582  }
583 
584  # if keyword pseudo-field was included in URL
585  if (isset($GetVars["FK"]))
586  {
587  # retrieve value and add to search parameters
588  $SearchGroups["MAIN"]["SearchStrings"]["XXXKeywordXXX"] = $GetVars["FK"];
589  }
590 
591  # set search logic
592  foreach ($SearchGroups as $GroupIndex => $Group)
593  {
594  $SearchGroups[$GroupIndex]["Logic"] = ($GroupIndex == "MAIN")
596  : (($GroupIndex[0] == "X")
598  }
599 
600  # return parameters to caller
601  return $SearchGroups;
602  }
603 
615  $IncludeHtml = TRUE, $StartWithBreak = TRUE, $TruncateLongWordsTo = 0)
616  {
617  return self::TranslateSearchGroupsToTextDescription($this->SearchGroups(),
618  $IncludeHtml, $StartWithBreak, $TruncateLongWordsTo);
619  }
620 
632  static function TranslateSearchGroupsToTextDescription($SearchGroups,
633  $IncludeHtml = TRUE, $StartWithBreak = TRUE, $TruncateLongWordsTo = 0)
634  {
635  $Schema = new MetadataSchema();
636 
637  # start with empty description
638  $Descrip = "";
639 
640  # set characters used to indicate literal strings
641  $LiteralStart = $IncludeHtml ? "<i>" : "\"";
642  $LiteralEnd = $IncludeHtml ? "</i>" : "\"";
643  $LiteralBreak = $IncludeHtml ? "<br>\n" : "\n";
644 
645  # if this is a simple keyword search
646  if (isset($SearchGroups["MAIN"]["SearchStrings"]["XXXKeywordXXX"])
647  && (count($SearchGroups) == 1)
648  && (count($SearchGroups["MAIN"]["SearchStrings"]) == 1))
649  {
650  # just use the search string
651  $Descrip .= $LiteralStart;
652  $Descrip .= defaulthtmlentities($SearchGroups["MAIN"]["SearchStrings"]["XXXKeywordXXX"]);
653  $Descrip .= $LiteralEnd . $LiteralBreak;
654  }
655  else
656  {
657  # start description on a new line (if requested)
658  if ($StartWithBreak)
659  {
660  $Descrip .= $LiteralBreak;
661  }
662 
663  # define list of phrases used to represent logical operators
664  $WordsForOperators = array(
665  "=" => "is",
666  ">" => "is greater than",
667  "<" => "is less than",
668  ">=" => "is at least",
669  "<=" => "is no more than",
670  "!" => "is not",
671  );
672 
673  # for each search group
674  foreach ($SearchGroups as $GroupIndex => $Group)
675  {
676  # if group is main
677  if ($GroupIndex == "MAIN")
678  {
679  # for each field in group
680  foreach ($Group["SearchStrings"] as $FieldName => $Value)
681  {
682  # determine wording based on operator
683  preg_match("/^[=><!]+/", $Value, $Matches);
684  if (count($Matches) && isset($WordsForOperators[$Matches[0]]))
685  {
686  $Value = preg_replace("/^[=><!]+/", "", $Value);
687  $Wording = $WordsForOperators[$Matches[0]];
688  }
689  else
690  {
691  $Wording = "contains";
692  }
693 
694  # if field is psuedo-field
695  if ($FieldName == "XXXKeywordXXX")
696  {
697  # add criteria for psuedo-field
698  $Descrip .= "Keyword ".$Wording." "
699  .$LiteralStart.htmlspecialchars($Value)
700  .$LiteralEnd.$LiteralBreak;
701  }
702  else
703  {
704  # if field is valid
705  $Field = $Schema->GetFieldByName($FieldName);
706  if ($Field !== NULL)
707  {
708  # add criteria for field
709  $Descrip .= $Field->GetDisplayName()." ".$Wording." "
710  .$LiteralStart.htmlspecialchars($Value)
711  .$LiteralEnd.$LiteralBreak;
712  }
713  }
714  }
715  }
716  else
717  {
718  # for each field in group
719  $LogicTerm = ($Group["Logic"] == SearchEngine::LOGIC_AND)
720  ? "and " : "or ";
721  foreach ($Group["SearchStrings"] as $FieldName => $Values)
722  {
723  # translate values
724  $Values = SavedSearch::TranslateValues(
725  $FieldName, $Values, "SearchGroup to Display");
726 
727  # for each value
728  $FirstValue = TRUE;
729  foreach ($Values as $Value)
730  {
731  # determine wording based on operator
732  preg_match("/^[=><!]+/", $Value, $Matches);
733  $Operator = $Matches[0];
734  $Wording = $WordsForOperators[$Operator];
735 
736  # strip off operator
737  $Value = preg_replace("/^[=><!]+/", "", $Value);
738 
739  # add text to description
740  if ($FirstValue)
741  {
742  $Descrip .= $FieldName." ".$Wording." "
743  .$LiteralStart.htmlspecialchars($Value)
744  .$LiteralEnd.$LiteralBreak;
745  $FirstValue = FALSE;
746  }
747  else
748  {
749  $Descrip .= ($IncludeHtml ? "&nbsp;&nbsp;&nbsp;&nbsp;" : " ")
750  .$LogicTerm.$Wording." ".$LiteralStart
751  .htmlspecialchars($Value).$LiteralEnd
752  .$LiteralBreak;
753  }
754  }
755  }
756  }
757  }
758  }
759 
760  # if caller requested that long words be truncated
761  if ($TruncateLongWordsTo > 4)
762  {
763  # break description into words
764  $Words = explode(" ", $Descrip);
765 
766  # for each word
767  $NewDescrip = "";
768  foreach ($Words as $Word)
769  {
770  # if word is longer than specified length
771  if (strlen(strip_tags($Word)) > $TruncateLongWordsTo)
772  {
773  # truncate word and add ellipsis
774  $Word = NeatlyTruncateString($Word, $TruncateLongWordsTo - 3);
775  }
776 
777  # add word to new description
778  $NewDescrip .= " ".$Word;
779  }
780 
781  # set description to new description
782  $Descrip = $NewDescrip;
783  }
784 
785  # return description to caller
786  return $Descrip;
787  }
788 
794  {
795  return self::TranslateSearchGroupsToSearchFieldNames($this->SearchGroups());
796  }
797 
803  static function TranslateSearchGroupsToSearchFieldNames($SearchGroups)
804  {
805  # start out assuming no fields are being searched
806  $FieldNames = array();
807 
808  # for each search group defined
809  foreach ($SearchGroups as $GroupIndex => $Group)
810  {
811  # for each field in group
812  foreach ($Group["SearchStrings"] as $FieldName => $Values)
813  {
814  # add field name to list of fields being searched
815  $FieldNames[] = $FieldName;
816  }
817  }
818 
819  # return list of fields being searched to caller
820  return $FieldNames;
821  }
822 
828  static function GetSearchFrequencyList()
829  {
830  # define list with descriptions
831  $FreqDescr = array(
832  self::SEARCHFREQ_NEVER => "Never",
833  self::SEARCHFREQ_HOURLY => "Hourly",
834  self::SEARCHFREQ_DAILY => "Daily",
835  self::SEARCHFREQ_WEEKLY => "Weekly",
836  self::SEARCHFREQ_BIWEEKLY => "Bi-Weekly",
837  self::SEARCHFREQ_MONTHLY => "Monthly",
838  self::SEARCHFREQ_QUARTERLY => "Quarterly",
839  self::SEARCHFREQ_YEARLY => "Yearly",
840  );
841 
842  # for each argument passed in
843  $Args = func_get_args();
844  foreach ($Args as $Arg)
845  {
846  # remove value from list
847  $FreqDescr = array_diff_key($FreqDescr, array($Arg => ""));
848  }
849 
850  # return list to caller
851  return $FreqDescr;
852  }
853 
857  function Delete()
858  {
859  $this->DB->Query("DELETE FROM SavedSearches"
860  ." WHERE SearchId = ".intval($this->SearchId));
861  $this->DB->Query("DELETE FROM SavedSearchTextParameters"
862  ." WHERE SearchId = ".intval($this->SearchId));
863  $this->DB->Query("DELETE FROM SavedSearchIdParameters"
864  ." WHERE SearchId = ".intval($this->SearchId));
865  }
866 
867 
868  # ---- PRIVATE INTERFACE -------------------------------------------------
869 
870  private $SearchId;
871  private $Record;
872  private $SearchGroups;
873 
874  # utility function to convert between value representations
875  # (method accepts a value or array and always return an array)
876  # (this is needed because values are represented differently:
877  # FLAG USER OPTION
878  # in DB / in URL / in forms 0/1 123 456
879  # used in SearchGroups 0/1 jdoe cname
880  # displayed to user On/Off jdoe cname
881  # where "123" and "456" are option or controlled name IDs)
882  private static function TranslateValues($FieldOrFieldName, $Values, $TranslationType)
883  {
884  # start out assuming we won't find any values to translate
885  $ReturnValues = array();
886 
887  # convert field name to field object if necessary
888  if (is_object($FieldOrFieldName))
889  {
890  $Field = $FieldOrFieldName;
891  }
892  else
893  {
894  static $Schema;
895  if (!isset($Schema)) { $Schema = new MetadataSchema(); }
896  $Field = $Schema->GetFieldByName($FieldOrFieldName);
897  }
898 
899  # if incoming value is not an array
900  if (!is_array($Values))
901  {
902  # convert incoming value to an array
903  $Values = array($Values);
904  }
905 
906  # for each incoming value
907  foreach ($Values as $Value)
908  {
909  switch ($TranslationType)
910  {
911  case "SearchGroup to Display":
912  # if field is Flag field
913  if ($Field->Type() == MetadataSchema::MDFTYPE_FLAG)
914  {
915  # translate value to true/false label and add leading operator
916  $ReturnValues[] = ($Value == "=1") ? "=".$Field->FlagOnLabel() : "=".$Field->FlagOffLabel();
917  }
918  elseif ($Field->Name() == "Cumulative Rating")
919  {
920  # translate numeric value to stars
921  $StarStrings = array(
922  "20" => "*",
923  "40" => "**",
924  "60" => "***",
925  "80" => "****",
926  "100" => "*****",
927  );
928  preg_match("/[0-9]+$/", $Value, $Matches);
929  $Number = $Matches[0];
930  preg_match("/^[=><!]+/", $Value, $Matches);
931  $Operator = $Matches[0];
932  $ReturnValues[] = $Operator.$StarStrings[$Number];
933  }
934  else
935  {
936  # use value as is
937  $ReturnValues[] = $Value;
938  }
939  break;
940 
941  case "SearchGroup to Database":
942  # strip off leading operator on value
943  $Value = preg_replace("/^[=><!]+/", "", $Value);
944 
945  # look up index for value
947  {
948  # (for flag or number fields the value index is already what is used in SearchGroups)
949  if ($Value >= 0)
950  {
951  $ReturnValues[] = $Value;
952  }
953  }
954  elseif ($Field->Type() == MetadataSchema::MDFTYPE_USER)
955  {
956  # (for user fields the value index is the user ID)
957  $User = new CWUser(strval($Value));
958  if ($User)
959  {
960  $ReturnValues[] = $User->Id();
961  }
962  }
963  elseif ($Field->Type() == MetadataSchema::MDFTYPE_OPTION)
964  {
965  if (!isset($PossibleFieldValues))
966  {
967  $PossibleFieldValues = $Field->GetPossibleValues();
968  }
969  $NewValue = array_search($Value, $PossibleFieldValues);
970  if ($NewValue !== FALSE)
971  {
972  $ReturnValues[] = $NewValue;
973  }
974  }
975  else
976  {
977  $NewValue = $Field->GetIdForValue($Value);
978  if ($NewValue !== NULL)
979  {
980  $ReturnValues[] = $NewValue;
981  }
982  }
983  break;
984 
985  case "Database to SearchGroup":
986  # look up value for index
987  if ($Field->Type() == MetadataSchema::MDFTYPE_FLAG)
988  {
989  # (for flag fields the value index (0 or 1) is already what is used in Database)
990  if ($Value >= 0)
991  {
992  $ReturnValues[] = "=".$Value;
993  }
994  }
995  elseif ($Field->Type() == MetadataSchema::MDFTYPE_NUMBER)
996  {
997  # (for flag fields the value index (0 or 1) is already what is used in Database)
998  if ($Value >= 0)
999  {
1000  $ReturnValues[] = ">=".$Value;
1001  }
1002  }
1003  elseif ($Field->Type() == MetadataSchema::MDFTYPE_USER)
1004  {
1005  $User = new CWUser(intval($Value));
1006  if ($User)
1007  {
1008  $ReturnValues[] = "=".$User->Get("UserName");
1009  }
1010  }
1011  elseif ($Field->Type() == MetadataSchema::MDFTYPE_OPTION)
1012  {
1013  if (!isset($PossibleFieldValues))
1014  {
1015  $PossibleFieldValues = $Field->GetPossibleValues();
1016  }
1017 
1018  if (isset($PossibleFieldValues[$Value]))
1019  {
1020  $ReturnValues[] = "=".$PossibleFieldValues[$Value];
1021  }
1022  }
1023  else
1024  {
1025  $NewValue = $Field->GetValueForId($Value);
1026  if ($NewValue !== NULL)
1027  {
1028  $ReturnValues[] = "=".$NewValue;
1029  }
1030  }
1031  break;
1032  }
1033  }
1034 
1035  # return array of translated values to caller
1036  return $ReturnValues;
1037  }
1038 
1041  # utility function for updating values in database
1042  private function UpdateValue($FieldName, $NewValue)
1043  {
1044  return $this->DB->UpdateValue("SavedSearches", $FieldName, $NewValue,
1045  "SearchId = ".$this->SearchId, $this->Record);
1046  }
1047 
1048  # legacy methods for backward compatibility
1049  function GetSearchId() { return $this->Id(); }
1050 
1052 }
const SEARCHFREQ_WEEKLY
Definition: SavedSearch.php:27
const SEARCHFREQ_NEVER
Definition: SavedSearch.php:24
static TranslateUrlParametersToSearchGroups($GetVars)
Metadata schema (in effect a Factory class for MetadataField).
const SEARCHFREQ_DAILY
Definition: SavedSearch.php:26
SQL database abstraction object with smart query caching.
Id()
Get ID of search.
const DB_NOVALUE
static TranslateSearchGroupsToUrlParameterArray($SearchGroups)
Translate a search group array to an URL parameter array.
const SEARCHFREQ_QUARTERLY
Definition: SavedSearch.php:30
UserId($NewValue=DB_NOVALUE)
Get/set user ID.
Frequency($NewValue=DB_NOVALUE)
Get/set search frequency.
const SEARCHFREQ_YEARLY
Definition: SavedSearch.php:31
SavedSearch($SearchId, $SearchName=NULL, $UserId=NULL, $Frequency=NULL, $SearchGroups=NULL)
Definition: SavedSearch.php:34
const SEARCHFREQ_HOURLY
Definition: SavedSearch.php:25
const SEARCHFREQ_BIWEEKLY
Definition: SavedSearch.php:28
static TranslateSearchGroupsToTextDescription($SearchGroups, $IncludeHtml=TRUE, $StartWithBreak=TRUE, $TruncateLongWordsTo=0)
Translate search group array into multi-line string describing search criteria.
DateLastRun($NewValue=DB_NOVALUE)
const SEARCHFREQ_MONTHLY
Definition: SavedSearch.php:29
static TranslateSearchGroupsToUrlParameters($SearchGroups)
Translate search group array into URL parameters (e.g.
GetSearchGroupsAsTextDescription($IncludeHtml=TRUE, $StartWithBreak=TRUE, $TruncateLongWordsTo=0)
Get multi-line string describing search criteria.
SearchGroups($NewSearchGroups=NULL)
GetSearchFieldNames()
Get list of fields to be searched.
Delete()
Delete saved search.
SearchName($NewValue=DB_NOVALUE)
GetSearchGroupsAsUrlParameterArray()
Get search groups as an URL parameter array.
GetSearchGroupsAsUrlParameters()
Get search groups as URL parameters (e.g.
LastMatches()
Return array of most recently matched ResourceIds for a search.
Factory for Resource objects.
CWIS-specific user class.
Definition: CWUser.php:13
static GetSearchFrequencyList()
Get array of possible search frequency descriptions.
static TranslateSearchGroupsToSearchFieldNames($SearchGroups)
Extract list of fields to be searched from search group array.
SaveLastMatches($ArrayofMatchingIds)
Save array of last matches.