/**
 * File:    PluginProperties.java
 * Created: 11.03.2006
 *
 *
/*******************************************************************************
 * Copyright (c) 2005-2011
 * University of Augsburg, Germany <www.ds-lab.org>
 *
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *    Markus Bauer, Programming distributed Systems Lab, University of Augsburg 
 *    	- initial API and implementation
 *    Mickael Istria, Open Wide, Lyon, France
 *      - Use NLS and static fields
 *    Marc Blachon, Bull SAS
 *      - adding extension point for the factoryRegistry
 *******************************************************************************/

package org.eclipse.jwt.meta;

import java.util.MissingResourceException;

import org.eclipse.emf.ecore.EAttribute;
import org.eclipse.emf.ecore.EClass;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.ecore.EStructuralFeature;
import org.eclipse.osgi.util.NLS;

/**
 * Provied access the <code>plugin.properties</code> file.
 * 
 * <p>
 * All keys in the <code>plugin.properties</code> are access with static
 * members. Some properties need parameters and they are represented by member
 * functions. They may also encapsulate a simple logic to find the right
 * property based on the parameters.
 * </p>
 * 
 * @version $Id: PluginProperties.java,v 1.4 2009-11-26 15:16:51 chsaad Exp $
 * @author Markus Bauer (markusbauer@users.sourceforge.net), Programming
 *         distributed Systems Lab, University of Augsburg, Germany,
 *         www.ds-lab.org
 * @since 0.6.0
 */
public class PluginProperties extends NLS
{

	// "plugin" references the plugin[_locale].properties file path
	// at the root of the jwt-we bundle.
	private static final String BUNDLE_NAME = "plugin"; //$NON-NLS-1$

	static
	{
		NLS.initializeMessages(BUNDLE_NAME, PluginProperties.class);
	}


	/**
	 * Returns the value associated to a property. Prefer using directly the
	 * field for this property when possible
	 * 
	 * @param string
	 * @return
	 */
	public static String getString(String key)
	{
		try
		{
			return (String) PluginProperties.class.getField(key).get(null);
		}
		catch (Exception ex)
		{
			return "!" + key + "!"; //$NON-NLS-1$ //$NON-NLS-2$
		}
	}


	/**
	 * Returns the value from the <code>plugin.properties</code> identified by a
	 * key.
	 * 
	 * <p>
	 * It the resource is not available a {@link MissingResourceException} is
	 * thrown.
	 * </p>
	 * 
	 * @param key
	 *            The key of the property.
	 * @return The value of the key.
	 * @throws MissingResourceException
	 *             If the resource can not be found.
	 */
	public static String getStringExpectMissing(String key)
			throws MissingResourceException
	{
		try
		{
			return (String) PluginProperties.class.getField(key).get(null);
		}
		catch (Exception ex)
		{
			throw new MissingResourceException(
					"Cannot find value associated to key [" + key + "]", PluginProperties.class.getName(), key); //$NON-NLS-1$ //$NON-NLS-2$
		}
	}


	/**
	 * Returns the value from the <code>plugin.properties</code> identified by a
	 * key and filled with a parameter.
	 * 
	 * <p>
	 * It the resource is not available a {@link MissingResourceException} is
	 * thrown.
	 * </p>
	 * 
	 * @param key
	 *            The key of the property.
	 * @param data
	 *            The parameter.
	 * @return The value of the key.
	 * @throws MissingResourceException
	 *             If the resource can not be found.
	 */
	public static String getStringExpectMissing(String key, Object[] data)
			throws MissingResourceException
	{
		return bind(getStringExpectMissing(key), data);
	}


	/**
	 * Returns a simple representing name of the type of an object.
	 * 
	 * @param object
	 *            The object, may be <code>null</code>.
	 * @return The name of the type.
	 */
	public static String getModelTypeName(Object object)
	{
		if (object == null)
		{
			return "null"; //$NON-NLS-1$
		}
		if (object instanceof EClass)
		{
			return ((EClass) object).getName();
		}
		if (object instanceof Class)
		{
			return ((Class<?>) object).getSimpleName();
		}
		if (object instanceof EObject)
		{
			return ((EObject) object).eClass().getName();
		}
		return object.getClass().getSimpleName();
	}

	//
	//
	//
	//
	//

	// //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
	//
	// Plugin data
	//

	public static String plugin_Name; // JWT Workflow Editor
	public static String plugin_ProviderName; // http://www.eclipse.org/jwt
	public static String pluginName; // JWT
	public static String providerName; // http://www.eclipse.org/jwt

	public static String category_id; // Java Workflow Tooling

	// //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
	//
	// Model
	//

	public static String model_DefaultPackage_name; // <default>
	public static String model_PackageName_separator; // /

	// {0}: model type.
	public static String model_Unnamed_name; // <?>

	//
	// Types:
	//
	// Name for the model and attribute types. The default is the typename
	// itself.
	//
	// Example:
	// model_Foo_type ; // FooType
	// model_Bar_datatype ; // Bar data type
	//

	public static String model_ModelElement_type; // Model Element
	public static String model_Comment_type; // Comment
	public static String model_NamedElement_type; // Named Element
	public static String model_Package_type; // Package
	public static String model_Model_type; // Model
	public static String model_PackageableElement_type; // Packageable Element
	public static String model_ReferenceableElement_type; // Referenceable
	// Element

	public static String model_Scope_type; // Scope
	public static String model_Activity_type; // Activity
	public static String model_StructuredActivityNode_type; // Embedded
	// Subprocess
	public static String model_ActivityLinkNode_type; // Subprocess Call
	public static String model_ActivityNode_type; // Activity Node
	public static String model_ActivityEdge_type; // Activity Edge
	public static String model_GuardSpecification_type; // Guard Specification
	public static String model_Guard_type; // Guard
	public static String model_ExecutableNode_type; // Executable Node
	public static String model_ControlNode_type; // Control Node
	public static String model_Action_type; // Action
	public static String model_InitialNode_type; // Initial Node
	public static String model_FinalNode_type; // Final Node
	public static String model_DecisionNode_type; // Decision Node
	public static String model_ForkNode_type; // Fork Node
	public static String model_JoinNode_type; // Join Node
	public static String model_MergeNode_type; // Merge Node
	public static String model_ParameterMapping_type; // Parameter Mapping

	public static String model_Event_type; // Event
	public static String model_EventHandler_type; // Event Handler

	public static String model_PrimitiveType_type; // Primitive Type
	public static String model_StringType_type; // String
	public static String model_IntegerType_type; // Integer

	public static String model_Function_type; // Function

	public static String model_Role_type; // Role
	public static String model_OrganisationUnit_type; // Organisation Unit

	public static String model_Application_type; // Application
	public static String model_WebServiceApplication_type; // WebService
	// Application
	public static String model_ApplicationType_type; // Application Type

	public static String model_Data_type; // Data
	public static String model_DataType_type; // Data Type
	public static String model_Parameter_type; // Parameter
	public static String model_InputParameter_type; // Input Parameter
	public static String model_OutputParameter_type; // Output Parameter
	public static String model_DataMapping_type; // Data Mapping
	public static String model_InformationType_type; // Information Type

	public static String model_GraphicalElement_type; // Graphical Element

	//
	// Features:
	//
	// Name and description for features of model elements.
	//
	// The default name for a feature is the name of the feature.
	//
	// The default description is taken from the property:
	// model_Default_feature_description
	// where:
	// {0}: Name of the type.
	// {1}: Name of the feature
	//
	//
	// Examples:
	// model_Foo_bar_name ; // bar of Foo
	// model_Foo_bar_description ; // The bar of the Foo.
	// model_Default_feature_description ; // The {0} of the {1}
	//

	// unknown feature
	public static String model_Unknown_feature_name; // unknown

	public static String model_ModelElement_ownedComment_name; // Comment
	public static String model_Comment_text_name; // Text

	public static String model_NamedElement_name_name; // Name
	public static String model_NamedElement_icon_name; // Icon

	public static String model_Package_subpackages_name; // Subpackages
	public static String model_Package_superpackage_name; // Superpackage
	public static String model_Package_elements_name; // Elements

	public static String model_Model_author_name; // Author
	public static String model_Model_version_name; // Version
	public static String model_Model_description_name; // Description
	public static String model_Model_fileversion_name; // File format version

	public static String model_PackageableElement_package_name; // Package

	public static String model_Scope_nodes_name; // Nodes
	public static String model_Scope_edges_name; // Transitions

	public static String model_Activity_eventHandler_name; // Event Handler
	public static String model_Activity_totalexecutiontime_name; // Total Time
	// (in
	// seconds)

	public static String model_ActivityNode_in_name; // Ingoing Transitions
	public static String model_ActivityNode_out_name; // Outgoing Transitions

	public static String model_ActivityLinkNode_linksto_name; // Links to
	public static String model_ActivityLinkNode_uses_name; // Mapped Parameters

	public static String model_ActivityEdge_source_name; // Source Node
	public static String model_ActivityEdge_target_name; // Target Node
	public static String model_ActivityEdge_guardConditions_name; // Guard
	// Conditions

	public static String model_GuardSpecification_data_name; // Data
	public static String model_GuardSpecification_attribute_name; // Attribute
	public static String model_GuardSpecification_operation_name; // Operation
	public static String model_GuardSpecification_value_name; // Value
	public static String model_GuardSpecification_Description_name; // Description
	public static String model_GuardSpecification_subSpecificationConnector_name; // Sub
	// specification
	// connector

	public static String model_Guard_textualdescription_name; // Textual
	// Description
	public static String model_Guard_shortdescription_name; // Short Description

	public static String model_Action_performedBy_name; // Performed by Role
	public static String model_Action_executedBy_name; // Executed by
	// Application
	public static String model_Action_realizes_name; // Realizes
	public static String model_Action_inputs_name; // Input Data
	public static String model_Action_outputs_name; // Output Data
	public static String model_Action_mappings_name; // Mappings
	public static String model_Action_targetexecutiontime_name; // Target Time
	// (in
	// seconds)

	public static String model_Function_subfunctions_name; // Subfunctions

	public static String model_Role_performedBy_name; // Performed by
	public static String model_OrganisationUnit_subUnit_name; // Subunit
	public static String model_OrganisationUnit_belongsTo_name; // Belongs to

	public static String model_ParameterMapping_source_name; // Element in this
	// process
	public static String model_ParameterMapping_target_name; // Element in
	// subprocess

	public static String model_Application_type_name; // Type
	public static String model_Application_jarArchive_name; // JAR Archive
	public static String model_Application_javaClass_name; // Java Class
	public static String model_Application_method_name; // Method
	public static String model_Application_input_name; // Input Parameter
	public static String model_Application_output_name; // Output Parameter

	public static String model_WebServiceApplication_interface_name; // Interface
	public static String model_WebServiceApplication_operation_name; // Operation

	public static String model_Data_value_name; // Value
	public static String model_Data_dataType_name; // Data Type
	public static String model_Data_informationType_name; // Information Type
	public static String model_Data_parameters_name; // Parameters
	public static String model_DataMapping_boundParameter_name; // Bound
	// Parameter
	public static String model_DataMapping_parameter_name; // Parameter

	public static String model_GraphicalElement_Location_name; // Location
	public static String model_GraphicalElement_Size_name; // Size

	public static String model_Parameter_name_name; // Name
	public static String model_Parameter_value_name; // Value

	// default description
	public static String model_Default_feature_description; // The {1} of the
	// {0}

	public static String model_ModelElement_ownedComment_description; // The
	// comment
	// of
	// the element
	public static String model_Comment_text_description; // The text of the
	// command
	public static String model_NamedElement_name_description; // The name of the
	// element
	public static String model_NamedElement_icon_description; // An icon
	// representing
	// the
	// element
	public static String model_Package_subpackages_description; // The
	// subpackages
	public static String model_Package_superpackage_description; // The
	// superpackages
	public static String model_Package_elements_description; // The Elements in
	// the
	// package
	public static String model_Model_author_description; // The author
	public static String model_Model_version_description; // The version
	public static String model_Model_description_description; // The description
	public static String model_PackageableElement_package_description; // The
	// package
	// in
	// that the
	// element is
	// contained
	public static String model_Scope_nodes_description; // Nodes in the scope
	public static String model_Scope_edges_description; // Edges in the scope
	// scope
	public static String model_Activity_eventHandler_description; // Event
	// handler
	// of the
	// activity
	public static String model_Activity_totalexecutiontime_description; // Time
	// that
	// the
	// whole activity
	// should take
	// max.
	public static String model_ActivityNode_in_description; // Ingoing
	// transitions of
	// the
	// node
	public static String model_ActivityNode_out_description; // Outgoing
	// transitions
	// of
	// the node
	public static String model_ActivityEdge_source_description; // Source node
	// of the
	// transition
	public static String model_ActivityEdge_target_description; // Target node
	// of the
	// transition
	public static String model_ActivityEdge_guardConditions_description; // Guard
	// conditions
	// of the edge
	public static String model_GuardSpecification_data_description; // The data
	// that is
	// compared
	public static String model_GuardSpecification_attribute_description; // The
	// attibute
	// of the data
	// to compare
	public static String model_GuardSpecification_operation_description; // The
	// operation
	// used to
	// compare
	public static String model_GuardSpecification_value_description; // The
	// value
	// to
	// compare the
	// data with
	public static String model_Guard_textualdescription_description; // The
	// description
	// of
	// the boolean
	// term
	public static String model_Guard_shortdescription_description; // A short
	// description
	// of the term
	public static String model_Action_performedBy_description; // The role the
	// action is
	// performed by
	public static String model_Action_executedBy_description; // The application
	// the
	// action is executed by
	public static String model_Action_realizes_description; // The function this
	// action
	// realizes
	public static String model_Action_inputs_description; // Input Data
	public static String model_Action_outputs_description; // Output Data
	public static String model_Action_mappings_description; // Mappings of data
	public static String model_Action_targetexecutiontime_description; // Time
	// that
	// this
	// action should
	// take max.
	public static String model_Function_subfunctions_description; // The
	// subfunctions
	// of
	// the function

	public static String model_Role_performedBy_description; // The organisation
	// unit this
	// role it performed by
	public static String model_OrganisationUnit_subUnit_description; // The
	// subunits
	// of
	// the
	// organisation
	// unit
	public static String model_OrganisationUnit_belongsTo_description; // The
	// organisation
	// unit this
	// organisation
	// unit belongs to

	public static String model_Application_type_description; // The type of the
	// application
	public static String model_Application_jarArchive_description; // The JAR
	// Archive
	// where this
	// application is
	// located
	public static String model_Application_javaClass_description; // The java
	// Class in
	// the
	// JAR archive
	public static String model_Application_method_description; // The method to
	// call
	public static String model_Application_input_description; // The input
	// Parameter
	public static String model_Application_output_description; // The output
	// Parameter

	public static String model_WebServiceApplication_type_description; // The
	// type
	// of
	// the
	// WebServiceApplication
	public static String model_WebServiceApplication_jarArchive_description; // The
	// JAR
	// Archive
	// where
	// this
	// WebServiceApplication
	// is
	// located
	public static String model_WebServiceApplication_javaClass_description; // The
	// java
	// Class in
	// the JAR
	// archive
	public static String model_WebServiceApplication_interface_description; // The
	// interface
	public static String model_WebServiceApplication_operation_description; // The
	// operation
	// to call

	public static String model_Data_value_description; // The value of the data
	public static String model_Data_dataType_description; // The data type of
	// this data
	public static String model_Data_informationType_description; // The
	// information
	// Type
	// of the data
	public static String model_Data_parameters_description; // The parameters of
	// the data
	public static String model_DataMapping_boundParameter_description; // The
	// bound
	// Parameter
	public static String model_DataMapping_parameter_description; // The
	// parameter

	public static String model_GraphicalElement_Location_description; // The
	// location
	// of
	// the element
	public static String model_GraphicalElement_Size_description; // The size of
	// the

	public static String model_Parameter_name_description; // The name of the
	// parameter
	public static String model_Parameter_value_description; // A standard value
	// for
	// calling a method for the
	// first time

	//
	// Text:
	//
	// Describes how the text of a model element is created.
	// {0}: Name of the type of the model.
	// {1},{2},...: The features of the model.
	//
	// Example: model_Foo_text ; // Type: {0}, feature: {1}
	//

	public static String model_ModelElement_text; // {0}
	public static String model_NamedElement_text; // {0}: {1}
	public static String model_Comment_text; // {0}: {1}
	public static String model_ActivityEdge_text; // {0} ({1} -> {2})
	public static String model_GuardSpecification_text; // {0}: {1} {2} {3}
	public static String model_Guard_text; // {0}: {1}
	public static String model_Parameter_text; // {0}: {1}
	public static String model_DataMapping_text; // {0}

	// //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
	//
	// Commands
	//

	// {0}: Name of child
	// {1}: Name of feature
	// {2}: Name of owner
	public static String command_CreateChild_text; // {0}
	public static String command_CreateChild_description; // Create a new child
	// of type
	// {0} for the {1} feature of
	// the selected {2}.
	public static String command_CreateSibling_description; // Create a new
	// sibling of
	// type {0} for the selected
	// {2}, under the {1} feature
	// of their parent.
	public static String command_CreateChild_tooltip; // Create New {0} Under
	// {1} Feature

	// {0}: Name of deleted type
	public static String command_Delete_label; // delete {0}
	public static String command_Create_label; // create {0}

	public static String command_Rename_label; // rename

	//
	//
	//
	//
	//
	//
	public static String editor_StillReferenced_title; // Element(s) still
	// referenced
	public static String editor_StillReferenced_message; // Cannot be removed.
	// The
	// following elements are
	// still referenced: {0}
	public static String editor_StillReferencedDelete_message; // The following
	// elements
	// are still referenced:
	// {0} Should all
	// references to this
	// element be deleted?
	public static String editor_StillReferencedConfirmation_message; // All
	// references
	// to
	// these elements
	// as well as the
	// elements
	// themselves will
	// be deleted. Are
	// you sure?
	public static String editor_DeleteActivities_title;
	public static String editor_DeleteActivities_message;


	// The

	/**
	 * The name of the type of a model.
	 * 
	 * @param model
	 *            The model or the type of the model.
	 * @return A name of the type.
	 */
	public static String model_type(Object model)
	{
		if (model instanceof EAttribute)
		{
			return model_datatype((EAttribute) model);
		}

		String modelType = getModelTypeName(model);
		try
		{
			return getStringExpectMissing("model_" + modelType + "_type"); //$NON-NLS-1$ //$NON-NLS-2$
		}
		catch (MissingResourceException e)
		{
		}

		return modelType;
	}


	/**
	 * The name of an attribute.
	 * 
	 * @param attribute
	 *            The attribute.
	 * @return A name of the type.
	 */
	public static String model_datatype(EAttribute attribute)
	{
		String name = attribute.getName();
		try
		{
			return getStringExpectMissing("model_" + name + "_datatype"); //$NON-NLS-1$ //$NON-NLS-2$
		}
		catch (MissingResourceException e)
		{
		}

		return name;
	}


	/**
	 * The name of a feature.
	 * 
	 * @param feature
	 *            The feature.
	 * @return The name of a feature.
	 */
	public static String model_feature_name(Object feature)
	{
		if (feature instanceof EStructuralFeature)
		{
			String featureName = ((EStructuralFeature) feature).getName();
			String modelType = getModelTypeName(((EStructuralFeature) feature)
					.getEContainingClass());

			try
			{
				return getStringExpectMissing("model_" + modelType + "_" + featureName //$NON-NLS-1$ //$NON-NLS-2$
						+ "_name"); //$NON-NLS-1$
			}
			catch (MissingResourceException e)
			{
			}

			return featureName;
		}

		return model_Unknown_feature_name;
	}


	/**
	 * The default description of a feature.
	 * 
	 * @param feature
	 *            The feature.
	 * @return The default description of a feature.
	 */
	public static String model_Default_feature_description(EStructuralFeature feature)
	{
		String featureName = model_feature_name(feature);
		String modelType = model_type(feature.getEContainingClass());

		return bind(model_Default_feature_description, modelType, featureName);
	}


	/**
	 * The description of a feature.
	 * 
	 * @param feature
	 *            The feature.
	 * @return The description of a feature.
	 */
	public static String model_feature_description(EStructuralFeature feature)
	{
		String featureName = feature.getName();
		String modelType = getModelTypeName(feature.getEContainingClass());
		String result = null;

		try
		{
			result = getStringExpectMissing("model_" + modelType + "_" + featureName //$NON-NLS-1$ //$NON-NLS-2$
					+ "_description"); //$NON-NLS-1$
		}
		catch (MissingResourceException e)
		{
		}

		if (result == null)
		{
			// try default
			result = model_Default_feature_description(feature);
		}

		return result;
	}


	/**
	 * The text to represent a model.
	 * 
	 * @param model
	 *            The model or the type of the model.
	 * @param features
	 *            Describes the features.
	 * @return A text representation of the model element.
	 */
	public static String model_text(Object model, Object[] features)
	{
		String modelType = getModelTypeName(model);
		try
		{
			return getStringExpectMissing("model_" + modelType + "_text", features); //$NON-NLS-1$ //$NON-NLS-2$
		}
		catch (MissingResourceException e)
		{
		}

		return modelType;
	}


	/**
	 * A default name if a model element does not provide a name.
	 * 
	 * TODO return other string if model null
	 * 
	 * @param model
	 *            The model or the type of the model.
	 * @return A name.
	 */
	public static String model_Unnamed_name(Object model)
	{
		return bind(model_Unnamed_name, model_type(model));
	}


	/**
	 * Label text for the create child command.
	 * 
	 * @param child
	 *            The child object.
	 * @param feature
	 *            The feature.
	 * @param owner
	 *            The owner object.
	 * @return The text.
	 */
	public static String command_CreateChild_text(Object child, Object feature,
			Object owner)
	{
		return NLS.bind(command_CreateChild_text, new Object[]
		{ model_type(child), model_feature_name(feature), model_type(owner) });
	}


	/**
	 * Description for the create child command.
	 * 
	 * @param child
	 *            The child object.
	 * @param feature
	 *            The feature.
	 * @param owner
	 *            The owner object.
	 * @return The description.
	 */
	public static String command_CreateChild_description(Object child, Object feature,
			Object owner)
	{
		return NLS.bind(command_CreateChild_description, new Object[]
		{ model_type(child), model_feature_name(feature), model_type(owner) });
	}


	/**
	 * Tooltip for the create child command.
	 * 
	 * @param child
	 *            The child object.
	 * @param feature
	 *            The feature.
	 * @param owner
	 *            The owner object.
	 * @return The tooltip.
	 */
	public static String command_CreateChild_tooltip(Object child, Object feature,
			Object owner)
	{
		return NLS.bind(command_CreateChild_tooltip, new Object[]
		{ model_type(child), model_feature_name(feature), model_type(owner) });
	}


	/**
	 * Description text for the create sibling command.
	 * 
	 * @param child
	 *            The child object.
	 * @param feature
	 *            The feature.
	 * @param owner
	 *            The owner object.
	 * @return The description.
	 */
	public static String command_CreateSibling_description(Object child, Object feature,
			Object owner)
	{
		return NLS.bind(command_CreateSibling_description, new Object[]
		{ model_type(child), model_feature_name(feature), model_type(owner) });
	}


	/**
	 * Returns a label for a delete command.
	 * 
	 * @param model
	 *            The model or the type of the model.
	 * @return A label.
	 */
	public static String command_Delete_label(Object model)
	{
		return NLS.bind(command_Delete_label, model_type(model));
	}


	/**
	 * Returns a label for a create command.
	 * 
	 * @param model
	 *            The model or the type of the model.
	 * @return A label.
	 */
	public static String command_Create_label(Object model)
	{
		return NLS.bind(command_Create_label, model_type(model));
	}

}
