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.

126 lines
3.4 KiB

<?php
namespace App\Models;
use App\Support\ChannelEntryEncryption;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
use Illuminate\Database\Eloquent\Relations\HasMany;
use Illuminate\Support\Str;
class SignupChannel extends Model
{
use HasFactory;
public const STATUS_ENABLED = 'enabled';
public const STATUS_DISABLED = 'disabled';
public const STATUSES = [
self::STATUS_ENABLED,
self::STATUS_DISABLED,
];
public const CALLBACK_TYPE_NONE = 'none';
public const CALLBACK_TYPE_WEB = 'web';
public const CALLBACK_TYPE_MINI_PROGRAM = 'mini_program';
public const CALLBACK_TYPES = [
self::CALLBACK_TYPE_NONE,
self::CALLBACK_TYPE_WEB,
self::CALLBACK_TYPE_MINI_PROGRAM,
];
public const MINI_PROGRAM_METHOD_NAVIGATE_TO = 'navigateTo';
public const MINI_PROGRAM_METHOD_REDIRECT_TO = 'redirectTo';
public const MINI_PROGRAM_METHOD_RE_LAUNCH = 'reLaunch';
public const MINI_PROGRAM_METHOD_SWITCH_TAB = 'switchTab';
public const MINI_PROGRAM_METHODS = [
self::MINI_PROGRAM_METHOD_NAVIGATE_TO,
self::MINI_PROGRAM_METHOD_REDIRECT_TO,
self::MINI_PROGRAM_METHOD_RE_LAUNCH,
self::MINI_PROGRAM_METHOD_SWITCH_TAB,
];
protected $fillable = [
'competition_id',
'channel_name',
'status',
'shared_secret',
'encryption_algorithm',
'entry_encryption_enabled',
'encryption_public_key',
'encryption_private_key',
'success_callback_url',
'success_callback_type',
'mini_program_callback_path',
'mini_program_callback_method',
'remark',
];
protected $hidden = [
'shared_secret',
'encryption_private_key',
];
protected $casts = [
'entry_encryption_enabled' => 'boolean',
'encryption_private_key' => 'encrypted',
];
protected static function booted(): void
{
static::creating(function (SignupChannel $channel): void {
$channel->ensureEncryptionKeyPair();
if ($channel->channel_code !== null && $channel->channel_code !== '') {
return;
}
do {
$channel->channel_code = (string) Str::ulid();
} while (static::query()->where('channel_code', $channel->channel_code)->exists());
});
}
public function ensureEncryptionKeyPair(): void
{
if (trim((string) $this->encryption_public_key) !== ''
&& trim((string) $this->encryption_private_key) !== '') {
return;
}
$keys = ChannelEntryEncryption::generateKeyPair();
$this->encryption_algorithm = ChannelEntryEncryption::ALGORITHM;
$this->encryption_public_key = $keys['public_key'];
$this->encryption_private_key = $keys['private_key'];
}
public function competition(): BelongsTo
{
return $this->belongsTo(Competition::class);
}
public function firstSourceUsers(): HasMany
{
return $this->hasMany(User::class, 'first_channel_id');
}
public function lastSourceUsers(): HasMany
{
return $this->hasMany(User::class, 'last_channel_id');
}
public function applications(): HasMany
{
return $this->hasMany(Application::class, 'signup_channel_id');
}
}