checking authentication before download the file


#1

Is there any way to check user authentication before downloading the file?
for example, I want that only specific users would be able to download mp3 files from direct link (but others can not download it, even though they have a direct link)


#2

For my knowledge, the assets and uploads storage is public accessible… but maybe you can:

  • forbid direct access via webserver (you may need to handle the proper paths, file type etc) and create a rest endpoint that will retrieve file for you based on the user
  • create a concept of private storage where you store your files (e.g. #storage:private => cockpit_folder/storage/private that is by default protected by webserver) and provide additional logic to save your mp3 files to that storage

#3

you can try a custom api entry point in combination with a webtoken. eg create the file config/api/public/download.php

with the content (not tested, just to give an idea):

<?php

$token = $this->param('token');

if (!$token) {
    $this->stop('Parameter token is missing', 412);
}

try {
    $data = (array)Firebase\JWT\JWT::decode($token, 'xxmypasswordxx', ['HS256']);
} catch(Exception $e) {
    $this->stop('Token is invalid', 412);
}

if (!file_exists($data['file']) {
   $this->stop('File not found', 404);
}

header('Pragma: public');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Cache-Control: private', false);
header('Content-Type: application/force-download');
header('Content-Disposition: attachment; filename="'.basename($data['file']).'";' );
header('Content-Transfer-Encoding: binary');
header('Content-Length: '.filesize($data['file']));


$handle = fopen($data['file'], 'rb');

while (!feof($handle)) {
    echo fread($handle, 1000);
}

fclose($handle);

$this->stop();

then just request /api/public/download?token={yourwebtoken}

FYI: Webtokens - https://jwt.io/


#4

But issue will persist if files are stored as normal assets, right? I mean, anyone that knows the path can download directly the file unless that is forbidden by webserver.


#5

you’re right. but I would then suggest to secure the folder via eg htpasswd


#6

I added a new rule in htaccess:
RewriteRule (.*).mp3$ checkmp3.php?i=$1 [L]
but I don’t know how to access current user permission and user authentication from php.