2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								< ? php  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-08-16 18:27:22 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								namespace  BookStack\Search ;  
						 
					
						
							
								
									
										
										
										
											2018-09-25 19:30:50 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-11-22 08:17:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  BookStack\Entities\EntityProvider ;  
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  BookStack\Entities\Models\BookChild ;  
						 
					
						
							
								
									
										
										
										
											2020-11-22 08:17:45 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								use  BookStack\Entities\Models\Entity ;  
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:41:14 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  BookStack\Entities\Models\Page ;  
						 
					
						
							
								
									
										
										
										
											2023-05-18 00:56:55 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  BookStack\Permissions\PermissionApplicator ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								use  BookStack\Users\Models\User ;  
						 
					
						
							
								
									
										
										
										
											2021-11-20 22:03:56 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  Illuminate\Database\Connection ;  
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  Illuminate\Database\Eloquent\Builder  as  EloquentBuilder ;  
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  Illuminate\Database\Eloquent\Collection  as  EloquentCollection ;  
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								use  Illuminate\Database\Eloquent\Relations\BelongsTo ;  
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  Illuminate\Database\Query\Builder ;  
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  Illuminate\Support\Collection ;  
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								use  Illuminate\Support\Facades\DB ;  
						 
					
						
							
								
									
										
										
										
											2019-09-14 06:58:40 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  Illuminate\Support\Str ;  
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								use  SplObjectStorage ;  
						 
					
						
							
								
									
										
										
										
											2017-03-19 20:48:44 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-11-22 08:17:45 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								class  SearchRunner  
						 
					
						
							
								
									
										
										
										
											2017-03-19 20:48:44 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								{  
						 
					
						
							
								
									
										
										
										
											2022-07-13 03:15:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    protected  EntityProvider  $entityProvider ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    protected  PermissionApplicator  $permissions ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  Acceptable  operators  to  be  used  in  a  query . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-13 03:15:41 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  @ var  string [] 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-16 18:27:22 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  array  $queryOperators  =  [ '<=' ,  '>=' ,  '=' ,  '<' ,  '>' ,  'like' ,  '!=' ]; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  Retain  a  cache  of  score  adjusted  terms  for  specific  search  options . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  From  PHP >= 8  this  can  be  made  into  a  WeakMap  instead . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  @ var  SplObjectStorage 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    protected  $termAdjustmentCache ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-13 03:15:41 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    public  function  __construct ( EntityProvider  $entityProvider ,  PermissionApplicator  $permissions ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-19 20:48:44 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $this -> entityProvider  =  $entityProvider ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-13 03:15:41 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $this -> permissions  =  $permissions ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $this -> termAdjustmentCache  =  new  SplObjectStorage (); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-19 20:48:44 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  Search  all  entities  in  the  system . 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								     *  The  provided  count  is  for  each  entity  to  search , 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-06 08:32:01 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								     *  Total  returned  could  be  larger  and  not  guaranteed . 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-15 00:28:01 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
									
										
										
										
											2022-10-24 19:12:48 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								     *  @ return  array { total :  int ,  count :  int ,  has_more :  bool ,  results :  Collection < Entity > } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-13 22:23:03 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    public  function  searchEntities ( SearchOptions  $searchOpts ,  string  $entityType  =  'all' ,  int  $page  =  1 ,  int  $count  =  20 ) :  array 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-19 20:48:44 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $entityTypes  =  array_keys ( $this -> entityProvider -> all ()); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-10 03:59:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $entityTypesToSearch  =  $entityTypes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( $entityType  !==  'all' )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $entityTypesToSearch  =  $entityType ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  elseif  ( isset ( $searchOpts -> filters [ 'type' ]))  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $entityTypesToSearch  =  explode ( '|' ,  $searchOpts -> filters [ 'type' ]); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-10 03:59:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-03-25 02:46:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $results  =  collect (); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-15 22:04:30 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $total  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-03-25 03:04:18 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $hasMore  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-15 22:04:30 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-04-10 03:59:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        foreach  ( $entityTypesToSearch  as  $entityType )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            if  ( ! in_array ( $entityType ,  $entityTypes ))  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-06 08:32:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $entityModelInstance  =  $this -> entityProvider -> get ( $entityType ); 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-13 22:23:03 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $searchQuery  =  $this -> buildQuery ( $searchOpts ,  $entityModelInstance ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $entityTotal  =  $searchQuery -> count (); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $searchResults  =  $this -> getPageOfDataFromQuery ( $searchQuery ,  $entityModelInstance ,  $page ,  $count ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-06 08:32:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( $entityTotal  >  ( $page  *  $count ))  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-03-25 03:04:18 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                $hasMore  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-06 08:32:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-03-25 03:04:18 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $total  +=  $entityTotal ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $results  =  $results -> merge ( $searchResults ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-10 03:59:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 02:24:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-04-15 22:04:30 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  [ 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            'total'     =>  $total , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            'count'     =>  count ( $results ), 
							 
						 
					
						
							
								
									
										
										
										
											2018-03-25 03:04:18 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            'has_more'  =>  $hasMore , 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            'results'   =>  $results -> sortByDesc ( 'score' ) -> values (), 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-15 22:04:30 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        ]; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 02:24:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  Search  a  book  for  entities . 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    public  function  searchBook ( int  $bookId ,  string  $searchString ) :  Collection 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $opts  =  SearchOptions :: fromString ( $searchString ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:31:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $entityTypes  =  [ 'page' ,  'chapter' ]; 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $entityTypesToSearch  =  isset ( $opts -> filters [ 'type' ])  ?  explode ( '|' ,  $opts -> filters [ 'type' ])  :  $entityTypes ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:31:11 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $results  =  collect (); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:31:11 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        foreach  ( $entityTypesToSearch  as  $entityType )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            if  ( ! in_array ( $entityType ,  $entityTypes ))  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $entityModelInstance  =  $this -> entityProvider -> get ( $entityType ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $search  =  $this -> buildQuery ( $opts ,  $entityModelInstance ) -> where ( 'book_id' ,  '=' ,  $bookId ) -> take ( 20 ) -> get (); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:31:11 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $results  =  $results -> merge ( $search ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-22 08:17:45 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:31:11 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  $results -> sortByDesc ( 'score' ) -> take ( 20 ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  Search  a  chapter  for  entities . 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    public  function  searchChapter ( int  $chapterId ,  string  $searchString ) :  Collection 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $opts  =  SearchOptions :: fromString ( $searchString ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $entityModelInstance  =  $this -> entityProvider -> get ( 'page' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $pages  =  $this -> buildQuery ( $opts ,  $entityModelInstance ) -> where ( 'chapter_id' ,  '=' ,  $chapterId ) -> take ( 20 ) -> get (); 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  $pages -> sortByDesc ( 'score' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  Get  a  page  of  result  data  from  the  given  query  based  on  the  provided  page  parameters . 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  getPageOfDataFromQuery ( EloquentBuilder  $query ,  Entity  $entityModelInstance ,  int  $page  =  1 ,  int  $count  =  20 ) :  EloquentCollection 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $relations  =  [ 'tags' ]; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( $entityModelInstance  instanceof  BookChild )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-13 21:28:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            $relations [ 'book' ]  =  function  ( BelongsTo  $query )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-23 07:33:55 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                $query -> scopes ( 'visible' ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            }; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( $entityModelInstance  instanceof  Page )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-13 21:28:17 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $relations [ 'chapter' ]  =  function  ( BelongsTo  $query )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-23 07:33:55 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                $query -> scopes ( 'visible' ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            }; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  $query -> clone () 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            -> with ( array_filter ( $relations )) 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            -> skip (( $page  -  1 )  *  $count ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            -> take ( $count ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            -> get (); 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  Create  a  search  query  for  an  entity . 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-16 02:16:07 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-13 22:23:03 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  buildQuery ( SearchOptions  $searchOpts ,  Entity  $entityModelInstance ) :  EloquentBuilder 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 02:24:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-17 02:54:25 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $entityQuery  =  $entityModelInstance -> newQuery () -> scopes ( 'visible' ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        if  ( $entityModelInstance  instanceof  Page )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-10-10 23:22:51 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            $entityQuery -> select ( array_merge ( $entityModelInstance :: $listAttributes ,  [ 'owned_by' ])); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $entityQuery -> select ([ '*' ]); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:41:14 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        // Handle normal search terms
 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $this -> applyTermSearch ( $entityQuery ,  $searchOpts ,  $entityModelInstance ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // Handle exact term matching
 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-22 08:17:45 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        foreach  ( $searchOpts -> exacts  as  $inputTerm )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $entityQuery -> where ( function  ( EloquentBuilder  $query )  use  ( $inputTerm ,  $entityModelInstance )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-04-27 23:33:24 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                $inputTerm  =  str_replace ( '\\' ,  '\\\\' ,  $inputTerm ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                $query -> where ( 'name' ,  'like' ,  '%'  .  $inputTerm  .  '%' ) 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                    -> orWhere ( $entityModelInstance -> textField ,  'like' ,  '%'  .  $inputTerm  .  '%' ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 18:57:33 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            }); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        // Handle tag searches
 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        foreach  ( $searchOpts -> tags  as  $inputTerm )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            $this -> applyTagSearch ( $entityQuery ,  $inputTerm ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // Handle filters
 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        foreach  ( $searchOpts -> filters  as  $filterTerm  =>  $filterValue )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-14 06:58:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $functionName  =  Str :: camel ( 'filter_'  .  $filterTerm ); 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            if  ( method_exists ( $this ,  $functionName ))  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:24:49 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                $this -> $functionName ( $entityQuery ,  $entityModelInstance ,  $filterValue ); 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-17 02:54:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  $entityQuery ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  For  the  given  search  query ,  apply  the  queries  for  handling  the  regular  search  terms . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  applyTermSearch ( EloquentBuilder  $entityQuery ,  SearchOptions  $options ,  Entity  $entity ) :  void 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $terms  =  $options -> searches ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        if  ( count ( $terms )  ===  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $scoredTerms  =  $this -> getTermAdjustments ( $options ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $scoreSelect  =  $this -> selectForScoredTerms ( $scoredTerms ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $subQuery  =  DB :: table ( 'search_terms' ) -> select ([ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            'entity_id' , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            'entity_type' , 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            DB :: raw ( $scoreSelect [ 'statement' ]), 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        ]); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $subQuery -> addBinding ( $scoreSelect [ 'bindings' ],  'select' ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:41:14 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $subQuery -> where ( 'entity_type' ,  '=' ,  $entity -> getMorphClass ()); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $subQuery -> where ( function  ( Builder  $query )  use  ( $terms )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            foreach  ( $terms  as  $inputTerm )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-04-27 23:33:24 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                $inputTerm  =  str_replace ( '\\' ,  '\\\\' ,  $inputTerm ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:29:25 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                $query -> orWhere ( 'term' ,  'like' ,  $inputTerm  .  '%' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $subQuery -> groupBy ( 'entity_type' ,  'entity_id' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $entityQuery -> joinSub ( $subQuery ,  's' ,  'id' ,  '=' ,  'entity_id' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $entityQuery -> addSelect ( 's.score' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $entityQuery -> orderBy ( 'score' ,  'desc' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  Create  a  select  statement ,  with  prepared  bindings ,  for  the  given 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  set  of  scored  search  terms . 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-09 23:13:15 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								     *  @ param  array < string ,  float >  $scoredTerms 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  @ return  array { statement :  string ,  bindings :  string []} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    protected  function  selectForScoredTerms ( array  $scoredTerms ) :  array 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // Within this we walk backwards to create the chain of 'if' statements
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // so that each previous statement is used in the 'else' condition of
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // the next (earlier) to be built. We start at '0' to have no score
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // on no match (Should never actually get to this case).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $ifChain  =  '0' ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $bindings  =  []; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        foreach  ( $scoredTerms  as  $term  =>  $score )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $ifChain  =  'IF(term like ?, score * '  .  ( float )  $score  .  ', '  .  $ifChain  .  ')' ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $bindings []  =  $term  .  '%' ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  [ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            'statement'  =>  'SUM('  .  $ifChain  .  ') as score' , 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            'bindings'   =>  array_reverse ( $bindings ), 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        ]; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-09 23:13:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  For  the  terms  in  the  given  search  options ,  query  their  popularity  across  all 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  search  terms  then  provide  that  back  as  score  adjustment  multiplier  applicable 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  for  their  rarity .  Returns  an  array  of  float  multipliers ,  keyed  by  term . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  @ return  array < string ,  float > 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  getTermAdjustments ( SearchOptions  $options ) :  array 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( isset ( $this -> termAdjustmentCache [ $options ]))  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            return  $this -> termAdjustmentCache [ $options ]; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $termQuery  =  SearchTerm :: query () -> toBase (); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $whenStatements  =  []; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $whenBindings  =  []; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        foreach  ( $options -> searches  as  $term )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $whenStatements []  =  'WHEN term LIKE ? THEN ?' ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $whenBindings []  =  $term  .  '%' ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $whenBindings []  =  $term ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $termQuery -> orWhere ( 'term' ,  'like' ,  $term  .  '%' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $case  =  'CASE '  .  implode ( ' ' ,  $whenStatements )  .  ' END' ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $termQuery -> selectRaw ( $case  .  ' as term' ,  $whenBindings ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $termQuery -> selectRaw ( 'COUNT(*) as count' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $termQuery -> groupByRaw ( $case ,  $whenBindings ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:41:14 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $termCounts  =  $termQuery -> pluck ( 'count' ,  'term' ) -> toArray (); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $adjusted  =  $this -> rawTermCountsToAdjustments ( $termCounts ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $this -> termAdjustmentCache [ $options ]  =  $adjusted ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  $this -> termAdjustmentCache [ $options ]; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  Convert  counts  of  terms  into  a  relative - count  normalised  multiplier . 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  @ param  array < string ,  int >  $termCounts 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     * 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  @ return  array < string ,  int > 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    protected  function  rawTermCountsToAdjustments ( array  $termCounts ) :  array 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        if  ( empty ( $termCounts ))  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            return  []; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-13 21:28:17 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $multipliers  =  []; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $max  =  max ( array_values ( $termCounts )); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        foreach  ( $termCounts  as  $term  =>  $count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $percent  =  round ( $count  /  $max ,  5 ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $multipliers [ $term ]  =  1.3  -  $percent ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:41:14 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 22:12:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  $multipliers ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-27 02:24:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  Get  the  available  query  operators  as  a  regex  escaped  list . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  getRegexEscapedOperators () :  string 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $escapedOperators  =  []; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        foreach  ( $this -> queryOperators  as  $operator )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $escapedOperators []  =  preg_quote ( $operator ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-10-27 05:04:18 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        return  implode ( '|' ,  $escapedOperators ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     *  Apply  a  tag  search  term  onto  a  entity  query . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-27 20:29:00 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  applyTagSearch ( EloquentBuilder  $query ,  string  $tagTerm ) :  EloquentBuilder 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        preg_match ( '/^(.*?)(('  .  $this -> getRegexEscapedOperators ()  .  ')(.*?))?$/' ,  $tagTerm ,  $tagSplit ); 
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $query -> whereHas ( 'tags' ,  function  ( EloquentBuilder  $query )  use  ( $tagSplit )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $tagName  =  $tagSplit [ 1 ]; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $tagOperator  =  count ( $tagSplit )  >  2  ?  $tagSplit [ 3 ]  :  '' ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $tagValue  =  count ( $tagSplit )  >  3  ?  $tagSplit [ 4 ]  :  '' ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $validOperator  =  in_array ( $tagOperator ,  $this -> queryOperators ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            if  ( ! empty ( $tagOperator )  &&  ! empty ( $tagValue )  &&  $validOperator )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                if  ( ! empty ( $tagName ))  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                    $query -> where ( 'name' ,  '=' ,  $tagName ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                if  ( is_numeric ( $tagValue )  &&  $tagOperator  !==  'like' )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                    // We have to do a raw sql query for this since otherwise PDO will quote the value and MySQL will
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                    // search the value as a string which prevents being able to do number-based operations
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                    // on the tag values. We ensure it has a numeric value and then cast it just to be sure.
 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-20 22:03:56 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                    /** @var Connection $connection */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                    $connection  =  $query -> getConnection (); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                    $tagValue  =  ( float )  trim ( $connection -> getPdo () -> quote ( $tagValue ),  " ' " ); 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-05 16:33:25 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                    $query -> whereRaw ( " value  { $tagOperator }   { $tagValue } " ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                }  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-04-27 23:33:24 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                    if  ( $tagOperator  ===  'like' )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                        $tagValue  =  str_replace ( '\\' ,  '\\\\' ,  $tagValue ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                    } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                    $query -> where ( 'value' ,  $tagOperator ,  $tagValue ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            }  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                $query -> where ( 'name' ,  '=' ,  $tagName ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        }); 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        return  $query ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  Custom  entity  search  filters . 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterUpdatedAfter ( EloquentBuilder  $query ,  Entity  $model ,  $input ) :  void 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        try  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $date  =  date_create ( $input ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'updated_at' ,  '>=' ,  $date ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  catch  ( \Exception  $e )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterUpdatedBefore ( EloquentBuilder  $query ,  Entity  $model ,  $input ) :  void 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        try  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $date  =  date_create ( $input ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'updated_at' ,  '<' ,  $date ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  catch  ( \Exception  $e )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterCreatedAfter ( EloquentBuilder  $query ,  Entity  $model ,  $input ) :  void 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        try  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $date  =  date_create ( $input ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'created_at' ,  '>=' ,  $date ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  catch  ( \Exception  $e )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterCreatedBefore ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        try  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $date  =  date_create ( $input ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'created_at' ,  '<' ,  $date ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 23:00:47 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        }  catch  ( \Exception  $e )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterCreatedBy ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-11 06:51:18 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $userSlug  =  $input  ===  'me'  ?  user () -> slug  :  trim ( $input ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $user  =  User :: query () -> where ( 'slug' ,  '=' ,  $userSlug ) -> first ([ 'id' ]); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( $user )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'created_by' ,  '=' ,  $user -> id ); 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterUpdatedBy ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-11 06:51:18 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $userSlug  =  $input  ===  'me'  ?  user () -> slug  :  trim ( $input ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $user  =  User :: query () -> where ( 'slug' ,  '=' ,  $userSlug ) -> first ([ 'id' ]); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( $user )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'updated_by' ,  '=' ,  $user -> id ); 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-02-14 18:39:18 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    protected  function  filterOwnedBy ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-16 02:27:03 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        $userSlug  =  $input  ===  'me'  ?  user () -> slug  :  trim ( $input ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $user  =  User :: query () -> where ( 'slug' ,  '=' ,  $userSlug ) -> first ([ 'id' ]); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        if  ( $user )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'owned_by' ,  '=' ,  $user -> id ); 
							 
						 
					
						
							
								
									
										
										
										
											2021-02-14 18:39:18 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterInName ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $query -> where ( 'name' ,  'like' ,  '%'  .  $input  .  '%' ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterInTitle ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $this -> filterInName ( $query ,  $model ,  $input ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterInBody ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $query -> where ( $model -> textField ,  'like' ,  '%'  .  $input  .  '%' ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterIsRestricted ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2022-10-10 23:22:51 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $query -> whereHas ( 'permissions' ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterViewedByMe ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $query -> whereHas ( 'views' ,  function  ( $query )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'user_id' ,  '=' ,  user () -> id ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        }); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterNotViewedByMe ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $query -> whereDoesntHave ( 'views' ,  function  ( $query )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-28 01:05:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            $query -> where ( 'user_id' ,  '=' ,  user () -> id ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        }); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  filterSortBy ( EloquentBuilder  $query ,  Entity  $model ,  $input ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-10-01 18:24:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-14 06:58:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $functionName  =  Str :: camel ( 'sort_by_'  .  $input ); 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        if  ( method_exists ( $this ,  $functionName ))  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            $this -> $functionName ( $query ,  $model ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2017-10-01 18:24:13 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    /** 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-26 23:23:15 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     *  Sorting  filter  options . 
							 
						 
					
						
							
								
									
										
										
										
											2017-10-01 18:24:13 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								     */ 
							 
						 
					
						
							
								
									
										
										
										
											2018-09-26 01:00:40 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    protected  function  sortByLastCommented ( EloquentBuilder  $query ,  Entity  $model ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-10-01 18:24:13 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $commentsTable  =  DB :: getTablePrefix ()  .  'comments' ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-10-01 18:24:13 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $morphClass  =  str_replace ( '\\' ,  '\\\\' ,  $model -> getMorphClass ()); 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-08 19:04:27 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        $commentQuery  =  DB :: raw ( '(SELECT c1.entity_id, c1.entity_type, c1.created_at as last_commented FROM '  .  $commentsTable  .  ' c1 LEFT JOIN '  .  $commentsTable  .  ' c2 ON (c1.entity_id = c2.entity_id AND c1.entity_type = c2.entity_type AND c1.created_at < c2.created_at) WHERE c1.entity_type = \''  .  $morphClass  .  '\' AND c2.created_at IS NULL) as comments' ); 
							 
						 
					
						
							
								
									
										
										
										
											2017-10-01 18:24:13 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        $query -> join ( $commentQuery ,  $model -> getTable ()  .  '.id' ,  '=' ,  'comments.entity_id' ) -> orderBy ( 'last_commented' ,  'desc' ); 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-29 00:58:52 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}