Jump to content

kongondo

PW-Moderators
  • Posts

    7,479
  • Joined

  • Last visited

  • Days Won

    146

Everything posted by kongondo

  1. Try Hooking into the inputfield instead like so. Note, example is from module context. See also notes below: public function init() { $this->pages->addHookAfter("InputfieldDatetime::processInput", $this, "hookAfter"); } public function hookAfter(HookEvent $event) { $field = $event->object; if($field->name == 'recurringdateend'){// @note: just a quick example; you might want to hook into 'date_end' as well $page = $this->wire('modules')->ProcessPageEdit->getPage(); #$this->message($field->name);// @note: testing only #$this->message($page->id);// @note: testing only /* // @note: testing only + FOR INFO $oldDate = $page->get($field->name);// existing DB value $newDate = $field->value;// incoming/NEW data $this->message("old date is: $oldDate");// returns timestamp $this->message("new date is: $newDate");// returns timestamp */ // @note: quick example, not useful to you but a good to know 'how-to' // @note: what you really want I suppose is to compare incoming values (from input) // @see above for that ($oldDate and $newDate) $firstdate = $page->get("date_end");//date field 1 $lastdate = $page->get("recurringdateend");// date field 2 if($firstdate >= $lastdate){ //check if the date of field 1 is higher than the value of field 2 // error here; @note $lastdate is not a field! // error example: $field->error('Some Error'); } } } @Note that in my example we are comparing existing DB values (not very useful). In your case, you want to compare incoming values, right? See the $oldDate and $newDate example. However, you would need to Hook into both 'date_end' and 'recurringdateend' in that case (i.e. run your Hook code if either is the field name). Edit2: See complete answer in next post.
  2. What version of ProcessWire is that? That function is not in any of ProcessWire's files. In addition, FYI, ProcessWire's /wire/core/Database.php extends PHP's mysqli class. Edit: Beaten by lostkobrai. I should have noticed there is no such file in ProcessWire
  3. ...mystery solved . Edit: Your OP stated that you needed the Hook to run when a new page is added. Why not Hook into that instead? i.e. 'Pages::added'
  4. Looking at your module code again, I notice this: // @kongondo note: here you are deleting the cache, meaning... $cache->delete("cacheName:" . $page->id); // @kongondo note:...that here we don't have that cache and one will be created afresh $cache->get("cacheName:" . $page->id, $cache::expireNever, function() use($page){ // code you want to cache $content = $page->title . "<br>"; $content .= $page->body; return $content; }); The code inside the Hook is executed because by that point, you have no cache; you have deleted it. So $cache->get() doesn't get the cache and one is created afresh. It seems to me that a Pages::saveReady is happening when you load your pages and that is triggering the cache to be deleted and recreated? But it doesn't make sense since when you reload, your page is reloaded from the cache. Are you sure about that? Have you checked the timestamps? Maybe confirm your workflow. Are pages being created via the API when you visit some page in the frontend?
  5. I assume you are talking about the frontend hence using the latter code in your example. According to the docs (see this example as well) on $cache->get(), it doesn't say whether a WireCache::expire* constant can be used in that combined get and save of cache, unlike in $cache->save() docs where it is explicit that those constants are allowed. Just guessing here, maybe try it like in the $cache->get() docs? i.e. passing null instead of a constant: $cache->get("cacheName:".$page->id, null, function() use($page){ // code should be the same as the one that preloads the cache $content = $page->title . "<br>"; $content .= $page->body; return $content; }); Edit: You can also see the differences in the code here (get) and here (save). save() accepts constants whereas get() doesn't seem to. Edit 2: I am also wondering whether in the template file you needed an explicit WireCache:expireNever rather than $cache::expireNever?
  6. I am not sure whether this is relevant in your case and it is from a while back but just thought to post to see if it helps:
  7. What @Klenkes said. You might want to add a limit=n in that selector though.
  8. Did you see this post in your other thread ? If podcast_shows is a multi-page field, it doesn't matter whether you have one or more pages selected in it; it will return a PageArray.
  9. Welcome to ProcessWire and the forums @swampmusic, You have two options. Media Library is a free module and Media Manager a commercial module (easily handles all sorts of media assets using a centralised approach; full disclaimer; I am the author of this module ). Oh, I think you meant Ryan, not Rory .
  10. OK. It seems you are using an older version of ProcessWire, pre-dating the change in using custom code in page fields (can't remember in what version of ProcessWire 3.x this was introduced). Anyway, then the below is the FORMAT of the code that you need to enter in the custom code textarea. Adapt it to your needs; e.g. a suggestion was made for $page->parent->podcast_show but I see you are using children instead. Also note that I don't know what podcast_show is, so don't know if that code will return anything. This is just a pointer return $page->children->podcast_show;
  11. Show us the code in your /site/ready,php as per Robin's suggestion...Maybe you have a typo there.
  12. OK....then go with what works .
  13. You should only have one set of files. That could have been the source of the problem. If you install (or upgrade) Blog via ProcessWire itself (i.e. as opposed to uploading the module yourself), the folder should be ProcessBlog (I think - not sure since being its developer, I don't install in that manner since I have the files locally). Whatever the case, you should only ever have one set of files, irrespective of whether they live in different folders. So, yes, delete one set and rename the Blog folder to what it should be (my guess is ProcessBlog; if not that, Blog, but definitely not MarkupBlog; I shouldn't think so). Hope this makes sense . Regarding _footer.php, is that a template file or a file you are including within some other template file? Btw, looking at the code in footer.php, I notice you are getting a number of pages by their IDs. Whilst that is the most foolproof way to do it, down the line, especially if there's several such calls in different template files, you will start to get confused what page 1040 was , especially if the code is not documented. In this regard, some people prefer to get by page: $pages->get('/path/to/page/'); Of course, if a page's path changed....you'll have a different problem to deal with. Just my 2p.
  14. No worries. You are just trying to help . @MaryMatlow, what @adrian said. I've been testing against 3.0.42 and Blog seems to work fine. If upgrading doesn't fix the issue, we'll focus on autoload modules.
  15. Actually not a good idea to do that . I made a decision not to namespace my modules (am the author of the Blog module) to instead let the compiler do its work. If @MaryMatlow did that, any changes will be overwritten by the next Blog update. There's something going on with this install which I'd like to get to the bottom of. @MaryMatlow, could you please confirm the ProcessWire version that you are running? (down to the 3.x.x please). The only difference between that module (in the Blog suite of modules) and the others is that BlogPublishDate is an autoload module. I haven't received any other similar reports from other Blog users, which makes me even more curious.
  16. Oops. Pure coincidence; I'm not on your case or anything, ha! .
  17. What @gebeer said. I'd be surprised if that solved your problem though since this line: <?php $deals_item = $pages->get("deals_show_on_endorse=$page->id");?> fetches one page, meaning the foreach in the next line makes no sense.
  18. I see. My point was that the compiler is supposed to take care of cases where a 'namespace' has not been declared (and it does so beautifully). It seems in this case something is tripping it. Although namespacing, in this case, might get around the problem, it will not solve the original issue. It would be helpful to get to the bottom of that since not everyone is able/willing to namespace (especially in existing sites) their template files. I'm wondering whether it is the '.inc.' that is throwing it off or the use of double quotes. Just guessing TBH.
  19. I'm curious why this matters in the present circumstance?
  20. To be honest, although that thread shows you how you can use the PW API to create (read, the HTML) forms, 'a basic (or non-basic) PW form' does not exist; You need to create a HTML form and use ProcessWire to process that form. It is that simple. OK, back to crux of the matter; how to handle user registration from the frontend. There are several issues/steps here: How to create the form (simple; use a HTML form) Where to post that form (i.e., post to the page where the form is displayed, or post to another page) How to handle spam + cross-site forgery How to handle double registrations Feedback to the user once form has been submitted How to deal with errors/validation - client and server-side How to process the form inputs on the server-side (including sanitizing inputs) How and where to save form inputs How to send confirmation email Tackling above: Create Form: This is simple. Create your HTML form in a template file. I suggest using 'post' for method and action to post to self, i.e. './' Post destination: I've suggested posting to self, but you can use some other URL (i.e. an existing page). Spam: I suggest using a honeypot or double honeypot AND CSRF (see $session->csrf). Please Google this forums for examples. If I get time to do this I'll update this post. Double registrations: You would need to check submitted email against saved emails. User Feedback: Some people prefer to redirect to a different page with a thank you message, others reload the same page but don't show the form, just the thank you message. Up to you. If redirecting, see $session->redirect(). Errors + Validation: I suppose you know how to deal with client-side validation. Server-side, you will use $input->post; Use that to check if all required inputs sent; Use $sanitizer to sanitize inputs, e.g. $sanitize->email() for emails. Process Form: See #6. Save Guest: This depends on how you want to save guests. Do you have an external database? Then make use of $database. However, I would go for pages, whereby, each registration is a page, tucked away under some parent page. The title of the page could be the guest's full name and the email would be saved in an email field. This means a template with two fields; title and email. Confirmation Email: See WireMail. Sorry, it's getting late here and cannot give you specific examples. Hopefully the above will give you some food for thought. Happy to provide more details later if you get stuck. Others may chime in too, so, you should be alright :-). ps: If you will be dealing with forms a lot, I recommend investing in Form Builder.
  21. That's coming from ProcessWire's file compiler; it is not a bug on Blog's side. Try clearing your file compiler cache to see if it solves the issue.
  22. Maybe two options to consider: WireCache: Create a natural sort field, say nat_sort. Have this hidden; we don't need to see it in the admin. Add that to the template of the pages you need to sort naturally + paginate (let's call the template 'nat-sort-pages'). Create your Hook and add a function that will build/refresh a non-expiring Wire Cache every time a page that uses 'nat-sort-pages' template is created (no need to do this when the page is edited; just when added). The cache will save the new page's ID, Title (the field to naturally sort) and a 'nat_sort' value of 0 (or whatever your starting index is; here we also assume this is the first page created). Subsequently, when another page is added, your Hook will retrieve the cache, add the details of the new page to the array, use PHP natsort() to sort that array (by Title) + change the values of nat_sort within the array, save it back to the Wire Cache, then use SQL to insert the values in your nat_sort field. Your nat_sort field will be an integer field, so you SQL (pseudo code) will INSERT nat_sort_value IN nat_sort WHERE id=page->id. That should be a very fast operation. In the frontend, use a find sorted by your 'nat_sort' field (sort=nat_sort in the selector) to retrieve paginated results. getById() + SQL nat sort: This approach does not require a nat_sort field nor a Hook. It is an on-demand method for use in the frontend. Use a suitable SQL workaround to naturally sort a limited number of results (i.e. see links above + you'll need to use SQL LIMIT and START). Your SQL will only need to fetch the IDs of those pages. Then use getById (see example here) to retrieve those pages, which you then pass on to your pagination. Both approaches have their pros and cons, obviously.
  23. @Doc, please wrap your code in code blocks using the <> icon (7th from the left). Much easier to read that way, thanks.
  24. Depends on the scenario: If I want to retrieve a limited number of pages (with no requirements for pagination), then have those naturally sorted, I'd go for PHP. If I want paginated results, it means I need them to be already 'naturally-sorted' as they are retrieved, meaning, doing it at the database level, then I'd go for SQL. The present case: Using a Hook to amend the values of a group of pages every time a new page is created. If that group of pages is substantially huge, if using PHP, it means, first retrieving the whole group, sorting them naturally, then saving them. That in itself could be a big hit on the server (we are loading lots of Page objects in memory). Assuming pages are created at a high frequency, that further compounds the issue. In such cases, SQL will most likely be faster and use less memory.
  25. No, it is not possible out-of-the-box but there are workarounds: http://www.mysqltutorial.org/mysql-natural-sorting/ https://www.copterlabs.com/natural-sorting-in-mysql/ https://chrisjean.com/mysql-natural-sort-order-by-on-non-numeric-field-type/ If we are talking a potentially huge result set, I would consider a SQL solution (see links above) to update that field for each page in the result set.
×
×
  • Create New...