#include "fileexporter.h"

#include "cmark.h"
#include <QDir>
#include <QStandardPaths>
#include <QPrinter>
#include <QString>
#include <QFileDialog>
#include <QFile>
#include <QTextStream>
#include <QTextDocument>
#include <QTextDocumentWriter>
#include "configmanager.h"
#include "global/kaglobal.h"

FileExporter::FileExporter(QObject *parent) : QObject(parent) {}

bool FileExporter::showSaveDialog(int type, const QString& docName, const QString& docContent, QWidget *parent)
{
    QString suffix;
    QString filter;
    switch (type) {
    case DOWNLOAD_TXT:
        suffix = "txt";
        break;
    case DOWNLOAD_PDF:
        suffix = "pdf";
        break;
    case DOWNLOAD_MARKDOWN:
        suffix = "md";
        break;
    default:
        KyInfo() << "Unsupported download type! type=" << type;
        return false; // 返回空字符串标识失败
    }

    filter = QString("*.%1").arg(suffix);

    if (docName.isEmpty()) {
        KyInfo() << "docName is empty, use default name";
        return false;
    }
    if (docContent.isEmpty()) {
        KyInfo() << "docContent is empty! docName=" << docName;
        return false;
    }

    // 使用 Globals::getDefaultSavePath() 获取默认保存路径，与QML设置界面保持一致
    QString baseDir = Globals::getinstance()->getDefaultSavePath();

    QString presetFileName = QString("%1.%2").arg(docName).arg(suffix);
    QString presetPath = QDir(baseDir).filePath(presetFileName);

    QFileDialog fileDialog(parent);
    fileDialog.setAccessibleName("kylin-aiassistant_QFileDialog_fileDialog");
    fileDialog.setModal(true);
    fileDialog.setAcceptMode(QFileDialog::AcceptSave);
    fileDialog.setDirectory(baseDir);
    fileDialog.setNameFilter(filter);
    fileDialog.selectFile(presetPath);

    QString finalSavePath;
    if (fileDialog.exec() == QFileDialog::Accepted) {
        finalSavePath = fileDialog.selectedFiles().value(0);
        if (finalSavePath.isEmpty()) {
            KyInfo() << "User selected empty path! docName=" << docName;
            return false;
        }

        QFileInfo fileInfo(finalSavePath);
        if (fileInfo.suffix().isEmpty()) {
            finalSavePath += QString(".%1").arg(suffix);
            KyInfo() << "Auto add suffix, path=" << finalSavePath;
        }

        bool saveSuccess = exportFile(docContent, static_cast<DownloadType>(type), finalSavePath);
        if (saveSuccess) {
            KyInfo() << "Save file success! path=" << finalSavePath;
        } else {
            KyInfo() << "Save file failed! path=" << finalSavePath;
            return false;
        }
    } else {
        KyInfo() << "User canceled save dialog! docName=" << docName;
        finalSavePath.clear();
    }

    return true;
}

bool FileExporter::exportFile(const QString& content, DownloadType type, const QString& savePath)
{
    if (savePath.isEmpty() || content.isEmpty()) {
        emit exportFailed("Content or save path is empty");
        return false;
    }

    bool success = false;
    switch (type) {
    case DOWNLOAD_TXT:
        success = exportTXT(content, savePath);
        break;
    case DOWNLOAD_PDF:
        success = exportPDF(content, savePath);
        break;
    case DOWNLOAD_MARKDOWN:
        success = exportMarkdown(content, savePath);
        break;
    }

    return success;
}

bool FileExporter::exportTXT(const QString& content, const QString& path)
{
    QFile file(path);
    if (!file.open(QIODevice::WriteOnly | QIODevice::Text)) {
        return false;
    }

    QString plainText;
    // 检查内容是否是HTML格式
    if (content.contains("<!DOCTYPE") || content.contains("<html") || content.contains("<body")) {
        // 是HTML格式，需要转换为纯文本
        QTextDocument document;
        document.setHtml(content);
        plainText = document.toPlainText();
    } else {
        // 已经是纯文本格式，直接使用
        plainText = content;
    }

    QTextStream out(&file);
    out << plainText;
    file.close();

    return true;
}

bool FileExporter::exportDOCX(const QString& content, const QString& path)
{
    QString htmlContent = convertMarkDownToHtml(content);
    QTextDocument document;
    document.setHtml(htmlContent);

    QDateTime currentTime = QDateTime::currentDateTime();
    QString formattedTime = currentTime.toString("yyyyMMdd_hhmmss");
    QString fileName = "文档_" + formattedTime + ".html";
    QString tmpPath = "/tmp/" + fileName ;
    QTextDocumentWriter writer(tmpPath);
    writer.setFormat("html"); // 保存为 HTML 格式
    if (!writer.write(&document)) {
        KyInfo() << "Failed to save document.";
    } else {
        KyInfo() << "Document saved as HTML:" << tmpPath;
    }

    // 使用外部工具将 html 转换为 DOCX
    QProcess process;
    QStringList arguments;
#ifdef BUILD_KAIMING
    arguments << tmpPath << "-o" << path << "--reference-doc=/share/kylin-aiassistant/custom-reference.docx";
#else
    arguments << tmpPath << "-o" << path << "--reference-doc=/usr/share/kylin-aiassistant/custom-reference.docx";
#endif
    process.start("pandoc", arguments);
    process.waitForFinished();

    // 删除临时文件
    QFile::remove(tmpPath);
    return true;
}

bool FileExporter::exportPDF(const QString& htmlContent, const QString& path)
{
    QTextDocument document;
    document.setHtml(htmlContent);

    QPrinter printer(QPrinter::HighResolution);
    printer.setOutputFormat(QPrinter::PdfFormat);
    printer.setOutputFileName(path);

    document.print(&printer);

    return true;
}

bool FileExporter::exportMarkdown(const QString& content, const QString& path)
{
    QFile file(path);
    if (!file.open(QIODevice::WriteOnly | QIODevice::Text)) {
        return false;
    }

    QString markdownContent;
    // 检查内容是否是HTML格式
    if (content.contains("<!DOCTYPE") || content.contains("<html") || content.contains("<body")) {
        // 是HTML格式，需要转换为Markdown
        QTextDocument document;
        document.setHtml(content);
        markdownContent = document.toMarkdown();
    } else {
        // 已经是Markdown格式，直接使用
        markdownContent = content;
    }

    QTextStream out(&file);
    out << markdownContent;
    file.close();

    return true;
}

QString FileExporter::convertMarkDownToHtml(const QString &markDown)
{
    // 将markDown格式转换为html格式
    if(markDown.length() < 1){
        return "";
    }else{
        return markdownToHtml(markDown.toStdString());
    }
}

QString FileExporter::markdownToHtml(const std::string &markdown)
{
    // Convert the markdown text to HTML
    const char* markdownText = markdown.c_str();
    char* html = cmark_markdown_to_html(markdownText, strlen(markdownText), CMARK_OPT_DEFAULT);

    // Handle the conversion result
    std::string htmlStr(html);
    //cmark_mem_free(html);
    QString qStr = QString::fromStdString(htmlStr);
    return qStr;
}



