/******************************************************************************
 *
 * Project:  OpenCPN
 *
 ***************************************************************************
 *   Copyright (C) 2019 Alec Leamas                                        *
 *                                                                         *
 *   This program is free software; you can redistribute it and/or modify  *
 *   it under the terms of the GNU General Public License as published by  *
 *   the Free Software Foundation; either version 2 of the License, or     *
 *   (at your option) any later version.                                   *
 *                                                                         *
 *   This program is distributed in the hope that it will be useful,       *
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
 *   GNU General Public License for more details.                          *
 *                                                                         *
 *   You should have received a copy of the GNU General Public License     *
 *   along with this program; if not, write to the                         *
 *   Free Software Foundation, Inc.,                                       *
 *   51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,  USA.         *
 ***************************************************************************
 */

#include <cstring>

#include <wx/log.h>


#if defined(__MINGW32__) && defined(Yield)
#undef Yield                 // from win.h, conflicts with mingw headers
#endif

#include "catalog_parser.h"
#include "ocpn_utils.h"
#include "catalog_handler.h"
#include "Downloader.h"
#include "pugixml.hpp"

#include <fstream>
#include <sstream>
#include <iterator>

bool ParseCatalog(const std::string xml, catalog_ctx* ctx)
{
    bool ok = true;
    PluginMetadata *plugin = 0;

    pugi::xml_document doc;
    doc.load_string(xml.c_str());
    
    pugi::xml_node elements = doc.child("plugins");
    for (pugi::xml_node element = elements.first_child(); element; element = element.next_sibling()){
        if( !strcmp(element.name(), "version") && ctx->version == "" ){
            ctx->version = ocpn::trim(element.first_child().value());
        }
        else if (strcmp(element.name(), "date")  == 0 && ctx->date == "") {
            ctx->date = ocpn::trim(element.first_child().value());
        }
        else if (strcmp(element.name(), "meta-url")  == 0 ) {
            ctx->meta_url = ocpn::trim(element.first_child().value());
        }
        else if( !strcmp(element.name(), "plugin") ){
            if (ctx->meta_url != "") {
                ctx->meta_urls.push_back(ctx->meta_url);
                ctx->meta_url = "";
            }
            else{
                if(plugin)
                    ctx->plugins.push_back(*plugin);
                plugin = new PluginMetadata;
            }

            for (pugi::xml_node plugin_element = element.first_child(); plugin_element; plugin_element = plugin_element.next_sibling()){
                if (strcmp(plugin_element.name(), "meta-url") == 0) {
                    auto url = ocpn::trim(plugin_element.first_child().value());
                    ctx->meta_url = url;
                }
                else if (strcmp(plugin_element.name(), "name") == 0) {
                    plugin->name = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "version") == 0) {
                    plugin->version = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "release") == 0) {
                    plugin->release = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "summary") == 0) {
                    plugin->summary = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "api_version") == 0) {
                    plugin->api_version = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "author") == 0) {
                    plugin->author = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "description") == 0) {
                    plugin->description = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "git-commit") == 0) {
                    plugin->git_commit = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "git-date") == 0) {
                    plugin->git_date = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "source") == 0) {
                    plugin->source = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "tarball-url") == 0) {
                    plugin->tarball_url = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "info-url") == 0) {
                    plugin->info_url = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "target") == 0) {
                    plugin->target = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "target-version") == 0) {
                    plugin->target_version = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "target-arch") == 0) {
                    plugin->target_arch = ocpn::trim(plugin_element.first_child().value());
                } else if (strcmp(plugin_element.name(), "open-source") == 0) {
                    plugin->openSource = ocpn::trim(plugin_element.first_child().value()) == "yes";
                }
            }
        }
    }

    // capture last plugin
    if(plugin)
        ctx->plugins.push_back(*plugin);
    else{
        if (ctx->meta_url != "") {
            ctx->meta_urls.push_back(ctx->meta_url);
            ctx->meta_url = "";
        }
    }

 
    return true;
}