org.libreplan.web.common.Util.java Source code

Java tutorial

Introduction

Here is the source code for org.libreplan.web.common.Util.java

Source

/*
 * This file is part of LibrePlan
 *
 * Copyright (C) 2009-2010 Fundacin para o Fomento da Calidade Industrial e
 *                         Desenvolvemento Tecnolxico de Galicia
 * Copyright (C) 2010-2012 Igalia, S.L.
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Affero 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 Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

package org.libreplan.web.common;

import static org.libreplan.web.I18nHelper._;

import java.io.IOException;
import java.math.BigDecimal;
import java.text.DateFormat;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Set;

import javax.servlet.http.HttpServletResponse;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.joda.time.DateTime;
import org.joda.time.LocalDate;
import org.joda.time.LocalTime;
import org.libreplan.business.common.BaseEntity;
import org.libreplan.business.common.Configuration;
import org.libreplan.business.common.Registry;
import org.springframework.web.context.ContextLoaderListener;
import org.zkoss.bind.DefaultBinder;
import org.zkoss.ganttz.util.ComponentsFinder;
import org.zkoss.image.AImage;
import org.zkoss.image.Image;
import org.zkoss.util.Locales;
import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.Execution;
import org.zkoss.zk.ui.Executions;
import org.zkoss.zk.ui.event.EventListener;
import org.zkoss.zk.ui.event.Events;
import org.zkoss.zk.ui.event.InputEvent;
import org.zkoss.zkplus.databind.AnnotateDataBinder;
import org.zkoss.zkplus.databind.DataBinder;
import org.zkoss.zul.Bandbox;
import org.zkoss.zul.Button;
import org.zkoss.zul.Checkbox;
import org.zkoss.zul.Combobox;
import org.zkoss.zul.Comboitem;
import org.zkoss.zul.Datebox;
import org.zkoss.zul.Decimalbox;
import org.zkoss.zul.Hbox;
import org.zkoss.zul.Intbox;
import org.zkoss.zul.Label;
import org.zkoss.zul.Radio;
import org.zkoss.zul.Row;
import org.zkoss.zul.Textbox;
import org.zkoss.zul.Timebox;
import org.zkoss.zul.Column;

/**
 * Utilities class.
 * <br />
 * @author scar Gonzlez Fernndez <ogonzalez@igalia.com>
 * @author Manuel Rego Casasnovas <mrego@igalia.com>
 * @author Susana Montes Pedreira <smontes@wirelessgalicia.com>
 * @author Vova Perebykivskyi <vova@libreplan-enterprise.com>
 */
public class Util {

    private static final Log LOG = LogFactory.getLog(Util.class);

    /**
     * Special chars from {@link DecimalFormat} class.
     */
    private static final String[] DECIMAL_FORMAT_SPECIAL_CHARS = { "0", ",", ".", "\u2030", "%", "#", ";", "-" };

    private static final String RELOADED_COMPONENTS_ATTR = Util.class.getName() + ":" + "reloaded";

    private static final ThreadLocal<Boolean> ignoreCreateBindings = new ThreadLocal<Boolean>() {
        protected Boolean initialValue() {
            return false;
        }
    };

    /**
     * Static object that contains logo image.
     */
    public static Image logo;

    private Util() {
    }

    /**
     * Forces to reload the bindings of the provided components if there is an associated {@link DefaultBinder}.
     *
     * @param toReload
     *            the components to reload
     */
    public static void reloadBindings(Component... toReload) {
        reloadBindings(ReloadStrategy.FORCE, toReload);
    }

    public enum ReloadStrategy {
        /**
         * If the {@link DefaultBinder} exists the bindings are reloaded no matter what.
         */
        FORCE,

        /**
         * Once the bindings for a component have been manually loaded in one
         * request, subsequent calls for reload the bindings of the same
         * component or descendants using this strategy are ignored.
         */
        ONE_PER_REQUEST;

        public static boolean isForced(ReloadStrategy reloadStrategy) {
            return reloadStrategy == ReloadStrategy.FORCE;
        }
    }

    /**
     * Reload the bindings of the provided components if there is an associated
     * {@link DefaultBinder} and the {@link ReloadStrategy} allows it.
     *
     * @param toReload
     *            the components to reload
     */
    public static void reloadBindings(ReloadStrategy reloadStrategy, Component... toReload) {
        reloadBindings(ReloadStrategy.isForced(reloadStrategy), toReload);
    }

    private static void reloadBindings(boolean forceReload, Component... toReload) {
        for (Component reload : toReload) {

            // TODO resolve deprecated
            DataBinder binder = Util.getBinder(reload);

            if (binder != null && (forceReload || notReloadedInThisRequest(reload))) {
                binder.loadComponent(reload);
                markAsReloadedForThisRequest(reload);
            }
        }
    }

    private static boolean notReloadedInThisRequest(Component reload) {
        return !getReloadedComponents(reload).contains(reload);
    }

    private static Set<Component> getReloadedComponents(Component component) {
        Execution execution = component.getDesktop().getExecution();

        @SuppressWarnings("unchecked")
        Set<Component> result = (Set<Component>) execution.getAttribute(RELOADED_COMPONENTS_ATTR);

        if (result == null) {
            result = new HashSet<>();
            execution.setAttribute(RELOADED_COMPONENTS_ATTR, result);
        }

        return result;
    }

    private static void markAsReloadedForThisRequest(Component component) {
        Set<Component> reloadedComponents = getReloadedComponents(component);
        reloadedComponents.add(component);
        reloadedComponents.addAll(getAllDescendants(component));
    }

    private static void markAsNotReloadedForThisRequest(Component component) {
        Set<Component> reloadedComponents = getReloadedComponents(component);
        reloadedComponents.remove(component);
        reloadedComponents.removeAll(getAllDescendants(component));
    }

    @SuppressWarnings("unchecked")
    private static List<Component> getAllDescendants(Component component) {
        List<Component> result = new ArrayList<>();
        for (Component each : component.getChildren()) {
            result.add(each);
            result.addAll(getAllDescendants(each));
        }

        return result;
    }

    public static void saveBindings(Component... toReload) {
        for (Component reload : toReload) {
            /* TODO resolve deprecated */
            DataBinder binder = Util.getBinder(reload);

            if (binder != null) {
                binder.saveComponent(reload);
            }
        }
    }

    /** TODO resolve deprecated */
    public static DataBinder getBinder(Component component) {
        return (DataBinder) component.getAttribute("binder", true);
    }

    public static void executeIgnoringCreationOfBindings(Runnable action) {
        try {
            ignoreCreateBindings.set(true);
            action.run();
        } finally {
            ignoreCreateBindings.set(false);
        }
    }

    public static void createBindingsFor(Component result) {
        if (ignoreCreateBindings.get()) {
            return;
        }

        /* TODO resolve deprecated */
        AnnotateDataBinder binder = new AnnotateDataBinder(result, true);

        /*
         * Before it was:
         * setAttribute("binder", binder, true)
         * And it is not correct. Because API changed ( even more before it was setVariable("binder", binder, true) ).
         * Boolean value for setAttribute() means recursive actions, but in setVariable() it was not so.
         * And after, it still was calling method setAttribute() with (attr1, attr2, !booleanValue).
         */
        result.setAttribute("binder", binder, false);

        markAsNotReloadedForThisRequest(result);
    }

    /**
     * Generic interface to represent a class with a typical get method.
     *
     * @author Manuel Rego Casasnovas <mrego@igalia.com>
     * @param <T>
     *           The type of the variable to be returned.
     */
    @FunctionalInterface
    public interface Getter<T> {
        /**
         * Typical get method that returns a variable.
         * @return A variable of type <T>.
         */
        T get();
    }

    /**
     * Generic interface to represent a class with a typical set method.
     *
     * @author Manuel Rego Casasnovas <mrego@igalia.com>
     * @param <T>
     *            The type of the variable to be set.
     */
    @FunctionalInterface
    public interface Setter<T> {
        /**
         * Typical set method to store a variable.
         * @param value
         *            A variable of type <T> to be set.
         */
        void set(T value);
    }

    /**
     * Binds a {@link Textbox} with a {@link Getter}. The {@link Getter} will be
     * used to get the value that is going to be showed in the {@link Textbox}.
     *
     * @param textBox
     *            The {@link Textbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Textbox} bound
     */
    public static Textbox bind(Textbox textBox, Getter<String> getter) {
        textBox.setValue(getter.get());
        textBox.setDisabled(true);
        return textBox;
    }

    /**
     * Binds a {@link Textbox} with a {@link Getter}. The {@link Getter} will be
     * used to get the value that is going to be showed in the {@link Textbox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Textbox}.
     *
     * @param textBox
     *            The {@link Textbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Textbox} bound
     */
    public static Textbox bind(final Textbox textBox, final Getter<String> getter, final Setter<String> setter) {
        textBox.setValue(getter.get());
        textBox.addEventListener(Events.ON_CHANGE, event -> {
            InputEvent newInput = (InputEvent) event;
            String value = newInput.getValue();
            setter.set(value);
            textBox.setValue(getter.get());
        });

        return textBox;
    }

    /**
     * Binds a {@link Textbox} with a {@link Getter}. The {@link Getter} will be
     * used to get the value that is going to be showed in the {@link Textbox}.
     *
     * @param comboBox
     *            The {@link Combobox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Combobox} bound
     */
    public static Combobox bind(Combobox comboBox, Getter<Comboitem> getter) {
        comboBox.setSelectedItem(getter.get());
        comboBox.setDisabled(true);
        return comboBox;
    }

    /**
     * Binds a {@link Textbox} with a {@link Getter}. The {@link Getter} will be
     * used to get the value that is going to be showed in the {@link Textbox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Textbox}.
     *
     * @param comboBox
     *            The {@link Combobox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Combobox} bound
     */
    public static Combobox bind(final Combobox comboBox, final Getter<Comboitem> getter,
            final Setter<Comboitem> setter) {

        comboBox.setSelectedItem(getter.get());

        comboBox.addEventListener("onSelect", event -> {
            setter.set(comboBox.getSelectedItem());
            comboBox.setSelectedItem(getter.get());
        });

        return comboBox;
    }

    /**
     * Binds a {@link Intbox} with a {@link Getter}. The {@link Getter} will be
     * used to get the value that is going to be showed in the {@link Intbox}
     *
     * @param intBox
     *            The {@link Intbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Intbox} bound
     */
    public static Intbox bind(Intbox intBox, Getter<Integer> getter) {
        intBox.setValue(getter.get());
        intBox.setDisabled(true);

        return intBox;
    }

    /**
     * Binds a {@link Intbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Intbox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Intbox}.
     *
     * @param intBox
     *            The {@link Intbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Intbox} bound
     */
    public static Intbox bind(final Intbox intBox, final Getter<Integer> getter, final Setter<Integer> setter) {
        intBox.setValue(getter.get());

        intBox.addEventListener(Events.ON_CHANGE, event -> {
            InputEvent newInput = (InputEvent) event;
            String value = newInput.getValue().trim();

            if (value.isEmpty()) {
                value = "0";
            }

            setter.set(Integer.valueOf(value));
            intBox.setValue(getter.get());
        });

        return intBox;
    }

    /**
     * Binds a {@link Datebox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Datebox}.
     *
     * @param dateBox
     *            The {@link Datebox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Datebox} bound
     */
    public static Datebox bind(final Datebox dateBox, final Getter<Date> getter) {
        dateBox.setValue(getter.get());
        dateBox.setDisabled(true);

        return dateBox;
    }

    /**
     * Binds a {@link Datebox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Datebox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Datebox}.
     *
     * @param dateBox
     *            The {@link Datebox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Datebox} bound
     */
    public static Datebox bind(final Datebox dateBox, final Getter<Date> getter, final Setter<Date> setter) {
        dateBox.setValue(getter.get());

        dateBox.addEventListener(Events.ON_CHANGE, event -> {
            setter.set(dateBox.getValue());
            dateBox.setValue(getter.get());
        });

        return dateBox;
    }

    /**
     * Binds a {@link Timebox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Timebox}.
     *
     * @param timeBox
     *            The {@link Timebox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Timebox} bound
     */
    public static Timebox bind(final Timebox timeBox, final Getter<Date> getter) {
        timeBox.setValue(getter.get());
        timeBox.setDisabled(true);

        return timeBox;
    }

    /**
     * Binds a {@link Timebox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Timebox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Timebox}.
     *
     * @param timeBox
     *            The {@link Timebox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Timebox} bound
     */
    public static Timebox bind(final Timebox timeBox, final Getter<Date> getter, final Setter<Date> setter) {
        timeBox.setValue(getter.get());

        timeBox.addEventListener(Events.ON_CHANGE, event -> {
            setter.set(timeBox.getValue());
            timeBox.setValue(getter.get());
        });

        return timeBox;
    }

    /**
     * Binds a {@link Decimalbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Decimalbox}.
     *
     * @param decimalBox
     *            The {@link Decimalbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Decimalbox} bound
     */
    public static Decimalbox bind(final Decimalbox decimalBox, final Getter<BigDecimal> getter) {
        decimalBox.setValue(getter.get());
        decimalBox.setDisabled(true);

        return decimalBox;
    }

    /**
     * Binds a {@link Decimalbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Decimalbox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Decimalbox}.
     *
     * @param decimalBox
     *            The {@link Decimalbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Decimalbox} bound
     */
    public static Decimalbox bind(final Decimalbox decimalBox, final Getter<BigDecimal> getter,
            final Setter<BigDecimal> setter) {

        decimalBox.setValue(getter.get());

        decimalBox.addEventListener(Events.ON_CHANGE, event -> {
            setter.set(decimalBox.getValue());
            decimalBox.setValue(getter.get());
        });

        return decimalBox;
    }

    /**
     * Binds a {@link Checkbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Checkbox}.
     *
     * @param decimalBox
     *            The {@link Checkbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Checkbox} bound
     */
    public static Checkbox bind(final Checkbox checkBox, final Getter<Boolean> getter) {
        checkBox.setChecked(getter.get());
        checkBox.setDisabled(true);
        return checkBox;
    }

    /**
     * Binds a {@link Checkbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Checkbox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Checkbox}.
     *
     * @param checkBox
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Checkbox} bound
     */
    public static Checkbox bind(final Checkbox checkBox, final Getter<Boolean> getter,
            final Setter<Boolean> setter) {
        checkBox.setChecked(getter.get());

        checkBox.addEventListener(Events.ON_CHECK, event -> {
            setter.set(checkBox.isChecked());
            checkBox.setChecked(getter.get());
        });
        return checkBox;
    }

    /**
     * Binds a {@link Checkbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Checkbox}.
     *
     * @param radio
     *            The {@link Radio} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Radio} bound
     */
    public static Radio bind(final Radio radio, final Getter<Boolean> getter) {
        radio.setSelected(getter.get());
        radio.setDisabled(true);
        return radio;
    }

    /**
     * Binds a {@link Radio} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Radio}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Radio}.
     *
     * @param radio
     *            The {@link Radio} to be bound
     * @param getter
     *            he {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Radio} bound
     */
    public static Radio bind(final Radio radio, final Getter<Boolean> getter, final Setter<Boolean> setter) {
        radio.setSelected(getter.get());

        radio.addEventListener(Events.ON_CHECK, event -> {
            setter.set(radio.isSelected());
            radio.setChecked(getter.get());
        });

        return radio;
    }

    /**
     * Binds a {@link Bandbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Bandbox}.
     *
     * @param bandBox
     *            The {@link Bandbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @return The {@link Bandbox} bound
     */
    public static Bandbox bind(Bandbox bandBox, Getter<String> getter) {
        bandBox.setValue(getter.get());
        bandBox.setDisabled(true);
        return bandBox;
    }

    /**
     * Binds a {@link Bandbox} with a {@link Getter}.
     * The {@link Getter} will be used to get the value that is going to be showed in the {@link Bandbox}.
     * The {@link Setter} will be used to store the value inserted by the user in the {@link Bandbox}.
     *
     * @param bandBox
     *            The {@link Bandbox} to be bound
     * @param getter
     *            The {@link Getter} interface that will implement a get method.
     * @param setter
     *            The {@link Setter} interface that will implement a set method.
     * @return The {@link Bandbox} bound
     */
    public static Bandbox bind(final Bandbox bandBox, final Getter<String> getter, final Setter<String> setter) {
        bandBox.setValue(getter.get());

        bandBox.addEventListener(Events.ON_CHANGE, event -> {
            InputEvent newInput = (InputEvent) event;
            String value = newInput.getValue();
            setter.set(value);
            bandBox.setValue(getter.get());
        });

        return bandBox;
    }

    /**
     * Creates an edit button with class and icon already set.
     *
     * @param eventListener
     *            A event listener for {@link Events#ON_CLICK}
     * @return An edit {@link Button}
     */
    public static Button createEditButton(EventListener eventListener) {
        Button result = new Button();
        result.setTooltiptext(_("Edit"));
        result.setSclass("icono");
        result.setImage("/common/img/ico_editar1.png");
        result.setHoverImage("/common/img/ico_editar.png");

        result.addEventListener(Events.ON_CLICK, eventListener);

        return result;
    }

    /**
     * Creates a remove button with class and icon already set.
     *
     * @param eventListener
     *            A event listener for {@link Events#ON_CLICK}
     * @return A remove {@link Button}
     */
    public static Button createRemoveButton(EventListener eventListener) {
        Button result = new Button();
        result.setTooltiptext(_("Remove"));
        result.setSclass("icono");
        result.setImage("/common/img/ico_borrar1.png");
        result.setHoverImage("/common/img/ico_borrar.png");

        result.addEventListener(Events.ON_CLICK, eventListener);

        return result;
    }

    @SuppressWarnings("unchecked")
    public static <T extends Component> T findComponentAt(Component container, String idOfComponentToBeFound) {
        return (T) container.getFellow(idOfComponentToBeFound);
    }

    public interface ICreation<T extends Component> {
        T createAt(Component parent);
    }

    public static <T extends Component> T findOrCreate(Component container, Class<T> klassOfComponentToFind,
            ICreation<T> ifNotFound) {
        @SuppressWarnings("unchecked")
        List<T> existent = ComponentsFinder.findComponentsOfType(klassOfComponentToFind, container.getChildren());
        if (!existent.isEmpty()) {
            return existent.get(0);
        }

        return ifNotFound.createAt(container);
    }

    /**
     * It removes all listeners registered for eventName and adds the new listener.
     * It's ensured that the only listener left in the component for events of name eventName is uniqueListener.
     *
     * @param component
     * @param eventName
     * @param uniqueListener
     */
    public static void ensureUniqueListener(Component component, String eventName, EventListener uniqueListener) {
        ensureUniqueListeners(component, eventName, uniqueListener);
    }

    /**
     * It removes all listeners registered for eventName and adds the new listeners.
     * It's ensured that the only listeners left in the component for events of name eventName is uniqueListeners.
     *
     * @param component
     * @param eventName
     * @param uniqueListeners
     *            new listeners to add
     */
    public static void ensureUniqueListeners(Component component, String eventName,
            EventListener... uniqueListeners) {
        // TODO Replace deprecated method
        Iterator<?> listenerIterator = component.getListenerIterator(eventName);

        while (listenerIterator.hasNext()) {
            listenerIterator.next();
            listenerIterator.remove();
        }
        for (EventListener each : uniqueListeners) {
            component.addEventListener(eventName, each);
        }
    }

    public static void setSort(Column column, String sortSpec) {
        try {
            column.setSort(sortSpec);
        } catch (Exception e) {
            LOG.error("failed to set sort property for: " + column + " with: " + sortSpec, e);
        }
    }

    /**
     * Gets currency symbol from {@link Configuration} object.
     *
     * @return Currency symbol configured in the application
     */
    public static String getCurrencySymbol() {
        return Registry.getTransactionService().runOnReadOnlyTransaction(
                () -> Registry.getConfigurationDAO().getConfiguration().getCurrencySymbol());
    }

    /**
     * Returns the value using the money format, that means, 2 figures for the
     * decimal part and concatenating the currency symbol from {@link Configuration} object.
     */
    public static String addCurrencySymbol(BigDecimal value) {
        BigDecimal valueToReturn = value == null ? BigDecimal.ZERO : value;
        DecimalFormat decimalFormat = (DecimalFormat) DecimalFormat.getInstance();
        decimalFormat.applyPattern(getMoneyFormat());

        return decimalFormat.format(valueToReturn);
    }

    /**
     * Gets money format for a {@link Decimalbox} using 2 figures for the
     * decimal part and concatenating the currency symbol.
     *
     * @return Format for a {@link Decimalbox} <code>###.##</code> plus currency symbol
     */
    public static String getMoneyFormat() {
        return "###.## " + escapeDecimalFormatSpecialChars(getCurrencySymbol());
    }

    /**
     * Escapes special chars used in {@link DecimalFormat} to define the number
     * format that appear in the <code>currencySymbol</code>.
     */
    private static String escapeDecimalFormatSpecialChars(String currencySymbol) {
        String stringToReturn = currencySymbol;

        for (String specialChar : DECIMAL_FORMAT_SPECIAL_CHARS) {
            stringToReturn = stringToReturn.replace(specialChar, "'" + specialChar + "'");
        }

        return stringToReturn;
    }

    /**
     * Appends the <code>text</code> as a {@link Label} into the specified {@link Row}.
     */
    public static void appendLabel(Row row, String text) {
        row.appendChild(new Label(text));
    }

    /**
     * Appends a edit button and a remove button to the {@link Row} inside a
     * {@link Hbox} and adds the <code>ON_CLICK</code> event over the
     * {@link Row} for the edit operation.<br />
     *
     * The edit button will call the <code>editButtonListener</code> when
     * clicked and the remove button the <code>removeButtonListener</code>.
     * <br />
     *
     * If <code>removeButtonListener</code> is null, it only adds the edit
     * button and the <code>ON_CLICK</code> event.
     *
     * @return An array of 1 or 2 positions (depending if
     *         <code>removeButtonListener</code> param is or not
     *         <code>null</code>) with the edit and remove buttons. As maybe you
     *         need to disable any of them depending on different situations.
     */
    public static Button[] appendOperationsAndOnClickEvent(Row row, EventListener editButtonListener,
            EventListener removeButtonListener) {

        Button[] buttons = new Button[removeButtonListener != null ? 2 : 1];

        Hbox hbox = new Hbox();
        buttons[0] = Util.createEditButton(editButtonListener);
        hbox.appendChild(buttons[0]);

        if (removeButtonListener != null) {
            buttons[1] = Util.createRemoveButton(removeButtonListener);
            hbox.appendChild(buttons[1]);
        }
        row.appendChild(hbox);

        row.addEventListener(Events.ON_CLICK, editButtonListener);

        return buttons;
    }

    /**
     * Checks if the <code>entity</code> is contained in the provided <code>list</code>.
     */
    public static boolean contains(List<? extends BaseEntity> list, BaseEntity entity) {
        for (BaseEntity each : list) {
            if (each.getId() != null && entity.getId() != null && each.getId().equals(entity.getId())) {
                return true;
            }
        }

        return false;
    }

    /**
     * Gets the {@link HttpServletResponse} from the current {@link Execution}
     * and uses the method {@link HttpServletResponse#sendError(int)} with the
     * code {@link HttpServletResponse#SC_FORBIDDEN}.
     */
    public static void sendForbiddenStatusCodeInHttpServletResponse() {
        try {
            HttpServletResponse response = (HttpServletResponse) Executions.getCurrent().getNativeResponse();
            response.sendError(HttpServletResponse.SC_FORBIDDEN);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * Format specific <code>date</code> using the {@link DateFormat#DEFAULT} format and showing only date without time.
     */
    public static String formatDate(Date date) {
        return date == null ? ""
                : DateFormat.getDateInstance(DateFormat.DEFAULT, Locales.getCurrent()).format(date);
    }

    /**
     * Format specific <code>date</code> using the {@link DateFormat#DEFAULT} format and showing both date and time.
     */
    public static String formatDateTime(Date dateTime) {
        return dateTime == null ? ""
                : DateFormat.getDateTimeInstance(DateFormat.DEFAULT, DateFormat.DEFAULT, Locales.getCurrent())
                        .format(dateTime);
    }

    /**
     * Format specific <code>date</code> using the {@link DateFormat#DEFAULT} format and showing only date without time.
     */
    public static String formatDate(DateTime dateTime) {
        return dateTime == null ? "" : formatDate(dateTime.toDate());
    }

    /**
     * Format specific <code>date</code> using the {@link DateFormat#DEFAULT} format and showing only date without time.
     */
    public static String formatDate(LocalDate date) {
        return date == null ? "" : formatDate(date.toDateTimeAtStartOfDay());
    }

    /**
     * Format specific <code>time</code> using the {@link DateFormat#SHORT} format and showing only the time.
     */
    public static String formatTime(Date time) {
        return time == null ? "" : DateFormat.getTimeInstance(DateFormat.SHORT, Locales.getCurrent()).format(time);
    }

    /**
     * Format specific <code>time</code> using the {@link DateFormat#SHORT} format and showing only the time.
     */
    public static String formatTime(LocalTime time) {
        return time == null ? "" : formatTime(time.toDateTimeToday().toDate());
    }

    /**
     * Setter of {@link Util#logo}.
     * Will trigger after uploading new image.
     *
     * @param name
     */
    static void setLogoFromTarget(String name) {
        try {
            logo = new AImage(
                    ContextLoaderListener.getCurrentWebApplicationContext().getResource(name).getFile().getPath());

        } catch (IOException ignored) {
        }
    }

    /**
     * Setter of {@link Util#logo}.
     * But it will trigger only if {@link Util#logo} is null.
     * So it is just kind of attempt to find logo with known data.
     */
    static void findLogo() {
        String name = Registry.getConfigurationDAO().getConfigurationWithReadOnlyTransaction().getCompanyLogoURL();

        try {
            if (!name.isEmpty()) {
                logo = new AImage(ContextLoaderListener.getCurrentWebApplicationContext().getResource(name)
                        .getFile().getPath());
            }
        } catch (IOException ignored) {
        }
    }

}