/*******************************************************************************
 *  Copyright 2017 Centre for Development of Advanced Computing(C-DAC), Pune
 *  
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *  
 *    http://www.apache.org/licenses/LICENSE-2.0
 *  
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *******************************************************************************/
package cdac.medinfo.sdk.hl7282.baselibs.datatypefactory;

import java.io.IOException;
import java.net.URL;
import java.net.URLConnection;

import cdac.medinfo.sdk.hl7282.exceptions.InvalidDictionaryException;
import cdac.medinfo.sdk.hl7282.utils.HL7Config;
import cdac.medinfo.sdk.hl7282.utils.HL7Logger;
import cdac.medinfo.sdk.hl7282.utils.IDataTypeMap;
import cdac.medinfo.sdk.hl7282.utils.IDataTypeMapReader;

/**
 * DataTypeMapReader provides implementation to IDataTypeMapReader.
 * It uses IDataTypeMap to represent DataType structure.
 */
public class DataTypeMapReader implements IDataTypeMapReader
{
	
	private final String strDataDictionaryPath = "DataTypeMapDictionary.xml";
	private static DataTypeMapReader objDataTypeMapReader = null;
	private static Object mutex = new Object();

	private DataTypeDictionary objDataTypeDictionary = null;

	private URL urlResourceName = null;

	/**
	 * This constructor is used if user wants to inherit DictionaryReader and override populate method 
	 */
	private DataTypeMapReader() throws InvalidDictionaryException
	{
		urlResourceName = DataTypeMapReader.class.getResource(strDataDictionaryPath);
		objDataTypeDictionary = DataTypeDictionary.createInstance();
	}

	/**
	 * Returns instance of Dictionary Reader if not created.
	 * @return - instance of DictionaryReader.
	 */
	public static DataTypeMapReader createInstance()throws InvalidDictionaryException
	{
		synchronized (mutex) 
		{
			if(objDataTypeMapReader == null)
			{
				objDataTypeMapReader = new DataTypeMapReader();	
			}
		}
		return objDataTypeMapReader;
	}

	/*
	 * Populates the Dictionary Data Provider with all the attributes from the Data Dictionary.
	 */
	private void populate(String strDataTypeName) throws InvalidDictionaryException
	{
		try
		{
			URLConnection objJarURLConnection = urlResourceName.openConnection();

			DataTypeXmlHandler objXmlHandler = new DataTypeXmlHandler(objJarURLConnection.getInputStream());
			IDataTypeMap objDataTypeMap = new DataTypeMap();

			if(objXmlHandler.populate(strDataTypeName, objDataTypeMap))
				objDataTypeDictionary.addDataTypeMap(strDataTypeName, objDataTypeMap);
		}
		catch(IOException ioe)
		{
			if(HL7Config.createInstance().isLoggingOn())
			{
				HL7Logger.getLogger().log(ioe.getMessage());
			}
			throw new InvalidDictionaryException(ioe);
		}
	}

	/**
	 * Retrieves DataTypeMap for given name of DataType
	 * @param strDataTypeName name of DataType
	 * @return IDataTypeMap - instance of DataTypeMap 
	 */
	public IDataTypeMap getDataTypeMap(String strDataTypeName)
	{
		if(!objDataTypeDictionary.isDataTypePopulated(strDataTypeName))
			populate(strDataTypeName);

		return objDataTypeDictionary.getDataTypeMap(strDataTypeName);
	}

}
