Jump to content

Stumped on two issues


digitex
 Share

Recommended Posts

return r=5773 r=5773 r=5773 r=5789

But that's the pages the repeater lives in same as $p in you code. Are you sure that's not the $r = $r->getForPage() you have in your code, that is returning the page the repeater is living on and not the repeater itself.

Link to comment
Share on other sites

return r=5773 r=5773 r=5773 r=5789

But that's the pages the repeater lives in same as $p in you code. Are you sure that's not the $r = $r->getForPage() you have in your code, that is returning the page the repeater is living on and not the repeater itself.

This is all picture.

pa=5773|5789 — Find result for 16.11.
 
p=5773 — First property
r=5975 — checkin 17.11, booked 0 
r=5976 —checkin 18.11, booked 0 
r=6816 — checkin 19.11, booked 0
 
p=5789 — Second property
r=5919 — checkin 16.11, booked 0
 
The problem is, that I need to remove not correct dates from results.
Link to comment
Share on other sites

It's a little confusing why you search for pages then search repeaters to then return the page the repeater is on to call renderItem($r), so you need to filter them again in renderItem() ? 

If you want to filter the repeater again with the date, then why don't you do it? :)

$p->calendar->find("booked=0, checkin_1=16.11.2013")

Or am I missing something?

You could as mentioned earlier search for repeaters directly and then get the page they live on, but I thought you want to render the repeater and not the page.

However this could look like

$repeaters = $pages->find("template=repeater_calendar, checkin_1=16.11.2013, booked=0, include=all");
foreach ($repeaters as $r) {
    $repPage = $r->getForPage();
    if($repPage->isPublic && $repPage->fireplace) $content .= renderItem($repPage);
}

But as said the renderItem($repPage) is confusing to me as I would expect you would want to render the repeater item $r.

  • Like 3
Link to comment
Share on other sites

Dear Soma, million thanks for your help. Your words and logic as always direct to the correct result.

For sure, your code is absolutely right and I try to use this code before, but with zero result.

$p->calendar->find("booked=0, checkin_1=16.11.2013")
All problem were with date field. In some reason (maybe output data format or something) selector don't find correct result for this date field. I try to use different date in selector, like d.m.y, y.m.d & etc but nothing works.

So, I just change data field to usual text field. Now works absolutely fine.

Link to comment
Share on other sites

I'm not sure the date is really recognized as date and that would work with strtotime() but maybe you should put it in as a string:

$p->calendar->find("booked=0, checkin_1='16.11.2013'");

This should definately work

$date = strtotime("16.11.2013");
$p->calendar->find("booked=0, checkin_1=$date");

Outputformatting has nothing to do with it.

  • Like 2
Link to comment
Share on other sites

  • 6 months later...

Me again. A big thanks again to Nik for his post on the first page of this thread. I got the date range search working very well and for a while everything was peachy.

Now, we want to add additional attributes to the search to go with the availability dates. The region and capacity of the properties is being added (possibly more later but I'll cross that bridge when I get to it. We want the date range, region(location) and capacity to be searchable together or separately and I have reached the limit of my very limited knowledge. I have the data fields on the same page as the repeater that contains the dates and booked status and although I got the date range search to work on it's own and the region/capacity working on it's own, I can't get them to work together. I hoped I could find all property pages matching the $selector and then refine that with the availability search but I can't make it work. The code I have now is:

<?php
$out = "";
$selector = "";
    
if($input->get->region) {
    $loc = ($input->get->region);
    $selector .= "location=$loc, ";
    $input->whitelist('region', $loc);
        
    }
if($input->get->capacity) {
    $cap = ($input->get->capacity);
        $cap = (int) $cap;
        $selector .= "sleeps>=$cap, ";
        $input->whitelist('capacity', $cap);
}

if($input->get->requestfrom && $input->get->requestto) {

    $fromvalue = $sanitizer->selectorValue($input->get->requestfrom);
    $tovalue = $sanitizer->selectorValue($input->get->requestto);
    $input->whitelist('requestfrom', $fromvalue);
    $input->whitelist('requestto', $tovalue);
    

    $start = new DateTime($fromvalue);
    $interval = new DateInterval('P7D');
    $end = new DateTime($tovalue);
    $period = new DatePeriod($start, $interval, $end);

    $all = $pages->find("template=property_availability, $selector, sort=cottage_name");
    
        $cottages = array();
            foreach($period as $term) {
             $df = $term->format("m/d/Y");
              $dt = $term->modify("+7 days")->format("m/d/Y");
              $matches = $all->find("rental_period.date_from>=$df, rental_period.date_to<=$dt, rental_period.booked=0");
 
              if(!count($matches)) {
                $cottages = array();
                break;
              }

          $termCottages = array();

          foreach($matches as $property) {
            
            if($property->viewable()) continue;

            $termCottages[] = $property;
          }

      
      if(count($cottages)) $cottages = array_intersect($cottages, $termCottages);
      else $cottages = $termCottages;
    }

} else {
    $cottages = $pages->find("$selector, sort=cottage_name");
}

$uniqueResults = array();
        foreach($cottages as $cottage) {
            $uniqueResults[$cottage->parent->parent->title]=$cottage->parent;
        }

    $total = count($uniqueResults);
    if($total) {
        $out .= "<h2>{$total} results for.</h2>";
        $out .= "<ul>";
        foreach($uniqueResults as $m) {

              $out .= "<li class='result'><a href='{$m->url}'>{$m->parent->cottage_name}</a><br><span><em>Location: {$m->parent->address} | Sleeps: {$m->child->sleeps}</em></span></li>\n";
              
        }
        $out .= "</ul>";
    } else {
        $out .= "<h2>Sorry, no results were found.</h2>";
    } ?>

If searching just for date range it returns every property regardless of date searched or booked status and if searching for date range, capacity and/or region together it ignores the dates and returns the other attributes, correctly. I hope there's just something wrong with the way I'm targetting the repeater fields but everything i've tried has failed. Does anyone have a suggestion on where I went wrong? i could use the help. Thanks in advance.

Link to comment
Share on other sites

I went back to the drawing board and tried a different approach and that didn't work either. i feel like I'm close and just missing something but maybe not. Maybe I need to go in a completely different direction.

I'm getting desperate. Any thoughts would be appreciated.

Link to comment
Share on other sites

I'm getting desperate. Any thoughts would be appreciated.

Well, I read through your code a week back but couldn't spot any obvious flaw. Now I had another look and feel like I should've seen it in the first place... Actually you did yourself in the very beginning as you had the very same problem then.

Me again. A big thanks again to Nik for his post on the first page of this thread. I got the date range search working very well and for a while everything was peachy.

You're welcome. And you should still hang on to what you had working ;). Here's the problem line (core of it anyway):

 $matches = $all->find("rental_period.date_from>=$df, rental_period.date_to<=$dt, rental_period.booked=0");

As you figured out before (and Ryan confirmed you right), this kind of selector is something to beware of. While all of the three conditions must match, they only have to match the same page (property_availability), not the same repeater item. So this would match any page that has rental_period-repeater with one item matching the condition for date_from, another item matching the condition for date_to and third item matching the condition for booked. All the conditions could have a match in the very same repeater item, but that's not required (and you'd want it to be). That's just the nature of repeaters. Nasty, I know.

Take the version with working date ranges and add the capacity and region handling like you have now in the beginning. Then, instead of first finding all cottages matching region and capacity, just go for the repeater items matching the date range like before and modify the match handling like this:

foreach($matches as $item) {

    $property = $item->getForPage();
    if(!$property->viewable()) continue; // skip if property is unpublished or something

    // add this: skip the match if it doesn't match your region or capacity
    if(!$property->matches($filterSelector)) continue;

    // now you have the $property and the matching repeater $item
    $termCottages[] = $item->id;
}

Here $filterSelector should be empty if no region or capacity has been chosen. Or it could be something like "location=xyz, sleeps>=10" to rule out any cottages not located in xyz or having capacity of less than 10. I haven't tested it but naturally it'll work like a charm ;).

So you were on the right track all along. Just don't go for something that's been proven faulty for this scenario before. :)

  • Like 7
Link to comment
Share on other sites

Nik you are a godsend. you're right and I slap my head for going in circles for so long.

I noticed that

if(!$property->viewable()) continue;

was a filter of sorts already as it removes non-viewable items and I should have clued in that that was where to try to filter results from the other parameters but this line

if(!$property->matches($filterSelector)) continue;

is something I've never seen before and it works great. I'll remember it.

It's gratifying to know that when you reach the limit of your abilities you can still come here and get access to such an enormous well of knowledge and insight.

Thank you again.

  • Like 2
Link to comment
Share on other sites

if(!$property->matches($filterSelector)) continue;

is something I've never seen before and it works great. I'll remember it.

It's gratifying to know that when you reach the limit of your abilities you can still come here and get access to such an enormous well of knowledge and insight.

Thank you again.

You're welcome. It's always a pleasure to be able to help someone. I'd suggest you (and everyone else for that matter!) take a look at Soma's great Cheatsheet. Click around and discover something new for your toolbox. :)

  • Like 5
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...