package jp.agentec.abook.abv.bl.logic;

import java.sql.Timestamp;
import java.util.List;

import jp.agentec.abook.abv.bl.acms.type.ContentReadingStatus;
import jp.agentec.abook.abv.bl.common.ABVEnvironment;
import jp.agentec.abook.abv.bl.common.log.Logger;
import jp.agentec.abook.abv.bl.data.dao.AbstractDao;
import jp.agentec.abook.abv.bl.data.dao.ContentPageReadingLogDao;
import jp.agentec.abook.abv.bl.dto.ContentPageReadingLogDto;
import jp.agentec.adf.util.DateTimeFormat;
import jp.agentec.adf.util.DateTimeUtil;

import org.json.adf.JSONArray;
import org.json.adf.JSONObject;
public  class ContentPageReadingLogLogic extends AbstractLogic {
	private static final String TAG = "ContentPageReadingLogLogic";
	private ContentPageReadingLogDao contentPageReadingLogDao = AbstractDao.getDao(ContentPageReadingLogDao.class);

	/*package*/ ContentPageReadingLogLogic() {
	}

	/**
	 * ページ閲覧開始
	 * 
	 * @param contentId
	 * @param readingLogId
	 * @param pageNum
	 */
	public void startContentPageReadLog(long contentId, int readingLogId, int pageNum) {
		if (ABVEnvironment.getInstance().disableLogSend) {
			return;
		}
		
		ContentPageReadingLogDto dto;
		dto = contentPageReadingLogDao.getContentPageReadingLog(contentId, pageNum, readingLogId);
		
		if (dto != null) {
			// ログが残っている場合再利用する
			if (dto.status != ContentReadingStatus.reading.type()) {
				dto.readingLogId = readingLogId;
				dto.status = ContentReadingStatus.reading.type();
				dto.resumeDate = DateTimeUtil.getCurrentDate();
				contentPageReadingLogDao.updateContentPageReadingLog(dto);
			}
		} else {
			dto = new ContentPageReadingLogDto();
			dto.pageReadingLogId = contentPageReadingLogDao.getNewContentPageReadingLogId();
			dto.readingLogId = readingLogId;
			dto.contentId = contentId;
			dto.pageNum = pageNum;
			dto.startDate = DateTimeUtil.getCurrentDate();
			dto.resumeDate = DateTimeUtil.getCurrentDate();
			dto.duration = 0;
			dto.status = ContentReadingStatus.reading.type();
			contentPageReadingLogDao.insertContentPageReadingLog(dto);
		}

	}

	/**
	 * バックグラウンド等によるページ閲覧一時停止
	 *
	 * @param contentId
	 * @param pageNum
	 * @param readingLogId
	 */
	public void pauseContentPageReadLog(long contentId, int pageNum, long readingLogId) {
		ContentPageReadingLogDto dto = contentPageReadingLogDao.getContentPageReadingLog(contentId, pageNum, readingLogId);

		if (dto == null) {
			Logger.e(TAG, "ContentPageReadingLogDto not found. contentId=" + contentId + ", pageNum=" + pageNum);
			return;
		}

		dto.status = ContentReadingStatus.suspend.type();
		dto.endDate = DateTimeUtil.getCurrentDate();
		// longで計算してからintにする
		long durationMilliSecond = DateTimeUtil.getCurrentDate().getTime() - dto.resumeDate.getTime();
		//ミリ秒から秒に変換（小数点以下切り捨て）
		dto.duration = dto.duration + (int)(durationMilliSecond / 1000L);
		contentPageReadingLogDao.updateContentPageReadingLog(dto);
	}


	/**
	 * ページ閲覧終了
	 * 
	 * @param contentId
	 * @param pageNum
	 * @param readingLogId
	 */
	public void endContentPageReadLog(long contentId, int pageNum, long readingLogId) {
		ContentPageReadingLogDto dto = contentPageReadingLogDao.getContentPageReadingLog(contentId, pageNum, readingLogId);
		if (dto != null) {
			dto.status = ContentReadingStatus.readed.type();
			dto.endDate = DateTimeUtil.getCurrentDate();
			// longで計算してからintにする
			long durationMilliSecond = DateTimeUtil.getCurrentDate().getTime() - dto.resumeDate.getTime();
			//ミリ秒から秒に変換（小数点以下切り捨て）
			dto.duration = dto.duration + (int)(durationMilliSecond / 1000L);
			contentPageReadingLogDao.updateContentPageReadingLog(dto);
		}
	}
	
	/**
	 * ページ別閲覧ログをcsvライクなjson形式にして返します
	 * 
	 * @param contentId
	 * @param readingLogId
	 * @return
	 */
	public JSONObject getContentPageReadLogJson(long contentId, int readingLogId) {
		JSONObject json = null;
		List<ContentPageReadingLogDto> list = contentPageReadingLogDao.getContentPageReadLogs(contentId, readingLogId);
		for (ContentPageReadingLogDto dto : list) {
			endContentPageReadLog(contentId, dto.pageNum, readingLogId);
		}

		if (list.size() > 0) {
			json = new JSONObject();
			
			// csvのheader部
			JSONArray headerArray = new JSONArray();
			headerArray.put("contentId");
			headerArray.put("pageNo");
			headerArray.put("readingStartDate");
			headerArray.put("readingEndDate");
			headerArray.put("readingTime");
			json.put("header", headerArray);

			JSONArray linesRootArray = new JSONArray();
			
			// csvのbody部
			for (ContentPageReadingLogDto dto : list) {
				// 3秒以上の場合のみJSONに含める
				if(dto.duration >= ABVEnvironment.getInstance().minPageLogSecond){
					JSONArray linesArray = new JSONArray();
					linesArray.put(dto.contentId);

					// Androidはページ数を0から管理しているので+1する
					linesArray.put(dto.pageNum + 1); 

					Timestamp startDate = new Timestamp(dto.startDate.getTime());
					linesArray.put(DateTimeUtil.toStringInTimeZone(startDate, DateTimeFormat.yyyyMMddHHmmss_hyphen, "GMT") + ",GMT");

					Timestamp endDate = new Timestamp(dto.endDate.getTime());
					linesArray.put(DateTimeUtil.toStringInTimeZone(endDate, DateTimeFormat.yyyyMMddHHmmss_hyphen, "GMT") + ",GMT");

					linesArray.put(dto.duration);

					linesRootArray.put(linesArray);
				}
			}
			json.put("lines", linesRootArray);
		}

		return json;
	}
}
