<?php
/**
 * コンテナクラス
 *
 * PHP versions 5
 *
 * LICENSE: This source file is licensed under the terms of the GNU General Public License.
 *
 * @package    Magic3 Framework
 * @author     平田直毅(Naoki Hirata) <naoki@aplo.co.jp>
 * @copyright  Copyright 2006-2007 Magic3 Project.
 * @license    http://www.gnu.org/copyleft/gpl.html  GPL License
 * @version    SVN: $Id: admin_bbs_mainMemberWidgetContainer.php 20 2007-11-16 05:13:27Z fishbone $
 * @link       http://www.magic3.org
 */
require_once($gEnvManager->getContainerPath() .			'/baseWidgetContainer.php');
require_once($gEnvManager->getCurrentWidgetDbPath() .	'/bbs_mainMemberDb.php');
require_once($gEnvManager->getCurrentWidgetDbPath() .	'/bbs_mainDb.php');

class admin_bbs_mainMemberWidgetContainer extends BaseWidgetContainer
{
	private $db;	// DB接続オブジェクト
	private $mainDb;	// DB接続オブジェクト
	private $sysDb;		// システムDBオブジェクト
	private $serialNo;			// シリアル番号
	private $firstNo;			// 項目番号
	private $state;				// 都道府県
	private $memberType;		// 会員タイプ
	private $langId;			// 現在の言語
	private $groupRows;			// すべてのグループ
	const DEFAULT_COUNTRY_ID = 'JPN';	// デフォルト国ID
	const THIS_WIDGET_ID = 'bbs_main';		// ウィジェットID
	const DEFAULT_LIST_COUNT = 20;			// 最大リスト表示数
	const USE_EMAIL		= 'use_email';		// EMAIL機能が使用可能かどうか
	const SEND_PASSWORD_FORM = 'send_password';		// パスワード送信用フォーム
	const AUTO_EMAIL_SENDER	= 'auto_email_sender';		// 自動送信メール用送信者アドレス
	const GUEST_GROUP_ID = 1;		// ゲストグループのID
	/**
	 * コンストラクタ
	 */
	function __construct()
	{
		global $gInstanceManager;
		
		// 親クラスを呼び出す
		parent::__construct();
		
		// DBオブジェクト作成
		$this->db = new bbs_mainMemberDb();
		$this->mainDb = new bbs_mainDb();
		$this->sysDb = $gInstanceManager->getSytemDbObject();
	}
	/**
	 * テンプレートファイルを設定
	 *
	 * _assign()でデータを埋め込むテンプレートファイルのファイル名を返す。
	 * 読み込むディレクトリは、「自ウィジェットディレクトリ/include/template」に固定。
	 *
	 * @param RequestManager $request		HTTPリクエスト処理クラス
	 * @param object         $param			任意使用パラメータ。そのまま_assign()に渡る
	 * @return string 						テンプレートファイル名。テンプレートライブラリを使用しない場合は空文字列「''」を返す。
	 */
	function _setTemplate($request, &$param)
	{
		return 'admin_member.tmpl.html';
	}
	/**
	 * テンプレートにデータ埋め込む
	 *
	 * _setTemplate()で指定したテンプレートファイルにデータを埋め込む。
	 *
	 * @param RequestManager $request		HTTPリクエスト処理クラス
	 * @param object         $param			任意使用パラメータ。_setTemplate()と共有。
	 * @param								なし
	 */
	function _assign($request, &$param)
	{
		global $gEnvManager;
		global $gMailManager;

		$now = date("Y/m/d H:i:s");	// 現在日時
		
		// ユーザ情報、表示言語
		$userId		= $gEnvManager->getCurrentUserId();
		$this->langId	= $gEnvManager->getCurrentLanguage();		// 表示言語を取得
		$countryId = self::DEFAULT_COUNTRY_ID;			// デフォルト国ID

		// グループ一覧を取得
		$this->db->getAllGroupInfo($this->langId, $this->groupRows);
		
		// 入力値を取得
		$act = $request->trimValueOf('act');
		$this->serialNo = $request->trimValueOf('serial');		// 選択項目のシリアル番号
		if (empty($this->serialNo)) $this->serialNo = 0;
		$pageNo = $request->trimValueOf('page');				// ページ番号
		if (empty($pageNo)) $pageNo = 1;
		
		// DBの保存設定値を取得
		$maxListCount = self::DEFAULT_LIST_COUNT;
		$serializedParam = $this->sysDb->getWidgetParam(self::THIS_WIDGET_ID);
		if (!empty($serializedParam)){
			$dispInfo = unserialize($serializedParam);
			$maxListCount = $dispInfo->maxMemberListCountByAdmin;		// 会員リスト最大表示数
		}
		
		$this->memberType	= $request->trimValueOf('member_type');				// 会員タイプ
		$name			= $request->trimValueOf('name');			// 会員名
		$email			= $request->trimValueOf('email');			// eメール(ログインアカウント)
		$url			= $request->trimValueOf('url');			// ホームーページ
		$signature		= $request->trimValueOf('signature');			// 署名
		$recvMailnews = 0;		// 新着情報メール受信
		
		// 所属グループを取得
		$groupArray = array('1');
		for ($i = 0; $i < count($this->groupRows); $i++){
			$id = $this->groupRows[$i]['sg_id'];
			$itemName = 'group_item' . $id;
			$itemValue = ($request->trimValueOf($itemName) == 'on') ? 1 : 0;
			if ($itemValue) $groupArray[] = $id;
		}
		sort($groupArray, SORT_NUMERIC);		// 昇順ソート
						
		$replaceNew = false;		// データを再取得するかどうか
		if ($act == 'select'){		// 項目選択の場合
			if ($this->serialNo == 0){		// シリアル番号が0のときは、新規追加モードにする
				// 入力値初期化
				$name = '';			// 名前
				$email = '';			// eメール(ログインアカウント)
				$url = '';			// ホームページ
				$signature = '';	// 署名
				$groupArray = array();			// 所属グループ
				$recvMailnews = 0;		// 新着情報メール受信
				$updateUser = '';	// 更新者
				$updateDt = '';	// 更新日時
			} else {
				$replaceNew = true;			// 会員情報を再取得
			}
		} else if ($act == 'add'){		// 項目追加の場合
			// 値取得
			$group = implode($groupArray, ',');		// 所属グループ
			
			// 入力チェック
			$this->checkInput($name, '名前');
			$this->checkMailAddress($email, 'Eメール');
			
			// 名前が重複していないかチェック
			if ($this->db->isExistsMemberName($name)) $this->setAppErrorMsg('同名の会員が存在します');

			// メールアドレスが登録済みかチェック
			if ($this->sysDb->isExistsAccount($email)){// メールアドレスがログインIDとして既に登録されているかチェック
					$this->setAppErrorMsg('このEメールアドレスは既に登録されています');
			}
			// エラーなしの場合は、データを登録
			if ($this->getMsgCount() == 0){
				// パスワードは自動生成
				$password = $this->makePassword();
				
				// トランザクションスタート
				$this->db->startTransaction();

				// ログインユーザを作成
				$ret = $this->db->addUser(1/* 正会員 */, $name, $email, $password, self::THIS_WIDGET_ID, $userId, $now, $loginUserId);		// 新規ログインユーザIDを取得

				// 会員情報を登録
				if ($ret) $ret = $this->db->updateMember(0, $this->langId, 1/*正会員*/, $loginUserId, $name, $group, $url, $signature, $recvMailnews, $userId, $now, $newSerial);

				// トランザクション終了
				$ret = $this->db->endTransaction();
				if ($ret){
					$this->setGuidanceMsg('データを追加しました');
					
					// シリアル番号更新
					$this->serialNo = $newSerial;
					$replaceNew = true;			// 会員情報を再取得
					
					// パスワード変更のメッセージ
					$this->tmpl->addVar("send_password", "pwd_message", '新規パスワード: ' . $password);
				} else {
					$this->setAppErrorMsg('データ追加に失敗しました');
				}
			}
		} else if ($act == 'update'){		// 項目更新の場合
			// 値取得
			$group = implode($groupArray, ',');		// 所属グループ
			
			// 登録済み会員情報を取得
			$ret = $this->db->getMemberBySerial($this->serialNo, $row);
			if ($ret){
				$loginUserId = $row['sv_login_user_id'];
				$oldName = $row['sv_name'];
			} else {
				$oldName = '';
				$this->setAppErrorMsg('ログインアカウントが見つかりません');
			}
				
			// 入力チェック
			$this->checkInput($name, '名前');
			
			// 名前が重複していないかチェック
			if ($name != $oldName && $this->db->isExistsMemberName($name)) $this->setAppErrorMsg('同名の会員が存在します');
			
			// エラーなしの場合は、データを登録
			if ($this->getMsgCount() == 0){
				// トランザクションスタート
				$this->db->startTransaction();

				// 会員情報更新
				if ($ret) $ret = $this->db->updateMember($this->serialNo, $this->langId, 1/*正会員*/, $loginUserId, $name, $group, $url, $signature, $recvMailnews, $userId, $now, $newSerial);
			
				// トランザクション終了
				$ret = $this->db->endTransaction();
				if ($ret){
					$this->setGuidanceMsg('データを更新しました');
					
					// 登録済みのカテゴリーを取得
					$this->serialNo = $newSerial;
					$replaceNew = true;			// 会員情報を再取得
				} else {
					$this->setAppErrorMsg('データ更新に失敗しました');
				}
			}
		} else if ($act == 'delete'){		// 項目削除の場合
			if (empty($this->serialNo)){
				$this->setUserErrorMsg('削除する会員が選択されていません');
			}
			// エラーなしの場合は、データを削除
			if ($this->getMsgCount() == 0){
				$ret = $this->db->delMemberBySerial($this->serialNo);
				if ($ret){		// データ削除成功のとき
					$this->setGuidanceMsg('データを削除しました');
				} else {
					$this->setAppErrorMsg('データ削除に失敗しました');
				}
			}
		} else if ($act == 'selmembertype'){	// 会員種別選択
			$this->serialNo = 0;
			
			// 入力値初期化
			$name = '';			// 名前
			$email = '';			// eメール(ログインアカウント)
			$url = '';			// ホームページ
			$signature = '';	// 署名
			$groupArray = array();			// 所属グループ
			$recvMailnews = 0;		// 新着情報メール受信
			$updateUser = '';	// 更新者
			$updateDt = '';	// 更新日時
		} else if ($act == 'search'){		// 検索再実行
			$this->serialNo = 0;
			
			// 入力値初期化
			$name = '';			// 名前
			$email = '';			// eメール(ログインアカウント)
			$url = '';			// ホームページ
			$signature = '';	// 署名
			$groupArray = array();			// 所属グループ
			$recvMailnews = 0;		// 新着情報メール受信
			$updateUser = '';	// 更新者
			$updateDt = '';	// 更新日時
		} else if ($act == 'sendpassword'){	// パスワードを送信
			// メール送信設定のときはメールを送信
			if ($this->mainDb->getConfig(self::USE_EMAIL) == '1'){
				// 登録済み会員情報を取得
				$ret = $this->db->getMemberBySerial($this->serialNo, $row);
				if ($ret){
					$loginUserId = $row['sv_login_user_id'];
					
					// パスワード作成
					$password = $this->makePassword();

					// パスワード変更
					$ret = $this->sysDb->updateLoginUserPassword($loginUserId, $password);
					if ($ret){
						$fromAddress = $this->mainDb->getConfig(self::AUTO_EMAIL_SENDER);	// 自動送信送信元
						$toAddress = $this->convertToDispString($row['login_user_account']);			// eメール(ログインアカウント)
						$mailParam = array();
						$mailParam['PASSWORD'] = $password;
						$ret = $gMailManager->sendFormMail(2, self::THIS_WIDGET_ID, $toAddress, $fromAddress, '', '', self::SEND_PASSWORD_FORM, $mailParam);// 手動送信
						
						// パスワード変更のメッセージ
						$this->tmpl->addVar("send_password", "pwd_message", '新規パスワード: ' . $password);
					}
				}

				if ($ret){
					$this->setGuidanceMsg('メール送信完了しました');
				} else {
					$this->setAppErrorMsg('メール送信に失敗しました');
				}
			} else {
				$this->setAppErrorMsg('メール送信できません');
			}
			$replaceNew = true;			// 会員情報を再取得
		} else {	// 初期表示
			// 入力値初期化
			$this->serialNo = 0;		// シリアル番号

			// 入力値初期化
			$name = '';			// 名前
			$email = '';			// eメール(ログインアカウント)
			$url = '';			// ホームページ
			$signature = '';	// 署名
			$groupArray = array();			// 所属グループ
			$recvMailnews = 0;		// 新着情報メール受信
			$updateUser = '';	// 更新者
			$updateDt = '';	// 更新日時
		}
		// 会員情報を再取得
		if ($replaceNew){
			// 指定会員の情報を取得
			$ret = $this->db->getMemberBySerial($this->serialNo, $row);
			if ($ret){
				// 取得値を設定
				$name = $this->convertToDispString($row['sv_name']);			// 名前
				//$email = $this->convertToDispString($row['lu_account']);			// eメール(ログインアカウント)
				$email = $this->convertToDispString($row['login_user_account']);// eメール(ログインアカウント)
				$registDt = $this->convertToDispDateTime($row['sv_regist_dt']);			// 登録日時
				$url = $this->convertToDispString($row['sv_url']);			// URL
				$signature = $this->convertToDispString($row['sv_signature']);	// 署名
				$updateUser = $this->convertToDispString($row['update_user_name']);	// 更新者
				$updateDt = $this->convertToDispDateTime($row['sv_create_dt']);	// 更新日時
				$groupArray = explode(',', $row['sv_group']);		// 所属グループ
			}
		}
		// 会員タイプ
		if (empty($this->memberType)){		// 正会員のとき
			$this->tmpl->addVar("_widget", "member_regular", 'selected');
		} else {
			$this->tmpl->addVar("_widget", "member_tmp", 'selected');
		}
		
		// ###### 会員一覧を作成 #####
		if (empty($this->memberType)){		// 正会員のとき
			// 総数を取得
			$totalCount = $this->db->getMemberCount(1);
		} else {
			// 総数を取得
			$totalCount = $this->db->getMemberCount(0);
		}
		
		// 表示するページ番号の修正
		$pageCount = (int)(($totalCount -1) / $maxListCount) + 1;		// 総ページ数
		if ($pageNo < 1) $pageNo = 1;
		if ($pageNo > $pageCount) $pageNo = $pageCount;
		$this->firstNo = ($pageNo -1) * $maxListCount + 1;		// 先頭番号
		
		if (empty($this->memberType)){		// 正会員のとき
			// 会員リストを表示
			$this->db->getMemberList(1, $maxListCount, ($pageNo -1) * $maxListCount, array($this, 'memberListLoop'));
		} else {
			// 仮会員リストを表示
			$this->db->getMemberList(0, $maxListCount, ($pageNo -1) * $maxListCount, array($this, 'memberListLoop'));
		}
		
		// ページング用リンク作成
		$pageLink = '';
		if ($pageCount > 1){	// ページが2ページ以上のときリンクを作成
			for ($i = 1; $i <= $pageCount; $i++){
				if ($i == $pageNo){
					$link = '&nbsp;' . $i;
				} else {
					$link = '&nbsp;<a href="#" onclick="selpage(\'' . $i . '\');return false;">' . $i . '</a>';
				}
				$pageLink .= $link;
			}
		}
		$this->tmpl->addVar("_widget", "page_link", $pageLink);
		
		// #### 更新、新規登録部をを作成 ####
		$this->tmpl->addVar("_widget", "name", $name);		// 会員名
		$this->tmpl->addVar("_widget", "email", $email);		// eメール(ログインアカウント)
		$this->tmpl->addVar("_widget", "regist_dt", $registDt);	// 登録日時
		$this->tmpl->addVar("_widget", "url", $url);			// URL
		$this->tmpl->addVar("_widget", "signature", $signature);// 署名
		$this->tmpl->addVar("_widget", "update_user", $updateUser);	// 更新者
		$this->tmpl->addVar("_widget", "update_dt", $updateDt);	// 更新日時
		
		// グループ選択欄
		if (count($this->groupRows) > 0) $this->tmpl->setAttribute('group', 'visibility', 'visible');
		for ($i = 0; $i < count($this->groupRows); $i++){
			$id = $this->groupRows[$i]['sg_id'];
			$checked = '';
			if ($id == self::GUEST_GROUP_ID || in_array($id, $groupArray)) $checked = 'checked';
			$readonly = '';
			if ($id == self::GUEST_GROUP_ID) $readonly = 'disabled';
			$row = array(
				'id'    => $id,			// ID
				'name'     => $this->groupRows[$i]['sg_name'],			// グループ名
				'group_checked' => $checked,						// 選択中かどうか
				'group_readonly' => $readonly						// 変更不可かどうか
			);
			$this->tmpl->addVars('group', $row);
			$this->tmpl->parseTemplate('group', 'a');
		}
					
		if (!empty($this->memberType)){		// 仮会員のときは変更不可
			$this->tmpl->addVar("_widget", "member_no_disabled", 'disabled');		// 会員No
			$this->tmpl->addVar("_widget", "email_disabled", 'disabled');		// eメール(ログインアカウント)
		}
		
		// ボタンの設定
		if ($this->serialNo == 0){		// 新規追加項目を選択しているとき
			$this->tmpl->addVar("_widget", "new_selected", 'checked');// 新規追加をチェック状態にする
			
			$this->tmpl->setAttribute('add_button', 'visibility', 'visible');// 「新規追加」ボタン
		} else {
			$this->tmpl->addVar("_widget", "email_disabled", 'disabled');		// eメール(ログインアカウント)
			
			// パスワード送信部の表示制御
			$this->tmpl->setAttribute('send_password', 'visibility', 'visible');
			
			// データ更新、削除ボタン表示
			$this->tmpl->setAttribute('delete_button', 'visibility', 'visible');// 削除ボタン
			
			if (empty($this->memberType)){		// 正会員のときは変更可
				$this->tmpl->setAttribute('update_button', 'visibility', 'visible');
			}
		}
		// メール送信可否状況によるボタンの制御
		$useEmail = $this->mainDb->getConfig(self::USE_EMAIL);
		if ($useEmail != '1'){		// メール送信不可のとき
			$this->tmpl->addVar("send_password", "send_message", 'メール送信不可に設定されています<br>');
			$this->tmpl->addVar("send_password", "send_pwd", 'disabled');
		}
		//$this->tmpl->addVar("send_password", "recreate_pwd", 'checked readonly');		// パスワード再作成は常にオン
		
		// 非表示項目の設定
		$this->tmpl->addVar("_widget", "serial", $this->serialNo);
		$this->tmpl->addVar("_widget", "page", $pageNo);		// 現在のページ番号
		
		// パスの設定
		$this->tmpl->addVar("_widget", "script_url", $gEnvManager->getScriptsUrl());
	}
	/**
	 * 取得したデータをテンプレートに設定する
	 *
	 * @param int $index			行番号(0～)
	 * @param array $fetchedRow		フェッチ取得した行
	 * @param object $param			未使用
	 * @return bool					true=処理続行の場合、false=処理終了の場合
	 */
	function memberListLoop($index, $fetchedRow, $param)
	{
		global $gEnvManager;
		
		// 行カラーの設定
		$lineColor = '';
		if ($index % 2 != 0){
			$lineColor = 'class="even"';		// 偶数行
		}
		$serial = $this->convertToDispString($fetchedRow['sv_serial']);
		$selected = '';
		if ($serial == $this->serialNo){
			$selected = 'checked';
		}
		// グループの設定
		$memberId = $fetchedRow['sv_id'];
		$group = '';
		if (!empty($fetchedRow['sv_group'])){
			$groupArray = explode(',', $fetchedRow['sv_group']);
			$count = count($groupArray);
			
			for ($j = 0; $j < count($this->groupRows); $j++){
				for ($i = 0; $i < $count; $i++){
					if ($this->groupRows[$j]['sg_id'] == $groupArray[$i]){
						// ゲストグループ以外を表示
						if ($groupArray[$i] != self::GUEST_GROUP_ID){
							$group .= $this->db->getGroupName($groupArray[$i], $this->langId) . ',';
						}
						break;
					}
				}
			}
		}
		$group = trim($group, ',');

		$row = array(
			'line_color' => $lineColor,											// 行のカラー
			'no' => $this->firstNo + $index,									// 行番号
			'serial' => $serial,	// シリアル番号
			'id' => $memberId,			// 会員ID
			'name' => $this->convertToDispString($fetchedRow['sv_name']),	// 名前
			'group' => $group,												// グループ名
			'account' => $this->convertToDispString($fetchedRow['lu_account']),	// アカウント
			'count' => $this->convertToDispString($fetchedRow['bl_count']),	// 投稿数
			'last_dt' => $this->convertToDispString($fetchedRow['bl_last_post_dt']),	// 投稿日時
			'selected' => $selected												// 項目選択用ラジオボタン
		);
		$this->tmpl->addVars('itemlist', $row);
		$this->tmpl->parseTemplate('itemlist', 'a');
		return true;
	}
}
?>
