<?php

class Edocman_Lite_Public {

    private $plugin_name;
    private $version;
    private $database;

    public function __construct( $plugin_name, $version ) {
        $this->plugin_name = $plugin_name;
        $this->version     = $version;
        $this->database    = new Edocman_Lite_Database();
    }

    public function enqueue_styles() {
        wp_enqueue_style( $this->plugin_name, EDOCMAN_LITE_PLUGIN_URL . 'public/assets/css/public.css', array(), $this->version, 'all' );
    }

    public function enqueue_scripts() {
        wp_enqueue_script( $this->plugin_name, EDOCMAN_LITE_PLUGIN_URL . 'assets/js/public.js', array( 'jquery' ), $this->version, true );
        wp_localize_script( $this->plugin_name, 'edocman_lite_public', array(
            'ajax_url'       => admin_url( 'admin-ajax.php' ),
            'confirm_delete' => __( 'Are you sure you want to delete this document?', 'edocman-lite' ),
            'error_delete'   => __( 'Could not delete document.', 'edocman-lite' ),
        ) );
    }

    public function init_shortcodes() {
        add_shortcode( 'edocman_lite_categories',      array( $this, 'shortcode_categories' ) );
        add_shortcode( 'edocman_lite_documents',       array( $this, 'shortcode_documents' ) );
        add_shortcode( 'edocman_lite_document',        array( $this, 'shortcode_document_detail' ) );
        add_shortcode( 'edocman_lite_upload_document', array( $this, 'shortcode_upload_document' ) );
        add_shortcode( 'edocman_lite_my_documents',    array( $this, 'shortcode_my_documents' ) );
    }

    public function shortcode_categories( $atts ) {
        $atts = shortcode_atts( array(
            'parent_id'        => 0,
            'show_description' => 1,
            'show_image'       => 1,
        ), $atts );

        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        $cat_id = isset( $_GET['cat_id'] ) ? absint( wp_unslash( $_GET['cat_id'] ) ) : 0;

        if ( $cat_id > 0 ) {
            // ✅ Verify the category exists and is published before rendering.
            $requested_category = $this->database->get_category( $cat_id );
            if ( ! $requested_category || empty( $requested_category->published ) ) {
                return '<p>' . esc_html__( 'Category not found.', 'edocman-lite' ) . '</p>';
            }

            return $this->shortcode_documents( array(
                'category_id'      => $cat_id,
                'show_description' => 1,
                'limit'            => 50,
            ) );
        }

        $categories = $this->database->get_categories( $atts['parent_id'], true );

        ob_start();
        include EDOCMAN_LITE_PLUGIN_PATH . 'public/partials/categories-list.php';
        return ob_get_clean();
    }

    public function shortcode_documents( $atts ) {
        $atts = shortcode_atts( array(
            'category_id'      => 0,
            'limit'            => 10,
            'show_description' => 1,
        ), $atts );

        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        $cat_id = isset( $_GET['cat_id'] ) ? absint( wp_unslash( $_GET['cat_id'] ) ) : 0;

        if ( $cat_id > 0 ) {
            // ✅ Verify the category is published before using it.
            $requested_category = $this->database->get_category( $cat_id );
            if ( ! $requested_category || empty( $requested_category->published ) ) {
                return '<p>' . esc_html__( 'Category not found.', 'edocman-lite' ) . '</p>';
            }
            $category_id = $cat_id;
        } else {
            $category_id = intval( $atts['category_id'] );
        }

        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        $doc_id = isset( $_GET['doc_id'] ) ? absint( wp_unslash( $_GET['doc_id'] ) ) : 0;
        if ( $doc_id > 0 ) {
            return $this->shortcode_document_detail( array() );
        }

        $limit     = intval( $atts['limit'] );
        $documents = $this->database->get_documents( $category_id, true, $limit );
        $category  = null;

        if ( $category_id > 0 ) {
            $category = $this->database->get_category( $category_id );
        }

        ob_start();
        include EDOCMAN_LITE_PLUGIN_PATH . 'public/partials/documents-list.php';
        return ob_get_clean();
    }

    public function shortcode_document_detail( $atts ) {
        $atts = shortcode_atts( array(
            'id' => 0,
        ), $atts );

        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        $document_id = isset( $_GET['doc_id'] ) ? absint( wp_unslash( $_GET['doc_id'] ) ) : intval( $atts['id'] );

        if ( $document_id <= 0 ) {
            return '<p>' . esc_html__( 'Document not found.', 'edocman-lite' ) . '</p>';
        }

        $document = $this->database->get_document( $document_id );

        if ( ! $document || $document->published != 1 ) {
            return '<p>' . esc_html__( 'Document not found.', 'edocman-lite' ) . '</p>';
        }

        // Increment hits.
        $this->database->increment_hits( $document_id );

        // Pass database instance to template.
        $edocman_lite_database = $this->database; // phpcs:ignore WordPress.NamingConventions.PrefixAllGlobals.NonPrefixedVariableFound

        ob_start();
        include EDOCMAN_LITE_PLUGIN_PATH . 'public/partials/document-detail.php';
        return ob_get_clean();
    }

    public function handle_download() {
        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        if ( ! isset( $_GET['edocman_lite_download'] ) || ! isset( $_GET['doc_id'] ) ) {
            return;
        }

        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        $document_id = absint( wp_unslash( $_GET['doc_id'] ) );
        $nonce       = isset( $_GET['nonce'] ) ? sanitize_text_field( wp_unslash( $_GET['nonce'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended

        if ( empty( $nonce ) || ! wp_verify_nonce( $nonce, 'edocman_lite_download_' . $document_id ) ) {
            wp_die( esc_html__( 'Security check failed.', 'edocman-lite' ) );
        }

        $document = $this->database->get_document( $document_id );

        if ( ! $document || $document->published != 1 ) {
            wp_die( esc_html__( 'Document not found.', 'edocman-lite' ) );
        }

        $allow_download = Edocman_Lite_Helper::get_config( 'allow_download', 1 );
        if ( ! $allow_download ) {
            wp_die( esc_html__( 'Download is not allowed.', 'edocman-lite' ) );
        }

        // Increment downloads.
        $this->database->increment_downloads( $document_id );

        // Resolve file path, respecting hierarchical folders.
        $file_path = $this->resolve_file_path( $document );

        if ( ! file_exists( $file_path ) ) {
            wp_die( esc_html__( 'File not found.', 'edocman-lite' ) );
        }

        // Force download.
        header( 'Content-Description: File Transfer' );
        header( 'Content-Type: application/octet-stream' );
        header( 'Content-Disposition: attachment; filename="' . sanitize_file_name( $document->original_filename ) . '"' );
        header( 'Content-Transfer-Encoding: binary' );
        header( 'Expires: 0' );
        header( 'Cache-Control: must-revalidate' );
        header( 'Pragma: public' );
        header( 'Content-Length: ' . filesize( $file_path ) );

        global $wp_filesystem;
        if ( ! function_exists( 'WP_Filesystem' ) ) {
            require_once ABSPATH . 'wp-admin/includes/file.php';
        }
        WP_Filesystem();
        // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
        echo $wp_filesystem->get_contents( $file_path );
        exit;
    }

    public function handle_document_view() {
        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        if ( ! isset( $_GET['edocman_lite_view'] ) || ! isset( $_GET['doc_id'] ) ) {
            return;
        }

        // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        $document_id = absint( wp_unslash( $_GET['doc_id'] ) );
        $nonce       = isset( $_GET['nonce'] ) ? sanitize_text_field( wp_unslash( $_GET['nonce'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended

        if ( empty( $nonce ) || ! wp_verify_nonce( $nonce, 'edocman_lite_view_' . $document_id ) ) {
            wp_die( esc_html__( 'Security check failed.', 'edocman-lite' ) );
        }

        $document = $this->database->get_document( $document_id );

        if ( ! $document || $document->published != 1 ) {
            wp_die( esc_html__( 'Document not found.', 'edocman-lite' ) );
        }

        $allow_view = Edocman_Lite_Helper::get_config( 'allow_view', 1 );
        if ( ! $allow_view ) {
            wp_die( esc_html__( 'View is not allowed.', 'edocman-lite' ) );
        }

        // Increment hits.
        $this->database->increment_hits( $document_id );

        // Resolve file path, respecting hierarchical folders.
        $file_path = $this->resolve_file_path( $document );

        if ( ! file_exists( $file_path ) ) {
            wp_die( esc_html__( 'File not found.', 'edocman-lite' ) );
        }

        // Get mime type.
        $finfo     = finfo_open( FILEINFO_MIME_TYPE );
        $mime_type = finfo_file( $finfo, $file_path );
        finfo_close( $finfo );

        // Display file.
        header( 'Content-Type: ' . $mime_type );
        header( 'Content-Disposition: inline; filename="' . sanitize_file_name( $document->original_filename ) . '"' );
        header( 'Content-Length: ' . filesize( $file_path ) );

        global $wp_filesystem;
        if ( ! function_exists( 'WP_Filesystem' ) ) {
            require_once ABSPATH . 'wp-admin/includes/file.php';
        }
        WP_Filesystem();
        // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
        echo $wp_filesystem->get_contents( $file_path );
        exit;
    }

    // -------------------------------------------------------------------------
    // Shortcodes: Upload Document & My Documents
    // -------------------------------------------------------------------------

    public function shortcode_upload_document( $atts ) {
        if ( ! is_user_logged_in() ) {
            return '<p>' . esc_html__( 'Please login to upload documents.', 'edocman-lite' ) . '</p>';
        }

        $message      = '';
        $message_type = 'success';

        // Handle POST submission.
        if ( isset( $_POST['edl_submit'] ) && isset( $_POST['edocman_lite_upload_nonce'] ) ) {
            if ( ! wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['edocman_lite_upload_nonce'] ) ), 'edocman_lite_upload_document' ) ) {
                $message      = esc_html__( 'Security check failed. Please try again.', 'edocman-lite' );
                $message_type = 'error';
            } else {
                $result = $this->process_frontend_upload();
                if ( $result['success'] ) {
                    $message      = esc_html__( 'Document uploaded successfully. It will be reviewed before publishing.', 'edocman-lite' );
                    $message_type = 'success';
                } else {
                    $message      = $result['message'];
                    $message_type = 'error';
                }
            }
        }

        $categories = $this->database->get_categories( 0, true );

        ob_start();
        include EDOCMAN_LITE_PLUGIN_PATH . 'public/partials/upload-document.php';
        return ob_get_clean();
    }

    public function shortcode_my_documents( $atts ) {
        if ( ! is_user_logged_in() ) {
            return '<p>' . esc_html__( 'Please login to view your documents.', 'edocman-lite' ) . '</p>';
        }

        $message      = '';
        $message_type = 'success';

        $documents = $this->database->get_documents_by_user( get_current_user_id() );

        ob_start();
        include EDOCMAN_LITE_PLUGIN_PATH . 'public/partials/my-documents.php';
        return ob_get_clean();
    }

    // -------------------------------------------------------------------------
    // AJAX handlers for front-end document management
    // -------------------------------------------------------------------------

    public function ajax_delete_my_document() {
        $document_id = isset( $_POST['document_id'] ) ? intval( $_POST['document_id'] ) : 0;
        $nonce       = isset( $_POST['nonce'] ) ? sanitize_text_field( wp_unslash( $_POST['nonce'] ) ) : '';

        if ( ! is_user_logged_in() ) {
            wp_send_json_error( array( 'message' => __( 'You must be logged in.', 'edocman-lite' ) ) );
        }

        if ( ! wp_verify_nonce( $nonce, 'edocman_lite_delete_my_doc_' . $document_id ) ) {
            wp_send_json_error( array( 'message' => __( 'Security check failed.', 'edocman-lite' ) ) );
        }

        if ( $document_id <= 0 ) {
            wp_send_json_error( array( 'message' => __( 'Invalid document ID.', 'edocman-lite' ) ) );
        }

        $document = $this->database->get_document( $document_id );

        if ( ! $document ) {
            wp_send_json_error( array( 'message' => __( 'Document not found.', 'edocman-lite' ) ) );
        }

        // Only allow the owner (or an admin) to delete.
        if ( intval( $document->created_user_id ) !== get_current_user_id() && ! current_user_can( 'manage_options' ) ) {
            wp_send_json_error( array( 'message' => __( 'Permission denied.', 'edocman-lite' ) ) );
        }

        // Delete the physical file.
        if ( ! empty( $document->filename ) ) {
            $file_path = $this->resolve_file_path( $document );
            if ( file_exists( $file_path ) ) {
                wp_delete_file( $file_path );
            }
        }

        $result = $this->database->delete_document( $document_id );

        if ( $result ) {
            wp_send_json_success( array( 'message' => __( 'Document deleted successfully.', 'edocman-lite' ) ) );
        } else {
            wp_send_json_error( array( 'message' => __( 'Could not delete document.', 'edocman-lite' ) ) );
        }
    }

    // -------------------------------------------------------------------------
    // Private helpers
    // -------------------------------------------------------------------------

    /**
     * Resolve the absolute file path for a document.
     *
     * The `filename` column now stores the relative path from `documents_path`
     * (e.g. "documents/file.pdf" or "cat/subcat/file.pdf"), so we simply
     * concatenate it with the configured documents_path.
     *
     * @param object $document Document object from DB.
     * @return string Absolute file path.
     */
    private function resolve_file_path( $document ) {
        $documents_path = Edocman_Lite_Helper::get_config( 'documents_path' );

        return rtrim( $documents_path, '/' ) . '/' . ltrim( $document->filename, '/' );
    }

    /**
     * Process a front-end document upload.
     *
     * @return array Array with 'success' bool and optional 'message' string.
     */
    private function process_frontend_upload() {
        // phpcs:ignore WordPress.Security.NonceVerification.Missing
        $title       = isset( $_POST['edl_title'] )       ? sanitize_text_field( wp_unslash( $_POST['edl_title'] ) )           : '';
        // phpcs:ignore WordPress.Security.NonceVerification.Missing
        $description = isset( $_POST['edl_description'] ) ? sanitize_textarea_field( wp_unslash( $_POST['edl_description'] ) ) : '';
        // phpcs:ignore WordPress.Security.NonceVerification.Missing
        $category_id = isset( $_POST['edl_category_id'] ) ? intval( $_POST['edl_category_id'] )                                : 0;

        if ( empty( $title ) ) {
            return array( 'success' => false, 'message' => esc_html__( 'Title is required.', 'edocman-lite' ) );
        }

        // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.InputNotValidated
        if ( ! isset( $_FILES['edl_file'] ) || $_FILES['edl_file']['error'] !== UPLOAD_ERR_OK ) {
            return array( 'success' => false, 'message' => esc_html__( 'Please select a file to upload.', 'edocman-lite' ) );
        }

        // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.InputNotSanitized
        $file           = $_FILES['edl_file'];
        $documents_path = Edocman_Lite_Helper::get_config( 'documents_path' );
        $allowed_raw    = Edocman_Lite_Helper::get_config( 'allowed_file_types', 'pdf,doc,docx' );
        $allowed_types  = ! empty( $allowed_raw ) ? array_map( 'trim', explode( ',', $allowed_raw ) ) : array();
        $max_size_mb    = intval( Edocman_Lite_Helper::get_config( 'max_file_size', 10 ) );
        $max_size_bytes = $max_size_mb * 1024 * 1024;

        // Validate file extension.
        $ext             = strtolower( pathinfo( $file['name'], PATHINFO_EXTENSION ) );
        $default_allowed = 'pdf,doc,docx,xls,xlsx,ppt,pptx,txt,zip,rar';
        if ( empty( $allowed_types ) ) {
            $allowed_types = array_map( 'trim', explode( ',', $default_allowed ) );
        }
        if ( ! in_array( $ext, $allowed_types, true ) ) {
            return array( 'success' => false, 'message' => __( 'File type not allowed.', 'edocman-lite' ) );
        }

        // Validate file size.
        if ( $file['size'] > $max_size_bytes ) {
            return array(
                'success' => false,
                'message' => sprintf(
                    /* translators: maximum allowed file size in MB */
                    __( 'File exceeds the maximum allowed size of %d MB.', 'edocman-lite' ),
                    $max_size_mb
                ),
            );
        }

        // Determine upload directory.
        $hierarchical_folders = Edocman_Lite_Helper::get_config( 'hierarchical_folders', '0' );
        $relative_dir         = 'documents';

        if ( $hierarchical_folders === '1' && $category_id > 0 ) {
            $category = $this->database->get_category( $category_id );
            if ( $category && ! empty( $category->path ) ) {
                $relative_dir = trim( $category->path, '/' );
            }
        }

        $upload_dir = rtrim( $documents_path, '/' ) . '/' . $relative_dir . '/';

        if ( ! file_exists( $upload_dir ) ) {
            wp_mkdir_p( $upload_dir );
        }

        $original_filename = basename( $file['name'] );
        $filename          = Edocman_Lite_Helper::sanitize_filename( $original_filename );
        $file_size         = $file['size'];

        // Use wp_handle_upload() instead of move_uploaded_file() for WordPress compliance.
        if ( ! function_exists( 'wp_handle_upload' ) ) {
            require_once ABSPATH . 'wp-admin/includes/file.php';
        }

        $target_dir  = untrailingslashit( $upload_dir );
        $target_name = $filename;
        $dir_filter  = static function( $uploads ) use ( $target_dir ) {
            $uploads['path']   = $target_dir;
            $uploads['url']    = '';
            $uploads['subdir'] = '';
            $uploads['error']  = false;
            return $uploads;
        };

        add_filter( 'upload_dir', $dir_filter );

        $upload_result = wp_handle_upload(
            $file,
            array(
                'test_form'                => false,
                'unique_filename_callback' => static function( $dir, $name, $ext ) use ( $target_name ) {
                    return $target_name;
                },
            )
        );

        remove_filter( 'upload_dir', $dir_filter );

        if ( ! isset( $upload_result['file'] ) || isset( $upload_result['error'] ) ) {
            return array( 'success' => false, 'message' => __( 'Could not save the uploaded file.', 'edocman-lite' ) );
        }

        // Store the relative path in filename column.
        $stored_filename = $relative_dir . '/' . $filename;

        $alias = Edocman_Lite_Helper::create_alias( $title );

        $data = array(
            'title'             => $title,
            'alias'             => $alias,
            'filename'          => $stored_filename,
            'original_filename' => $original_filename,
            'short_description' => '',
            'description'       => $description,
            'published'         => 0,
            'file_size'         => Edocman_Lite_Helper::format_file_size( $file_size ),
        );

        $doc_id = $this->database->save_document( $data );

        if ( $doc_id && $category_id > 0 ) {
            $this->database->link_document_to_category( $doc_id, $category_id, true );
        }

        return array( 'success' => true );
    }
}
