You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
106 lines
6.6 KiB
106 lines
6.6 KiB
<?php
|
|
namespace App\Services\SupplyDemand;
|
|
use App\Models\User;
|
|
use App\Models\SupplyDemand;
|
|
use App\Models\Dialogue;
|
|
use App\Models\Message;
|
|
use Illuminate\Support\Facades\DB;
|
|
class Handover
|
|
{
|
|
// 手机验证流程合并临时微信账号时,连同已有对接资料一起迁移。
|
|
public static function mergeAccount($from, $to) {
|
|
if ((int) $from === (int) $to) return;
|
|
DB::transaction(function () use ($from, $to) {
|
|
SupplyDemand::where('user_id', $from)->update(['user_id' => $to]);
|
|
Message::where('user_id', $from)->update(['user_id' => $to]);
|
|
Message::where('to_user_id', $from)->update(['to_user_id' => $to]);
|
|
$dialogues = Dialogue::where(function ($q) use ($from) { $q->where('user_id', $from)->orWhere('to_user_id', $from); })->lockForUpdate()->get();
|
|
foreach ($dialogues as $d) {
|
|
$a = (int) $d->user_id === (int) $from ? $to : $d->user_id;
|
|
$b = (int) $d->to_user_id === (int) $from ? $to : $d->to_user_id;
|
|
$key = Conversations::key($d->supply_demand_id, $a, $b);
|
|
$existing = Dialogue::where('conversation_key', $key)->where('id', '!=', $d->id)->lockForUpdate()->first();
|
|
if ($existing) {
|
|
Message::where('dialogue_id', $d->id)->update(['dialogue_id' => $existing->id]);
|
|
if ($d->last_datetime > $existing->last_datetime) {
|
|
$existing->last_content = $d->last_content; $existing->last_datetime = $d->last_datetime; $existing->save();
|
|
}
|
|
$d->delete();
|
|
} else {
|
|
$d->user_id = $a; $d->to_user_id = $b; $d->conversation_key = $key; $d->save();
|
|
}
|
|
}
|
|
Message::where('user_id', $to)->where('to_user_id', $to)->update(['is_read' => 1]);
|
|
});
|
|
}
|
|
public static function verified(User $user) {
|
|
$user->supply_mobile_verified_at = now(); $user->save();
|
|
return self::autoBind($user);
|
|
}
|
|
private static function identityMismatch(SupplyDemand $d, User $user) {
|
|
$issues = [];
|
|
foreach (['姓名'=>[$d->publisher_name, $user->name], '公司'=>[$d->publisher_company, $user->company_name]] as $label=>$values) {
|
|
$imported = preg_replace('/^\s+|\s+$/u', '', (string) $values[0]);
|
|
$actual = preg_replace('/^\s+|\s+$/u', '', (string) $values[1]);
|
|
if ($imported === '' || $actual === '') $issues[] = $label.'信息不完整';
|
|
elseif ($imported !== $actual) $issues[] = $label.'不一致';
|
|
}
|
|
return $issues ? implode('、', $issues).',请人工核实' : null;
|
|
}
|
|
public static function autoBind(User $user) {
|
|
$mobile = $user->getRawOriginal('mobile');
|
|
if (!$user->supply_mobile_verified_at || !preg_match('/^1\d{10}$/', (string) $mobile)) return 0;
|
|
if (User::where('mobile', $mobile)->count() !== 1) {
|
|
SupplyDemand::where('is_proxy', 1)->where('publisher_mobile', $mobile)->where('user_id', 0)->update(['binding_note' => '手机号对应多个学员,请人工核实']);
|
|
return 0;
|
|
}
|
|
$count = 0;
|
|
foreach (SupplyDemand::where('is_proxy', 1)->where('user_id', 0)->where('publisher_mobile', $mobile)->get() as $d) {
|
|
$reason = self::identityMismatch($d, $user);
|
|
if ($reason) { $d->binding_note = $reason; $d->save(); continue; }
|
|
self::bind($d, $user); $count++;
|
|
}
|
|
return $count;
|
|
}
|
|
public static function bindRelated(SupplyDemand $selected, User $user, $adminId) {
|
|
return DB::transaction(function () use ($selected, $user, $adminId) {
|
|
$rows = SupplyDemand::where('is_proxy',1)->where('user_id',0)->where('publisher_mobile',$selected->publisher_mobile)->orderBy('id')->lockForUpdate()->get();
|
|
$name = trim((string) $selected->publisher_name);
|
|
$company = trim((string) $selected->publisher_company);
|
|
if (!$rows->contains('id',$selected->id)) throw new \InvalidArgumentException('该需求已绑定或已删除,请刷新');
|
|
$count = 0;
|
|
foreach ($rows as $row) {
|
|
if ($row->id !== $selected->id && (!$name || !$company || trim((string) $row->publisher_name) !== $name || trim((string) $row->publisher_company) !== $company)) continue;
|
|
self::bind($row,$user,$adminId);$count++;
|
|
}
|
|
return ['demand'=>$selected->fresh(),'count'=>$count];
|
|
});
|
|
}
|
|
public static function bind(SupplyDemand $d, User $user, $confirmedByAdminId = null) {
|
|
return DB::transaction(function () use ($d, $user, $confirmedByAdminId) {
|
|
$d = SupplyDemand::whereKey($d->id)->lockForUpdate()->firstOrFail();
|
|
if (!$d->is_proxy || $d->user_id) throw new \InvalidArgumentException('仅可绑定尚未认领的代发需求');
|
|
if (!preg_match('/^1\d{10}$/', (string) $user->getRawOriginal('mobile'))) throw new \InvalidArgumentException('学员手机号无效,请先完善学员资料');
|
|
if ($confirmedByAdminId === null && !$user->supply_mobile_verified_at) throw new \InvalidArgumentException('请先让该学员完成手机号验证');
|
|
if ($confirmedByAdminId === null) {
|
|
if ((string) $d->publisher_mobile !== (string) $user->getRawOriginal('mobile')) throw new \InvalidArgumentException('手机号不一致,请人工核实');
|
|
$reason = self::identityMismatch($d, $user);
|
|
if ($reason) throw new \InvalidArgumentException($reason);
|
|
}
|
|
$d->user_id = $user->id; $d->bound_at = now(); $d->binding_note = $confirmedByAdminId !== null ? '管理员人工核实绑定:'.$confirmedByAdminId : null; $d->save();
|
|
foreach (Dialogue::where('supply_demand_id', $d->id)->where('to_user_id', 0)->lockForUpdate()->get() as $dialogue) {
|
|
// 本人此前咨询的需求在认领后保留历史,禁止继续向自己发消息。
|
|
$dialogue->to_user_id = $user->id;
|
|
$dialogue->conversation_key = Conversations::key($d->id, $dialogue->user_id, $user->id);
|
|
$dialogue->save();
|
|
}
|
|
$pending = Message::where('supply_demand_id', $d->id)->where('to_user_id', 0)->where('user_id', '!=', $user->id);
|
|
$hasPending = (clone $pending)->exists();
|
|
$pending->update(['to_user_id' => $user->id, 'is_read' => 0]);
|
|
Message::where('supply_demand_id', $d->id)->where('to_user_id', 0)->where('user_id', $user->id)->update(['to_user_id' => $user->id, 'is_read' => 1]);
|
|
if ($hasPending) Notices::queue($user->id);
|
|
return $d;
|
|
});
|
|
}
|
|
}
|