Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Trouble setting up storage disk for Laravel app on Azure

Tags:

php

laravel

azure

I'm having trouble with a Laravel 6 app on Azure. I'm using TCG/Navigator to build my admin interface. Everything's hunky-dory in local development, but when I push the code to my development site in Azure, items from the storage disk are unavailable. I see this as broken images in the Navigator admin panel.

It looks like Laravel's file storage requires a symlink to operate:

https://laravel.com/docs/6.x/filesystem#the-public-disk

but symlinks don't appear to be supported in Azure's Windows web apps. I need something else to map /public/storage to /storage/app/public.

I can create a new virtual directory, but that didn't solve the problem. I mapped "/storage" to "site\wwwroot\storage\app\public" but I'm still seeing broken images in the Navigator admin panel.

I found this issue in Navigator's repo:

https://github.com/the-control-group/voyager/issues/417#issuecomment-304525223

and it seems like just the fix I need, but it's not working, either.

I've added:

        'azure' => [
            'driver' => 'local',
            'root' => storage_path('..\public\storage'),
            'url' => env('APP_URL').'/storage',
            'visibility' => 'public',
        ],

to filesystems.php. In voyager.php, I see:

    'storage' => [
        'disk' => env('FILESYSTEM_DRIVER', 'public'),
    ],

so to leave things as is (ie, working) in local dev, I've added an application setting to my web app:

FILESYSTEM_DRIVER, set to 'azure'

I know that my Azure web app is trying to use the azure filesystem because I initially forgot to push the updated code and my app told me it was missing.

So now I think my problem might be that I don't have the right values in the definition of the azure storage disk. Got any ideas? Or maybe suggestions on a different approach to try to get Laravel's file storage working on Azure?

like image 246
Janine Hempy Avatar asked Jan 21 '26 05:01

Janine Hempy


1 Answers

I've solved this problem in what's probably the right way, but it isn't the solution I was looking for.

Ultimately, I need a place to store media that's uploaded through the site's admin interface. Navigator uses Laravel File Storage, which by default in local dev drops uploaded files into /storage/app/public. The quick and easy solution for deployment is if your dev/staging/prod servers work the same way; that is, uploaded files are stored in the /storage/app/public on the same server. This is what I was trying to do at first.

My development and production servers are on Azure, though. They are scalable web apps, so in theory, if my website is swamped with tons of users enjoying my content, multiple instances may be serving my content. I shouldn't expect every instance having the same local storage. The better scalable solution is for all uploaded content, regardless of which instance was running the admin interface that uploaded the content, to live in a dedicated file storage location. This might seem wacky at first, but it's the same concept as having one database spit out content for any number of webservers to display for users.

So after wrestling with the uncooperative symlink for 2 days, I jumped ahead to dedicated file storage location solution. And it worked! Here are the steps I took to make the magic happen:

  1. Create a storage account in Azure.
  2. Created a blob container in the storage account.
  3. Added the Laravel Azure Storage package to my project (https://github.com/matthewbdaly/laravel-azure-storage).
  4. Updated filesystems.php per the package's directions:
       'azure' => [
            'driver'    => 'azure',
            'name'      => env('AZURE_STORAGE_NAME'),
            'key'       => env('AZURE_STORAGE_KEY'),
            'container' => env('AZURE_STORAGE_CONTAINER'),
            'url'       => env('AZURE_STORAGE_URL'),
            'prefix'    => null,
        ],
  1. Added the AZURE_STORAGE_NAME (name of my storage account), AZURE_STORAGE_CONTAINER (name of my container), and AZURE_STORAGE_KEY (found under "Access Keys" in the storage account data) to my web app's Application Settings.
  2. Used '''Storage::url($page->image)''' in my views to properly create the src values for my images in both local dev (using local storage) and on Azure (using the storage account.
  3. Excluded the local storage data from my repo by updating my project's .gitignore files. (It's not necessary for my test images to be tracked by git.)

Whew. I'm still interested in learning if it's possible to get local storage working in an Azure web app, but this configuration leapfrogs me over that stumbling block toward a production-ready solution.

like image 100
Janine Hempy Avatar answered Jan 22 '26 20:01

Janine Hempy