Searching and the Partialmatch filter

150 views
Skip to first unread message

Anselm Christophersen

unread,
Oct 14, 2012, 9:05:26 AM10/14/12
to silverst...@googlegroups.com
I'm writig a small search form to search for a specific page type on the frontend.
In the documentation (http://doc.silverstripe.org/framework/en/topics/datamodel) it's mentioned that you can write something like below, when you want to search for more than one field:

$members = Member::get()->filter(array(
    'FirstName,Surname:PartialMatch' => 'sam'
));

Running this on both master and the 3.0 branch gives the error "Couldn't find field FirstName,Surname in any of Member's tables.".
I've dug a little into the problem, and see that the constructor of SearchFilter.php (which PartialmatchFilter.php extends) is internally setting "fullName" to "FirstName,Surname" instead of checking whether it's dealing with a list and converting it to an array (and then doing it's magic).

Rather than being a bug it seems to me that this feature has just not been implemented yet?


Anselm 

Ingo Schommer

unread,
Oct 16, 2012, 9:10:25 AM10/16/12
to silverst...@googlegroups.com
I've confirmed that its not possible to do this,
and think this was documentation-driven development getting a bit out of hand.
Removed the paragraph for now, until its fixed or decided not worth implementing.
I think its an unnecessary duplication of the existing array syntax (paragraph above),
and makes the API both more ambiguous for users, as well as harder to handle inputs internally.
Sorry for the confusion.

Ingo

Anselm Christophersen

unread,
Oct 16, 2012, 9:47:36 AM10/16/12
to silverst...@googlegroups.com
Hi Ingo,
thanks for checking up on this.
Maybe I'm getting things wrong, but I think there is no other way of doing it with the new ORM (or at least no documented way).

I just checked up with the following example. Let's say I'm searching for "$query = New York", and there is a dataobject with a City attribute that has the value "New York". This code returns nothing:

$projects = $projects->filter(array(
'Title:PartialMatch' => $query,
'City:PartialMatch' => $query,
));

If I'm uncommenting the Title part, I'm getting the dataobject with the city "New York", which leads me to conclude that this is an AND statement. 
What I was looking for was an OR statement, which I believe the previous example would have given.
Maybe I'm missing something?

I got around it using the "where" method. Here is how I did for a small search functioniality:


$query = strtolower(addslashes($query)); $qarr = preg_split('/[ +]/', $query); $filter = ''; $first = true; foreach ($qarr as $qitem) { if (!$first) { $filter .= " AND "; } $filter .= " ( Title LIKE '%$qitem%' OR City LIKE '%$qitem%' )"; $first = false; } $projects = $projects->where($filter);

Again, forgive me if I should have missed something obvious in the documentation, but I believe there might be no way of writing OR statements with the partialmatch filter.


Anselm





--
You received this message because you are subscribed to the Google Groups "SilverStripe Core Development" group.
To view this discussion on the web visit https://groups.google.com/d/msg/silverstripe-dev/-/p6OXhu6k1eIJ.
To post to this group, send email to silverst...@googlegroups.com.
To unsubscribe from this group, send email to silverstripe-d...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/silverstripe-dev?hl=en.

Ingo Schommer

unread,
Oct 16, 2012, 10:02:49 AM10/16/12
to silverst...@googlegroups.com
Yep, filter() works with AND conjunctives.
The lack of a way to do OR disjunctives through the ORM was
a major API omission in 3.0, but alas, we're getting there…

Anselm Christophersen

unread,
Oct 16, 2012, 10:16:19 AM10/16/12
to silverst...@googlegroups.com
Awesome :)
Reply all
Reply to author
Forward
0 new messages