Jump to content

Recommended Posts

Hello,

i would like to give registered users the possibility to download PDF files.
What is the best way to make the user template show which PDFs the user has downloaded?
Is this possible?

THX

Share this post


Link to post
Share on other sites

There are multiple ways to do this. The "standard" approach I'd say would be event tracking using a JavaScript tracker. If you're already using some tracking system like Google Analytics or Matomo, you can do that by attaching an event listener to the download link / button and triggering an event (guides for Google Analytics and Matomo).

Of course, in this case the events will end up in your analytics software, not in the user page on your site (though if you are using some tracking software already this may be preferable). You can also roll your own version of this, by sending your JavaScript-triggered events to a custom API endpoint on your site that records the download for the current user (you can use the active session for this, or send the user ID alongside the event).

Another approach which completely avoids JavaScript is to not link to your downloads directly, but instead link to yet another custom endpoint which will (1) log the request and (2) serve the download manually. I have written a bit about manually serving downloads here and here.

  • Like 3

Share this post


Link to post
Share on other sites

Hi Moritz,

thank you very much! There are some interesting approaches.
For another request i can certainly use some of it. but unfortunately
i can't realize my intention with it.

 

THX

Share this post


Link to post
Share on other sites
1 hour ago, entschleunigung said:

but unfortunately
i can't realize my intention with it.

Why not?

Once you have the user-ID and the document he/she wants to download, you can write this into fields of your (user) page(s).

If you want to show a user his/her history, simply prepare and render the stored data from the user page.

  • Like 2

Share this post


Link to post
Share on other sites

Here's an example of a basic module to store each download as a row on a separate table. I hope it can be useful somehow 🙂

Spoiler

<?php namespace ProcessWire;

class ExternalDownloadCounter extends WireData implements Module
{

    public static function getModuleInfo()
    {
        return array(
            'title' => __('External Download Counter'),
            'summary' => __('Adds external file download count mechanism.'),
            'singular' => true,
            'autoload' => false
        );
    }


    /**
     * Table created by this module
     *
     */
    const dbTableName = 'ext_download_count';

    public function countDownload($page_name, $resource_file, $selected_language)
    {

        $table = self::dbTableName;

        $sql = "INSERT INTO $table SET path=:path, file=:file, file_language=:file_language, downloaded=NOW()";

        $query = $this->database->prepare($sql);
        $query->bindValue(":path", $page_name);
        $query->bindValue(":file", $resource_file);
        $query->bindValue(":file_language", $selected_language);

        try {
            $query->execute();

            wire('log')->save("download-counter", "New resource downloaded: /resources/".$page_name);

        } catch(\Exception $e) {
            // intentionally blank
        }
        
    }

    public function ___install()
    {


        $len = $this->wire('database')->getMaxIndexLength();
        $table = self::dbTableName;

        $this->database->exec("CREATE TABLE IF NOT EXISTS `$table` (
          `id` int(11) NOT NULL AUTO_INCREMENT,
          `path` varchar($len) NOT NULL,
          `file` varchar($len) NOT NULL,
          `file_language` varchar(50) NULL,
          `downloaded` TIMESTAMP NOT NULL,
          PRIMARY KEY (`id`),
          INDEX `path` (`path`)
        ) ENGINE=InnoDB DEFAULT CHARSET=utf8 ;");

        wire('log')->save("download-counter", "Module installed");


    }

    /**
     * Uninstall
     *
     */
    public function ___uninstall()
    {
        $db = $this->wire('database');
        $table = self::dbTableName;
        $new_table = $table.'_'.date("Y_m_d");

        // $this->database->query("DROP TABLE " . self::dbTableName);
        $this->database->exec("RENAME TABLE `$table` TO `$new_table`");
    }

}

 

 

And here's how to call it from your template, form hook etc.:

$download_counter = wire('modules')->get("ExternalDownloadCounter");
$download_counter->countDownload($page_name, $resource_file, $selected_language);

 

  • Like 4

Share this post


Link to post
Share on other sites
16 hours ago, horst said:

Why not?

I'm sorry, maybe I expressed myself a bit unlucky, because what moritz wrote is certainly good and right.  it's rather due to my own failings 🙂
i'm trying to solve it now by adding the filename of the pdf file to a repeater field in the user template using jquery and ajax.

THX

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.

×
×
  • Create New...