// M2Plus web ログイン情報 共通処理スクリプト
//
// 現在のログイン状態の把握やログイン・ログアウト処理を実装しています。
// 外部モジュールが、ログイン・ログアウトと連携して何か実施したい場合は
// 本モジュールにコールバックを登録します。
//
// 現行の実装はajaxでログインを行わないので、ログインイベントが発生するのは
// 「画面の初期化完了時にログイン済み状態が確定したら」です。
//
// 本スクリプトは以下に依存しています。
// jquery
// jquery.cookie
// jquery.jsonp
//


/**
 * クッキー処理用の情報
 */
var M2PLOGIN_COOKIE_CONFIG = {
		"domain":  '.m2plus.com',
		"path":    '/',
		"expires": ''
}

/**
 * ユーザー情報を自動更新する時間間隔(秒).
 */
var M2PLOGIN_REFRESH_PERIOD = 1800;


/**
 * ログアウト完了時のコールバック.
 * m2plogin_add_logoutcallbackで登録する.
 */
var m2plogin_logout_callbacks = new Array();

/**
 * ログイン完了時のコールバック.
 * m2plogin_add_logincallbackで登録する.
 */
var m2plogin_login_callbacks = new Array();


/**
 * 初期化完了フラグ(ラッチ).
 * m2plogin_refreshが１度でも実行されるとtrueに変化します。
 */
var m2plogin_initialized_flg = false;


/**
 * ログイン情報の初期化.
 * 過去のログインチケットが存在する場合、会員情報をサーバーから取得します。
 * @return
 */
function m2plogin_init() {
	m2plogin_refresh();
}

/**
 * ログアウト後に呼んでほしいコールバックを登録する.
 * @param callback コールバック関数(引数無し)のシグネチャ
 * @return
 */
function m2plogin_add_logoutcallback(callback) {
	m2plogin_logout_callbacks.push( callback );
	
	// 登録時にログアウト状態なら即座にコールバック実行.
	if (m2plogin_initialized_flg && ! m2plogin_check_login() ) {
		callback();
	}
}

/**
 * ログイン後に呼んでほしいコールバックを登録する.
 * 現行の使用ではAjaxでログインするわけではないので、画面表示の初期化が完了して
 * ログイン済み状態であればコールバックが呼ばれる、という動作になります。
 * 
 * @param callback コールバック関数(ユーザー情報jsonを引数にとる)のシグネチャ
 * @return
 */
function m2plogin_add_logincallback(callback) {
	m2plogin_login_callbacks.push( callback );
	
	// 登録時にログイン状態なら即座にコールバック実行.
	if (m2plogin_initialized_flg && m2plogin_check_login() ) {
		callback( m2plogin_get_user() );
	}
}

/**
 * 認証チケットを持っているかどうか.
 * 過去にログインに成功している場合はtrueを返します。
 * 本メソッドがtrueを返した場合、メールアドレス、チケット等が
 * 存在している事を意味します。
 * <br />
 * チケットが残っていても認証がタイムアウトしている場合もあるので、
 * セキュアな処理の実行可否に使用することはできません。
 * @return
 */
function m2plogin_check_login() {
	var ticket = $.cookie('m2p_ticket') || '';
	
	return ( ticket.length > 0 );
}

/**
 * ユーザー情報(JSON)を取得する.
 * ログインしていない状態で実行しても意味がないので注意
 * @return
 */
function m2plogin_get_user() {
	var user = {
		maddr: m2plogin_get_maddr(),
		names: m2plogin_get_names(),
		namem: m2plogin_get_namem(),
		point: m2plogin_get_point()
	};
	
	return user;
}

/**
 * メールアドレス（会員アカウント）のゲッター.
 * @return
 */
function m2plogin_get_maddr() {
	return $.cookie('m2p_maddr') || '';
}
/**
 * 氏名（姓）のゲッター.
 * @return
 */
function m2plogin_get_names() {
	return $.cookie('m2plogin_names') || '';
}
/**
 * 氏名（名）のゲッター.
 * @return
 */
function m2plogin_get_namem() {
	return $.cookie('m2plogin_namem') || '';
}
/**
 * ポイントのゲッター.
 * @return
 */
function m2plogin_get_point() {
	return $.cookie('m2plogin_point') || '';
}

/**
 * ユーザー情報の最終更新時刻.
 * ユーザー情報が存在しない(時刻がセットされていない場合) 0 が返ります。
 * @return Integer unixtime
 */
function m2plogin_lastrefresh() {
	var lastrefresh = parseInt( $.cookie('m2plogin_lastrefresh') );
	
	return isNaN(lastrefresh) ? 0 : lastrefresh;
}

/**
 * ユーザー情報の有効時間を強制的にexpireさせる.
 * 外部利用者が、ユーザー情報が変更されたことを通知したい場合に呼ぶメソッド.
 */
function m2plogin_expire_userinfo() {
	$.cookie( 'm2plogin_lastrefresh', '1', M2PLOGIN_COOKIE_CONFIG);
}

/**
 * ユーザー情報を更新する.
 * 必要に応じてサーバーから情報を取得し、ログインまたはログアウト処理が実行されます。
 * 
 * @param isForce boolean 自動更新期間前でも強制的に更新する場合 trueを指定
 */
function m2plogin_refresh(isForce) {
	// 過去のログインチケットが存在しなければログアウト処理を実行
	if ( ! m2plogin_check_login() ) {
		m2plogin_logout();
		m2plogin_initialized_flg = true;
		return;
	}
	
	// 現在時刻と最終更新を比較して所定の時間内ならログイン済みとして何もしない
	var now = parseInt((new Date)/1000);

	if ( ! isForce && (m2plogin_lastrefresh() + M2PLOGIN_REFRESH_PERIOD > now) ) {
		m2plogin_login();
		m2plogin_initialized_flg = true;
		return;
	}
	
	// ajaxでユーザー情報を取得して更新する.
	$.jsonp( { 
		url       : 'https://ssl.m2plus.com/cgi-bin/user/userinfo.cgi?callback=?',
		success   : m2plogin_response_ok,
		error     : m2plogin_response_ng,
		cache     : false,
		pageCache : false
	} );
}

/**
 * ユーザー情報取得Ajax呼び出し(JSONP)のOKコールバック.
 * @param json
 * @param status
 * @return
 */
function m2plogin_response_ok(json, status) {
	if ( json.err != 0 ) {
		// エラー応答であればログアウトする
		m2plogin_logout();

	} else {
		// ユーザー情報をクッキーに保存
		$.cookie( 'm2plogin_names',  json.names,  M2PLOGIN_COOKIE_CONFIG);
		$.cookie( 'm2plogin_namem',  json.namem,  M2PLOGIN_COOKIE_CONFIG);
		$.cookie( 'm2plogin_point',  m2plib_addcomma(json.point),  M2PLOGIN_COOKIE_CONFIG);
		// 最終更新時刻を更新
		$.cookie( 'm2plogin_lastrefresh', parseInt((new Date)/1000), M2PLOGIN_COOKIE_CONFIG);	
		
		// ログインコールバックの呼び出し
		m2plogin_login();
	}
	
	// 初期化完了フラグをON
	m2plogin_initialized_flg = true;
}

/**
 * ユーザーログインを仮想的に実行する.
 * (画面の初期化が完了してログイン中の場合に実行される)
 * 実装としてはコールバック呼び出ししかしていません。
 */
function m2plogin_login() {
	// ログインコールバックの呼び出し
	var user = m2plogin_get_user();
	
	for (var i=0; i < m2plogin_login_callbacks.length; i++) {
		m2plogin_login_callbacks[i]( user );
	}
}

/**
 * ユーザー情報取得Ajax呼び出し(JSONP)のNGコールバック.
 * @param json
 * @param status
 * @return
 */
function m2plogin_response_ng(json, status) {
	// ログアウトする
	m2plogin_logout();

	// 初期化完了フラグをON
	m2plogin_initialized_flg = true;
}

/**
 * ログアウトを実行する.
 * @return
 */
function m2plogin_logout() {
	// クッキー情報をクリア
	$.cookie( 'm2plogin_names', null, M2PLOGIN_COOKIE_CONFIG);
	$.cookie( 'm2plogin_namem', null, M2PLOGIN_COOKIE_CONFIG);
	$.cookie( 'm2plogin_point', null, M2PLOGIN_COOKIE_CONFIG);
	$.cookie( 'm2plogin_lastrefresh', null, M2PLOGIN_COOKIE_CONFIG);	
	$.cookie( 'm2p_maddr',      null, M2PLOGIN_COOKIE_CONFIG);
	$.cookie( 'm2p_ticket',     null, M2PLOGIN_COOKIE_CONFIG);
	
	// ログアウトコールバックの呼び出し
	for (var i=0; i < m2plogin_logout_callbacks.length; i++) {
		m2plogin_logout_callbacks[i]();
	}	
}

