<?php

namespace App\Http\Controllers\Employee;

use App\Http\Controllers\Controller;
use App\Http\Requests\Employee\RuleRequest;
use App\Models\Personality;
use App\Models\Rule;
use App\Models\Statement;
use App\Models\Weight;
use Illuminate\Http\RedirectResponse;
use Illuminate\View\View;

class RuleController extends Controller
{
    public function index(): View
    {
        // * Get all rules ordered by rule code ordered by ascending 
        $rules = Rule::orderBy('rule_code', 'asc')->get();

        return view('employee.pages.rule.index', compact('rules'));
    }

    public function graph(): View
    {
        // * Get all personalities ordered by personality code ordered by ascending
        $personalities = Personality::orderBy('personality_code', 'asc')->get();

        // * Get all rules ordered by rule code ordered by ascending
        $rules = Rule::orderBy('rule_code', 'asc')->get();

        // * Create an empty array to store unique statements
        $uniqueStatements = [];

        //* Mengelompokkan pernyataan berdasarkan nilai kunci dan menambahkan kepribadian ke dalam array
        foreach ($rules as $rule) {
            $statement = $rule->statement->statement;
            $personality = $rule->personality->personality;

            //* Jika pernyataan sudah ada, tambahkan kepribadian baru ke dalam array kepribadian
            if (isset($uniqueStatements[$statement])) {
                $uniqueStatements[$statement]['personalities'][] = $personality;
            } else {
                //* Jika pernyataan belum ada, buat kunci baru dan tambahkan array kepribadian baru
                $uniqueStatements[$statement] = [
                    'statement_code' => $rule->statement->statement_code,
                    'personalities' => [$personality],
                ];
            }
        }

        return view('employee.pages.rule.graph', compact('personalities', 'rules', 'uniqueStatements'));
    }

    public function generateRuleCode(): string
    {
        // * Get the latest rule ordered by rule code descending
        $latestRule = Rule::orderBy('rule_code', 'desc')->first();

        // * If there is no rule yet in the database then the next rule code is R001
        if (!$latestRule) {
            $nextRuleCode = 'R0001';

            // * If there is a rule, the next rule code will be the latest rule code + 1
        } else {
            $latestRuleCode = $latestRule->rule_code;
            $number = (int) substr($latestRuleCode, 1);
            $nextNumber = $number + 1;
            $nextRuleCode = 'R' . str_pad($nextNumber, 4, '0', STR_PAD_LEFT);
        }

        return $nextRuleCode;
    }

    public function create(): View
    {
        // * Get all statements ordered by statement code ordered by ascending
        $statements = Statement::orderBy('statement_code', 'asc')->get();

        // * Get all personalities ordered by personality code ordered by ascending
        $personalities = Personality::orderBy('personality_code', 'asc')->get();

        // * Get all weights ordered by weight ordered by ascending
        $weights = Weight::orderBy('weight', 'asc')->get();

        // * Generate rule code
        $generateRuleCode = $this->generateRuleCode();

        return view('employee.pages.rule.create', compact('statements', 'personalities', 'weights', 'generateRuleCode'));
    }

    public function store(RuleRequest $request): RedirectResponse
    {
        // * Create the rule
        Rule::create([
            'rule_code' => $request->rule_code,
            'statement_id' => $request->statement_id,
            'personality_id' => $request->personality_id,
            'weight_id' => $request->weight_id,
        ]);

        // * Notification
        $notification = [
            'message' => 'Aturan telah berhasil ditambahkan',
            'alert-type' => 'info',
        ];

        return redirect()->route('rules')->with($notification);
    }

    public function edit(Rule $rules): View
    {
        // * Get all statements ordered by statement code ordered by ascending
        $statements = Statement::orderBy('statement_code', 'asc')->get();

        // * Get all personalities ordered by personality code ordered by ascending
        $personalities = Personality::orderBy('personality_code', 'asc')->get();

        // * Get all weights ordered by weight ordered by ascending
        $weights = Weight::orderBy('weight', 'asc')->get();

        return view('employee.pages.rule.edit', compact('rules', 'statements', 'personalities', 'weights'));
    }

    public function update(RuleRequest $request, Rule $rules): RedirectResponse
    {
        // * Update the rule
        $rules->update([
            'rule_code' => $request->rule_code,
            'statement_id' => $request->statement_id,
            'personality_id' => $request->personality_id,
            'weight_id' => $request->weight_id,
        ]);

        // * Notification
        $notification = [
            'message' => 'Aturan telah berhasil diperbarui',
            'alert-type' => 'info',
        ];

        return redirect()->route('rules')->with($notification);
    }

    public function reorderRuleCode(): void
    {
        // * Get all rule code ordered by rule code ascending
        $ruleCode = Rule::orderBy('rule_code', 'asc')->get();

        // * Reorder rule code
        foreach ($ruleCode as $key => $rule) {
            $rule->update([
                'rule_code' => 'R' . str_pad($key + 1, 4, '0', STR_PAD_LEFT),
            ]);
        }
    }

    public function destroy(Rule $rules): RedirectResponse
    {
        // * Delete the rule
        $rules->delete();

        // * Reorder rule code
        $this->reorderRuleCode();

        // * Notification
        $notification = [
            'message' => 'Aturan telah berhasil dihapus',
            'alert-type' => 'info',
        ];

        return redirect()->route('rules')->with($notification);
    }
}
