package com.dreamer.devcentre.client.xletProfiling.presenter;

import java.util.Date;
import java.util.HashMap;
import java.util.Map;

import com.dreamer.devcentre.client.main.events.MainEventBus;
import com.dreamer.devcentre.client.xletProfiling.rpc.SqsServiceAsync;
import com.dreamer.devcentre.client.xletProfiling.rpc.XletProfilingServiceAsync;
import com.dreamer.devcentre.client.xletProfiling.view.WebSimulator;
import com.dreamer.devcentre.shared.UserCookies;
import com.dreamer.devcentre.shared.bean.SimpleDateFormat;
import com.google.gwt.dom.client.InputElement;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.event.dom.client.HasClickHandlers;
import com.google.gwt.json.client.JSONArray;
import com.google.gwt.json.client.JSONObject;
import com.google.gwt.json.client.JSONParser;
import com.google.gwt.user.client.DOM;
import com.google.gwt.user.client.Timer;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.ui.FileUpload;
import com.google.gwt.user.client.ui.FormPanel;
import com.google.gwt.user.client.ui.HTML;
import com.google.gwt.user.client.ui.HTMLPanel;
import com.google.gwt.user.client.ui.HasVerticalAlignment;
import com.google.gwt.user.client.ui.ListBox;
import com.google.gwt.user.client.ui.TextBox;
import com.google.gwt.user.client.ui.VerticalPanel;
import com.google.gwt.user.client.ui.Widget;
import com.google.gwt.user.client.ui.FormPanel.SubmitCompleteEvent;
import com.google.gwt.user.client.ui.FormPanel.SubmitCompleteHandler;
import com.mvp4g.client.annotation.InjectService;
import com.mvp4g.client.annotation.Presenter;
import com.mvp4g.client.presenter.BasePresenter;
import com.smartgwt.client.data.DataSource;
import com.smartgwt.client.data.Record;
import com.smartgwt.client.widgets.AnimationCallback;
import com.smartgwt.client.widgets.HTMLFlow;
import com.smartgwt.client.widgets.HTMLPane;
import com.smartgwt.client.widgets.form.DynamicForm;
import com.smartgwt.client.widgets.form.fields.ComboBoxItem;
import com.smartgwt.client.widgets.grid.ListGrid;
import com.smartgwt.client.widgets.grid.ListGridRecord;
import com.smartgwt.client.widgets.grid.events.CellMouseDownEvent;
import com.smartgwt.client.widgets.tab.Tab;

@Presenter(view = WebSimulator.class)
public class WebSimulatorPresenter
		extends
		BasePresenter<WebSimulatorPresenter.WebSimulatorInterface, MainEventBus> {

	private XletProfilingServiceAsync service = null;
	private FormPanel form = null;
	private static String newFileName = null;
	private static String currentTime = null;
	private String iteration = null;
	private String alias = null;
	private final String formAction = "http://ec2-174-129-24-119.compute-1.amazonaws.com:8080/server_side/upload";
	private static UserCookies cookie = UserCookies.getInstance();
	private SqsServiceAsync sqsService = null;
	// private final String USER_ID = cookie.getEmailAddressFromCookie();
	private final String USER_ID = "dreamer.co.kr@gmail.com";
	private String status = "PROFILING";
	private SimpleDateFormat format = new SimpleDateFormat(
			"yyyy-MM-dd HH:mm:ss");
	private final String bucketName = "sinnytest";
	private ListGrid listGrid = null;
	private boolean tableInsertbool = true;
	private boolean submitDataInsert = false;
	private int timerRunCnt = 0;
	private int addRowCnt = 0;
	private Timer submitTimer = null;

	private HTMLPane loadMsg = new HTMLPane();
	private VerticalPanel vPanel = new VerticalPanel();
	DataSource ds = new DataSource();
	public interface WebSimulatorInterface {

		public HasClickHandlers getSubmitButton();

		public HasClickHandlers getCancelButton();

		public FormPanel getFormPanel();

		public Widget getViewWidget();

		public ListGrid getListGrid();

		public TextBox getAliasTextBox();

		public TextBox getXletName();

		public FileUpload getFileUploadBtn();

		public InputElement[] getRadioBtn();

		public HTMLPanel getHtmlPanel();
	}

	@Override
	public void bind() {
		createLoadMsg();
		listGrid = view.getListGrid();

		view.getCancelButton().addClickHandler(new ClickHandler() {

			@Override
			public void onClick(ClickEvent event) {
				cancelBtnClick();
			}
		});

		view.getSubmitButton().addClickHandler(new ClickHandler() {
			@Override
			public void onClick(ClickEvent event) {
				formSubmit();
			}
		});

		// listGrid.addCellMouseDownHandler(new CellMouseDownHandler() {
		//
		// @Override
		// public void onCellMouseDown(CellMouseDownEvent event) {
		// getKindOfJob(event);
		// }
		// });
	}

	private void createLoadMsg() {
		loadMsg.setWidth(50);
		loadMsg.setHeight(10);
		loadMsg.setVisible(true);// false
	}

	// updateData -> addChangeHanders Job
	private void getKindOfJob(CellMouseDownEvent event) {
		int rowNum = event.getRowNum();
		int colNum = event.getColNum();
		if (colNum == 6) {
			String job = (String) view.getListGrid().getEditedCell(rowNum,
					colNum);
			if (job.equals("Delete")) {
				if (confirmMessage()) {
					// cancleAllTimer();
					deleteFilesFromS3(rowNum);
				} else {
					// Actions tmpBox = (Actions)event.getSource();
					// Window.alert(tmpBox.getSelectedIndex()+"");
					// tmpBox.setSelectedIndex(0);
				}
			} else if (job.equals("View Result")) {
				// cancleAllTimer();
				viewResultFromS3(rowNum);
			} else {
				Window.alert("No Action");
			}
		}
	}

	private void deleteFilesFromS3(final int rowNum) {
		loadMsgStart("Deleting...");
		final String xletName = (String) listGrid.getEditedCell(rowNum, 2);
		final String timeStamp = (String) listGrid.getEditedCell(rowNum, 3);
		// service.deleteFiles(cookie.getEmailAddressFromCookie(), xletName,
		// timeStamp, new AsyncCallback<String>() {
		service.deleteFiles("dreamer.co.kr@gmail.com", xletName, timeStamp,
				new AsyncCallback<String>() {
					@Override
					public void onFailure(Throwable caught) {
						Window.alert("DeleteS3 Method : " + caught.toString());
					}

					@Override
					public void onSuccess(String result) {
						System.out.println("deleteFiles result : " + result);
						// removeMessage();//progressbar
						deleteRow(xletName, timeStamp, rowNum);
					}
				});
	}// deleteFilesFromS3

	private void viewResultFromS3(final int rowNum) {

		final String xletName = (String) listGrid.getEditedCell(rowNum, 2);
		final String timeStamp = (String) listGrid.getEditedCell(rowNum, 3);

		cookie.setCookies("alias", (String) listGrid.getEditedCell(rowNum, 1));
		cookie.setCookies("xletName", xletName);
		cookie.setCookies("timeStamp", timeStamp);
		cookie.setCookies("bucketName", bucketName);
		// cookie.setCookies("key",
		// cookie.getEmailAddressFromCookie()+"/"+xletName+"."+timeStamp+".jar");
		cookie.setCookies("key", USER_ID + "/" + xletName + "." + timeStamp
				+ ".jar");

		// cancleAllTimer();
		// removeMessage(); // progressbar
		// call profillingResultServerWidget
		eventBus.goToProfilingResultServer();

	}// viewResultFromS3

	private void deleteRow(final String fileName, final String timeStamp,
			final int rowNum) {
		service.deleteFromSimpleDB("W", USER_ID, fileName, timeStamp,
				new AsyncCallback<Boolean>() {
					@Override
					public void onFailure(Throwable caught) {
					}

					@Override
					public void onSuccess(Boolean result) {
						System.out.println("remove start : " + rowNum);
						listGrid.removeData(listGrid.getRecord(rowNum));
						System.out.println("remove end");
					}
				});
		loadMsgEnd();
		cancelBtnClick();
	}// deleteRows

	private void cancelBtnClick() {
		view.getAliasTextBox().setText("");
		view.getAliasTextBox().setFocus(true);
		view.getXletName().setText("");
		view.getRadioBtn()[1].setChecked(true);
		view.getFileUploadBtn().setName("");
		view.getFileUploadBtn().setTitle("");

	}

	private void tableDataSet() {
		// eventBus.goToLoadMsgStart();
		System.out.println("tableDataSet_start");
		service.listAll("W", "dreamer.co.kr@gmail.com",
				new AsyncCallback<String>() {
					@Override
					public void onFailure(Throwable caught) {
						caught.printStackTrace();
					}

					@Override
					public void onSuccess(String result) {
						// removeMessage();
						loadDesign(result);
					}
				});
		System.out.println("tableDataSet_end");

	}

	private void loadDesign(String result) {
		if ((result != null) && (result.trim().length() != 0)) {
			System.out.println("addData , result : " + result);
			if (tableInsertbool) {
				updateRows(result);
			}
			tableInsertbool = false;
		}
		loadMsgEnd();
	}// loadDesig

	private void updateRows(String result) {
		JSONArray jArr = (JSONArray) JSONParser.parse(result);
		JSONObject jOjb = null;
		int len = jArr.size();
		Record[] recordArr = new Record[len];
		for (int i = 0; i < len; i++) {// for
			jOjb = (JSONObject) jArr.get(i);
			if( jOjb != null ){
				String date = format.format(new Date(Long.parseLong(jOjb.get(
						"timeStamp").toString().replaceAll("\"", ""))));
				String alias = jOjb.get("alias").toString().replaceAll("\"", "");
				String xletName = jOjb.get("xletName").toString().replaceAll("\"",
						"");
				String timeStamp = jOjb.get("timeStamp").toString().replaceAll(
						"\"", "");
				String ite = jOjb.get("iteration").toString().replaceAll("\"", "");
				if (ite.equals("null")) {
					ite = "100";
				}
				String iteration = Integer.parseInt(ite) <= 100 ? "Light"
						: (Integer.parseInt(ite) <= 200 ? "Medium" : "Heavy");
				String status = jOjb.get("status").toString().replaceAll("\"", "");
				ComboBoxItem cbi = new ComboBoxItem("actions", "actions");
				cbi.setValueMap("Choose Action", "Delete", "View Result");
				
				ListGridRecord record = new ListGridRecord();
				record.setAttribute("alias", alias);
				record.setAttribute("xletName", xletName);
				record.setAttribute("date", date);
				record.setAttribute("timeStamp", timeStamp);
				record.setAttribute("iteration", iteration);
				record.setAttribute("status", status);
				record.setAttribute("actions", "Choose Action");
				recordArr[i] = record;
				
	//			Actions listBox = new Actions(status, i);
	//			listBox.init();
	//			listGrid.addData(new CompanyRecord(date, alias, xletName,
	//					timeStamp, iteration, status, cbi));// ,
			}
		}// for
		listGrid.setUseAllDataSourceFields(true);
		listGrid.setData(recordArr);
		// listGrid.focus();
		// listGrid.focusInFilterEditor();
		// listGrid.setEditOnFocus(true);
		// listGrid.setData(comArr);
	}// updateRows

	private void formSubmit() {
		tableInsertbool = true;
		addRowCnt = 0;
		timerRunCnt = 0;
		form = view.getFormPanel();
		form.setEncoding(FormPanel.ENCODING_MULTIPART);
		form.setMethod(FormPanel.METHOD_POST);
		DOM.setElementProperty(form.getElement(), "name", "frm");
		newFileName = view.getXletName().getValue().trim();
		currentTime = System.currentTimeMillis() + "";
		iteration = getIterationTime();
		alias = view.getAliasTextBox().getValue().trim();
		// String sid = cookie.getEmailAddressFromCookie() + "&newFileName="
		// + newFileName + "." + currentTime + ".jar";
		// cookie.setCookies(cookie.getEmailAddressFromCookie() + "/"
		// + newFileName + "." + currentTime + ".jar" + "_alias", alias);
		// cookie.setCookies(cookie.getEmailAddressFromCookie() + "/"
		// + newFileName + "." + currentTime + ".jar" + "_iteration",
		// iteration);

		boolean result = false;
		result = submitDataNullCheck(result, view.getFileUploadBtn()
				.getFilename());

		String sid = "dreamer.co.kr@gmail.com" + "&newFileName=" + newFileName
				+ "." + currentTime + ".jar";
		cookie.setCookies("dreamer.co.kr@gmail.com" + "/" + newFileName + "."
				+ currentTime + ".jar" + "_alias", alias);
		cookie.setCookies("dreamer.co.kr@gmail.com" + "/" + newFileName + "."
				+ currentTime + ".jar" + "_iteration", iteration);

		form.setAction(formAction + "?sid=" + sid);

		if (result) {
			timerInit();
			timerStart();
			form.submit();
		} else {
			cancelBtnClick();
		}

		form.addSubmitCompleteHandler(new SubmitCompleteHandler() {
			@Override
			public void onSubmitComplete(SubmitCompleteEvent event) {
				System.out.println("DataSubmit_addSubmitCompleteHandler");
				submitDataInsert = true;
				String result = event.getResults();
				try {
					String message = result;
					// sqsService.pushQueue(newFileName, cookie
					// .getEmailAddressFromCookie(), currentTime,
					// getIterationTime(), new AsyncCallback<String>() {
					sqsService.pushQueue(newFileName,
							"dreamer.co.kr@gmail.com", currentTime,
							getIterationTime(), new AsyncCallback<String>() {
								@Override
								public void onFailure(Throwable caught) {
								}

								@Override
								public void onSuccess(String result) {
									// removeMessage();
									cancelBtnClick();
								}
							});
				} catch (Exception e) {
					// setMessage("Internal Error: Illegal result message.");
					Window.alert(e.toString());
				}
				// after the form submition, excutes insert into sdb
				try {
					service.addToSimpleDB("W", USER_ID, newFileName, iteration,
							currentTime, alias, status, null,
							new AsyncCallback<String>() {
								@Override
								public void onFailure(Throwable caught) {
									// extTimer.cancel();

								}

								@Override
								public void onSuccess(String result) {
									if (submitDataInsert) {
										addNewRow(result);
										tableInsertbool = false;
										submitDataInsert = false;
									}
								}
							});
				} catch (Exception e) {
					// setMessage("Internal Error: Illegal result message.");
					Window.alert(e.toString());
				}
			}
		});

	}

	private boolean submitDataNullCheck(boolean boolResutl, String filename) {
		boolean result = boolResutl;

		if ("".equals(iteration) || iteration == null) {
			Window.alert("Iteration is required");
			result = false;
		} else if ("".equals(newFileName) || newFileName == null) {
			Window.alert("Xlet Name is required");
			view.getXletName().setFocus(true);
			result = false;
			// setFocus("newFileName");
		} else if ("".equals(alias) || alias == null) {
			Window.alert("Alias is required");
			view.getAliasTextBox().setFocus(true);
			result = false;
			// setFocus("alias");
		} else if (filename == null || filename.length() == 0) {
			Window.alert("No file specified.");
			result = false;
		} else {
			result = true;
			// Progressbar
			// setMessage("Upload in progress...");
		}
		return result;
	}

	private String getIterationTime() {
		String value = null;
		for (InputElement input : view.getRadioBtn()) {
			if (input.isChecked()) {
				value = input.getValue();
			}
		}
		return value;

	}

	native boolean confirmMessage() /*-{
		var ret = false;

		if( $wnd.confirm("Are you sure you want to delete?")){
		ret = true;
		}
		return ret;
	}-*/;

	private void addNewRow(String resutl) {
		System.out.println("addNewRow");
		// addRowCnt = 0;
		String date = format.format(new Date(Long.parseLong(currentTime)));
		String inputAlias = alias;
		String xletName = newFileName;
		String timeStamp = currentTime;
		String inputIteration = Integer.parseInt(iteration) <= 100 ? "Light"
				: (Integer.parseInt(iteration) <= 200 ? "Medium" : "Heavy");
		String status = "PROFILING";
		String actions = "Delete";
		// String []actions = {"Choose Action", "Delete", "View Result"}; //
		// Test
		// listGrid.addData(new CompanyRecord(date, inputAlias, xletName,
		// timeStamp, inputIteration, status, actions));
		addRowCnt = 1;

	}

	public void onGoToWebSimulator() {
		Tab tab = new Tab("Web simulator", "/img/quota.png");
		HTMLFlow dydForm = new HTMLFlow();
		// DynamicForm dyForm = new DynamicForm();
		dydForm.setWidth100();
		dydForm.setHeight100();
		tableDataSet();
		dydForm.addChild(view.getViewWidget());
		tab.setPane(dydForm);
		tab.setCanClose(true);
		eventBus.addTab(tab);
		loadMsgStart("Loading...");
	}

	public void onStart() {
		loadMsgStart("Loading...");
		System.out.println("Web_onStart_Start");
		Tab tab = new Tab("Web simulator", "/img/quota.png");
		DynamicForm dyForm = new DynamicForm();
		dyForm.setWidth100();
		dyForm.setHeight100();
		tableDataSet();
		dyForm.addChild(view.getViewWidget());
		tab.setPane(dyForm);
		tab.setCanClose(true);
		eventBus.addTab(tab);
		System.out.println("Web_onStart_End");
	}

	@InjectService
	public void setService(XletProfilingServiceAsync service) {
		this.service = service;
	}

	@InjectService
	public void setService(SqsServiceAsync sqsService) {
		this.sqsService = sqsService;
	}

	public void loadMsgStart(final String msg) {
		System.out.println("load_Start");
		vPanel.clear();
		vPanel.setStyleName("vPanel");
		vPanel.setWidth("800");
		vPanel.setHeight("70");
		vPanel.add(loadMsg);
		vPanel.setVerticalAlignment(HasVerticalAlignment.ALIGN_MIDDLE);
		view.getFormPanel().clear();
		view.getFormPanel().add(vPanel);
		loadMsg.setVisible(true);
		loadMsg.animateResize(200, 10, new AnimationCallback() {// 170,10

					@Override
					public void execute(boolean earlyFinish) {
						loadMsg.animateResize(200, 35);// 170,33
						loadMsg
								.setContents("&nbsp;&nbsp;&nbsp;<img width='19' height='19' src='/img/cube_frame.png'>&nbsp;<font size='2'>&nbsp;"
										+ msg + "</font>");
					}
				});
		loadMsg.redraw();
	}

	public void loadMsgEnd() {
		System.out.println("load_End");
		// popup.setWidget(loadMsg);
		loadMsg
				.setContents("&nbsp;<img width='19' height='19' src='/img/cube_frame.png'>&nbsp;<font size='2'> Loading...</font>");
		loadMsg.animateResize(170, 10, new AnimationCallback() {

			@Override
			public void execute(boolean earlyFinish) {
				loadMsg.animateResize(50, 10);
			}
		});
		loadMsg.setVisible(false);
		loadMsg.redraw();
		view.getFormPanel().clear();
		view.getFormPanel().add(view.getHtmlPanel());
		// popup.hide();
	}

	private void timerInit() {
		submitTimer = new Timer() {

			@Override
			public void run() {
				if (addRowCnt == 1) {
					stopTimer();
				} else {
					showTimer();
				}
			}
		};
	}

	private void timerStart() {
		stopTimer();
		submitTimer.scheduleRepeating(500);
		submitTimer.run();

	}

	private void stopTimer() {
		submitTimer.cancel();
		view.getFormPanel().clear();
		view.getFormPanel().add(view.getHtmlPanel());
	}

	private void showTimer() {
		String[] imgSrcVal = { "blue", "green", "grey", "red", "yellow" };

		view.getFormPanel().clear();
		view.getFormPanel().add(
				new HTML("&nbsp;<img width='24' height='24' src='/img/star_"
						+ imgSrcVal[timerRunCnt]
						+ ".png'><font size='2' color='"
						+ imgSrcVal[timerRunCnt] + "'>Data Update...</font>"));
		timerRunCnt++;
		if (timerRunCnt == 5) {
			timerRunCnt = 0;
		}

	}

}
