Keyword modifier ^contains using regex - is it possible/planned?


(Tim Davison) #1

Hi all

 

Wondering if it's possible to use regex for the ^contains keyword modifier.  I know it can be used for ^replace, but I use ^contains a lot more as it provides me with (very basic) if/else logic.  

 

Manual don't seem to indicate it is do-able, only for ^replace.

 

I can get around it (sometimes) with multiple keywords all using contains, but only if my 'else' logic is to display nothing for all cases.

 

Matrix v4.12

 

If not possible, is it planned for future release?  Any others who would think this would be nice feature?

 

Cheers

 

 


(Bart Banda) #2

It is not planned functionality at the moment, but you might be able to use the preg_replace keyword modifiers and the reg ex asset for this? http://manuals.matrix.squizsuite.net/other-cms-assets/chapters/regular-expression-asset

 

That was added in 4.18.4 however. 

 

Is there a specific modification you are wanting to do with this?


(Tim Davison) #3

Thanks Bart.  preg_replace looks pretty nice, but as you say is in a later version.

 

The specific functionality I was after was being able show/hide content based on which section of the site the user is in based on the top-level page (while avoiding design customisations).  And then make it re-usable so it can be nested in multiple places within the site, update once, update everywhere, etc.  I was doing this by inspecting the url.  But a nuance of our system is we have replicated master/slave server setup, and the master url's don't match the slave url's 1:1, not even close.

 

How I've resolved it was this:

%globals_asset_url^contains:domain.slaver.au/top_name: do_stuff_here: ^trim%
%globals_asset_url^contains:domain.master.au/some_extra_nuisance/top_name: do_stuff_here: ^trim%

It works, but I didn't like it, specifically because 'do_stuff_here' is the same for both lines, but I've got to define it twice.

 

Then repeat that for each item you want to display/hide, in these cases lists of links, so a couple hundred lines of code (so far).

 

If I could have used regex in the ^contains modifier I could have captured both those conditions in the one line.

 

Also, I know could have been achieved a number of other ways (e.g. design customisations, pure css, keywords with HTML comment bracing, javascript) but each of these options was ruled out for one reason or another.  Above approach is working for now, albeit more verbose than I would like.

 

Looks like I can look forward to this functionality in a later version.

 

Thanks


(Bart Banda) #4

What content are you printing conditionally? Hardcoded HTML in the parse file or can you use nesting for it? The good thing in 5.0 is that you can use the conditional content feature on standard pages, so you can have a global complex condition setup using regex, then just %begin %else %end keywords to print everything.

 

To make that keyword you are using for now easier though, maybe just use the replace modifier first and then the contains modifier? That way you can do it all in 1 line, something like:

%globals_asset_url^replace:au/top_name|nuisance/top_name:XXX^contains:XXX:do_stuff_here: ^trim%

Would that make it easier?


(Tim Davison) #5

Aha, that's an excellent idea (daisy-chaining replace before contains, I mean).  I will try that out today and let you know how it goes, but that should definitely capture it nicely.

 

Looking forward to some of the nice features in v5, also.


(Tim Davison) #6

To Bart Banda, you, sir, are a star.

 

Works exactly as you said.  Expression I eventually went with:

%globals_asset_url^replace:.domain.au\/nuisance:.vic.gov.au^contains:.domain.au/top-page:<li><a href="#">top-page-link</a></li>: ^trim%

This basically strips back the 'nuisance' part back to the barebones, and then the contains figures out the rest.

 

This method of stripping out the nuisance part with replace first is something I'm going to be able to re-use again and again.  Above example is relatively simple, but with more and more complex regex in the replace you could really do so much more.  

 

Much kudos to you.

 

Cheers


(Bart Banda) #7

Good to hear it helped and made it easier for you! :)


(Buttrose) #8

I am interested in getting the first of the following  to work:

 

<p>%ds__event-type^contains:Conference:<b>%ds__title%</b>:Not Conference%</p>
<p>%ds__event-type^contains:Conference:<b>CON</b>:Not CON%</p>

 

The second will print either CON or Not CON

 

The first screws up completely because the parser can't handle the nested %% pair around the keyword %ds__title%. Surely there is a way to do this?

 

Even if it can be made to work it is a very cumbersome method. I can't  for the life me see why Matrix does not have a general  "if  then else "  so that you could write say

 

% if  (%ds__event-type^contains:Conference%) %

<p>  some output </p>

%else%

<p>some other output</p>

%endif%

 

Very flexible and simple and particulary useful for asset listings of data source records.


(Tim Davison) #9

I think you would need to use the 'replace_keywords' modifier first.  Not at work so can't test right now, but could you do:

%ds__event-type^replace_keywords:contains:Conference:<b>{ds__title}</b>:Not Conference%

Whether this is supported or not depends on your Matrix version - I don't think it's supported on my v4.12.  Would need to double-check.

 

I also believe in later still versions of Matrix that type of if/else tagging is also available.


(Buttrose) #10

Yes that does work. Thank you.

It would have been easier to have the parser  accept escaping of the inner  % s or smart enough to match up the pairs but there you go.