/**
 * This file is part of the Meeds project (https://meeds.io/).
 *
 * Copyright (C) 2020 - 2025 Meeds Association contact@meeds.io
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 3 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
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser 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.
 */
package org.exoplatform.portal;

import java.io.FileInputStream;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Locale;

import org.gatein.common.util.Tools;
import org.jibx.runtime.*;

import org.exoplatform.portal.config.model.*;
import org.exoplatform.portal.config.model.Page.PageSet;
import org.exoplatform.portal.pom.spi.portlet.Portlet;
import org.exoplatform.portal.pom.spi.portlet.PortletBuilder;

import junit.framework.TestCase;

/**
 * Thu, May 15, 2003 @
 *
 */
public class TestJIBXXmlMapping extends TestCase {

    public TestJIBXXmlMapping(String name) {
        super(name);
    }

    public void setUp() throws Exception {
    }

    public void testPageSetMapping() throws Exception {
        InputStream input = new FileInputStream(
                "src/test/resources/org/exoplatform/portal/config/conf/portal/classic/pages.xml");
        UnmarshalledObject<PageSet> obj = ModelUnmarshaller.unmarshall(PageSet.class, input);
        PageSet pages = obj.getObject();
        assertNotNull(pages);
        assertEquals(3, pages.getPages().size());
    }

    public void testPortalConfigMapping() throws Exception {
        InputStream input = new FileInputStream(
                "src/test/resources/org/exoplatform/portal/config/conf/portal/classic/portal.xml");
        UnmarshalledObject<PortalConfig> obj = ModelUnmarshaller.unmarshall(PortalConfig.class, input);
        PortalConfig portalConfig = obj.getObject();
        assertNotNull(portalConfig);
        assertEquals("classic", portalConfig.getName());
    }

    public void testNavigationMapping() throws Exception {
        InputStream input = new FileInputStream(
                "src/test/resources/org/exoplatform/portal/config/conf/portal/classic/navigation.xml");
        UnmarshalledObject<PageNavigation> obj = ModelUnmarshaller.unmarshall(PageNavigation.class, input);
        PageNavigation pageNavigation = obj.getObject();
        assertEquals("portal::classic::homepage", pageNavigation.getFragment().getNode("home").getPageReference());

        input = new FileInputStream(
                "src/test/resources/org/exoplatform/portal/mop/management/navigation-empty.xml");
        obj = ModelUnmarshaller.unmarshall(PageNavigation.class, input);
        pageNavigation = obj.getObject();
        assertEquals(PageNavigation.UNDEFINED_PRIORITY, pageNavigation.getPriority());

        /*
         * IMarshallingContext mctx = bfact.createMarshallingContext(); mctx.setIndent(2); mctx.marshalDocument(obj, "UTF-8",
         * null, new FileOutputStream("target/navigation.xml"));
         *
         * obj = uctx.unmarshalDocument(new FileInputStream("target/navigation.xml"), null); assertEquals(PageNavigation.class,
         * obj.getClass());
         */
    }

    public void testPortletApplicationMapping() throws Exception {
        IBindingFactory bfact = BindingDirectory.getFactory(PortalConfig.class);
        IUnmarshallingContext uctx = bfact.createUnmarshallingContext();
        @SuppressWarnings("unchecked")
        Application app = (Application) uctx.unmarshalDocument(new FileInputStream(
                "src/test/resources/jibx/portlet-application.xml"), null);
        TransientApplicationState portletState = (TransientApplicationState) app.getState();
        assertNotNull(portletState);
        assertEquals("web/BannerPortlet", portletState.getContentId());
        Portlet preferences = (Portlet) portletState.getContentState();
        assertEquals(new PortletBuilder().add("template", "template_value").build(), preferences);
    }

    public void testSimpleNavigationMapping() throws Exception {
        UnmarshalledObject<PageNavigation> obj = ModelUnmarshaller.unmarshall(PageNavigation.class, new FileInputStream(
                "src/test/resources/jibx/simple-navigation.xml"));
        ;
        PageNavigation nav = obj.getObject();
        assertEquals(Version.V_1_6, obj.getVersion());

        //
        PageNode bar = nav.getFragment().getNode("bar");
        assertEquals("bar_label", bar.getLabel());
        ArrayList<LocalizedString> barLabels = bar.getLabels();
        assertNotNull(barLabels);
        assertEquals(1, barLabels.size());
        assertEquals("bar_label", barLabels.get(0).getValue());
        assertEquals(null, barLabels.get(0).getLang());
        assertEquals(null, bar.getLabels().getExtended(Locale.ENGLISH));
    }

    public void testExtendedNavigationMapping() throws Exception {
        UnmarshalledObject<PageNavigation> obj = ModelUnmarshaller.unmarshall(PageNavigation.class, new FileInputStream(
                "src/test/resources/jibx/extended-navigation.xml"));
        PageNavigation nav = obj.getObject();
        assertEquals(Version.V_1_6, obj.getVersion());

        //
        PageNode foo = nav.getFragment().getNode("foo");
        assertEquals("foo_label", foo.getLabel());
        ArrayList<LocalizedString> fooLabels = foo.getLabels();
        assertNotNull(fooLabels);
        assertEquals(3, fooLabels.size());
        assertEquals("foo_label_en", fooLabels.get(0).getValue());
        assertEquals(Locale.ENGLISH, fooLabels.get(0).getLang());
        assertEquals("foo_label", fooLabels.get(1).getValue());
        assertEquals(null, fooLabels.get(1).getLang());
        assertEquals("foo_label_fr", fooLabels.get(2).getValue());
        assertEquals(Locale.FRENCH, fooLabels.get(2).getLang());
        assertEquals(Tools.toSet(Locale.ENGLISH, Locale.FRENCH), foo.getLabels().getExtended(Locale.ENGLISH).keySet());
        assertEquals(Tools.toSet(Locale.ENGLISH, Locale.FRENCH, Locale.GERMAN), foo.getLabels().getExtended(Locale.GERMAN)
                .keySet());

        //
        PageNode bar = nav.getFragment().getNode("bar");
        assertEquals("bar_label", bar.getLabel());
        ArrayList<LocalizedString> barLabels = bar.getLabels();
        assertNotNull(barLabels);
        assertEquals(1, barLabels.size());
        assertEquals("bar_label", barLabels.get(0).getValue());
        assertEquals(null, barLabels.get(0).getLang());
        assertEquals(null, bar.getLabels().getExtended(Locale.ENGLISH));

        //
        PageNode juu = nav.getFragment().getNode("juu");
        assertEquals(null, juu.getLabel());
        ArrayList<LocalizedString> juuLabels = juu.getLabels();
        assertNotNull(juuLabels);
        assertEquals(3, juuLabels.size());
        assertEquals("juu_label_en", juuLabels.get(0).getValue());
        assertEquals(Locale.ENGLISH, juuLabels.get(0).getLang());
        assertEquals("juu_label_fr", juuLabels.get(1).getValue());
        assertEquals(Locale.FRENCH, juuLabels.get(1).getLang());
        assertEquals("juu_label_fr_FR", juuLabels.get(2).getValue());
        assertEquals(Locale.FRANCE, juuLabels.get(2).getLang());
    }

    public void testNavigationFragment() throws Exception {
        UnmarshalledObject<PageNavigation> obj = ModelUnmarshaller.unmarshall(PageNavigation.class, new FileInputStream(
                "src/test/resources/jibx/fragment-navigation.xml"));
        PageNavigation nav = obj.getObject();
        assertEquals(Version.V_1_6, obj.getVersion());

        //
        ArrayList<NavigationFragment> fragments = nav.getFragments();
        assertNotNull(fragments);
        assertEquals(1, fragments.size());
        NavigationFragment fragment = fragments.get(0);
        assertEquals("foo", fragment.getParentURI());
        assertEquals(1, fragment.getNodes().size());
        PageNode bar = fragment.getNode("bar");
        assertNotNull(bar);
    }
}
