<?php

namespace App\Models;

use App\Repositories\AbstractsRepository;
use App\Traits\HasFiles;
use Illuminate\Database\Eloquent\Casts\AsArrayObject;
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\Facades\DB;

/**
 * @property mixed $id
 * @property mixed $data
 * @property int|mixed $step
 * @property mixed|string $submission_status
 * @property string $selection_status
 * @property false|mixed $edit_request
 * @property mixed $user_id
 * @property mixed $presentation_type
 * @property mixed $no_of_votes
 */
class Abstracts extends Model
{
    use HasFactory, HasFiles;

    const FILE_SAVE_PATH = 'private/media/abstracts/';
    const FILE_PUBLIC_PATH = null;
    const PRIVATE_FILE_SAVE_PATH = 'private/media/abstracts/';

    protected $fillable = [
        'data',
        'user_id',
        'event_id',
        'step',
        'submission_status',
        'submission_date',
        'selection_status',
        'edit_request',
        'rank',
        'score',
        'no_of_votes',
        'presentation_invite',
        'presentation_type',
        'submission_flag',
        'submitter_presenters_count'
    ];

    protected $casts = [
        'data' => AsArrayObject::class,
        'edit_track' => AsArrayObject::class,
        'last_edited_data' => AsArrayObject::class,
        'created_at' => 'date:Y-m-d H:i:s',
        'updated_at' => 'date:Y-m-d H:i:s'
    ];

    //===========================================//
    //relations

    public function users($role = null)
    {
        $query = $this->belongsToMany(User::class, 'abstract_user')
            ->using(AbstractUser::class)
            ->withPivot(['id'])
            ->withTimestamps();
        $query
            ->join('model_has_roles as mhs', 'mhs.model_id', '=', 'abstract_user.id')
            ->where('mhs.model_type', '=', AbstractUser::class)
            ->join('roles as r', 'r.id', '=', 'mhs.role_id')
            ->groupBy('users.id')
            ->addSelect([
                'users.*',
                DB::raw("GROUP_CONCAT(r.name) as abstract_roles")
            ]);
        if ($role) {
            $query->where('r.name', '=', $role);
        }
        return $query;
    }

    public function scores(): HasMany
    {
        return $this->hasMany(Score::class, 'abstract_id');
    }

    public function event(): BelongsTo
    {
        return $this->belongsTo(Event::class);
    }

    // End of relations
    //===========================================//

    public function useRepository($event = null): AbstractsRepository
    {
        return new AbstractsRepository($event);
    }
}
