Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Laravel - Using Values Returned from Middleware Group for Global Variables

Background: I want to use the same code for multiple templated web sites. I want the code to identify the domain being accessed and then be able to set global variables to be used throughout the app.

At first, I created \config\global.php and had the logic in there working as expected:

$webUrl = url()->current();

/**************************************************
 * Set Conference name based on URL
 **************************************************/
$confId = 0;
$confName = '';
$confAbbrev = '';
if(strpos($webUrl, 'webdomain1') > 0) {
    $confName = 'Domain 1 Full Name';
    $confAbbrev = 'Dom1';
    $confId = 25;
}
elseif(strpos($webUrl, 'webdomain2') >0) {
    $confName = 'Domain 2 Full Name';
    $confAbbrev = 'Dom2';
    $confId = 35;
}

However, I eventually found that the "url()" was causing errors which prevented me from using "php artisan" commands throughout the app. After consulting my professional web developer co-worker, he said using a "global" config file for global variables was not best practice and recommended Middleware instead. He took control of my laptop and went REALLY fast...

In \app\Http\Kernel.php, he added the SetDomainVariables line at the end of $middlewareGroups:

    protected $middlewareGroups = [
    'web' => [
        \App\Http\Middleware\EncryptCookies::class,
        \Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
        \Illuminate\Session\Middleware\StartSession::class,
        // \Illuminate\Session\Middleware\AuthenticateSession::class,
        \Illuminate\View\Middleware\ShareErrorsFromSession::class,
        \App\Http\Middleware\VerifyCsrfToken::class,
        \Illuminate\Routing\Middleware\SubstituteBindings::class,
        \App\Http\Middleware\SetDomainVariables::class,
    ],

    'api' => [
        'throttle:60,1',
        'bindings',
    ],
];

He then created a new file: \app\Http\Middleware\SetDomainVariables.php

<?php

namespace App\Http\Middleware;

use Closure;

class SetDomainVariables
{
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        dd($request->getHttpHost());
        return $next($request);
    }
}

The results of "$request->getHttpHost()" is what I need... it returns the "foo" of www.foo.com. However, I don't know how to assign this value to a variable and return it via "$next" and then how I can put logic around it to set my global variables that I can reference in a Blade partial, etc.

Thank you!

EDIT: If using the \config\global.php is really the right way to accomplish what I want, could I just comment out the "url()" line whenever I want to do a "php artisan" command?

like image 788
thePITman Avatar asked Oct 23 '25 10:10

thePITman


1 Answers

There are a few different ways to approach this problem, the easiest would be to make use of config -- which allows you to get and set configuration values dynamically.

  1. Create a new file called config/sites.php containing an array for each of your sites, ensuring you start each domain with www and replace any . in the domain with - (because . in a config key will not work as Laravel uses a period to access child values).
return [
    'default' => [
        'id' => 15,
        'name' => 'Default Full Name',
        'abbreviation' => 'Def',
    ],
    'www-webdomain1-com' => [
        'id' => 25,
        'name' => 'Domain 1 Full Name',
        'abbreviation' => 'Web1',
    ],
    'www-webdomain2-com' => [
        'id' => 35,
        'name' => 'Domain 2 Full Name',
        'abbreviation' => 'Web2',
    ],
];

You now have configuration values for each of your sites accessible anywhere in your application, e.g: config('sites.www-webdomain1-com.name').

  1. Add the following to your middleware:
public function handle($request, Closure $next)
{
    $host = str_slug(starts_with('www.', $request->getHttpHost()));

    $configuration = config("sites.{$host}") ?: config('sites.default');

    config(['site' => $configuration]);

    return $next($request);
}

You've now set the configuration value for the key site to the contents of the site configuration you set in config/sites.php for the request domain.

  1. Anywhere you need to access the active site's configuration option use config('site.property'), e.g:
Hello, welcome to {{ config('site.name') }}

There are better ways to approach this problem, personally I would create a Site model and then use Route Model Binding however the way I've outlined here is very easy to set up for a beginner and should meet your needs.

like image 168
sam Avatar answered Oct 25 '25 23:10

sam



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!