跳转到内容

“XOOPS中的服务层模式”

2.5.x ✅ 4.0.x ✅

:::提示[今天和明天都有效] 服务层模式适用于 XOOPS 2.5.x 和 XOOPS 4.0.x。这些概念是通用的——只是语法不同:

特色XOOPS2.5.xXOOPS4.0
PHP版本7.4+8.2+
构造函数注入✅ 手动接线✅ 容器自动装配
类型化属性@var 文档区块本机类型声明
只读属性❌ 不可用readonly 关键字

下面的代码示例使用 PHP 8.2+ 语法。对于 2.5.x,省略 readonly 并使用传统的属性声明。 :::

服务层模式将业务逻辑封装在专用服务类中,在控制器和数据访问层之间提供清晰的分离。该模式提高了代码的可重用性、可测试性和可维护性。

服务层:

  • 包含领域业务逻辑
  • 协调多个存储库
  • 处理复杂的操作
  • 管理交易
  • 执行验证和授权
  • 为控制器提供高-level操作
  • 跨多个控制器可重用的业务逻辑
  • 易于隔离测试
  • 集中式业务规则实施
  • 明确的关注点分离
  • 简化的控制器代码
<?php
// Service with injected dependencies
class UserService
{
private $userRepository;
private $emailService;
public function __construct(
UserRepositoryInterface $userRepository,
EmailServiceInterface $emailService
) {
$this->userRepository = $userRepository;
$this->emailService = $emailService;
}
public function registerUser($username, $email, $password)
{
// Validate
$this->validate($username, $email, $password);
// Create user
$user = new User();
$user->setUsername($username);
$user->setEmail($email);
$user->setPassword($password);
// Save
$userId = $this->userRepository->save($user);
// Send welcome email
$this->emailService->sendWelcome($email, $username);
return $userId;
}
private function validate($username, $email, $password)
{
$errors = [];
if (strlen($username) < 3) {
$errors['username'] = 'Username too short';
}
if (!filter_var($email, FILTER_VALIDATE_EMAIL)) {
$errors['email'] = 'Invalid email';
}
if (strlen($password) < 6) {
$errors['password'] = 'Password too short';
}
if (!empty($errors)) {
throw new ValidationException('Invalid input', $errors);
}
}
}
?>
<?php
class ServiceContainer
{
private $services = [];
public function __construct($db)
{
// Register repositories
$this->services['userRepository'] = new UserRepository($db);
// Register services
$this->services['userService'] = new UserService(
$this->services['userRepository']
);
}
public function get($name)
{
if (!isset($this->services[$name])) {
throw new \InvalidArgumentException("Service not found: $name");
}
return $this->services[$name];
}
}
?>
<?php
class UserController
{
private $userService;
public function __construct(ServiceContainer $container)
{
$this->userService = $container->get('userService');
}
public function registerAction()
{
if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
return [];
}
try {
$userId = $this->userService->registerUser(
$_POST['username'],
$_POST['email'],
$_POST['password']
);
return [
'success' => true,
'userId' => $userId,
];
} catch (ValidationException $e) {
return [
'success' => false,
'errors' => $e->getErrors(),
];
}
}
}
?>
  • 每项服务处理一个领域问题
  • 服务依赖于接口,而不是实现
  • 使用构造函数注入依赖项
  • 服务应该可以单独测试
  • 抛出域-specific异常
  • 服务不应依赖于 HTTP 请求详细信息
  • 保持服务的重点和凝聚力

另请参阅:


标签:#服务-layer#业务-logic#依赖-injection#设计-patterns