Upload File and Download Hiding Real URL In Laravel

Hello Artisan 

In this tutorial i am going to show you how we can download file from external url in Laravel. I this laravel file upload and download from url tutorial i will use UUID generator package to hide our real url. 

Cause file uploads are one of the common things in web application these days. But secure download of these files is even more important i think.

So how to store files securely so people wouldn’t have access to them or guess their URLs or IDs of their records? Here’s a small demo tutorial for you.

In this tutorial we will create migration to upload file into database and then we download it from the storage folder using this file link. So follow the below step to learn laravel download file from storage.

 

Step 1 : Install Laravel

In first step, we require to get fresh Laravel application using bellow command, So open your terminal OR command prompt and run bellow command:

composer create-project --prefer-dist laravel/laravel test

 

Step 2: Create Migration 

Now we have to create a table to upload file. So create it.

php artisan make:model Book -m

 

and paste this code to your books table.

public function up()
{
    Schema::create('books', function (Blueprint $table) {
        $table->increments('id');
        $table->uuid('uuid')->nullable();
        $table->string('title');
        $table->string('cover')->nullable();
        $table->timestamps();
    });
}

now run migrate command.

php artisan migrate

 

Field uuid will be used to hide original ID, and field cover will store the original filename. Now open Model app/Book.php and paste this below code.

app/Book.php

protected $fillable = ['uuid', 'title', 'cover'];

 

Step 3 : Setup Route

In this step, we will create routes. Laravel provide web.php file for write web services route. So, let's add new route on that file.

routes/api.php

Route::resource('books', 'BookController');
Route::get('books/{uuid}/download', '[email protected]')->name('books.download');

 

So we manage books with resourceful BookController and will have a separate route for download.

app/Http/Controllers/BookController.php

use App\Book;

class BookController extends Controller
{
    public function index()
    {
        $books = Book::all();
        return view('books.index', compact('books'));
    }

    public function create()
    {
        return view('books.create');
    }
}

 

This is how our views look like – just a simple table and form.

resources/views/books/index.blade.php:

 

And for creating file upload form, paste this code to below file.

resources/views/books/create.blade.php:

 

Step 4 : Upload FIle

In this step we have upload our file. So open BookController and paste this below code. In this we will use uuid generator. So first install it via composer command.

composer require "webpatser/laravel-uuid:^3.0"

You can visit here to see docs

app/Http/BookController.php

use Webpatser\Uuid\Uuid;

public function store(Request $request)
{
    $book = $request->all();
    $book['uuid'] = (string)Uuid::generate();
    if ($request->hasFile('cover')) {
        $book['cover'] = $request->cover->getClientOriginalName();
        $request->cover->storeAs('books', $book['cover']);
    }
    Book::create($book);
    return redirect()->route('books.index');
}

 

Step 5: Downloading File by UUID

We already have this route:

Route::get('books/{uuid}/download', '[email protected]')->name('books.download');

 

In our Blade file, we refer to this route with this syntax:

 

Finally, this is how download method looks like in 

app/Http/Controllers/BookController.php:

public function download($uuid)
{
    $book = Book::where('uuid', $uuid)->firstOrFail();
    $pathToFile = storage_path('app/books/' . $book->cover);
    return response()->download($pathToFile);
}

 

Read also: Don't use if else ladder in php rather use this method

 

Now see users can download the file with its original filename, but without knowing where it is stored on the server. Hope it can help you.