/////////////////////////////////////////////////////////////////
//Copyright (C) 2005 NTT CORPORATION.
//
//	ロール管理処理　ロールの更新画面表示Actionクラス
//
//		変更履歴
//			2005.02.16  新規作成  氏名 石崎賢太郎
//
//	機能
//
//	ロール更新画面表示Actionクラスです。
//
/////////////////////////////////////////////////////////////////
package jp.co.ntt.lms.xmf.actions.xmo.Roles;

import java.util.Hashtable;
import java.util.StringTokenizer;
import java.util.Vector;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import jp.co.ntt.lms.xmo.Environment;
import jp.co.ntt.lms.xmo.Base.XMSBaseClient;
import jp.co.ntt.lms.xmo.Roles.RolesClient;
import jp.co.ntt.lms.xmo.Roles.RolesRelationCheck;

import org.apache.struts.action.Action;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.util.MessageResources;

/**
 * ロール更新画面表示Actionクラスです。
 * 
 * @author Kentaro Ishizaki (UNITEC)
 * @version 1.0
 */
public class RolesUpdateAction extends Action
{
	/**
	 * strutsフレームワークから呼ばれるメソッドです。
	 * 
	 * @param mapping マッピングオブジェクト。
	 * @param form アクションフォームオブジェクト。
	 * @param request リクエストオブジェクト。
	 * @param response レスポンスオブジェクト。
	 * @return ActionForward アクションフォワードオブジェクト。
	 * @throws Exception
	 */
	public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception
	{
		///////////////////////////////////////////
		// パラメータ取得
		// 	・returnURL	戻りページ		必須
		// 	・roleName	ロール名		必須
		//	・roleId	ロールID		必須
		// 	・xmo_id	XMOID
		// 	・act		アクションフラグ
		///////////////////////////////////////////
		String strReturnURL_o = request.getParameter("returnURL"); 		// 戻りページ
		String strRoleID_o = request.getParameter("roleId");			// ロールID
		String strRoleName_o = request.getParameter("roleName");		// ロール名称
		String strFunction = request.getParameter("xmo_id"); 			// XMOID
		String strAction = request.getParameter("act"); 				// アクションフラグ
		if(strAction != null && strAction.equals("on")){
			// キャッシュ無効処理
			response.setHeader( "cache-control", "no-cache" );
		}

		String strErrorMessage = null;

		// メッセージリソース取得
		MessageResources resources = getResources(request, "msg.xmf.xmo.Roles.MessageResources");

		///////////////////////////////////////////
		// パラメータチェック
		///////////////////////////////////////////
		if( strRoleID_o == null || strRoleID_o.equals( "" ) ) {
			Exception e = new Exception();
			e.printStackTrace();
			String strMessage = resources.getMessage("M052006");
			String strDetail = resources.getMessage("D052006");
			request.setAttribute("message", strMessage);
			request.setAttribute("detail", strDetail);
			request.setAttribute("close", "on");
			request.setAttribute("errorurl", "");
			return mapping.findForward("error");
		}
		if( strRoleName_o == null || strRoleName_o.equals( "" ) ) {
			Exception e = new Exception();
			e.printStackTrace();
			String strMessage = resources.getMessage("M052007");
			String strDetail = resources.getMessage("D052007");
			request.setAttribute("message", strMessage);
			request.setAttribute("detail", strDetail);
			request.setAttribute("close", "on");
			request.setAttribute("errorurl", "");
			return mapping.findForward("error");
		}
		if( strReturnURL_o == null || strReturnURL_o.equals( "" ) ) {
			Exception e = new Exception();
			e.printStackTrace();
			request.setAttribute("message", "");
			request.setAttribute("detail", "");
			request.setAttribute("close", "on");
			request.setAttribute("errorurl", "../Com/ComSystemErr.vm");
			return mapping.findForward("error");
		}

		// XMSBaseの取得
		XMSBaseClient objXMS = new XMSBaseClient();
		// ロールXMOクライアントのインスタンス化
		RolesClient objRoles = new RolesClient();

		String[][] strAddXmoCopy_o = new String[20][2];

		
		///////////////////////////////////////////////
		//アクションフラグがonの場合、更新処理をします。
		///////////////////////////////////////////////
		if(strAction != null && strAction.equals("on")){

			///////////////////////////////////////////
			// パラメータ取得
			///////////////////////////////////////////
			//更新パラメータクリア
			objRoles.clear();
			
			//ロール名称の存在チェック
			objRoles.setWhereRoleName(strRoleName_o);
			if(!objRoles.select()){
				// 検索がうまくいかなかった場合
				if( objRoles.isErr() )
				{
					// エラーの場合
					request.setAttribute("message", "");
					request.setAttribute("detail", "");
					request.setAttribute("close", "on");
					request.setAttribute("errorurl", objRoles.getURL());
					return mapping.findForward("error");
				}
				else
				{
					String strMessage =  objRoles.getMessage();
					request.setAttribute("message", strMessage);
					request.setAttribute("detail", "");
					request.setAttribute("close", "on");
					request.setAttribute("errorurl", "");
					return mapping.findForward("error");
				}
			}
			
			//ロール名称重複エラー
			while( objRoles.next() )
			{
				if(!strRoleID_o.equals(objRoles.getRoleID())){
					strErrorMessage = resources.getMessage("M052009");
				}
			}
			
			if(strErrorMessage == null || strErrorMessage.equals("")){

				//更新パラメータ設定
				objRoles.clear();
				objRoles.setWhereRoleID( strRoleID_o );// ロールID

				//Xmo配列のインスタンス化
				Vector vecFunctionList = new Vector();
				StringTokenizer objToken = new StringTokenizer( strFunction, "," );

				while( objToken.hasMoreTokens() ) {
					vecFunctionList.add( objToken.nextToken() );
				}

				objRoles.setRoleName( strRoleName_o );// ロール名
				objRoles.setDeleted( "0" );			// 隠しフラグID

				for( int i = 0; i < vecFunctionList.size(); i++ ) {
					objRoles.addFunction( (String)vecFunctionList.get(i) );	// XMO_ID
				}

				// 関連XMOチェック
				RolesRelationCheck objCheck = new RolesRelationCheck();
				objCheck.setRoleList(vecFunctionList);
				if(!objCheck.checkXmoRelation())
				{
					// エラーメッセージのマクロ展開
					String strRoleErrorXmoName = objCheck.getRoleErrorXmoName();
					String strRelationErrorXmoName = objCheck.getRelationErrorXmoName();
					if(strRoleErrorXmoName != null ||
						strRelationErrorXmoName != null)
					{
						strErrorMessage = resources.getMessage("M052008");
						String strDetail = resources.getMessage("D052008");
						Hashtable htbData = new Hashtable();
						htbData.put("XMO_NAME", strRoleErrorXmoName);
						htbData.put("TARGET_NAME", strRelationErrorXmoName);
						strErrorMessage = Environment.expand(strErrorMessage, htbData);
					}
					else
					{
						request.setAttribute("message", "");
						request.setAttribute("detail", "");
						request.setAttribute("close", "on");
						request.setAttribute("errorurl", objRoles.getURL());
						return mapping.findForward("error");
					}
				}
				// 登録可能です
				else
				{
					// 更新メソッド実行
					if( !objRoles.update() ) {
						// 更新がうまくいかなかった場合
						if( objRoles.isErr() ) {
							// エラーの場合
							request.setAttribute("message", "");
							request.setAttribute("detail", "");
							request.setAttribute("close", "on");
							request.setAttribute("errorurl", objRoles.getURL());
							return mapping.findForward("error");
						}
						else {
							String strMessage =  objRoles.getMessage();
							request.setAttribute("message", strMessage);
							request.setAttribute("detail", "");
							request.setAttribute("close", "on");
							request.setAttribute("errorurl", "");
							return mapping.findForward("error");
						}
					}
				}
			}
		}

		///////////////////////////////////////////
		//XMO詳細情報を取得する
		///////////////////////////////////////////

		// XmoIDを保持する
		Vector vecXmoIDList = new Vector();

		try {
				// XmoIDの取得
				objRoles.clear();

				objRoles.setWhereRoleID( strRoleID_o );

				if( !objRoles.select() ) {
					// 検索がうまくいかなかった場合
					if( objRoles.isErr() ) {
						// エラーの場合
						request.setAttribute("message", "");
						request.setAttribute("detail", "");
						request.setAttribute("close", "on");
						request.setAttribute("errorurl", objRoles.getURL());
						return mapping.findForward("error");
					}
					else {
						String strMessage =  objRoles.getMessage();
						request.setAttribute("message", strMessage);
						request.setAttribute("detail", "");
						request.setAttribute("close", "on");
						request.setAttribute("errorurl", "");
						return mapping.findForward("error");
					}
				}

				/*XmoID,Xmo名称の取得 */
				Vector vecAddXmoList = new Vector();
				while( objRoles.next() ) {
					int intFunctionCount = objRoles.getFunctionCount();


					for (int i=0;i<intFunctionCount;i++){
						strFunction = objRoles.getFunction(i);
							/* XmoIDの重複Check */
							if (vecXmoIDList.indexOf(strFunction) == -1){
								vecXmoIDList.addElement(strFunction);
								//XmoIDの検索
								objXMS.clear();
								objXMS.setWhereXmoID(strFunction);

								//XmoIDがある時

								if(objXMS.select()){
									//Xmo名称の取得

									if(objXMS.next()){
										String[] strAddXmoInfo = new String[2];
										strAddXmoInfo[0] = strFunction;
										strAddXmoInfo[1] = objXMS.getXmoName();
										vecAddXmoList.add(strAddXmoInfo);
									}
								}else{
									// 検索がうまくいかなかった場合
									if( objXMS.isErr() ) {
										// エラーの場合
										request.setAttribute("message", "");
										request.setAttribute("detail", "");
										request.setAttribute("close", "on");
										request.setAttribute("errorurl", objXMS.getURL());
										return mapping.findForward("error");
									}
									else {
										String strMessage =  objXMS.getMessage();
										request.setAttribute("message", strMessage);
										request.setAttribute("detail", "");
										request.setAttribute("close", "on");
										request.setAttribute("errorurl", "");
										return mapping.findForward("error");
									}
								}
							}
						}
					}
				//Xmo情報リストをベクターから配列にコピーします。
				strAddXmoCopy_o = new String[vecAddXmoList.size()][2];
				vecAddXmoList.copyInto( strAddXmoCopy_o );

				// xmo_idでソート処理
				strAddXmoCopy_o = sortArray(strAddXmoCopy_o);
				objRoles.clear();
			}
			catch( Throwable e ) {
				request.setAttribute("message", e.getMessage());
				request.setAttribute("detail", "");
				request.setAttribute("close", "on");
				request.setAttribute("errorurl", "");
				return mapping.findForward("error");
			}

		////////////////////////////////////
		//権限一覧の取得
		////////////////////////////////////
		Vector vecXmoList = new Vector();
		objXMS.clear();
		objXMS.setOrderBy(XMSBaseClient.XMO_ID);
		// オンフラグがたっているものを検索する
		objXMS.setWhereXmoOnFlag();
		//取得できなかったらエラー
		if(!objXMS.select()){
			// 検索がうまくいかなかった場合
			if( objXMS.isErr() ) {
				// エラーの場合
				request.setAttribute("message", "");
				request.setAttribute("detail", "");
				request.setAttribute("close", "on");
				request.setAttribute("errorurl", objXMS.getURL());
				return mapping.findForward("error");
			}
			else {
				String strMessage =  objXMS.getMessage();
				request.setAttribute("message", strMessage);
				request.setAttribute("detail", "");
				request.setAttribute("close", "on");
				request.setAttribute("errorurl", "");
				return mapping.findForward("error");
			}
		}
		StringBuffer strXmoLine = new StringBuffer();
		//権限を1行の文字列で取得する。
		while(objXMS.next()){
			String[] strXmoInfo = new String[2];
			strXmoInfo[0] = objXMS.getXmoID();
			strXmoInfo[1] = objXMS.getXmoName();
			vecXmoList.add(strXmoInfo);
		}
		//Xmo情報リストをベクターから配列にコピーします。
		String[][] strXmoCopy_o = new String[vecXmoList.size()][2];
		vecXmoList.copyInto( strXmoCopy_o );
		// XMO ID(数値イメージ)でソート
		strXmoCopy_o = sortArray(strXmoCopy_o);
		
		
		// リクエストに変数をセット
		request.setAttribute("strErrorMessage", strErrorMessage);
		request.setAttribute("strAction", strAction);
		request.setAttribute("strReturnURL_o", strReturnURL_o);
		request.setAttribute("strRoleID_o", strRoleID_o);
		request.setAttribute("strRoleName_o", strRoleName_o);
		request.setAttribute("strAddXmoCopy_o", strAddXmoCopy_o);
		request.setAttribute("strXmoCopy_o", strXmoCopy_o);
		
		return mapping.findForward("success");
	}
	
	

	/**
	 * String[2]が入っているString[]を、String[0]をキーにソートします。
	 *
	 * @param srcArray ソート元。String[2]の配列で、String[0]が数値であること。
	 * @return ソート結果
	 */
	private String[][] sortArray(String[][] targetArray) throws Exception{

		String[] tmp;					// テンポラリ
		int minIndex;					// 最小データのキー値

		// 全件検索し、最小値から先頭に詰めていく
		int arrSize = targetArray.length;
		for(int i=0; i < arrSize-1; i++){
			// 先頭を最小値として先に取得
			minIndex = Integer.parseInt(targetArray[i][0]);

			// 最小データを検索
			for(int j=i+1; j < arrSize; j++){
				int nowIndex = Integer.parseInt(targetArray[j][0]);
				if(nowIndex < minIndex){
					// 最小値を入替
					tmp = targetArray[i];
					targetArray[i] = targetArray[j];
					targetArray[j] = tmp;
					minIndex = nowIndex;
				}
			}
		}

		return targetArray;
	}
}
