You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I have a single Laravel application that serves API endpoints for multiple products. Each product also has a frontend SPA (using Vue) that users access. For example:
Product Name
Frontend Domain
Laravel API Domain
Foo
app.fooproduct.com
api.fooproduct.com
Bar
app.barproduct.com
api.barproduct.com
Baz
app.bazproduct.com
api.bazproduct.com
Basically the only difference between the products is the skin of the application.
I use Sanctum for authentication. This works fine for GET requests, because the browser properly stores the session cookie for the correct api.[PRODUCT].com domain.
The problem is that POST requests require access to the XSRF-TOKEN cookie. Because the Vue app is on a different subdomain, it cannot read the cookie from the Laravel subdomain.
If I configure Laravel's SESSION_DOMAIN environment variable to .fooproduct.com, that allows the application to work for the Foo product, but not for the Bar and Baz products.
I wrote a middleware that checks if the current domain is recognized as a product and overrides the cookie domain, but I think it is fragile, and it will prevent using Octane in the future because it modifies the CookieJar singleton.
namespaceApp\Http\Middleware;
useClosure;
useIlluminate\Contracts\Config\Repository;
useIlluminate\Cookie\CookieJar;
useIlluminate\Support\Arr;
useIlluminate\Support\Str;
class ChooseProduct
{
protected$config;
protected$cookie;
publicfunction__construct(Repository$config, CookieJar$cookie)
{
$this->config = $config;
$this->cookie = $cookie;
}
publicfunctionhandle($request, Closure$next)
{
// Strips off the port, if present$requestDomain = strtok($request->server('HTTP_HOST'), ':');
$theme = collect($this->config->get('products'))
->first(function ($theme) use ($requestDomain) {
if (Str::endsWith($requestDomain, $theme['main_domain'])) {
returntrue;
}
if (Arr::has($theme, 'alt_domains') && Str::endsWith($requestDomain, $theme['alt_domains'])) {
returntrue;
}
returnfalse;
});
if ($theme !== null) {
$cookieConfig = $this->config->get('session');
$this->cookie->setDefaultPathAndDomain($cookieConfig['path'], ".{$theme['main_domain']}", $cookieConfig['same_site']);
$this->config->set('session.domain', ".{$theme['main_domain']}");
}
return$next($request);
}
}
Other than setting up multiple copies of the Laravel app with different SESSION_DOMAIN values, is there a better/safer way to do what I'm trying to do?
reacted with thumbs up emoji reacted with thumbs down emoji reacted with laugh emoji reacted with hooray emoji reacted with confused emoji reacted with heart emoji reacted with rocket emoji reacted with eyes emoji
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
I have a single Laravel application that serves API endpoints for multiple products. Each product also has a frontend SPA (using Vue) that users access. For example:
app.fooproduct.com
api.fooproduct.com
app.barproduct.com
api.barproduct.com
app.bazproduct.com
api.bazproduct.com
Basically the only difference between the products is the skin of the application.
I use Sanctum for authentication. This works fine for
GET
requests, because the browser properly stores the session cookie for the correctapi.[PRODUCT].com
domain.The problem is that
POST
requests require access to theXSRF-TOKEN
cookie. Because the Vue app is on a different subdomain, it cannot read the cookie from the Laravel subdomain.If I configure Laravel's
SESSION_DOMAIN
environment variable to.fooproduct.com
, that allows the application to work for the Foo product, but not for the Bar and Baz products.I wrote a middleware that checks if the current domain is recognized as a product and overrides the cookie domain, but I think it is fragile, and it will prevent using Octane in the future because it modifies the
CookieJar
singleton.Other than setting up multiple copies of the Laravel app with different
SESSION_DOMAIN
values, is there a better/safer way to do what I'm trying to do?Note: cross-posted to SO.
Beta Was this translation helpful? Give feedback.
All reactions