*/ use HasFactory; private const RECENT_FETCH_THRESHOLD_HOURS = 2; private const DAILY_FETCH_THRESHOLD_HOURS = 24; protected $fillable = [ 'name', 'url', 'type', 'language_id', 'description', 'settings', 'is_active', 'last_fetched_at' ]; protected $casts = [ 'settings' => 'array', 'is_active' => 'boolean', 'last_fetched_at' => 'datetime' ]; public function getTypeDisplayAttribute(): string { return match ($this->type) { 'website' => 'Website', 'rss' => 'RSS Feed', default => 'Unknown' }; } public function getStatusAttribute(): string { if (!$this->is_active) { return 'Inactive'; } if (!$this->last_fetched_at) { return 'Never fetched'; } $hoursAgo = $this->last_fetched_at->diffInHours(now()); if ($hoursAgo < self::RECENT_FETCH_THRESHOLD_HOURS) { return 'Recently fetched'; } elseif ($hoursAgo < self::DAILY_FETCH_THRESHOLD_HOURS) { return "Fetched {$hoursAgo}h ago"; } else { return "Fetched " . $this->last_fetched_at->diffForHumans(); } } public function channels(): BelongsToMany { return $this->belongsToMany(PlatformChannel::class, 'feed_platform_channels') ->using(FeedPlatformChannel::class) ->withPivot(['is_active', 'priority', 'filters']) ->withTimestamps(); } public function activeChannels(): BelongsToMany { return $this->channels() ->wherePivot('is_active', true) ->orderByPivot('priority', 'desc'); } public function articles(): HasMany { return $this->hasMany(Article::class); } public function language(): BelongsTo { return $this->belongsTo(Language::class); } }