/*******************************************************************************
 *  Copyright 2017-2018 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.dcm30_04.services.ndelete.scp;

import java.io.IOException;
import java.util.Locale;


import cdac.medinfo.sdk.dcm30_04.enums.EnumCommandField;
import cdac.medinfo.sdk.dcm30_04.enums.EnumPDUType;
import cdac.medinfo.sdk.dcm30_04.enums.EnumSOPClassUIDs;
import cdac.medinfo.sdk.dcm30_04.exceptions.ParseException;
import cdac.medinfo.sdk.dcm30_04.exceptions.SerializeException;
import cdac.medinfo.sdk.dcm30_04.services.association.AAbort;
import cdac.medinfo.sdk.dcm30_04.services.association.AReleaseRQorRP;
import cdac.medinfo.sdk.dcm30_04.services.association.AssociateRQ;
import cdac.medinfo.sdk.dcm30_04.services.association.AssociationNegotiator;
import cdac.medinfo.sdk.dcm30_04.services.association.DefaultAssociation;
import cdac.medinfo.sdk.dcm30_04.services.association.IDIMSEAssociation;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.EnumAbortReason;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.EnumAbortSource;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.EnumDataSink;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.EnumEarlyFailedStatus;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.EnumImplOpsStatus;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.EnumNDeleteStatus;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.EnumServiceType;
import cdac.medinfo.sdk.dcm30_04.services.dicomnetcommons.SinkException;
import cdac.medinfo.sdk.dcm30_04.services.dimsecommons.DIMSEResponse;
import cdac.medinfo.sdk.dcm30_04.services.dimsecommons.DicomMessage;
import cdac.medinfo.sdk.dcm30_04.services.dimsecommons.IDataSink;
import cdac.medinfo.sdk.dcm30_04.services.ndelete.commons.NDeleteRQ;
import cdac.medinfo.sdk.dcm30_04.services.ndelete.commons.NDeleteRSP;
import cdac.medinfo.sdk.dcm30_04.services.scp.commons.ClientSession;
import cdac.medinfo.sdk.dcm30_04.services.scp.commons.SCP;
import cdac.medinfo.sdk.dcm30_04.services.scp.commons.SCPSession;
import cdac.medinfo.sdk.dcm30_04.utils.DicomConfig;
import cdac.medinfo.sdk.dcm30_04.utils.DicomConstants;
import cdac.medinfo.sdk.dcm30_04.utils.DicomLogger;

import cdac.medinfo.sdk.dcm30_04.utils.IPairedCollection;
import cdac.medinfo.sdk.dcm30_04.utils.ResourceBundleWrapper;

/**
 * NCreateSCP works as a processor for NDelete Service.
 * The N-Delete service is used by a DIMSE-service-user to request a peer DIMSE-service-user to delete
 * a SOP Instance, complete with its identification and the values of its associated Attributes,
 * and simultaneously to unregister its identification.
 * It is a confirmed service.
 * It processes the arrived N-Delete Request and generates the response.
 * It processes the request according to the Service Class SOP ClassUID specified in request.
 */
public class NDeleteSCP extends SCP
{
	

	private final String N_DELETE = ResourceBundleWrapper.getValue("status", "NDelete", new Locale(DicomConfig.createInstance().getLocale()));

	/* Paired collection containing  DataSink*/
	private IPairedCollection<EnumDataSink, IDataSink> objDataSinkCollection = null;

	private SCPSession objSCPSession = null;
	/**
	 * Instantiates object of NDelete SCP.
	 */
	private NDeleteSCP()
	{
	}

	/**
	 * This is private constructor for NDelete SCP. It is a singleton class.
	 * @param objClientSession object of client session.
	 */
	private NDeleteSCP(ClientSession objClientSession)
	{
		super(objClientSession);
	}

	/**
	 * This method returns new object of N-Delete SCP.
	 * @param objClientSession object of Client session.
	 * @return NDeleteSCP object of NDelete SCP.
	 */
	public static NDeleteSCP createInstance(ClientSession objClientSession)
	{
		return (new NDeleteSCP(objClientSession));
	}

	/**
	 * Instantiates a new N-Delete SCP.
	 * @return NDeleteSCP  - instance of N-Delete SCP.
	 */
	public static NDeleteSCP createInstance()
	{
		return (new NDeleteSCP());
	}

	/**
	 * 
	 * @param strIP IP at which Server has to be started.
	 * @param strAETitle value of AE Title for service provider.
	 * @param port at which Server has to be started.
	 * @throws IOException throws IOException if IO operation fails.
	 */
	public void start(String strAETitle,String strIP, int port) throws IOException
	{
		objSCPSession = new SCPSession();
		objSCPSession.setIProcessHandler(this);
		EnumServiceType[] arrenumServiceType = new EnumServiceType[7];
		arrenumServiceType[0] = EnumServiceType.NDELETE_BASIC_COLOR_PRINT_MANAGEMENT;
		arrenumServiceType[1] = EnumServiceType.NDELETE_BASIC_GRAYSCALE_PRINT_MANAGEMENT;
		arrenumServiceType[2] = EnumServiceType.NDELETE_BASIC_PRINT_IMAGE_OVERLAY;
		arrenumServiceType[3] = EnumServiceType.NDELETE_PRESENTATION_LUT;
		arrenumServiceType[4] = EnumServiceType.NDELETE_PULLPRINT;
		arrenumServiceType[5] = EnumServiceType.NDELETE_RT_CONVENTIONAL_MACHINE_VERIFICATION;
		arrenumServiceType[6] = EnumServiceType.NDELETE_RT_ION_MACHINE_VERIFICATION;

		objSCPSession.selectServices(arrenumServiceType);
		objSCPSession.start(strAETitle,strIP,port);
	}

	/**
	 * This method will Start the Server on the local host at the port specified.
	 * @param strAETitle value of AE Title for service provider.
	 * @param port port at which Server has to be started at local host.
	 * @throws IOException throws IOException if IO operation fails.
	 */
	public void start(String strAETitle,int port) throws IOException
	{
		objSCPSession = new SCPSession();
		objSCPSession.setIProcessHandler(this);
		EnumServiceType[] arrenumServiceType = new EnumServiceType[7];
		arrenumServiceType[0] = EnumServiceType.NDELETE_BASIC_COLOR_PRINT_MANAGEMENT;
		arrenumServiceType[1] = EnumServiceType.NDELETE_BASIC_GRAYSCALE_PRINT_MANAGEMENT;
		arrenumServiceType[2] = EnumServiceType.NDELETE_BASIC_PRINT_IMAGE_OVERLAY;
		arrenumServiceType[3] = EnumServiceType.NDELETE_PRESENTATION_LUT;
		arrenumServiceType[4] = EnumServiceType.NDELETE_PULLPRINT;
		arrenumServiceType[5] = EnumServiceType.NDELETE_RT_CONVENTIONAL_MACHINE_VERIFICATION;
		arrenumServiceType[6] = EnumServiceType.NDELETE_RT_ION_MACHINE_VERIFICATION;
		objSCPSession.selectServices(arrenumServiceType);
		objSCPSession.start(strAETitle,port);
	}

	/**
	 * Retrieves the DataSink List
	 * @return IPairedCollection<EnumDataSink, IDataSink> - collection of DataSink
	 */
	public IPairedCollection<EnumDataSink, IDataSink> getDataSinkList() 
	{
		return objDataSinkCollection;
	}

	/**
	 * Sets the Data Sink List.
	 * @param objSinkCollection collection of Data Sink.
	 */
	public void setDataSinkList(IPairedCollection<EnumDataSink, IDataSink> objSinkCollection) 
	{
		this.objDataSinkCollection = objSinkCollection;
	}

	/**
	 * This will give the response of C-Echo Request.
	 * @param objDicomMessage  object of DIMSE request.
	 * @return DIMSEResponse - instance of service response .
	 * @throws IOException if IO operation fails.
	 */
	public DIMSEResponse processRequest(DicomMessage objDicomMessage) 
	{
		/*
		 * NDelete Response to be send
		 */
		NDeleteRSP objNDeleteRSP = null;

		/*
		 * NDelete Request
		 */
		NDeleteRQ objNDeleteRQ  = null;

		/*
		 * Get the early failed status.
		 */
		EnumEarlyFailedStatus enumEarlyFailedStatus = objClientSession.getEarlyFailedStatus();

		try
		{
			//check for null value of object of DicomMessage, if DicomMessage is null or if DICOMMsgValidationStatus is false, then Processing failure RSP will be send.
			if(objDicomMessage == null || objClientSession.getDICOMMsgValidationStatus() == false)
			{
				if(DicomConfig.createInstance().isLoggingOn())
				{
					DicomLogger objDicomLogger = DicomLogger.getLogger();
					objDicomLogger.log(ResourceBundleWrapper.getValue("warning","InvalidDicomMessage",new Locale(DicomConfig.createInstance().getLocale())));
				}

				objNDeleteRQ = new NDeleteRQ(objDicomMessage);

				objNDeleteRSP = new NDeleteRSP();
				objNDeleteRSP.setCommandField(EnumCommandField.N_ACTION_RSP);
				objNDeleteRSP.setAffectedSOPClassUID(objNDeleteRQ.getRequestedSOPClassUID());
				objNDeleteRSP.setMessageIDBeingRespondedTo(objNDeleteRQ.getMessageID());
				//constant should be used here.
				objNDeleteRSP.setCommandDataSetType(DicomConstants.DCM_DATASET_NOT_PRESENT);
				objNDeleteRSP.setStatus(EnumNDeleteStatus.PROCESSING_FAILURE);
				return objNDeleteRSP;
			}
			
			/*
			 * Construct NDelete RQ from Dicom Message.
			 */
			objNDeleteRQ = new NDeleteRQ(objDicomMessage);

			if(DicomConfig.createInstance().isLoggingOn())
			{
				DicomLogger objDicomLogger = DicomLogger.getLogger();
				objDicomLogger.log(ResourceBundleWrapper.getValue("status", "ProcessingServiceRequest", new Locale(DicomConfig.createInstance().getLocale())) + objDicomMessage.getCommandType().name());
				objDicomLogger.log(ResourceBundleWrapper.getValue("status", "AbstractSyntaxName", new Locale(DicomConfig.createInstance().getLocale())) + objNDeleteRQ.getRequestedSOPClassUID());
				if(objNDeleteRQ.getDataSet() != null)
					objDicomLogger.log(ResourceBundleWrapper.getValue("status", "TransferSyntax", new Locale(DicomConfig.createInstance().getLocale())) + objNDeleteRQ.getDataSet().getTransferSyntax().getTransferSyntaxUID());
				objDicomLogger.log(ResourceBundleWrapper.getValue("status", "NDeleteRequest", new Locale(DicomConfig.createInstance().getLocale())) + objNDeleteRQ.getRequestedSOPInstanceUID());
			}

			if(objClientSession.getAssociationStatus())
			{
				objNDeleteRSP = new NDeleteRSP();

				//Initializing RSP 
				objNDeleteRSP.setAffectedSOPClassUID(objNDeleteRQ.getRequestedSOPClassUID());
				objNDeleteRSP.setCommandField(EnumCommandField.N_DELETE_RSP);
				objNDeleteRSP.setMessageIDBeingRespondedTo(objNDeleteRQ.getMessageID());
				//Constant should be used here.
				objNDeleteRSP.setCommandDataSetType(DicomConstants.DCM_DATASET_NOT_PRESENT);
				//If SOP Instance UID is not given in Request then new value needs to be generated and send it in Response. 
				objNDeleteRSP.setAffectedSOPInstanceUID(objNDeleteRQ.getRequestedSOPInstanceUID());

				/*
				 * This if-else block checks for the status of arrived RQ and takes corresponding action.
				 */
				if(enumEarlyFailedStatus == EnumEarlyFailedStatus.NO_EARLY_FAILED)
				{
					IDataSink objIDataSink = null;
					String strAffectedSOPUid = objNDeleteRQ.getRequestedSOPClassUID();

					if(objDataSinkCollection != null)
					{
						//Retrieving appropriate DataSink according to service class 
						if(strAffectedSOPUid.equals(EnumSOPClassUIDs.BASICFILMSESSIONIOD.getValue()) || strAffectedSOPUid.equals(EnumSOPClassUIDs.BASICFILMBOXIOD.getValue()) || 
								strAffectedSOPUid.equals(EnumSOPClassUIDs.PRESENTATIONLUTIOD.getValue()) || strAffectedSOPUid.equals(EnumSOPClassUIDs.PULLPRINTREQUESTIOD.getValue()) ||
								strAffectedSOPUid.equals(EnumSOPClassUIDs.BASICPRINTIMAGEOVERLAYBOXIOD.getValue()))
							objIDataSink = objDataSinkCollection.get(EnumDataSink.PRINT_MANAGEMENT);
						
						else if(strAffectedSOPUid.equals(EnumSOPClassUIDs.RTCONVENTIONALMACHINEVERIFICATIONINFORMATIONOBJECTDEFINITION.getValue()) 
								|| strAffectedSOPUid.equals(EnumSOPClassUIDs.RTIONMACHINEVERIFICATIONINFORMATIONOBJECTDEFINITION.getValue())  
								)
							objIDataSink = objDataSinkCollection.get(EnumDataSink.RTMACHINEVERIFICATION);

						if(objIDataSink != null)
						{
							short shStatus = objIDataSink.store(objDicomMessage,null);
							objNDeleteRSP.setStatus(shStatus);
							if(shStatus != EnumImplOpsStatus.SUCCESS.getValue())
							{
								if(DicomConfig.createInstance().isLoggingOn())
								{
									DicomLogger objDicomLogger = DicomLogger.getLogger();
									objDicomLogger.log(ResourceBundleWrapper.getValue("warning","ImplOperationFailure",new Locale(DicomConfig.createInstance().getLocale()))+ N_DELETE);
								}
							}
						}
						else
						{
							objNDeleteRSP.setStatus(EnumNDeleteStatus.PROCESSING_FAILURE);
							if(DicomConfig.createInstance().isLoggingOn())
							{
								DicomLogger objDicomLogger = DicomLogger.getLogger();
								objDicomLogger.log(ResourceBundleWrapper.getValue("warning","ImplementationNotProvided",new Locale(DicomConfig.createInstance().getLocale()))+ N_DELETE);
							}
						}
					}
					else
					{
						objNDeleteRSP.setStatus(EnumNDeleteStatus.PROCESSING_FAILURE);
						if(DicomConfig.createInstance().isLoggingOn())
						{
							DicomLogger objDicomLogger = DicomLogger.getLogger();
							objDicomLogger.log(ResourceBundleWrapper.getValue("warning","ImplementationNotProvided",new Locale(DicomConfig.createInstance().getLocale()))+ N_DELETE);
						}
					}

				}
				else
				{
					objNDeleteRSP.setStatus(EnumNDeleteStatus.SOP_CLASS_NOT_SUPPORTED);
					if(DicomConfig.createInstance().isLoggingOn())
					{
						DicomLogger objDicomLogger = DicomLogger.getLogger();
						objDicomLogger.log(ResourceBundleWrapper.getValue("warning","EarlyFailedResponse",new Locale(DicomConfig.createInstance().getLocale()))+ N_DELETE);
					}
				}

				int iGroupLength = objNDeleteRSP.getCommandSet().getCommandSetLength();
				objNDeleteRSP.setCommandGroupLength(iGroupLength);
			}
			else
			{
				if(DicomConfig.createInstance().isLoggingOn())
				{
					DicomLogger objDicomLogger = DicomLogger.getLogger();
					objDicomLogger.log(ResourceBundleWrapper.getValue("status","AssociationDoesNotExists",new Locale(DicomConfig.createInstance().getLocale()))+ N_DELETE);
				}
			}
		}
		catch(ParseException pe)
		{
			if(DicomConfig.createInstance().isLoggingOn() )
			{
				String strService = ResourceBundleWrapper.getValue("exceptions", "NDelete", new Locale(DicomConfig.createInstance().getLocale()));
				DicomLogger objDicomLogger = DicomLogger.getLogger();
				objDicomLogger.log( strService + pe.getMessage());
			}
			
			objNDeleteRSP = getNDeleteResponse(objDicomMessage,EnumNDeleteStatus.UNABLE_TO_PROCESS_PARSING_FAILED);
		}
		catch(SerializeException pe)
		{ 
			if(DicomConfig.createInstance().isLoggingOn() )
			{
				String strService = ResourceBundleWrapper.getValue("exceptions", "NDelete", new Locale(DicomConfig.createInstance().getLocale()));
				DicomLogger objDicomLogger = DicomLogger.getLogger();
				objDicomLogger.log( strService + pe.getMessage());
			}
			
			objNDeleteRSP = getNDeleteResponse(objDicomMessage,EnumNDeleteStatus.INVALID_ATTRIBUTE_VALUE);
		}
		catch(SinkException se)
		{
			if(DicomConfig.createInstance().isLoggingOn() )
			{
				String strService = ResourceBundleWrapper.getValue("exceptions", "NDelete", new Locale(DicomConfig.createInstance().getLocale()));
				DicomLogger objDicomLogger = DicomLogger.getLogger();
				objDicomLogger.log( strService + se.getMessage());
			}
			objNDeleteRSP = getNDeleteResponse(objDicomMessage,EnumNDeleteStatus.PROCESSING_FAILURE);
		}
		catch(IOException ioe)
		{
			if(DicomConfig.createInstance().isLoggingOn() )
			{
				String strService = ResourceBundleWrapper.getValue("exceptions", "NDelete", new Locale(DicomConfig.createInstance().getLocale()));
				DicomLogger objDicomLogger = DicomLogger.getLogger();
				objDicomLogger.log( strService + ioe.getMessage());
			}
			objNDeleteRSP = getNDeleteResponse(objDicomMessage,EnumNDeleteStatus.PROCESSING_FAILURE);
		}
		if(DicomConfig.createInstance().isLoggingOn())
		{
			DicomLogger objDicomLogger = DicomLogger.getLogger();
			objDicomLogger.log(objDicomMessage.getCommandType() + " " +ResourceBundleWrapper.getValue("status","RSPStatus",new Locale(DicomConfig.createInstance().getLocale()))+ Integer.toHexString(objNDeleteRSP.getStatus()));
		}
		return objNDeleteRSP;
	}

	/**
	 * This method notifies when Association Request, Associate Release Request or Abort is received from one of the 
	 * SCUs. 
	 * If Association Request is received,
	 * 		Create Association Negotiator which negotiates the request with the existing default association and
	 * 		creates an AgreedAssociation which contains the negotiated association values. Association Negotiator
	 * 		returns the Association Response as AssociateAC when request is accepted or returns AssociateRQ is 
	 * 		none of the values in Association Request are acceptable.
	 * 	If Associate Release Request is received,
	 * 		Create a Associate Release Response and send the response to the SCU using the respective ClientSession.
	 *  If Abort is received,
	 *  	An Abort response must be generated and sent using ClientSession.
	 *    
	 * @param objClientSession instance of Client Session.
	 */
	public void onAssociateReceive(ClientSession objClientSession) 
	{
		//Get Association RQ
		IDIMSEAssociation objIDIMSEAssociation = objClientSession.getDIMSEAssociation();
		EnumPDUType enumPDUType = objIDIMSEAssociation.getPDUType();
		IDIMSEAssociation objAssociationRSP = null;

		//For Association Request negotiate with Default Association and generate Response
		switch(enumPDUType)
		{
		case ASSOCIATE_RQ :
		{
			boolean associationStatus = objClientSession.getAssociationStatus();
			if(associationStatus)
			{
				if(DicomConfig.createInstance().isLoggingOn())
				{
					DicomLogger objDicomLogger = DicomLogger.getLogger();
					objDicomLogger.log(ResourceBundleWrapper.getValue("exceptions", "Association.UnexpectedAssociationRQ",new Locale(DicomConfig.createInstance().getLocale())));
				}
				/*
				 * If association already exists then abort will be generated
				 */
				AAbort objAAbort = new AAbort();
				objAAbort.setReason(EnumAbortReason.UNEXPECTED_PDU);
				objAAbort.setSource(EnumAbortSource.SERVICE_PROVIDER);

				objClientSession.sendAssociationMessage(objAAbort);
				return;
			}
			AssociateRQ objAssociateRQ = (AssociateRQ)objIDIMSEAssociation;

			//get the default association from Client Session.
			DefaultAssociation objDefaultAssociation = objClientSession.getDefaultAssociation();

			//Negotiate and get Response
			AssociationNegotiator objAssNegotiator = new AssociationNegotiator();
			objAssociationRSP = objAssNegotiator.negotiate(objDefaultAssociation, objAssociateRQ);

			//set agreed association in client Session.
			objClientSession.setAgreedAssociation(objAssNegotiator.getAgreedAssociation());

			//Send Response
			objClientSession.sendAssociationMessage(objAssociationRSP);
			break;
		}
		case RELEASE_RQ :
		{
			System.out.println("Release Request Received");

			//Create Release Response.
			objAssociationRSP = new AReleaseRQorRP(EnumPDUType.RELEASE_RP);

			//Send Release Response.
			objClientSession.sendAssociationMessage(objAssociationRSP);
			System.out.println("Release Response sent");

			//Close Client Session
			objClientSession.close();
			break;
		}
		case ABORT :
		{
			System.out.println("Abort has arrived Stop Porcessing -- Association is no longer available");
			break;
		}
		}
	}


	/**
	 * Closes client Session.
	 * @param objClientSession Object of Client Session.
	 */
	public void onClose(ClientSession objClientSession) 
	{
		objClientSession.close();
	}

	/**
	 * This method notifies when a new client connection is requested. A decision is to be made whether to
	 * accept or reject the connection.  
	 * @param objClientSession  object of client session.
	 */
	public void onConnect(ClientSession objClientSession)
	{
		objClientSession.acceptConnection(true);
	}

	/**
	 * This method notifies when a service related request is received.
	 * For Example,
	 * If C-Store-RQ is received,
	 * 		Create CStoreSCP using the ClientSession.
	 * 		Process the request using the CStoreSCP which actually serializes the DataSet on a Stream and returns
	 * 		a CStoreRSP containing the response.
	 * 		Send this response using the ClientSession.
	 * @see objClientSession Object of Client Session.
	 */
	public void onServiceRequest(ClientSession objClientSession)
	{
		/*
		 * Create CSTORE_SCP get RQ from ClientSession call processRequest and pass C_STORE_RQ on CSTORE_SCP
		 * receive response from CSTORE_SCP sendResponse using ClientSession
		 */
		DIMSEResponse objDResponse = null;
		try
		{
			objDResponse = processRequest(objClientSession.getDicomMessage());

			/*
			 * Send the service message through Client Session.
			 */
			if(objDResponse != null)
				objClientSession.sendServiceMessage(objDResponse);
		}catch(Exception ioe)
		{
			if(DicomConfig.createInstance().isLoggingOn())
				DicomLogger.getLogger().log(ioe);
			objClientSession.close();
			
			
		}  
	}
	
	/**
	 * Stops accepting new connection's from SCU's and continue to process 
	 * already connected clients.
	 */
	public void stopListening()
	{
		if(null != objSCPSession)
			objSCPSession.stopListening();
	}
	
	/**
	 * Closes all the currently executing sessions gracefully.	 
	 */
	public void close()
	{
		if(null != objSCPSession)
			objSCPSession.close();
		else
		{	
			if(DicomConfig.createInstance().isLoggingOn())
			{
				DicomLogger objDicomLogger = DicomLogger.getLogger();
				objDicomLogger.log(ResourceBundleWrapper.getValue("warning", "NoSCPSessionRunning",new Locale(DicomConfig.createInstance().getLocale())));
			}
		}
	}
	
	/**
	 * Gives NDelete Response.
	 * @param objDicomMessage Object of DicomMessage.
	 * @param enumStatus Enum for EnumNDeleteStatus which specifies status of response.
	 * @return objNDeleteRSP - Object of NDeleteRSP.
	 */
	private NDeleteRSP getNDeleteResponse(DicomMessage objDicomMessage, EnumNDeleteStatus enumStatus)
	{
		NDeleteRSP objNDeleteRSP = new NDeleteRSP();
		
		objNDeleteRSP.setAffectedSOPClassUID(objDicomMessage.getCommandSet().getValue(0x0000, 0x0003).toString());
		objNDeleteRSP.setCommandField(EnumCommandField.N_DELETE_RSP);
		objNDeleteRSP.setMessageIDBeingRespondedTo(Short.parseShort(objDicomMessage.getCommandSet().getValue(0x0000,0x0110).toString()));
		
		objNDeleteRSP.setCommandDataSetType((short)0x0101);										
		objNDeleteRSP.setAffectedSOPInstanceUID(objDicomMessage.getCommandSet().getValue(0x0000, 0x1001).toString());
		objNDeleteRSP.setStatus(enumStatus);
		objNDeleteRSP.setCommandGroupLength(objNDeleteRSP.getCommandSet().getCommandSetLength());
		
		return objNDeleteRSP;
	}
}

