290 lines
No EOL
7.5 KiB
PHP
290 lines
No EOL
7.5 KiB
PHP
<?php
|
|
|
|
namespace App\Domain;
|
|
|
|
use App\Models\UserShop;
|
|
|
|
/**
|
|
* Domain Context - Immutable context object representing current domain state
|
|
*
|
|
* This class provides a clean, immutable way to pass domain context
|
|
* throughout the application without relying on global state.
|
|
*/
|
|
class DomainContext
|
|
{
|
|
public function __construct(
|
|
public readonly string $type, // 'main', 'main-shop', 'crm', 'portal', 'checkout', 'user-shop', 'unknown'
|
|
public readonly string $fullDomain, // Complete domain (e.g., 'shop.mivita.care')
|
|
public readonly string $domain, // Base domain (e.g., 'mivita')
|
|
public readonly ?string $subdomain, // Subdomain part (e.g., 'shop') or null
|
|
public readonly string $tld, // TLD (e.g., '.care')
|
|
public readonly ?UserShop $userShop = null, // For user shop contexts
|
|
public readonly array $config = [] // Additional configuration
|
|
) {}
|
|
|
|
/**
|
|
* Check if this is the main domain (mivita.care)
|
|
*/
|
|
public function isMainDomain(): bool
|
|
{
|
|
return $this->type === 'main';
|
|
}
|
|
|
|
/**
|
|
* Check if this is the main shop domain (mivita.shop)
|
|
*/
|
|
public function isMainShopDomain(): bool
|
|
{
|
|
return $this->type === 'main-shop';
|
|
}
|
|
|
|
/**
|
|
* Check if this is any main domain variant
|
|
*/
|
|
public function isAnyMainDomain(): bool
|
|
{
|
|
return $this->isMainDomain() || $this->isMainShopDomain();
|
|
}
|
|
|
|
/**
|
|
* Check if this is the CRM domain (my.mivita.care)
|
|
*/
|
|
public function isCrmDomain(): bool
|
|
{
|
|
return $this->type === 'crm';
|
|
}
|
|
|
|
/**
|
|
* Check if this is the portal domain (in.mivita.care)
|
|
*/
|
|
public function isPortalDomain(): bool
|
|
{
|
|
return $this->type === 'portal';
|
|
}
|
|
|
|
/**
|
|
* Check if this is the checkout domain (checkout.mivita.care)
|
|
*/
|
|
public function isCheckoutDomain(): bool
|
|
{
|
|
return $this->type === 'checkout';
|
|
}
|
|
|
|
/**
|
|
* Check if this is a user shop domain ({slug}.mivita.care)
|
|
*/
|
|
public function isUserShopDomain(): bool
|
|
{
|
|
return $this->type === 'user-shop';
|
|
}
|
|
|
|
/**
|
|
* Check if this is an unknown/invalid domain
|
|
*/
|
|
public function isUnknownDomain(): bool
|
|
{
|
|
return $this->type === 'unknown';
|
|
}
|
|
|
|
/**
|
|
* Check if this domain supports e-commerce functionality
|
|
*/
|
|
public function supportsEcommerce(): bool
|
|
{
|
|
return in_array($this->type, ['main-shop', 'user-shop']);
|
|
}
|
|
|
|
/**
|
|
* Check if this domain requires authentication
|
|
*/
|
|
public function requiresAuthentication(): bool
|
|
{
|
|
return in_array($this->type, ['crm', 'portal']);
|
|
}
|
|
|
|
/**
|
|
* Get the appropriate route prefix for this domain
|
|
*/
|
|
public function getRoutePrefix(): ?string
|
|
{
|
|
return match($this->type) {
|
|
'crm' => 'crm',
|
|
'portal' => 'portal',
|
|
'checkout' => 'checkout',
|
|
'user-shop' => 'shop',
|
|
default => null
|
|
};
|
|
}
|
|
|
|
/**
|
|
* Get the user shop slug (if applicable)
|
|
*/
|
|
public function getUserShopSlug(): ?string
|
|
{
|
|
return $this->userShop?->slug ?? $this->subdomain;
|
|
}
|
|
|
|
/**
|
|
* Get the middleware stack appropriate for this domain
|
|
*/
|
|
public function getMiddlewareStack(): array
|
|
{
|
|
$middleware = ['web']; // Base middleware
|
|
|
|
switch ($this->type) {
|
|
case 'crm':
|
|
$middleware[] = 'auth';
|
|
break;
|
|
|
|
case 'portal':
|
|
$middleware[] = 'auth:customers';
|
|
break;
|
|
|
|
case 'checkout':
|
|
$middleware[] = 'checkout';
|
|
break;
|
|
|
|
case 'user-shop':
|
|
$middleware[] = 'subdomain';
|
|
break;
|
|
}
|
|
|
|
return $middleware;
|
|
}
|
|
|
|
/**
|
|
* Get the view namespace for this domain
|
|
*/
|
|
public function getViewNamespace(): ?string
|
|
{
|
|
return match($this->type) {
|
|
'crm' => 'crm',
|
|
'portal' => 'portal',
|
|
'checkout' => 'checkout',
|
|
'user-shop' => 'shop',
|
|
default => null
|
|
};
|
|
}
|
|
|
|
/**
|
|
* Get the layout template for this domain
|
|
*/
|
|
public function getLayoutTemplate(): string
|
|
{
|
|
return match($this->type) {
|
|
'crm' => 'layouts.crm',
|
|
'portal' => 'layouts.portal',
|
|
'checkout' => 'layouts.checkout',
|
|
'user-shop' => 'web.layouts.application',
|
|
'main-shop' => 'web.layouts.application',
|
|
default => 'layouts.app'
|
|
};
|
|
}
|
|
|
|
/**
|
|
* Check if this domain allows cart functionality
|
|
*/
|
|
public function allowsCart(): bool
|
|
{
|
|
return $this->supportsEcommerce();
|
|
}
|
|
|
|
/**
|
|
* Get session configuration for this domain
|
|
*/
|
|
public function getSessionConfig(): array
|
|
{
|
|
$config = [
|
|
'lifetime' => config('session.lifetime'),
|
|
'expire_on_close' => config('session.expire_on_close'),
|
|
];
|
|
|
|
// Set domain-specific session domain
|
|
if ($this->isUserShopDomain()) {
|
|
$config['domain'] = '.' . $this->domain . $this->tld;
|
|
}
|
|
|
|
return $config;
|
|
}
|
|
|
|
/**
|
|
* Create a new context with updated user shop
|
|
*/
|
|
public function withUserShop(UserShop $userShop): self
|
|
{
|
|
return new self(
|
|
$this->type,
|
|
$this->fullDomain,
|
|
$this->domain,
|
|
$this->subdomain,
|
|
$this->tld,
|
|
$userShop,
|
|
$this->config
|
|
);
|
|
}
|
|
|
|
/**
|
|
* Create a new context with additional configuration
|
|
*/
|
|
public function withConfig(array $config): self
|
|
{
|
|
return new self(
|
|
$this->type,
|
|
$this->fullDomain,
|
|
$this->domain,
|
|
$this->subdomain,
|
|
$this->tld,
|
|
$this->userShop,
|
|
array_merge($this->config, $config)
|
|
);
|
|
}
|
|
|
|
/**
|
|
* Convert to array for debugging/logging
|
|
*/
|
|
public function toArray(): array
|
|
{
|
|
return [
|
|
'type' => $this->type,
|
|
'full_domain' => $this->fullDomain,
|
|
'domain' => $this->domain,
|
|
'subdomain' => $this->subdomain,
|
|
'tld' => $this->tld,
|
|
'user_shop_slug' => $this->getUserShopSlug(),
|
|
'user_shop_id' => $this->userShop?->id,
|
|
'config' => $this->config,
|
|
];
|
|
}
|
|
|
|
/**
|
|
* Get a human-readable description of this domain context
|
|
*/
|
|
public function getDescription(): string
|
|
{
|
|
return match($this->type) {
|
|
'main' => 'Main Website',
|
|
'main-shop' => 'Main Shop',
|
|
'crm' => 'CRM System',
|
|
'portal' => 'Customer Portal',
|
|
'checkout' => 'Checkout System',
|
|
'user-shop' => "User Shop ({$this->getUserShopSlug()})",
|
|
'unknown' => 'Unknown Domain',
|
|
default => 'Undefined Domain Type'
|
|
};
|
|
}
|
|
|
|
/**
|
|
* Static factory method to create context from domain service
|
|
*/
|
|
public static function fromDomainInfo(array $domainInfo, ?UserShop $userShop = null): self
|
|
{
|
|
return new self(
|
|
$domainInfo['type'],
|
|
$domainInfo['full_domain'],
|
|
$domainInfo['domain'],
|
|
$domainInfo['subdomain'],
|
|
$domainInfo['tld'],
|
|
$userShop
|
|
);
|
|
}
|
|
} |