Jump to content

Raymond Geerts

Members
  • Posts

    362
  • Joined

  • Last visited

  • Days Won

    4

Posts posted by Raymond Geerts

  1. On 10/22/2020 at 6:00 PM, Marc said:

    Nice to see ProcessWire being used in the Netherlands. Too bad I live a two hour drive away from you guys (I'm from the south). Is working mostly from home an option? (I am a native Dutch speaker btw.)

    Hello Marc, I have sent you a reaction as private message. Working mostly from home is an option.

  2. On 10/16/2020 at 5:13 PM, JeevanisM said:

     

    Only for Dutch Speakers ? any Remote position  open ?

    Hello JeevanisM, Indeed for this position we are looking for people who have a good command of the Dutch and English language. Initially, this was in the original job offer, but we didn't consider there would be interest internationally. We have added the line about language now to the job offer.

  3. Agrio is a medium-sized publisher with more than 70 employees and offers a leading cross-media agricultural portfolio. In the more than 30 years that Agrio has existed, we have managed to gain the position of market leader, with the highest reach in the agricultural in the Netherlands. In addition, our customers know where to find us for various printing, web design, copywriting, video productions and graphic design.

    Agrio does all this with a lot of passion and a proactive attitude. Farmer sobriety predominates. Independence, job satisfaction and growth are important core values within the organization. There is always room for new talent.

    We currently have room for a PHP Developer in our Media and Design department.

    https://www.agrio.nl/vacatures/php-developer/

    • Like 7
  4. This is great news for our dev team. I can image it took some effort to dig into this but i am glad you found the bottle neck.

    I can imagine, when the parents table will contain less page parent references, this might give an overall performance boost with large sites that have a lot of repeater (matrix) pages.

    • Like 3
  5. After doing a fresh install of MySQL 5.7 on macOS High Sierra, the installer generates a temporary password for the root user. The problem is as soon the installer is finished, the given root password is already expired. Resulting in not being able to login as root to MySQL.

    It took me a while of reading, fiddling around, and trying all kinds of tips and examples on how to reset the root password.

    The following worked for me. And in the hope it an help somebody else, and for backup purposes, I'll leave it here.

    Open the following folder in a Terminal window:

    /usr/local/mysql/bin

    Type in (copy + paste) the following commands, where `xxxxxxxx` is the desired root password:

    ./mysql -u root -p --connect-expired-password
    
    SET PASSWORD FOR 'root'@'localhost' = PASSWORD('xxxxxxxx');
    
    UPDATE user SET authentication_string='xxxxxxxx' WHERE User='root'

    The last line with the UPDATE command was necessary for me to finish the process.

    • Like 1
    • Thanks 1
  6. No answer yet, just stumbled on this topic, since i was looking for this too.

    Is there any way to listen, observe in javascript to fire an action when the PageList loading / rendering is completed. In that i mean on init, but also when user pagination or alike.

  7. Still having some difficulties here when updating a repeater inside a repeater matrix.

    Somehow it is not possible to use the same code for adding a new page, and updating the same page with a repeater inside a repeater matrix, as shown in the below example.

    I do not seem to be able to update the page, and keep getting the following error message:

    Error: Exception: Can't save page 0: /1486742936-8959-4/: It has no parent assigned (in /Users/raymond/Dropbox/www_domains/testing123/htdocs/wire/core/PagesEditor.php line 464)

     

    The code to add a new page, and data to a repeater inside a repeater matrix.
     

    $urls = array(
      'https://www.youtube.com/watch?v=e5gvzCOhBLQ',
      'https://www.youtube.com/watch?v=rbhnkeh9liQ',
      'https://www.youtube.com/watch?v=poRFOvxyOWI'
    );
    
    /**
     * First run, adds new article page
     *
     */
    $options = array(
      'template' => 'article',
      'parent' => $parent = $pages->get('template=articles'),
      'title' => 'This is a test',
      'date_pub_start' => time()
    );
    
    $p = $pages->add(
      $options['template'],
      $options['parent'],
      $options
    );
    $p->of(false);
    
    // repeater_matrix_content - type: intro
    $intro = $p->repeater_matrix_content->getNew();
    $intro->repeater_matrix_type = 1; // intro
    $intro->intro = 'Lorem ipsum';
    $p->save('repeater_matrix_content');
    
    // repeater_matrix_content - type: text
    $text = $p->repeater_matrix_content->getNew();
    $text->repeater_matrix_type = 2; // text
    $text->body = 'Lorem ipsum dolor sit amet';
    $p->save('repeater_matrix_content');
    
    $videos = $p->repeater_matrix_content->getNew();
    $videos->repeater_matrix_type = 4; // videos
    $videos->save();
    foreach($urls as $url) {
      if (empty($url)) continue;
      $repeater_video = $videos->repeater_videos->getNew();
      $repeater_video->link_url = $url;
      $videos->save('repeater_videos');
    }
    $p->save('repeater_matrix_content');

     

    The code to update the just added page. (not working).
    Note that the code for adding the repeater matrix items are identical to the above code.

    The first two items of the type (1=intro, 2=text) are succesfully added and saved.
    The problem occurs when trying to add repeater items to the repeater matrix type 3=video.

    What am i doing wrong?
     

    $options = array(
      'template' => 'article',
      'parent' => $parent = $pages->get('template=articles'),
      'title' => 'This is a test',
      'date_pub_start' => time()
    );
    
    /**
     * Second run, updates existing article page
     *
     */
    $id = $p->id;
    
    unset($p);
    
    $p = $pages->get($id);
    $p->of(false);
    $p->title = $options['title'];
    $p->date_pub_start = time();
    $p->save();
    
    foreach($p->repeater_matrix_content as $rp) {
        $pages->delete($rp, true);
    }
    
    // repeater_matrix_content - type: intro
    $intro = $p->repeater_matrix_content->getNew();
    $intro->repeater_matrix_type = 1; // intro
    $intro->intro = 'Lorem ipsum';
    $p->save('repeater_matrix_content');
    
    // repeater_matrix_content - type: text
    $text = $p->repeater_matrix_content->getNew();
    $text->repeater_matrix_type = 2; // text
    $text->body = 'Lorem ipsum dolor sit amet';
    $p->save('repeater_matrix_content');
    
    $videos = $p->repeater_matrix_content->getNew();
    $videos->repeater_matrix_type = 4; // videos
    $videos->save();
    foreach($urls as $url) {
      if (empty($url)) continue;
      $repeater_video = $videos->repeater_videos->getNew();
      $repeater_video->link_url = $url;
      $videos->save('repeater_videos');
    }
    $p->save('repeater_matrix_content');

     

  8. Can any one point me in the right direction / or give a working example how to add repeater items to a repeater field inside a repeater matrix field.

    I tried many different approaches, reading many topics on the forum, but can not get it working.

    The following example gives an error about not being able to add page with ID 0

    $rpm = $page->repeater_matrix_content->getNew();
    $prm->repeater_matrix_type = 1;
    $prm->save();
    $prm->of(false);
    foreach($videos as $video) {
        if (empty($video['url'])) continue;
        $rp = $prm->repeater_videos->getNew();
        $rp->save();
        $rp->link_url = $video['url'];
        $rp->save();
        $prm->repeater_videos->add($rp);
    }
    $prm->save();
    $page->repeater_matrix_content->add($prm);

     

  9. Quote

    Maybe you can adapt this to work as you need it: 

    This example works by adding (prepending) an item to the list. What i'm looking for is a way to manipulate the `start` value and wonder if the following might do the trick.
     

    <?php
    
    $limit = 10;
    $limit_first = 8;
    $offset = $limit_first - $limit;
    
    if ($input->pageNum == 1){
        $products = $pages->find("template=product, sort=-date_pub, start=0, limit=$limit_first");
    }
    else {
        $start = (($input->pageNum - 1) * $limit) + $offset;
        $products = $pages->find("template=product, sort=-date_pub, start=$start, limit=$limit");
    }


     

    • Like 1
  10. I was wondering how to achieve the following.

    A total of 100 pages which are listed with a limit of 10 items per page, resulting in 10 pages of 10 items.

    Instead i desire the following (below), and wondering how to setup the code / selector(s).

    The first page should show a list of 8 items. After that all following pages should have a limit of 10 items.

    • page 1 -> items 1 - 8 -> (limit 8)
    • page 2 -> items 9 - 18 -> (limit 10)
    • page 3 -> items 19 - 28 -> (limit 10)
    • ...
    • page 9 -> items 79 - 88 -> (limit 10)
    • page 10 -> items 89 - 98 -> (limit 10)
    • page 11 -> items 98 - 100 -> (limit 10)

    The ideal situation would be to have an extra page selector property aside of 'limit', something named 'limit_first' or alike.

  11. Trekkerweb Supply & Demand

    https://markt.trekkerweb.nl/

    Trekkerweb.nl brings agricultural mechanization news and supply & demand together in a single online platform for all the tractor and machine enthusiasts and others interested in the mechanization sector.

    Tractors__agricultural_machinery_and_spare_parts_supply___demand___Trekkerweb.pngTractors  agricultural machinery and spare parts supply   demand   Trekkerweb(1).png

    The site is multi-language with English as default. None Dutch browsers will get the English version of the site, currently we are finetuning the German version which will be available somewhere in the near future.

    The search page in English and Dutch language

    - https://markt.trekkerweb.nl/search/
    - https://markt.trekkerweb.nl/nl/zoeken/


    Used modules

    • Profields Table
    • Profields Textareas
    • MarkupLoadRSS (fetches brand related new from the main website)
    • PageImageManipulator 2 (PIM2) (for placing watermark image)
    • ProCache
    • ProcessGetVideoThumbs
    • TextformatterVideoEmbed
    • WireMailSmtp
    • LanguageSupport (Site is multi language: Dutch, German and Default English)
    • Couple of custom made modules for user profiles and cross page linkage of the datamodel


    (Bower) components

    • awesome-bootstrap-checkbox
    • bootstrap-dropdowns-enhancement-sass
    • bootstrap-sass
    • bootstrap-select
    • font-awesome
    • formvalidation.io
    • hashids
    • jquery
    • jquery-file-upload
    • jquery-throttle-debounce
    • jquery.mmenu
    • js-cookie
    • lifestampjs
    • moment
    • semantic-ui-sass
    • verge


    Front-end user profiles (custom module)

    • Account registration
      • Customizable fields (in module settings)
      • Per field privacy configurable (private, public, on a per user basis).
    • Front-end login/ logout
    • Reset password
    • Email activation for account
    • Request activation mail
    • View profile
    • Public profile
    • Edit profile
    • Set profile picture (cover image and avatar)
    • Modify password
    • Language choice
    • Profile dashboard
    • Front-end Ads management
      • Create new ad
      • Edit existing ad
      • Manage media (images / video)
      • Preview and approve ad
      • Remove ad


    Data model

    • Categories
    • Subcategories
    • Brands
    • Input fields
    • Options

    An intuitive data model drives the whole site. A couple custom made modules take care of the cross page assigning of categories to subcategories and brands. Per subcategory we are able to assign the related input fields and options which will be rendered on the 'Create new ad/ Edit ad' form page and combined with the given values rendered on the ad detail page.

    Screen Shot 2016-09-06 at 13.45.30.png


    Database caching + Pro caching

    One of the challenges was to keep the whole project as low weight as possible. Since the data model with categories, subcategories, brands, inputfields and options is the backbone of the site we came up with the solution to have the names, titles, ids, and relations between them cached. Completely as json/javascript with pro cache and separated with database caching.

    With the Wire Fuel we made the $dm object available for accessing anywhere in PHP and globalJS.dm from within javascript. This means the whole data model is called only once per request, and while it exists in the database cache and pro-cache it is incredibly fast.


    Subcategory page

    The first image shown below represent one of the subcategories (Tractors) with assigned categories, brands, input fields and options. The image there after is a screenshot of the add ad page, where the input fields, options and brands are dynamicly rendered after being loaded via Ajax.

    Edit Page  Tractors • markt.trekkerweb.nl.png

    Add ad   Trekkerweb.png

    Other features

    • cookie based favourites
    • cookie based last-viewed list
    • advanced filter search
    • related ads

    Thanks to the whole team (Ferdi, Bastiaan, Alex, John, Hessel) and last but not least Ryan for creating ProcessWire and all module developers out there :)

    • Like 24
  12. I must admit i dont know that much about encryption myself, so I have used the following example with a little modification.

    http://stackoverflow.com/questions/16600708/how-do-you-encrypt-and-decrypt-a-php-string/16606352#16606352

    Do not use BLOWFISH and EBC (this it too predictable) as in the example, instead of that i'm using RIJNDAEL_128 (or 256 if you like) and CBC

    I also recommend to use a long encryption key, maybe something above 1024 characters, or even 2048 long

    function encrypt($pure_string, $encryption_key) {
        $iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC);
        $iv = mcrypt_create_iv($iv_size, MCRYPT_RAND);
        $encrypted_string = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $encryption_key, utf8_encode($pure_string), MCRYPT_MODE_CBC, $iv);
        return strtr(base64_encode($iv.$encrypted_string), '+/=', '-_.');
    }
    
    function decrypt($encrypted_string, $encryption_key) {
        $iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC);
        $encrypted_string_dec = base64_decode(strtr($encrypted_string, '-_.', '+/='));
        $iv_dec = substr($encrypted_string_dec, 0, $iv_size);
        $decrypted_string = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $encryption_key, substr($encrypted_string_dec, $iv_size), MCRYPT_MODE_CBC, $iv_dec);
        return trim(utf8_decode($decrypted_string));
    }
    

    update: The base64 encode/decode i threw in so that it should be possible to use the encrypted strings as url segments and so are able to use it together with procache

    • Like 3
  13. @LostKobrakai thanks for the tip. Martijn also mentioned this method.

    To be sure the temp file gets removed properly after a certain amount of time, i will use the WireTempDir class to create a tmp folder which will be removed automaticly after a X amount of time.

    Create the file (from base64) in there with fwrite and assign the file path of the tmp file to my image field.

    • Like 1
  14. I'm working on a XML RPC api to communicate between WoodWing Enterprise and a ProcessWire site.

    One of the method calls i'm building is pw.uploadPWFile which has to upload files, it does this by posting a XML RPC call to this method sending the following parameters as payload:

    • Page ID
    • Username
    • Password
    • Data
      • Filename
      • MIME Type
      • Bits (base64)

    I could not find any example on how to upload a file from base64 binary posted data, and how to assign this file to a field.

    Are there any examples available or can sombody point me in the right direction?

×
×
  • Create New...