<?php

namespace App\Classes;

use App\Models\Config;
use App\Models\Optimer;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\File;
use Illuminate\Support\Facades\Storage;
use Spatie\ImageOptimizer\OptimizerChain;
use Spatie\ImageOptimizer\Optimizers\Svgo;
use Spatie\ImageOptimizer\Optimizers\Cwebp;
use Spatie\ImageOptimizer\Optimizers\Gifsicle;
use Spatie\ImageOptimizer\Optimizers\Pngquant;
use Spatie\ImageOptimizer\Optimizers\Jpegoptim;

class wasabiS3Storage
{
    public function wasabiFunction($request)
    {
        // Query
        $config = Config::get();

        // Request file
        $file = $request->file('file');

        // Generate Name, width, height
        $imageName = random_int(000000000000001, 99999999999999) . '.' . $request->file->extension();
        $width = 0;
        $height = 0;

        // Get extension, original name, MIME type
        $extension = $file->getClientOriginalExtension();
        $originalname = $file->getClientOriginalName();
        $mimetype = $file->getClientMimeType();

        // Move original image
        $originalPath = $file->move(public_path('/storage/files/' . Auth::user()->id . '/'), $imageName);

        // Create optimize image folder
        $optimizePath = public_path() . '/storage/files/' . Auth::user()->id . '/optimize/';
        File::makeDirectory($optimizePath, 0777, true, true);

        // Move image original folder to optimize folder
        File::copy(public_path('/storage/files/' . Auth::user()->id . '/' . $imageName), $optimizePath . $imageName);

        // Get image size in kb
        $imgsizes = $originalPath->getSize();

        // Get image width and height
        if ($extension != "svg" || $extension != "SVG") {
            // $data = getimagesize($originalPath);
            // $width = $data[0];
            // $height = $data[1];
            $width = 500;
            $height = 500;
        }

        // Upload wasabi S3
        $path = Storage::disk('wasabi')->put('files/' . Auth::user()->id . '/' . $imageName, file_get_contents('storage/files/' . Auth::user()->id . '/' . $imageName));
        $request->merge([
            'path' => $path
        ]);

        // Get original AWS path
        $AWSOriginalPath = $request->only('path', 'title');

        $optimizerChain = "";

        // Optimize Path (JPG)
        if ($extension == "jpg" || $extension == "jpeg" || $extension == "JPG" || $extension == "JPEG") {
            $optimizerChain = (new OptimizerChain)
                ->addOptimizer(new Jpegoptim([
                    '-m' . $config[38]->config_value, // set maximum quality to 85%
                    '--strip-all',  // this strips out all text information such as comments and EXIF data
                    '--all-progressive'  // this will make sure the resulting image is a progressive one
                ]));
        }

        // Optimize Path (PNG)
        if ($extension == "png" || $extension == "PNG") {
            $optimizerChain = (new OptimizerChain)
                ->addOptimizer(new Pngquant([
                    '--force' // required parameter for this package
                ]));
        }

        // Optimize Path (SVG)
        if ($extension == "svg" || $extension == "SVG") {
            $optimizerChain = (new OptimizerChain)
                ->addOptimizer(new Svgo([
                    '--disable={cleanupIDs,removeStyleElement, removeViewBox}', // disabling because it is know to cause 
                    '--enable={removeTitle,collapseGroups,convertPathData,removeDimensions,removeStyleElement,removeScriptElement,removeEmptyContainers}',
                ]));
        }

        // Optimize Path (GIF)
        if ($extension == "gif" || $extension == "GIF") {
            $optimizerChain = (new OptimizerChain)
                ->addOptimizer(new Gifsicle([
                    '-b', // required parameter for this package
                    '-0' // this produces the slowest but best results
                ]));
        }
        // Optimize Path (WEBP)
        if ($extension == "webp" || $extension == "WEBP") {
            $optimizerChain = (new OptimizerChain)
                ->addOptimizer(new Cwebp([
                    '-m 6', // for the slowest compression method in order to get the best compression.
                    '-pass 10', // for maximizing the amount of analysis pass.
                    '-mt', // multithreading for some speed improvements.
                    '-q ' . $config[39]->config_value, //quality factor that brings the least noticeable changes.
                ]));
        }

        // Optimize
        $optimizerChain->optimize('storage/files/' . Auth::user()->id . '/optimize/' . $imageName);

        // Get optimize image
        $optimizeImage = file_get_contents('storage/files/' . Auth::user()->id . '/optimize/' . $imageName);

        // Upload wasabi S3
        $path = Storage::disk('wasabi')->put('files/' . Auth::user()->id . '/optimize/' . $imageName, $optimizeImage);
        $request->merge([
            'path' => $path
        ]);

        // Get optimize AWS path
        $AWSOptimizePath = $request->only('path', 'title');

        // Get optimize image size
        $OptimizeAWSPathSize = filesize($optimizePath . $imageName);

        // Save Optimer
        $optimer = new Optimer();
        $optimer->optimer_id = random_int(000000000000001, 99999999999999);
        $optimer->uploaded_by = Auth::user()->id;
        $optimer->disk = 'wasabi';
        $optimer->name = $originalname;
        $optimer->mime = $mimetype;
        $optimer->extension = $extension;
        $optimer->width = $width;
        $optimer->height = $height;
        $optimer->actual_image = Storage::disk('wasabi')->url('.') . "files/" . Auth::user()->id . '/' . $imageName;
        $optimer->optimized_image = Storage::disk('wasabi')->url('.') . "files/" . Auth::user()->id . '/optimize/' . $imageName;
        $optimer->cdn_url = Storage::disk('wasabi')->url('.') . "files/" . Auth::user()->id . '/optimize/' . $imageName;
        $optimer->actual_image_size = $imgsizes;
        $optimer->optimized_image_size = $OptimizeAWSPathSize;
        $optimer->save();

        $this->media_url = Storage::disk('wasabi')->url('.') . "files/" . Auth::user()->id . '/optimize/' . $imageName;

        return $this->media_url;
    }
}
