111 lines
3.7 KiB
PHP
111 lines
3.7 KiB
PHP
<?php
|
||
declare(strict_types=1);
|
||
|
||
namespace app\service\admin\member;
|
||
|
||
use app\dao\member\MemberDao;
|
||
use app\enum\member\PointSource;
|
||
use app\enum\member\PointType;
|
||
use app\adminapi\event\PointsChangedEvent;
|
||
use core\base\BaseService;
|
||
use core\exception\handler\AdminException;
|
||
use support\Container;
|
||
|
||
/**
|
||
* 会员服务类
|
||
* @method getUsersListByTagId(mixed $where, mixed $field, mixed $page, mixed $limit)
|
||
* @method getUsersExcludingTag(mixed $where, mixed $field, mixed $page, mixed $limit)
|
||
*/
|
||
class MemberService extends BaseService
|
||
{
|
||
/**
|
||
* 构造方法
|
||
*/
|
||
public function __construct(MemberDao $dao)
|
||
{
|
||
$this->dao = $dao;
|
||
}
|
||
|
||
/**
|
||
* 分配标签
|
||
*
|
||
* @throws \core\exception\handler\AdminException
|
||
*/
|
||
public function assignTags(int|string $id, array $tags = []): void
|
||
{
|
||
try {
|
||
$model = $this->dao->get($id);
|
||
if (empty($model)) {
|
||
throw new AdminException('会员不存在');
|
||
}
|
||
$model->tags()->sync($tags);
|
||
} catch (\Exception $exception) {
|
||
throw new AdminException($exception->getMessage());
|
||
}
|
||
}
|
||
|
||
/**
|
||
* 调整会员积分(使用 Laravel ORM)
|
||
*
|
||
* @param int|string $id 会员ID
|
||
* @param int $points 积分变动值(正数增加,负数减少)
|
||
* @param array $options
|
||
*
|
||
* @throws \Throwable
|
||
* @throws \core\exception\handler\AdminException
|
||
*/
|
||
public function adjustPoints(int|string $id, int $points, array $options = []): void
|
||
{
|
||
try {
|
||
$this->transaction(function () use ($id, $points, $options) {
|
||
// 使用 Laravel ORM 查询会员
|
||
$member = $this->dao->get($id);
|
||
if (!$member) {
|
||
throw new AdminException('会员不存在');
|
||
}
|
||
// 检查积分是否足够(如果是减少积分)
|
||
if ($points < 0 && $member->points < abs($points)) {
|
||
throw new AdminException('会员积分不足');
|
||
}
|
||
|
||
// 计算新积分
|
||
$newPoints = abs($points);
|
||
// 积分不能小于0
|
||
if ($newPoints < 0) {
|
||
throw new AdminException('积分不能小于0');
|
||
}
|
||
//添加积分记录
|
||
$pointsService = Container::make(MemberPointsService::class);
|
||
$params = [
|
||
'member_id' => $member->id,
|
||
'points' => $points,
|
||
'balance' => $newPoints,
|
||
'type' => $options['type'] ?? PointType::ADJUST->value,
|
||
'source' => $options['source'] ?? PointSource::ADMIN->value,
|
||
'remark' => $options['remark'] ?? '',
|
||
];
|
||
$pointsService->save($params);
|
||
$member->update(['points' => $newPoints]);
|
||
|
||
$source = PointSource::ADMIN;
|
||
if (!empty($params['source'])) {
|
||
$source = PointSource::tryFrom($params['source']) ?? PointSource::ADMIN;
|
||
}
|
||
|
||
$event = new PointsChangedEvent(
|
||
$member->id,
|
||
$points,
|
||
$source,
|
||
PointType::INCREASE,
|
||
$member->points,
|
||
$newPoints,
|
||
$options['remark'] ?? ''
|
||
);
|
||
$event->dispatch();
|
||
});
|
||
} catch (\Throwable $exception) {
|
||
throw new AdminException('调整积分失败: ' . $exception->getMessage());
|
||
}
|
||
}
|
||
|
||
} |