Jump to content

How to hook a multi-language title field on page creation (Pages::setupNew)


masslevel
 Share

Recommended Posts

Hello!

I apologize in advance if I missed something on the forums. I'm not yet that experienced with hooks and already tried a lot. Maybe someone else has an idea or could give me a hint in the right direction.

  • In my ready.php file I'm creating a random generated URL slug on Pages::setupNew for a specific template.
  • When creating a page and I type in the default language title and leave the other languages blank, the slug gets appended to the page names because the pages have the same url/slug/title but in different trees ( ex. /myarticle-myslug/ and /en/myarticle-myslug/ )
  • When creating a page and I enter a title for each language, the slug gets only applied to the default language and I get an error that the name for the default language already exists and it was changed to /myarticle-myslug/. The other language gets the page name /en/my-article/ applied.
  • Additionally I noticed that the settings from Module -> Page Name (InputfieldPageName) are not applied when creating the page name using the code below. So non-ascii characters get stripped instead of sanitized

Here is a simplified code snippet that I have in the ready.php file:

wire()->addHookBefore('Pages::setupNew', function($event) {
    $page = $event->arguments('page');
    if ($page->template->name == 'news-article') {
        $page->name = $page->title . '-myslug';
    }
});

I've read this topic and if this still applies, LanguageSupportPageNames isn't used on Pages::setupNew.  Especially the post by @Soma looks interesting but I'm not sure how to apply it.

Thank you very much in advance.

Link to comment
Share on other sites

I was wondering if it would be better to change the name of the page after publishing ...

wire()->addHookBefore('Pages::publishReady', function($event) {
    $page = $event->arguments('page');
    if ($page->template->name == 'news-article') {
		$page->name = $page->title . '-myslug';
    }
});

 

  • Like 1
Link to comment
Share on other sites

5 hours ago, rafaoski said:

I was wondering if it would be better to change the name of the page after publishing ...


wire()->addHookBefore('Pages::publishReady', function($event) {
    $page = $event->arguments('page');
    if ($page->template->name == 'news-article') {
		$page->name = $page->title . '-myslug';
    }
});

 

Thanks for your reply and input, @rafaoski. That would be fine too, BUT I sadly encounter the following issues:

  • '-myslug' in my simplified example is actually a random hash generator. If I unpublish the page and republish it, another string is attached to the already existing one (ex. my-article-my-slug-my-slug after the second publish.
  • even when using the Pages::publishReady hook, the slug is only appended to the default language page name/url and not to other languages.
  • Like 1
Link to comment
Share on other sites

The following hook should do what you want. It's based on old @Soma's post. All you have to is to edit $myslug with your random hash generator.

$wire->addHookBefore("Pages::saveReady", function(HookEvent $event) {

  $page = $event->arguments[0];
  if ($page->template->name != 'news-article') return;

  foreach ($this->languages as $lang) {

    $lname = $lang->isDefault() ? '' : $lang->id;
    $default = $this->languages->get("default");
    $myslug = '-myslug';

    if ($page->title->getLanguageValue($lang)) {
      $page->set("name$lname", $page->title->getLanguageValue($lang) . $myslug);
    } else {
      $page->set("name$lname", $page->title->getLanguageValue($default) . $myslug);
    }
  }

});

 

  • Like 2
Link to comment
Share on other sites

23 hours ago, PWaddict said:

The following hook should do what you want. It's based on old @Soma's post. All you have to is to edit $myslug with your random hash generator.


$wire->addHookBefore("Pages::saveReady", function(HookEvent $event) {

  $page = $event->arguments[0];
  if ($page->template->name != 'news-article') return;

  foreach ($this->languages as $lang) {

    $lname = $lang->isDefault() ? '' : $lang->id;
    $default = $this->languages->get("default");
    $myslug = '-myslug';

    if ($page->title->getLanguageValue($lang)) {
      $page->set("name$lname", $page->title->getLanguageValue($lang) . $myslug);
    } else {
      $page->set("name$lname", $page->title->getLanguageValue($default) . $myslug);
    }
  }

});

 

Thanks so much, @PWaddict. Now the slug gets applied also to other languages. Awesome! Many steps closer. What is still happening is:

  • When I publish the page or save it, the page name/url gets a new slug everytime.
    How can I restrict this so that a new page name gets only generated once? When the URL should be changed afterwards, it should only be possible manually or for example when the page name field is cleared.

    The problem is when an editor decides to unpublish/publish or just does a simple resave of the page, it will have a new URL.
     
  • When I create a new article page in the Add New screen and press save, I get redirected to the page edit screen, which is correct but it shows an red error notice on top:
    Session: Warning, the name you selected "my-new-article" was already in use and has been changed to "my-new-article-myslughash". 


Your snippet is very close. Thank you for that.

I will try to make some changes to it - not really sure how exactly 😉 but trial and error I guess. Maybe changing Pages::saveReady to something different so the page->name gets only generated once? Don't know yet what to do about the warning.

Link to comment
Share on other sites

2 hours ago, masslevel said:

Maybe changing Pages::saveReady to something different so the page->name gets only generated once?

Try hooking after Pages::added, but you'll need to add a line to save $page within your hook when hooking that method.

 

2 hours ago, masslevel said:

When I create a new article page in the Add New screen and press save, I get redirected to the page edit screen, which is correct but it shows an red error notice on top:
Session: Warning, the name you selected "my-new-article" was already in use and has been changed to "my-new-article-myslughash". 

There's an open issue about that problem: https://github.com/processwire/processwire-issues/issues/648

  • Like 4
Link to comment
Share on other sites

On 7/27/2018 at 5:22 AM, Robin S said:

Try hooking after Pages::added, but you'll need to add a line to save $page within your hook when hooking that method.

 

There's an open issue about that problem: https://github.com/processwire/processwire-issues/issues/648

Thanks for the suggestion, @Robin S. I will take a look and see what I can figure out.

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.
  • Similar Content

    • By nuel
      Hi
      I'm working with PW for some time now, but – please don't laugh – never used hooks.
      I have 200 – 300 subpages with the template 'artist', the title of each page represents the full name, sometimes John Doe, sometimes John Emmet Brown Doe. I want to auto-populate the field 'artist_last_name' with the word that is most likely the last name, the last word of the page title. If there are more names, it can be changed manually. I need this for easier and quicker alphabetical sorting.
      What I put together is this, in ready.php. Doesn't work. Again, I'm new to hooks..
      <?php     $wire->addHookBefore('Pages::saved', function(HookEvent $event) {     $p = $event->arguments('page');     if($p->template != 'artist') return;     if($p->artist_last_name) return;     $ln = end(explode(' ', $p->title));     $p->set('artist_last_name',$ln);     }); ?> In the best case this would be done once globally without having to open and save every page. But new pages should populate the field on page save.
      Thanks for your help, I think it's easy, I just need a push..
      Nuél
    • By picarica
      So hello i am trying to get a .png file from file field and put it automatically to image field, why png image is in the file field is because i already have a hook that extracts .zip and uploads all content into file field, but i just realizes i cant use size() function on image in file field so i am tryin got reupload it to images field
      i already have something like  this in ready.php
      $word = ".png"; foreach($page->subor_hry as $file) { if(strpos($file, $word) !== false){ $page->images_thumb = $file->url; } } by my logic it should work but it dosnt i get error ProcessPageEdit: Unable to read: /site-hry/assets/files/1027/flash_fishy_screenshot.png
      when i remove url from $file->url i just get ProcessPageEdit: Item added to ProcessWire\Pageimages is not an allowed type
      so what am i doing wrong? is there some other way to do this ?
      also can i have all this in
      $this->addHookAfter('Pages::saveReady', function(HookEvent $event) { whats the correct function to have it apply on all pages ?
    • By rooofl
      Hi! I am trying to create a hook that takes the value of a form file field, and add it to an image gallery of an existing page.
      $forms->addHookBefore('FormBuilderProcessor::processInputDone', function($e) { $form = $e->arguments(0); if($form->name == 'new-inuse') { // related_font is a page selector $font = $form->getChildByName('related_font'); // getting the page name $fontName = $font->attr('value')->name; // finds the page from its name $fontPage = wire('pages')->find("name=$fontName"); // in_use_image is a file upload field $image = $form->getChildByName('in_use_image'); // trying to add the image to the existing image gallery in_use field $fontPage->in_use->add('$image'); // error here $fontPage->save(); } }); This outputs the following error: `Call to a member function add() on null`. Any idea what’s wrong with my code?
    • By picarica
      so what i am trying to do is that i uploded some files into file field, and then i want hook to get MD5sum and other stuff from .xml and put it into text field into it coresponding pages, pages like this are gonna be many, for each one i want it to output it into its fields
    • By Paul Greinke
      Hi there. I wrote a custom module for one of my projects. In fact I maybe want to use my module in other projects too. In order to be variable and customizable  I need to implement some custom hooks into my module. So I can afterwards hook into the my functions in order to modify them to match the needs of the new project.
      I tried simply defining functions with the '__' prefix. But that did not work. I'm imagining something like the following:
      <?php class MyClass { public function ___someFunction() { // Do something } } // ready.php $this->addHookBefore('MyClass::someFunction', function($event) { // some customization }); Is there a way to accomplish that? 
×
×
  • Create New...