diff --git a/htdocs/api/v2/index.php b/htdocs/api/v2/index.php index f319ef7..7e54d09 100644 --- a/htdocs/api/v2/index.php +++ b/htdocs/api/v2/index.php @@ -1294,6 +1294,144 @@ $app->group('/tokens', 'APIrequest', function () use ($app, $app_template) { )); } }); + + /* + * 推薦學習點 + * POST http://localhost/api/v2/tokens/{登入Token}/activitys/{學習中活動編號}/recommand?current_point={目前所在的學習點編號} + * TODO: 將上方的重複的程式碼片段獨立開來 + */ + $app->post('/:token/activitys/:said/recommand', function ($token, $saId) use ($app) { + if(isset($_GET['current_point'])) { $currentTId = $_GET['current_point']; } + + function output_the_target_array($tId, $isEntity, $materialMode) { + $thisOutput = array(); + $target = new Target\Target($tId); + $thisOutput = array( + 'target_id' => $target->getId(), + 'is_entity' => $isEntity, + 'hall_id' => $target->getHallId(), + 'area_id' => $target->getAreaId(), + 'target_number' => $target->getNumber(), + 'name' => $target->getName(), + 'map_url' => $target->getMapUrl(), + 'material_url' => $target->getMaterialUrl($isEntity, $materialMode), + 'learn_time' => $target->getLearnTime(), + 'PLj' => $target->getPLj(), + 'Mj' => $target->getMj(), + 'S' => $target->getS(), + 'Fj' => $target->getFj() + ); + return $thisOutput; + } + + try { + // 查詢使用者 + $session = new User\UserSession(); + $user_id = $session->getUserId($token); + + // 取得開始後的學習活動資訊 + $sact = new Study\StudyActivity($saId); + + // 確認此學習活動是否為本人所有 + if($sact->getUserId() == $user_id) { + + // 必填參數有填 + if( isset($currentTId) ) { + + // 查詢目前所在的標的 + $inTId = $sact->getCurrentInTarget(); + // 登記離開此標的 + if($inTId) { + $sact->toOutTarget($inTId); + } + + $currentTId = (int)$currentTId; + + $tid = $sact->getThemeId(); // 取得此活動的主題 + $maxItemTotal = $sact->getLearnStyle(); // 取得最大推薦數 + + // 取得本次採用的教材風格 + $materialMode = $sact->getMaterialStyle(); + + // 取得推薦的學習點 + $recommand = new Recommand\RecommandPoint(); + $recommandResult = $recommand->recommand($currentTId, $saId); + $recommandTotal = count($recommandResult); + if($recommandTotal > $maxItemTotal) { + $result_recommand_total = $maxItemTotal; + } + else { + $result_recommand_total = $recommandTotal; + } + // 是否已經學完了 + if($sact->getRemainingPointTotal() <= 0) { + $isEnd = true; + } + else { + $isEnd = false; + } + + // 製作 + $output_targets = array(); + for($i=0; $i<$result_recommand_total; $i++) { + $target_id = $recommandResult[$i]['nextPoint']; + $isEntity = $recommandResult[$i]['isEntity']; + array_push($output_targets, output_the_target_array($target_id, $isEntity, $materialMode)); + + // TODO: 標的進出資料多增加行進中、確實進入的欄位 + if($maxItemTotal == 1) { + $sid = $sact->enteringInTarget($target_id, true); + } + + } + + // 噴出結果 + $app->render(201,array( + 'token' => $token, + 'user_id' => $user_id, + 'activity_id' => $sact->getId(), + 'current_target_id' => $currentTId, + 'is_end' => $isEnd, + 'recommand_total' => $result_recommand_total, + 'recommand_target' => $output_targets, + 'error' => false + )); + + } + else { + $app->render(400,array( + 'token' => $token, + 'error' => true, + 'msg' => 'No input \'current_point\' param.', + 'msg_cht' => '缺少 \'current_point\' 參數' + )); + } + + } + // 若非本人所有,則視同無此活動 + else { + throw new Exception\StudyActivityNoFoundException($saId); + } + + } + catch (Exception\LoginTokenNoFoundException $e) { + $app->render(401,array( + 'token' => $token, + 'error' => true, + 'msg' => 'No \''.$token.'\' session. Please login again.', + 'msg_cht' => '沒有\''.$token.'\'登入階段,請重新登入', + 'substatus' => 204 + )); + } + catch (Exception\StudyActivityNoFoundException $e) { + $app->render(404,array( + 'token' => $token, + 'error' => true, + 'msg' => 'No found this activity.', + 'msg_cht' => '沒有此學習活動' + )); + } + }); }); // ============================================================================ diff --git a/htdocs/lib/Database/DBStudy.php b/htdocs/lib/Database/DBStudy.php index 283d231..7cd8da5 100644 --- a/htdocs/lib/Database/DBStudy.php +++ b/htdocs/lib/Database/DBStudy.php @@ -41,7 +41,7 @@ class DBStudy extends Database { protected function queryByWhere($where) { $sqlString = "SELECT `SID`, `SaID`, ". - "`TID`, `IsEntity`, `In_TargetTime`, `Out_TargetTime` ". + "`TID`, `IsEnter`, `IsEntity`, `In_TargetTime`, `Out_TargetTime` ". "FROM `".$this->table('Study')."` ". "WHERE ".$where; @@ -59,11 +59,16 @@ class DBStudy extends Database { $output_entity = true; } else { $output_entity = false; } + if($thisResult['IsEnter'] != '0') { + $output_enter = true; + } + else { $output_enter = false; } array_push($result, array( 'study_id' => (int)$thisResult['SID'], 'activity_id' => (int)$thisResult['SaID'], 'target_id' => (int)$thisResult['TID'], + 'is_enter' => $output_enter, 'is_entity' => $output_entity, 'in_target_time' => $thisResult['In_TargetTime'], 'out_target_time' => $thisResult['Out_TargetTime'] @@ -88,6 +93,7 @@ class DBStudy extends Database { * 'study_id' => <流水編號>, * 'activity_id' => <活動編號>, * 'target_id' => <標的編號>, + * 'is_enter' => <是否為已進入的狀態,若否代表行進中>, * 'is_entity' => <是否為現場學習>, * 'in_target_time' => <進入時間>, * 'out_target_time' => <離開時間> @@ -118,6 +124,7 @@ class DBStudy extends Database { * 'study_id' => <流水編號>, * 'activity_id' => <活動編號>, * 'target_id' => <標的編號>, + * 'is_enter' => <是否為已進入的狀態,若否代表行進中>, * 'is_entity' => <是否為現場學習>, * 'in_target_time' => <進入時間>, * 'out_target_time' => <離開時間> @@ -157,6 +164,7 @@ class DBStudy extends Database { * * @param string $activity_id 活動編號 * @param string $target_id 標的編號 + * @param string $is_enter 是否為已進入的狀態,若否代表行進中 * @param string $is_entity 是否為現場學習 * @param int $in_target_time 進入時間 * @param int $out_target_time 離開時間 @@ -164,22 +172,26 @@ class DBStudy extends Database { * @return int 剛新增的記錄編號 * @since 2.0.0 */ - public function insert($activity_id, $target_id, + public function insert($activity_id, $target_id, $is_enter, $is_entity, $in_target_time, $out_target_time) { + if(!isset($is_enter)) { + $is_enter = true; + } if(!isset($is_entity)) { $is_entity = true; } // 寫入 $sqlString = "INSERT INTO `".$this->table('Study'). - "` (`SaID`, `TID`, `IsEntity`, `In_TargetTime`, `Out_TargetTime`) + "` (`SaID`, `TID`, `IsEnter`, `IsEntity`, `In_TargetTime`, `Out_TargetTime`) VALUES ( :said , :tid , :entity , :intime , :outtime )"; $query = $this->connDB->prepare($sqlString); $query->bindParam(":said", $activity_id); $query->bindParam(":tid", $target_id); + $query->bindParam(":enter", $is_enter); $query->bindParam(":entity", $is_entity); $query->bindParam(":intime", $in_target_time); $query->bindParam(":outtime", $out_target_time); @@ -233,7 +245,7 @@ class DBStudy extends Database { * @return int 剛新增的記錄編號 * @since 2.0.0 */ - public function toInTaeget($activity_id, $target_id, $is_entity) + public function toInTarget($activity_id, $target_id, $is_entity) { if(!isset($is_entity)) { @@ -242,8 +254,8 @@ class DBStudy extends Database { // 寫入 $sqlString = "INSERT INTO `".$this->table('Study'). - "` (`SaID`, `TID`, `IsEntity`, `In_TargetTime`, `Out_TargetTime`) - VALUES ( :said , :tid , :entity , NOW() , NULL )"; + "` (`SaID`, `TID`, `IsEnter`, `IsEntity`, `In_TargetTime`, `Out_TargetTime`) + VALUES ( :said , :tid , '1' , :entity , NOW() , NULL )"; $query = $this->connDB->prepare($sqlString); $query->bindParam(":said", $activity_id); @@ -260,6 +272,65 @@ class DBStudy extends Database { return $resultId; } + /** + * 行進中,準備進入的學習點 + * + * @param string $activity_id 活動編號 + * @param string $target_id 標的編號 + * @param string $is_entity 是否為現場學習 + * @return int 剛新增的記錄編號 + * @since 2.0.0 + */ + public function enteringInTarget($activity_id, $target_id) + { + + if(!isset($is_entity)) { + $is_entity = true; + } + + // 寫入 + $sqlString = "INSERT INTO `".$this->table('Study'). + "` (`SaID`, `TID`, `IsEnter`, `IsEntity`, `In_TargetTime`, `Out_TargetTime`) + VALUES ( :said , :tid , '0' , '1' , NOW() , NULL )"; + + $query = $this->connDB->prepare($sqlString); + $query->bindParam(":said", $activity_id); + $query->bindParam(":tid", $target_id); + $query->execute(); + + // 取得剛剛加入的ID + $sqlString = "SELECT LAST_INSERT_ID()"; + $query = $this->connDB->query($sqlString); + $queryResult = $query->fetch(); + $resultId = $queryResult[0]; + + return $resultId; + } + + /** + * 取消所有行進中準備進入的學習點的狀態 + * + * @param string $activity_id 活動編號 + * @return 影響數 + * @since 2.0.0 + */ + public function allOutEnteringInTarget($activity_id) + { + + // 寫入 + $sqlString = "UPDATE `".$this->table('Study'). + "` SET `Out_TargetTime` = NOW() + WHERE `SaID` = :id ". + "AND `IsEnter` = '0'". + " AND `Out_TargetTime` IS NULL"; + + $query = $this->connDB->prepare($sqlString); + $query->bindParam(":id", $activity_id); + $query->execute(); + $count = $query->rowCount(); + return $count; + } + /** * 離開學習點 * @@ -308,7 +379,35 @@ class DBStudy extends Database { public function getCurrentInTargetId($activity_id) { $sqlString = "SELECT `TID` FROM `".$this->table('Study')."` ". - "WHERE `Out_TargetTime` IS NULL AND `SaID` = :said "; + "WHERE `Out_TargetTime` IS NULL AND `SaID` = :said ". + "AND `IsEnter` = '1'"; + + $query = $this->connDB->prepare($sqlString); + $query->bindParam(":said", $activity_id); + $query->execute(); + + $queryResult = $query->fetch(); + // 如果有查到一筆以上 + if( count($queryResult) >= 1 ) { + return (int)$queryResult[0]; + } + else { + return null; + } + } + + /** + * 取得目前正在行進中標的編號 + * + * @param int $activity_id 活動編號 + * @return int 標的編號 + * @since 2.0.0 + */ + public function getCurrentEnteringInTargetId($activity_id) { + + $sqlString = "SELECT `TID` FROM `".$this->table('Study')."` ". + "WHERE `Out_TargetTime` IS NULL AND `SaID` = :said ". + "AND `IsEnter` = '0'"; $query = $this->connDB->prepare($sqlString); $query->bindParam(":said", $activity_id); @@ -334,7 +433,8 @@ class DBStudy extends Database { public function getCurrentInStudyId($activity_id) { $sqlString = "SELECT `SID` FROM `".$this->table('Study')."` ". - "WHERE `Out_TargetTime` IS NULL AND `SaID` = :said "; + "WHERE `Out_TargetTime` IS NULL AND `SaID` = :said ". + " AND `IsEnter` = '1'"; $query = $this->connDB->prepare($sqlString); $query->bindParam(":said", $activity_id); @@ -364,7 +464,8 @@ class DBStudy extends Database { $queryResultAll = $this->queryByWhere( "`TID` = ".$this->connDB->quote($target_id). - " AND `SaID` = ".$this->connDB->quote($activity_id)); + " AND `SaID` = ".$this->connDB->quote($activity_id). + " AND `IsEnter` = '1'"); return $queryResultAll; } @@ -384,7 +485,29 @@ class DBStudy extends Database { $queryResultAll = $this->queryByWhere( "`TID` = ".$this->connDB->quote($target_id). " AND `SaID` = ".$this->connDB->quote($activity_id). - " AND `Out_TargetTime` IS NULL"); + " AND `Out_TargetTime` IS NULL ". + " AND `IsEnter` = '1'"); + + return $queryResultAll; + } + + /** + * 取得在此標學習中的記錄編號 + * + * 正常來說只會有一個,但考量使用者可能在這次活動內同一標的進出兩次以上,故還是以陣列輸出。 + * + * @param int $activity_id 活動編號 + * @param int $target_id 標的編號 + * @return array 所有進出記錄資訊陣列 + * @since 2.0.0 + */ + public function getEnteringInStudyIdByTargetId($activity_id, $target_id) { + + $queryResultAll = $this->queryByWhere( + "`TID` = ".$this->connDB->quote($target_id). + " AND `SaID` = ".$this->connDB->quote($activity_id). + " AND `Out_TargetTime` IS NULL ". + " AND `IsEnter` = '0'"); return $queryResultAll; } diff --git a/htdocs/lib/Study/StudyActivity.php b/htdocs/lib/Study/StudyActivity.php index 989e4c6..269c771 100644 --- a/htdocs/lib/Study/StudyActivity.php +++ b/htdocs/lib/Study/StudyActivity.php @@ -492,6 +492,31 @@ class StudyActivity { } + /** + * 行進中,準備進入的學習點 + * + * @param int $target_id 標的編號 + * @param bool $is_entity 是否為現場學習 + * @throw UElearning\Exception\InLearningException + * return int 進出紀錄編號 + */ + public function enteringInTarget($target_id, $is_entity) { + + // 活動編號 + $saId = $this->id; + + $sct = new StudyManager(); + // 進入學習點 + try{ + return $sct->enteringInTarget($saId, $target_id, $is_entity); + } + // 若狀態為正在標的內學習時,送出例外 + catch (Exception\InLearningException $e) { + throw $e; + } + + } + /** * 離開標的 * diff --git a/htdocs/lib/Study/StudyManager.php b/htdocs/lib/Study/StudyManager.php index 492081a..8d92fff 100644 --- a/htdocs/lib/Study/StudyManager.php +++ b/htdocs/lib/Study/StudyManager.php @@ -78,9 +78,11 @@ class StudyManager { // 若沒有任一個點正在學習中 if($this->getCurrentInTargetId($activity_id) == null) { - // 紀錄進資料庫 + $db = new Database\DBStudy(); - $id = $db->toInTaeget($activity_id, $target_id, $is_entity); + + // 紀錄進資料庫 + $id = $db->toInTarget($activity_id, $target_id, $is_entity); // 將標的目前人數+1 if($is_entity) { @@ -95,6 +97,65 @@ class StudyManager { } } + /** + * 行進中,準備進入的學習點 + * + * @param int $activity_id 活動編號 + * @param int $target_id 標的編號 + * @throw UElearning\Exception\TargetNoFoundException + * return int 進出紀錄編號 + */ + public function enteringInTarget($activity_id, $target_id) { + + // 若沒有任一個點正在學習中 + if($this->getCurrentInTargetId($activity_id) == null) { + $db = new Database\DBStudy(); + + // 紀錄進資料庫 + $id = $db->enteringInTarget($activity_id, $target_id); + + // 將標的目前人數+1 + $target = new Target\Target($target_id); + $target->addMj(1); + + return $id; + } + else { + throw new Exception\InLearningException(); + } + } + + /** + * 取消行進中,準備進入的學習點 + * + * @param int $activity_id 活動編號 + * @param int $target_id 標的編號 + */ + public function outEnteringInTarget($activity_id, $target_id) { + + // 從資料庫取得此活動此標的學習中資料 + $db = new Database\DBStudy(); + $learning_array = $db->getEnteringInStudyIdByTargetId($activity_id, $target_id); + $target = new Target\Target($target_id); + + // 將所有此標的的進入紀錄全部標示 + // 找到正在學習中的資料 + if(isset($learning_array)) { + + foreach($learning_array as $thisArray) { + + // 將此紀錄標示為已離開 + $db->toOutTarget($thisArray['study_id']); + + // 將標的目前人數-1 + if($thisArray['is_entity'] = true) { + $target = new Target\Target($target_id); + $target->addMj(-1); + } + } + } + } + /** * 離開標的 *