Javascript deleting $_POST data - form results will not render

Okay, I will try to explain this as simply as possible. I have a form that collects data and then has a large amount of logic applied to it. The resulting information needs to be output back to the user so they can copy/paste, download, etc. This is not a problem and works fine…

However, this information is a paid product, so I am using Snipcart and a ‘Buy Now’ button to allow the user to process their card in hopes of delivering the output for them afterwards (same as above, only with an extra step for the order).

The problem occurs when binding the event for Snipcart’s order.complete to a redirect in javascript/jquery. As soon as the event fires, the $POST data is lost and my results will not render. I have tried a number of different ways to get this to work, but end up with the results, minus the data or nothing at all depending on my methodology.

Anyone know how I can store the information from $POST and re-render the form results (which is basically a modified ‘forms/data.html.twig’ template) AFTER the sale completes?

Can you use session storage? I see Grav supports it, but I don’t see much in the documentation. I’ve dealt with this same problem when dealing with OAuth (not in Grav, but other systems I’ve created) where you have to redirect via GET but somehow not lose POSTed data. I’ve always just relied on sessions.

Just looking at the source code. I’d try accessing $this->grav['session'] and look at this API documentation and see what you can do.

Looks like I need to do some research as I am reminded how new I am to php every time I attempt to do something with a plugin in Grav.

Thank you for the reply and pointing me in the right direction though!

I’m no PHP native myself. If you look in the plugins forum, you will see me bashing my head against a wall time and time again :slight_smile: PHP is far from an elegant language, to be diplomatic about it.

Getting $POST into a session variable was actually really easy, now I just need to assign that back to $POST so that the form results render. I’m not sure where to start on this…

PHP is beauty, PHP is elegance, PHP is all. From your description, @aeskew, it sounds like a couple of approaches might work:

  1. Take Input, perform calculations, store an identifier through SnipCart, show output on return.
  2. Take payment, store an identifier through SnipCart, take input, perform calculations, show output.

That is, the second method does not require storage of data prior to purchase, but rather allows access to it (and storage with this identifier) after purchase. I am not familiar with SnipCart as I’ve not used it, but am intimately familiar with the process through PHP.

Basically, my assumption is that SnipCart yields an identifier of the purchase, and a verification of this identifier on subsequent redirect. Thus:

  1. Store identifier in Grav’s data-storage (any machine-readable format through/with PHP in the data-folder).
  2. When customer is redirected to some page, verify identifier against purchase.
  3. If verified, perform calculations (through PHP, JS, or what-have-you).
  4. Store calculations (through PHP, same as above).
  5. Show output to v erified customer, which could also be retrievable later by the URL with the identifier they were returned to the page by.

I got this working for anyone else trying to achieve something similar. Here are the steps that worked for me:

  1. Create a plugin with the onTwigSiteVariables event registered
  2. Create a twig accessible variable for $_SESSION:
    public function onTwigSiteVariables()
    {
        if (!$this->active) {
            return;
        }
        if (isset($_SESSION['data'])) {
        $this->grav['twig']->twig_vars['session'] = $_SESSION['data'];
        } else {
            $_SESSION['data'] = '';
        }
    }
  1. Add the custom form process that sets $_POST to $_SESSION:
    public function onFormProcessed(Event $event)
    {
        $form = $event['form'];
        $action = $event['action'];
        $params = $event['params'];
        
        switch ($action) {
        case 'snipcart':
            $_SESSION['data'] = $_POST;

        }
    }
  1. In my forms/data.html.twig template I replaced all of my field.value.form_field entries with session.form_field
  2. Add - snipcart to my form.md process (I will add some params here later)
  3. Add - redirect: '/reportdata' to my form.md process section which takes me to my order page with the Snipcart Product button

Now the only thing left to do is add a hidden field to the form data with the Snipcart Order ID and match this up once the transaction completes successfully in order to show the results.

Glad you got it figured out. At some point you’ll want to store purchase information to allow users to re-retrieve already purchased information and other functions. Grav can handle flat YAML files as persistent storage in the user/data folders. See the Comments plugin for an example.

I’m guessing some implementation of find and the order id or form-nonce while iterating through those files and matching to grav.user would work. I am planning to use my new session variable and/or the data folder to allow multiple purchases in one session.

Eventually, as things develop, I will probably store this info in a DB. But I really love flat file…just suits my brain better, so I will avoid if I can!

Thanks again for pointing out the session variable and the great advice!