bmacnaughton

How to capture page containing a pagetable?

Recommended Posts

When a PageTable field in a specific template is being edited I need to know the Page that contains the PageTable so I can fill in hidden fields in the PageTable.

I can capture the page being edited via:

// $this->addHookBefore('ProcessPageEdit::execute', ...

public function pageEditExecuteBefore(HookEvent $e) {
    $p = $e->object->getPage();
    if ($p->template !== 'rtw-product') return;
    // $p is the page being edited
}

I can intercept PageTable entry being saved:

// $this->addHookBefore('Pages::save'

public function savePageBefore (HookEvent $e) {
    $p = $this->wire('page')->id;
    $page = $e->arguments('page');
    $obj = $e->object;
    $name = $page->name;                       // page name of PageTable page
    $template = $page->template->name;         // template of PageTable page
    $parent = $page->parent->name;             // parent directory for PageTable items

What I am trying to find is the page in which the PageTable field is located.

I've also tried having pageEditExecuteBefore() saving $p in $this->context and then accessing that in savePageBefore() but it's a different instance of the class because $this->context is null when it gets to savePageBefore(). I could save the page ID in session, but that seems error prone.

Does anyone know how to achieve this?

Share this post


Link to post
Share on other sites

Try this

$fieldList = $fields->find('type%=PageTable');
foreach($fieldList as $f) {
    if($page->template->hasField($f)) {
        // page has the field
    }
}

Or simply:

if($page->fields->find('type%=PageTable')->count)) {
	// page has a PageTable field
}

// check for a specific field
if($myField = $page->fields->get('type%=PageTable')) {
	// $myField of PageTable type exists on this page.
}

Here I used find() method with a selector for matching type. You can be more specific, or use any other WireArray methods of course.

https://processwire.com/api/ref/wire-array/

Edited by abdus
Added a simpler way
  • Like 2

Share this post


Link to post
Share on other sites

Thanks Abdus. I have a little different problem - I am looking for the specific page instance that has the field being edited. There are multiple pages based on the template that contains that field. I need to know which specific page instance is the "logical parent", not the set of pages that contain that field, i.e., are instances of the template that includes that PageTable field.

To try to make it more concrete:

PageA, PageB, and PageC all have the PageTable field Variations.

When in the Admin interface PageA is being edited and the user wants to add a variation then they click "Add New" under Variations.

At that point an iFrame overlay pops up to enter data for the new PageTable page in Variations.

When that PageTable page is saved I need to know that it is associated with PageA.

If the PageTable pages were in their default location (children of PageA) then I could just look at parent. But the PageTable pages are all kept in a single directory for grouping purposes.

Make sense?

Share this post


Link to post
Share on other sites

usually what i do in these cases is add a page field to the template of the pagetable page, and set that field to the page that it is being edited from. I used a save hook on the main page to look at the items in the page table and for any where that page field is not set, it assigns that field to the page being edited (so setting the page field on the pagetable item to PageA). that field is also hidden using CSS.

  • Like 4

Share this post


Link to post
Share on other sites

Another way perhaps:

When you look in the database at field_pagetablefieldname you will see 3 columns -

pages_id = the page on which the PageTable appears (this is what you need)

data = the id of the PageTable page

sort = sort order for the items to appear on the pages_id page

You could hook after the new PageTable entry is saved (ie Pages::saved), and do a $database call to select the pages_id that has the newly created page id in the data field.

 

Screenshot 2017-05-04 09.37.05.png

Share this post


Link to post
Share on other sites

@bmacnaughton, give the following hook a try (must be in /site/init.php or in init method of module). Seems to work well for both PageTable additions and edits of existing items.

$this->addHookBefore('InputfieldPageTableAjax::checkAjax', function($event) {
    $page_id = (int) $this->input->get('id');
    $item_id = (int) $this->input->get('InputfieldPageTableAdd');
    if($page_id) $page = $this->pages->get($page_id); // $page is the container page
    if($item_id) $item = $this->pages->get($item_id); // $item is the PageTable item
    // ...
});

 

  • Like 2

Share this post


Link to post
Share on other sites

Thank you @Robin S. I am going to give this a try - I solved this particular problem by forcing the new entries under the page they are contained by but that is a suboptimal solution. 

Share this post


Link to post
Share on other sites

You're all wrong and most only work with entries already added and saved to the pagetable. It doesn't work for when adding a new item, cause the new entry page isn't saved yet to the pagetable field... Only easy way is to store them as children, so you can check for the parent. But storing the entries in a different place there's no way to tell in the newly created entry what source page it is going to land in. 

I created a github issue 3! years ago https://github.com/ryancramerdesign/ProcessWire/issues/699 and never got a single response from Ryan...

The solution I came up with was to store the id in the session and transfer that over to the page edit of the entry, Since I had not autoname feature enabled there, there was a step in between where the entry page isn't even created yet. Kinda hacky but worked.

The other issue I got with PageTable also never got answered https://github.com/ryancramerdesign/ProcessWire/issues/700

  • Like 1

Share this post


Link to post
Share on other sites
7 hours ago, Soma said:

The solution I came up with was to store the id in the session and transfer that over to the page edit of the entry,

I tried the same thing - it was the last way I could think of. I'm not sure why it didn't work but will try again.

Share this post


Link to post
Share on other sites

yeah, to achieve what i was referring to above, i had a hook on the save of the main page, which iterated through all of the items in the pagetable where the field was blank, and set that value...

Has anyone come up with a reliable way to get the ID of the page that contains the page table field, either through hook, database query, or session vars? would be very helpful to know if this has been solved - maybe @Soma could you post an example of how to set the id of the page in the session; my issue with this is i have a page in a page table, which then has another page table in it, so the system is having trouble with any get var because it ends up being the root/bottom page, not the 2nd level up modal which is the page id i need...

Share this post


Link to post
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


  • Recently Browsing   0 members

    No registered users viewing this page.

  • Similar Content

    • By louisstephens
      I have been looking up everything I can to try to find what's going wrong with this. I have a very simple form (title and file field set to multiple) that will create a new page with the name and attachments. However, it appears that I am missing something crucial as only 1 item gets uploaded to the field. Here is my code:
      <?php $uploadpage = new Page(); $uploadpage->template = "dashboard"; $uploadpage->parent = $pages->get("/testing/"); $uploadpage->title = $sanitizer->text($input->post->new_title); $uploadpage->save(); $uploadpage->setOutputFormatting(false); $u = new WireUpload('test_upload'); $u->setMaxFiles(6); $u->setOverwrite(false); $u->setDestinationPath($uploadpage->test_upload->path()); $u->setValidExtensions(array('jpg', 'jpeg', 'gif', 'png', 'pdf')); foreach($u->execute() as $filename) { $uploadpage->test_upload->add($filename); } $uploadpage->save(); ?> I have the max files set to 6, and have a foreach loop to add the files, but it is only uploading one. Does anyone see where I might have gone astray?
    • By Pixrael
      Hi guys!
      What do you think about something like this? Because I use this option regularly in the Windows File Explorer breadcrumb and it's very useful. The drop-down menu can display only published/visible child pages. I've tried to find how to do it as a module, but I'm not a coder with enough skills for that ... or I don't know if I can use hooks to do that ...

    • By AAD Web Team
      Hi,
      I've put in a support request (as a followup on an existing one) for this but it's nearly 10pm Ryan's time, so I thought I'd ask on here just in case someone can help...
      Yesterday we purchased ProDrafts, but I couldn't get the key to validate. Every time I hit submit on the module settings screen the key would be removed from the field I entered it in, and then it would complain about the missing value. I put in a support request and Ryan responded last night. It turned out it was because we're behind a proxy/firewall. He gave me a fix to get around that issue - some code to go into admin.php. I put that code in and saved admin.php, but now I can't even get into our admin anymore!
      (Just to clarify, I took the code back out and saved admin.php but that made no difference. It's definitely not the new code causing the error.)
      The errors relate to a lack of permission on the ProDrafts module (see attached screenshot). We do have a key, but evidently the code Ryan gave me to add the key in via admin.php isn't taking effect before the error is thrown...?
      I tried removing the ProDrafts directory from the modules directory, but that hasn't helped.
      Is there a hook I can put in somewhere to tell it not to load ProDrafts at all, or not check the permissions? Or is there some way to manually uninstall it from the file system?
      Thanks!
      Margaret

    • By SwimToWin
      In my world, Super Users / Editors should only be able to work with Pages and administer users.
      Everything else is the domain of the web master. The purpose is to prevent technically inexperienced editors from destroying core elements of a site, such as fields and templates.
      That leaves me with the question, how to deny Super Users access to Setup, Modules and Roles / Permissions?
      PS: May I also suggest that it shall be possible to set Permission for each of the main menu items - including their sub-menu items.

    • By louisstephens
      So maybe has already figured this out, but I am stumped. I have a field (test_field) that is set to pdfs, and I was trying to get a count of the number of pdfs in that field so I could add it to a status bubble on the front end. I tried:
      function testPDF() { $a = $page->test_field->count(); echo "<span class=\"bubble\">" . $a . "</span>"; } but it is returning "NULL" . I currently have 3 added to the field. I also tried putting this function in _func.php, though I need to use wire('pages'), but I only need to get the count for that specific page, so I am sort of at a loss of how to proceed.