<?php

namespace App\Http\Controllers;

use App\Models\Gallery;
use App\Models\Image;
use App\Models\Tenant;
use App\Rules\dateOrNull;
use App\Rules\urlOrNull;
use Illuminate\Foundation\Auth\Access\AuthorizesRequests;
use Illuminate\Foundation\Bus\DispatchesJobs;
use Illuminate\Foundation\Validation\ValidatesRequests;
use Illuminate\Http\Request;
use Illuminate\Routing\Controller as BaseController;
use Illuminate\Support\Facades\Redirect;
use Illuminate\Support\Facades\Storage;
use Illuminate\Validation\Rule;

class GalleryController extends BaseController
{
    use AuthorizesRequests, DispatchesJobs, ValidatesRequests;

    public function listView() {
        $galleries = Gallery::query()->where("tenant", "=", session("current_tenant_id"))->orderByDesc("gallery_create_time")->orderByDesc("id")->get();
        $tenant = Tenant::query()->where("id", "=", session("current_tenant_id"))->firstOrFail();
        return view("gallery.index", [ "galleries" => $galleries, "tenant" => $tenant]);
    }

    public function newView(Request $request) {
        $gallery = new Gallery();
        $status = "preview";
        if(!empty($request->old("status"))) {
            $status = $request->old("status");
        }
        $listed = true;
        if(!empty($request->old("listed"))) {
            $listed = $request->old("listed");
        }
        $tags = "";
        return view("gallery.new", ["gallery" => $gallery, "tags" => $tags, "status" => $status, "listed" => $listed]);
    }

    public function newGallery(Request $request) {
        $validated = $request->validate([
            'name' => 'required|max:255',
            'description' => 'max:15000000',
            'url' => [new urlOrNull()],
            'date' => [new dateOrNull()],
            'status' => ['required', Rule::in(['preview', 'online', 'archiv'])],
            'listed' => '',
            'tags' => ''
        ]);

        if(!array_key_exists("listed", $validated)) {
            $validated["listed"] = false;
        }
        if(strtolower($validated["listed"]) == "off") {
            $validated["listed"] = false;
        }
        $validated["listed"] = (bool)$validated["listed"];

        //Check if Gallery Date is in the feature
        if(!empty($validated["date"])) {
            $t = new \DateTime($validated["date"]);
            if($t > (new \DateTime())) {
                return Redirect::back()->withErrors(["date" => "Gallery date can't be in the feature"])->withInput($validated);
            }
        }

        if(empty($validated["url"])) {
            $prepairdName = strtolower($validated["name"]);
            $prepairdName = str_replace(" ", "-", $prepairdName);
            $prepairdName = str_replace("ö", "oe", $prepairdName);
            $prepairdName = str_replace("ü", "üe", $prepairdName);
            $prepairdName = str_replace("ö", "oe", $prepairdName);
            $prepairdName = str_replace("ß", "ss", $prepairdName);

            while (strlen($prepairdName) < 8) {
                $prepairdName = $prepairdName."0";
            }
            preg_match_all("@[a-z0-9\-]@", $prepairdName, $matches);
            $newUrl = "";
            foreach($matches[0] as $letter) {
                $newUrl .= $letter;
            }

            $baseUrl = $newUrl;
            $i = 1;
            while (true) {
                $r = Gallery::getByTenantAndUrl(session("current_tenant_id"), $newUrl);
                if($r == null) {
                    break;
                }
                $newUrl = $baseUrl.$i;
                $i++;
            }
        } else {
            $newUrl = $validated["url"];
        }

        //Check if url is free
        $galleryTMP = Gallery::getByTenantAndUrl(session("current_tenant_id"), $newUrl);
        if(!empty($galleryTMP)) {
            return Redirect::back()->withErrors(["url" => "URL is already used"])->withInput($validated);
        }

        $gallery = new Gallery();
        $gallery->name = $validated["name"];
        $gallery->url = $newUrl;
        $gallery->description = $validated["description"];
        $gallery->tenant = session("current_tenant_id");
        $gallery->status = $validated["status"];
        $gallery->listed = $validated["listed"];
        $gallery->tags = json_encode(mb_split(",", $validated["tags"]));
        if(!empty($validated["date"])) {
            $gallery->gallery_create_time = $validated["date"];
        } else {
            $gallery->gallery_create_time = date("Y-m-d");
        }
        $gallery->saveOrFail();



        return \redirect("/g/".$gallery->url."/upload");
    }

    public function editGalleryView($name, Request $request) {
        $gallery = Gallery::getByTenantAndUrl(session("current_tenant_id"), $name);
        $status = $gallery->status;
        if(!empty($request->old("status"))) {
            $status = $request->old("status");
        }
        $listed = $gallery->listed;
        if(!empty($request->old("listed"))) {
            $listed = $request->old("listed");
        }
        $tagsArray = json_decode($gallery->tags);

        $tags = "";
        if(is_array($tagsArray)) {
            $tags = implode(",", $tagsArray);
        }
        return view("gallery.new", ["gallery" => $gallery, "tags" => $tags, "status" => $status, "listed" => $listed]);
    }

    public function editGallery($name, Request $request) {
        $validated = $request->validate([
            'name' => 'required|max:255',
            'description' => 'max:15000000',
            'url' => 'required|regex:/^[a-z0-9\-]{8,30}$/i',
            'date' => 'required|regex:/^\d{4}-\d{2}-\d{2}$/i',
            'status' => ['required', Rule::in(['preview', 'online', 'archiv'])],
            'listed' => '',
            'tags' => ''
        ]);

        if(!array_key_exists("listed", $validated)) {
            $validated["listed"] = false;
        }
        if(strtolower($validated["listed"]) == "off") {
            $validated["listed"] = false;
        }
        $validated["listed"] = (bool)$validated["listed"];

        $gallery = Gallery::getByTenantAndUrl(session("current_tenant_id"), $name);
        $gallery->name = $validated["name"];
        $gallery->description = $validated["description"];
        $gallery->url = $validated["url"];
        $gallery->gallery_create_time = $validated["date"];
        $gallery->status = $validated["status"];
        $gallery->listed = $validated["listed"];
        $gallery->tags = json_encode(mb_split(",", $validated["tags"]));
        $gallery->saveOrFail();


        return Redirect::back()->with(["msg" => "Saved"]);
    }

    public function imagesUploadView($name) {
        return view("gallery.upload");
    }

    public function imageUpload($name, Request $request) {
        $gallery = Gallery::getByTenantAndUrl(session("current_tenant_id"), $name);
        $validated = $request->validate([
            'files.0' => 'required|image'
        ]);
        $path = $validated["files"][0]->store("uploads/".session("current_tenant_id")."/".$name);


        $image = new Image();
        $image->path = $path;
        $image->driver = env('FILESYSTEM_DRIVER', 'local');
        $image->filename = $validated["files"][0]->getClientOriginalName();
        $image->gallery = $gallery->id;
        $image->size = $validated["files"][0]->getSize();
        $image->saveOrFail();

        if(is_null($gallery->main_image)) {
            $gallery->main_image = $image->id;
            $gallery->saveOrFail();
        }

        return $name;
    }

    public function showImagesView($name) {
        $gallery = Gallery::getByTenantAndUrl(session("current_tenant_id"), $name);
        $tenant = Tenant::query()->where("id", "=", $gallery->tenant)->firstOrFail();
        $images = Image::query()
            ->where("gallery", "=", $gallery->id)
            ->orderBy("rating")
            ->orderBy("DateTimeOriginal")
            ->whereNull("deleted_at")
            ->get();
        return view("gallery.images", ["images" => $images, "gallery" => $gallery, "tenant" => $tenant]);
    }

    public function setDefault($name, Request $request) {
        $gallery = Gallery::getByTenantAndUrl(session("current_tenant_id"), $name);
        $gallery->main_image = $request->input("id");
        $gallery->saveOrFail();
        return "OK";
    }

    public function deleteImage($name, Request $request) {
        $gallery = Gallery::getByTenantAndUrl(session("current_tenant_id"), $name);
        $image = Image::query()->where("id", "=", $request->input("id"))->firstOrFail();
        if($image->gallery != $gallery->id) {
            abort(400);
        }

        Storage::disk($image->driver)->delete($image->path);
        $image->deleted_at = date("Y-m-d H:i:s");
        $image->saveOrFail();
        return "OK";
    }

    public function saveImage($name, Request $request) {
        $gallery = Gallery::getByTenantAndUrl(session("current_tenant_id"), $name);
        $image = Image::query()->where("id", "=", $request->input("id"))->firstOrFail();
        if($image->gallery != $gallery->id) {
            abort(400);
        }

        $image->name = $request->input("name");
        $image->description = $request->input("description");
        $image->rating = $request->input("rating");
        $image->saveOrFail();
        return "OK";
    }
}
