Jump to content
psy

PushAlert notifications for ProcessWire

Recommended Posts

This module enables you to send push notifications and receive information about sent notifications on your HTTPS ProcessWire website.

It enables you to:

  1. Create a field of type FieldtypePushAlert that you can add to a page template. This is a multi-input field widget that enables you to send notifications from your page in the admin Page Edit and monitor statistics - Attempted, Delivered, Clicked, etc
  2. Send notifications from a page template directly using the API, eg to PW users who have a specific role and have subscribed to notifications
  3. Capture subscriptions on your website front end

All kudos to the great support team at PushAlert and to all the ProcessWire developers who've helped me with this project.

Download from the Modules directory at: https://modules.processwire.com/modules/push-alert/

or from GitHub at: https://github.com/clipmagic/PushAlert

Full instructions for use are in the module README.md file.

Enjoy!

  • Like 15

Share this post


Link to post
Share on other sites

Great stuff!

Do you know if Pushalert only accepts the root of a site/domain? I have a test-site installed @ dev.domain.com/project-name/

When I enter the above URL, Pushalert just saves dev.domain.com/

That's probably why I don't see anything in the bottom right corner in my frontend:

Quote

Go to the front end and confirm you see a bell icon in the bottom right corner. This default icon and can be changed in your PushAlert Dashboard.

Edit: actually, it works - but only after I copy and pasted the JS myself in the HTML HEAD (module didn't insert anything).

Share this post


Link to post
Share on other sites

Sorry, I already have another question: Once I subscribe, I see the bell icon on every subsequent page. Is that intended? I would expect to see this icon just once. Wouldn't you expect to not see it again after you either click "yes, subscribe" or "no thanks"?

When I publish my page, I get the following error: 

Session: SQLSTATE[HY093]: Invalid parameter number: mixed named and positional parameters


Something weird is happening when I want to set "Schedule send time":
The field always stays @ 2019-02-21 15:02:00, although I set it to 2019-02-21 15:55:00
(no matter if I set it via Date/Timepicker, or manually). It jumps back to this time after saving.

Are any timezones hard-coded? The time is a couple of minutes in the future. If I set it to sometime in the next hour, the time saves correctly. o_O

When I click on the notification (which appeared twice, by the way, stacked on top of each other), I get redirected to mysite.com/pw-backend/page/edit - and of course I see the login-screen there. I don't get redirected to my page with template pushalert. 

Edited by dragan
added some more questions

Share this post


Link to post
Share on other sites

Hi @dragan

Thanks for the feedback.

I believe PushAlert only accepts the root domain. I will ask PushAlert support for clarification.

The icon is always visible. After you've subscribed, it changes to an unsubscribe button.

5 hours ago, dragan said:

Session: SQLSTATE[HY093]: Invalid parameter number: mixed named and positional parameters

Not sure but may be related to the date issue?

No timezones are hardcoded. It is a standard PW Date Time picker inputfield. It gets converted to a timestamp for submission to PushAlert and saved in the field json data. It gets reconverted to a string when the page edit is redisplayed by the date field.

The URL submitted to PushAlert should be the frontend URL (always has been in my testing?), called in the code with $page->httpUrl. 

Are you using ProCache and stripping optional tags? The script needs the closing </head> tag. I'll work on an alternative way to manually call the script in the template. When you use only the PushAlert code, you miss the custom onSuccess callback function. This function posts back to PW to save the subscriber ID and logged-in user ID in the database.

            <script>
                function callbackOnSuccess(result) {                    
                    let topw = {};
                    topw.subscriber_id = result.subscriber_id;
                    topw.alreadySubscribed = result.alreadySubscribed;            
                    var json = JSON.stringify(topw);
                    return fetch("https://mywebsite.com/pushalert-endpoint/", {
                        method: "POST",
                        headers: {
                            "Content-Type": "application/json",
                        },
                        body: json
                    });
                }
                </script>

The only time, very early on in the development cycle, I got double notifications was when I had both sw.js and the PWABuilder service worker installed and they clashed horribly. The existing service worker called the page as did PW for faster load times and so the notification went twice.

Are you using multi-language? Maybe that's having an effect?

Share this post


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

Something weird is happening when I want to set "Schedule send time"

Good pick up @dragan Fixed.

Had H:m:s instead of H:i:s in line 135 of InputfieldPushAlert.module.php

Share this post


Link to post
Share on other sites
9 hours ago, dragan said:

I get redirected to mysite.com/pw-backend/page/edit

Oh dear, this wasn't happening before but have been able to reproduce the issue.

Will let you know when the fix is available

FIXED and updated in gitHub:

In PushAlert.module, change lines 160 and 161 to:

        $paUrl       = $widget->pa_message_url;
        if (empty($paUrl) || stripos($paUrl, '/page/edit/') !== false) {
            $paUrl= substr($this->wire('config')->urls->httpRoot, 0, -1) . $page->path;
        }

 

Edited by psy
Solved problem

Share this post


Link to post
Share on other sites
17 hours ago, dragan said:

Do you know if Pushalert only accepts the root of a site/domain? I have a test-site installed @ dev.domain.com/project-name/

When I enter the above URL, Pushalert just saves dev.domain.com/

@dragan spoke with Alex @ PushAlert and the short answer is it has to be in the root. Long answer is that there is alternate, unpublished code that allows integration in sub-directories. Alex will send me the code to review. Will keep you posted 

 

Update

Using PushAlert from PW site installed in a subdirectory is not difficult. It will require an additional field on the module config page and is on the roadmap for the next release.

  • Like 1

Share this post


Link to post
Share on other sites

@psy very excited to see this, thank you!

I had a few problems, on install:

/processwire/setup/field/edit?id=146 SQLSTATE[42S02]: Base table or view not found: 1146 Table mydominaname_processwire.field_PushAlert' doesn't exist (in /site/modules/PushAlert/PushAlert.module line 347)
 

and on trying to uninstall:

/processwire/module/edit?name=PushAlert&collap…

Method WireFileTools::unlink does not exist or is not callable in this context (in /wire/core/Wire.php line 519)

I couldn't get any notification sent on publishing a page with a FieldtypePushAlert field on it, but alerts work from the PushAlert website.

Has anyone else tried & had any issues/got any pointers? I've checked modsecurity on the server & no errors & am running php 5.6.40.

Thanks

Nick.

 

Share this post


Link to post
Share on other sites

@dab

Thanks for the feedback. I'll investigate.

I spent more time on the install/uninstall process than the actual integration but that's development for you. I tested on PW 3.0.74+ and PHP 7.0. Not sure if the fact you're using PHP 5.6.40 is the cause.

From your post it seems that the database table field_PushAlert was not found. Is your field name PushAlert? Maybe there is a problem with capital letters for field names in the DB?

Your second issue is a puzzle too. The only place in the module where unlink is used is in __uninstall to remove the push_alert_endpoint.php template. Was this created?

Share this post


Link to post
Share on other sites
6 hours ago, psy said:

@dab

Thanks for the feedback. I'll investigate.

I spent more time on the install/uninstall process than the actual integration but that's development for you. I tested on PW 3.0.74+ and PHP 7.0. Not sure if the fact you're using PHP 5.6.40 is the cause.

From your post it seems that the database table field_PushAlert was not found. Is your field name PushAlert? Maybe there is a problem with capital letters for field names in the DB?

Your second issue is a puzzle too. The only place in the module where unlink is used is in __uninstall to remove the push_alert_endpoint.php template. Was this created?

@psy, thanks for getting back.

>field_PushAlert was not found

ah yes, resolved when i used lowercase for the Pushalert field name on a later try (hope I didn't miss this instruction - sorry).

>push_alert_endpoint.php template. Was this created?

Yes,  that was created OK.

I'm thinking the lack of alerts might be PHP version related. I'll await any feedback from other users.

Once again, huge thanks for all the work on the module - it's absolutely fab 🙂.

Share this post


Link to post
Share on other sites

@dab Thank you ☺️

The field creation bit is pure PW, not PushAlert related at all so not sure why this occurred but good to know about uppercase/lowercase in field names.

The deletion of the pushalert_endpoint.php template is also pure PW/PHP as per the docs: https://processwire.com/api/ref/wire-file-tools/unlink/

        // Delete the endpoint template file - should never be customised
        $templatePath = $this->wire('config')->paths->templates . "pushalert_endpoint.php";
        if (is_file($templatePath))
            $this->wire('files')->unlink($templatePath);

Could it be a permissions error?

 

Share this post


Link to post
Share on other sites

Thanks @psy, all template files are 644 - not run in to permissions problems before. Not to worry re this one. With thanks.

  • Like 1

Share this post


Link to post
Share on other sites

Just testing it, look great 😉

 

I suggest a more verbose message when there is an error. I got the following message "There was a problem sending the notification" and I needed to put a bd($resultObj); on line 200 to know which error was triggered. In my case, was :

msgerror.png.fa7f8f83f7f6b6d14273f01f02c4ba7a.png

 

I also got a notice for an undefined variable when there are error with $resultObj , the variable should be affected to false just before the if($resultObj->success) condition to avoid this notice :

dbupdaterror.png.cecc4701e013421da3b129529564b97c.png

 

 

Thanks again for this useful module !

  • Like 1

Share this post


Link to post
Share on other sites

@flydev Great feedback and excellent suggestion. On the list for the next release 🙂 

  • Thanks 1

Share this post


Link to post
Share on other sites

On ProcessWire 3.0.124, I can't get it working. There is a weird issue with headers. The module keep saying that the API Key is invalid, I then tried with cURL on a terminal and it worked as expected. 

So I put a Tracy call to the core WireHttp to dump the headers set in the object :

https://github.com/processwire/processwire/blob/dev/wire/core/WireHttp.php#L576-L578

[...]
	bd($key .' => '. $value);
[...]

and as a result, we can see a string ( "0 : " ) before the Authorization header :

The header is treated as an array, see the index '0' ($key dumped here) :

headererror.png.a46b86193a768462e2b6ade43885d383.png

 

It's strange and its explain why my PulsewayPush module stopped working suddenly since some weeks after an upgrade. 

 

I just upgraded the system to ProcessWire 3.0.127, same things happen..

Share this post


Link to post
Share on other sites
Posted (edited)

@flydev Thanks again for the detailed feedback. My development site runs PW 3.0.124 so I don't understand why the behaviour would be different? C'est la vie.

In version 3.0.124, Ryan introduced support for cURL in WireHttp https://processwire.com/blog/posts/pw-3.0.124-and-new-site/#wirehttp-updated-with-curl-support

In the PushAlert.module I tried to take advantage of this new feature, from Line 439:

        // Prepare and send the request
        $slug = "send";

        if($this->wire('config')->version('3.0.124')) {
            // ProcessWire version is 3.0.124 or newer
            $result = $this->_sendHttp($slug, $options);
        } else {
            $result = $this->_sendCurl($slug, $options);
        }
        return $result;
    }

    /**
     * @param $slug
     * @param $options
     * @return mixed
     */
    private function _sendHttp ($slug, $options) {
        $http = new WireHttp();
        $headers = Array();
        $headers[] = "Authorization: api_key=". $this->api_key;
        $http->setHeaders( $headers);
        $result = $http->send($this->api_url . $slug, $options);
        return $result;

    }

    /**
     * @param $slug
     * @param $options
     * @return bool|string
     */
    private function _sendCurl ($slug, $options) {
        $headers = Array();
        $headers[] = "Authorization: api_key=" . $this->api_key;

        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $this->api_url . $slug);
        curl_setopt($ch, CURLOPT_POST, true);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($options));
        curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
        $result = curl_exec($ch);
        return $result;
    }

 

Because I cannot recreate the issue, would you please try commenting out lines 458, 459 & 460 and replacing them with:

//        $headers = Array();
//        $headers[] = "Authorization: api_key=". $this->api_key;
//        $http->setHeaders( $headers);

        $http->setHeader("Authorization: api_key=". $this->api_key);

and let me know if this resolves the issue.

More:  I used Array() in WireHttp to keep it consistent with the cURL method. Happy to change in the module _sendHttp method if WireHttp headers array works differently. Still wondering why it worked on my PW 3.0.124 and not for you...

Edited by psy
more info
  • Like 1

Share this post


Link to post
Share on other sites
11 hours ago, psy said:

//        $headers = Array();
//        $headers[] = "Authorization: api_key=". $this->api_key;
//        $http->setHeaders( $headers);

        $http->setHeader("Authorization: api_key=". $this->api_key);

 

It works like that, just FYI this function take 2 arguments so it need to be called :  $http->setHeader("Authorization", api_key=". $this->api_key);

After that, the API key is reconized. So I tested the module with the field in the template and trought the API, worked like a charm 👌

 

11 hours ago, psy said:

Still wondering why it worked on my PW 3.0.124 and not for you...

...

  • Thanks 1

Share this post


Link to post
Share on other sites
Posted (edited)

@flydev grateful for your patience with me on resolving this issue. Fixed in gitHub

Working code is:

$http->setHeader("Authorization", "api_key=". $this->api_key);

Also updated the _getHttp function with same fix in gitHub

Edited by psy
  • Like 2

Share this post


Link to post
Share on other sites

@psy, many thanks, with the latest update, I can see alerts are now being sent from Processwire to pushalert.co!  Thank you 🙂🙂.

My next step is to find out why push deliveries back to the subscribers are shown as "attempted" & not yet "delivered".

Share this post


Link to post
Share on other sites

@dab Great it's now working for you. All credit to flydev for the fix 🙂

The reporting of "Attempted" rather than "Delivered" is a question for PushAlert support. Once PW sends the notification, it hands over to PushAlert and then catches the response to report the status. 

Share this post


Link to post
Share on other sites

@psy, all resolved.  Now working beautifully thank you @psy!

Make sure, if you recreate your website entry on the PushAlert site you download a FRESH copy of the manifest.json & sw.js (oh dear, I thought I had!).

The PushAlert support team were super fast & very friendly if you run in to any problems. Thank you PushAlert.

  • Like 1

Share this post


Link to post
Share on other sites

@dab, yes, the PushAlert support team are almost as helpful as the PW devs here 😉

DON'T use the PushAlert sw.js file. It's the vanilla version and doesn't include the PW custom code to save subscriber ID's with PW user ID's. The module will automatically add sw.js + the custom function to the <head> for you. See my post to @dragan about this above.

Also see the IMPORTANT section of the README about manifest.json. If you're site already has one, just add the gcm_sender_id code line.

 

Share this post


Link to post
Share on other sites

@psy, thanks....so sorry...... PushAlert said I had to download the .js files. Apologies for not following the README properly - thanks for being so patient!

  • Like 1

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.


  • Recently Browsing   0 members

    No registered users viewing this page.

  • Similar Content

    • By psy
      Background
      I'm creating a module to integrate https://pushalert.co/ into ProcessWire. You actually don't even need a module. You could just use the "Other Websites" javascript provided by PushAlert for basic functionality, ie send a broadcast notification to all subscribers. This is essentially what all the other integrations, including WordPress, do. The WP integration installs a widget with a form enabling the admin to enter details such as title, message, etc from a blog post. It does not:
      collect any statistics within the CMS about the notification enable audience fine tuning to eg a particular subscriber or subscriber segment within WP. The admin needs to use the PA dashboard for that functionality PushAlert has a javascript and REST API. It's intended that this module will use both. https://pushalert.co/documentation 
      What my module does so far:
      associate a subscription with a user. FE user clicks a button on the website front end to subscribe and/or agrees to the browser popup to accept notifications from this site send broadcast push alerts from a page within admin It doesn't have a 'widget' but easy enough to create a fieldsetpage with the relevant fields and add that fs page to any appropriate templates, then with a hook, send the notification. Need to be careful that once published/sent, the notification is not automatically re-sent on subsequent page edits.
      Looking for help/collaboration on how best:
      to send a notification, eg from a blog post, then track the statistics. Dilemma is that the push notification must come from the admin page. Responses go to the sending page which, as it's an admin page, is restricted and will not accept the https response. This is where the other CMS integrations stop. The only json response from PushAlert is the status, eg 'success', and the notification id. There is no opportunity at this point to capture the sending page id. handle, 'once sent on page publish', do not automatically resend on future page edits Am thinking along the lines that FS Page will have a @kongondo runtime markup field https://modules.processwire.com/modules/fieldtype-runtime-markup/ to pull the stats from PushAlert. Every time an admin visits the page, the stats will update.
      Once an admin checks the 'Send notification on page publish' checkbox, a hook creates new front end page that records the 'sender page', sends the notification request to PA, which then uses that newly created frontend page, as the response endpoint. Another rook re-associates the front end page with the admin page (eg blog post), to update the stats.
      Potential use cases:
      Notify individual and/or users with a particular role of an event, eg "New work opportunity" for job seekers; new blog post published; entries now open, etc...
      Looking for help/ideas/collaboration on this module. Please let me know if you're interested and as I do, believe this would be a great addition to ProcessWire
       
       
       
       
       
       
       
       
    • By flydev
      PulsewayPush
      Send "push" from ProcessWire to Pulseway.
       
      Description
      PulsewayPush simply send a push to a Pulseway instance. If you are using this module, you probably installed Pulseway on your mobile device: you will receive notification on your mobile.
      To get more information about Pulseway, please visit their website.
      Note
      They have a free plan which include 10 notifications (push) each day.
       
      Usage
      Install the PulsewayPush module.
      Then call the module where you like in your module/template code :
      <?php $modules->get("PulsewayPush")->push("The title", "The notification message.", "elevated"); ?>  
      Hookable function
      ___push() ___notify() (the two function do the same thing)
       
      Download
      Github:  https://github.com/flydev-fr/PulsewayPush Modules Directory: https://modules.processwire.com/modules/pulseway-push/  
      Examples of use case
      I needed for our work a system which send notification to mobile device in case of a client request immediate support. Pulseway was choosen because it is already used to monitor our infrastructure.
      An idea, you could use the free plan to monitor your blog or website regarding the number of failed logins attempts (hooking Login/Register?), the automated tool then block the attacker's IP with firewall rules and send you a notification.
       

       
      - - -
      2017-11-22: added the module to the modules directory
       
    • By burning
      Hi all,
      Im currently building a photo sharing website and have a first version finished. Next step is to incorporate notifications in the website if a user likes one of your photo's, or comments on a photo you posted.
      Just like the notification bell at the top of the forums. Any idea how to approach this functionality?
      Thanks in advance.
    • By Harmen
      Hi folks,
       
      On the website I am working on I do have a form which needs to be filled in (duh) and when the user clicks on download, the data is send with ajax and processed in the same file by using the ProcessWire API with $config->ajax;
      The data which is provided by the user will be checked with data in my database. If the data is correct I want to push a file download. But this is not working at the moment. It seems like the content of the (.exe) file is pasted in the console instead of pushing the file. My code looks like this:
      if ($config->ajax){ $serial = $input->post('serial'); $DB = DB(); $query = $DB->prepare("/*My query here*/"); $query->bindParam("comparision", $serial, PDO::PARAM_STR); $query->execute(); $reply = ''; $SN_rows = $query->rowCount(); if (!$SN_rows > 0) { $reply = 'error'; } else { $reply = 'success'; $installer = $page->attachments->eq(1); $filename = "Filename"; $filepath = $installer->filename; $options = array( 'forceDownload' => true, 'exit' => true, 'downloadFilename' => $filename ); wireSendFile($filepath, $options); } echo $reply; exit(); } What am I doing wrong here or is it a bug? Is there another way to do this with the processwire API?
       
      Thanks in advance,
       
      ~Harmen
×
×
  • Create New...