123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458 |
- <?php
- /**
- * 批量生成物理教师讲案(新版)
- * User: Administrator
- * Date: 2021/3/24
- * Time: 17:57
- */
- require_once __DIR__.'/../controllers/TeachingPhysics.php';
- class TeachingCommand extends CConsoleCommand
- {
- protected $busConnObj = null;//业务数据库连接对象
- protected $busDbTime = 0;//业务数据库连接时间
- protected $schConnObj = null;//学校数据库连接对象
- protected $schDbTime = 0;//学校数据库连接时间
- protected $databaseInfo = array();//学校数据库连接信息
- protected $dbTimeout = 28;//数据库超时时间
- public function init() {
- parent::init();
- @ini_set('memory_limit', '1024M');
- set_time_limit(0);
- }
- public function actionTask($YII_ENV = 'production')
- {
- //需要生成的学校考试
- $schoolRelExam = $this->getNeedSchoolExam();
- if (!$schoolRelExam) {
- $this->showMsg(1, '没有需要处理的考试');
- return '';
- }
- $schoolIds = array_keys($schoolRelExam);
- $this->showMsg(1, '共有' . count($schoolIds) . '个学校需要处理 .....');
- //查询学校数据库连接地址
- $schoolDatabases = $this->getSchoolDatabases($schoolIds);
- foreach ($schoolRelExam as $schoolId => $examRelClass) {
- $this->showMsg(1, '当前学校ID:' . $schoolId . ' .......');
- $this->databaseInfo = isset($schoolDatabases[$schoolId]) ? $schoolDatabases[$schoolId] : array();
- if (!$this->databaseInfo) {
- $this->showMsg(1, '学校ID:' . $schoolId . '没有数据库连接信息');
- continue;
- }
- //连接学校数据库
- $this->schConnObj = null;
- $this->schConnObj = $this->getSchConnObj();
- if (!$this->schConnObj) {
- $this->showMsg(1, '学校ID:' . $schoolId . '数据库连接失败!!!!!');
- continue;
- }
- MyActiveRecord::$schoolId = $schoolId;
- foreach ($examRelClass as $examGroupId => $classAndId) {
- $classStr = $classAndId['class_ids'];
- $tableId = $classAndId['id'];//表主键ID
- $classNameArr = $this->getClassName($classAndId);
- $this->showMsg(1, '当前考试组ID:' . $examGroupId . ' .......');
- $examInfoArr = $this->getNeedExamIds($examGroupId, $classStr);
- if (!$examInfoArr) {
- $this->showMsg(1, '当前考试组ID:' . $examGroupId . '没有可以生产的教学宝');
- continue;
- }
- $pdfPathArr = array();
- foreach ($examInfoArr as $examId => $examInfo) {
- $time = microtime(true);
- $this->showMsg(1, '当前考试ID:' . $examId . ' .......');
- //更新生成中状态
- $bool = $this->updateStatus($tableId, 4);
- if ($bool === false) {
- $pdfPathArr = array();
- break;
- }
- echo '开始生成教学宝PDF......' . PHP_EOL;
- //生成PDF
- $bool = $this->getPdf($pdfPathArr,$tableId,$schoolId,$examId,$examInfo['class_id']);
- if ($bool === false) {
- $pdfPathArr = array();
- break;
- }
- echo '生成一个PDF耗时:' . round(microtime(true) - $time, 2) . 's' . PHP_EOL;
- }
- //打包PDF
- $successArr = array();
- if ($pdfPathArr) {
- $examName = $examInfo['name'];
- $filenamePath = dirname(dirname(dirname(__FILE__))) . '/upload/tmpDir/academicr_batch/' . $examGroupId . "/" . $tableId;
- if (!is_dir($filenamePath)) {
- if (!mkdir($filenamePath, 0777, true)) {
- $bool = $this->updateStatus($tableId, 3,'创建压缩文件目录失败: ' . $filenamePath);
- }else{
- exec('chown -R www:www '.$filenamePath);
- }
- }
- $filename = $filenamePath ."/".$examGroupId.".zip";
- // file_put_contents($filename, '');
- $successArr = $this->zipPdf($pdfPathArr, $filename, $examName, $classNameArr);
- }
- //全部成功更新状态
- if ($successArr && count($successArr) == array_sum($successArr)) {
- //上传qcloud文件
- $filename = $this->characet($filename);
- $ucloud = new Qcloud();
- $filename = iconv("UTF-8","GBK//IGNORE",$filename);
- $examName = $this->characet($examName);
- $putRs = $ucloud->putFile('zsyas2/academicr_batch/'.$examGroupId.'/'.$tableId.'/'.$examName.'.zip',$filename);
- if(isset($putRs['status']) && $putRs['status'] == 1){
- $url = $putRs['url'];
- $url = str_replace("%2F","/",$url);
- $bool = $this->updateStatus($tableId, 2,'',$url);
- $this->showMsg(1, 'zip文件上传Ucloud成功!,地址:'.$url);
- }else{
- $msg = 'zip文件上传Ucloud失败!!!,错误信息:' . $putRs['msg'];
- $bool = $this->updateStatus($tableId, 3,$msg);
- }
- @unlink($filename);
- }else{
- $bool = $this->updateStatus($tableId, 3,'生成zip文件失败');
- }
- }
- //关闭数据库
- if ($this->schConnObj) {
- $this->getSchConnObj()->close();
- }
- echo '下一个学校' . PHP_EOL;
- }
- echo 'End.' . PHP_EOL;
- }
- public function getDbConnection($databaseHost,$databaseName,$databaseUser,$databasePassword)
- {
- if($databaseHost && $databaseName && $databaseUser && $databasePassword){
- $myDbDsn = 'mysql:host=' . $databaseHost . ';dbname=' . $databaseName;
- $myConnection = new CDbConnection($myDbDsn, $databaseUser, $databasePassword);
- $myConnection->emulatePrepare = true;
- $myConnection->enableProfiling = true;
- $myConnection->enableParamLogging = true;
- $myDbDsn = null;
- return $myConnection;
- }else{
- return null;
- }
- }
- /**
- * 获取学校数据库
- * @param $schoolIds
- * @return array
- */
- protected function getSchoolDatabases($schoolIds)
- {
- $schoolDatabases = array();
- $sql = "select school_id,database_host,database_user,database_password,database_name,group_id from `database` where school_id in (" . implode(',', $schoolIds) . ")";
- $rs = $this->getBusConn()->createCommand($sql)->queryAll();
- if ($rs) {
- foreach ($rs as $value) {
- $schoolDatabases[$value['school_id']] = $value;
- }
- }
- return $schoolDatabases;
- }
- /**
- * 业务数据库对象
- * @return CDbConnection|null
- */
- protected function getBusConn()
- {
- $time = time();
- if ($this->busConnObj) {
- if ($time - $this->busDbTime > $this->dbTimeout) {
- echo '关闭超时业务数据库重新连接' . PHP_EOL;
- }else{
- return $this->busConnObj;
- }
- }
- $dbParams = Yii::app()->params["default_server"];
- $busConnObj = $this->getDbConnection($dbParams['addr'], Yii::app()->params["default_db"]['name'], $dbParams['username'], $dbParams['password']);
- $this->busConnObj = $busConnObj;
- $this->busDbTime = $time;
- return $busConnObj;
- }
- /**
- * 学校数据库对象
- * @return mixed
- */
- public function getSchConnObj()
- {
- $time = time();
- if ($this->schConnObj) {
- if ($time - $this->schDbTime > $this->dbTimeout) {
- echo '关闭超时学校数据库重新连接' . PHP_EOL;
- }else{
- return $this->schConnObj;
- }
- }
- $databaseInfo = $this->databaseInfo;
- $schConnObj = $this->getDbConnection($databaseInfo['database_host'], $databaseInfo['database_name'], $databaseInfo['database_user'], $databaseInfo['database_password']);
- $this->schConnObj = $schConnObj;
- $this->schDbTime = $time;
- return $schConnObj;
- }
- /**
- * 查询需要处理的考试
- * @param $examGroupId
- * @param $classStr
- * @return array
- */
- protected function getNeedExamIds($examGroupId, $classStr)
- {
- $examInfoArr = array();
- $rs = array();
- $sql = "SELECT exam_id,class_id,`name` FROM exam WHERE exam_group_id = '{$examGroupId}' AND class_id IN ({$classStr}) AND `status` = 1";
- $result = $this->getSchConnObj()->createCommand($sql)->queryAll();
- if (!$result) {
- return $examInfoArr;
- }
- foreach ($result as $value) {
- $examInfoArr[$value['exam_id']] = $value;
- }
- unset($result);
- if ($examInfoArr) {
- $sql = "SELECT exam_id FROM paper WHERE exam_id in (" . implode(',', array_keys($examInfoArr)) . ") and is_labelled = 1";
- $result = $this->getSchConnObj()->createCommand($sql)->queryAll();
- if ($result) {
- foreach ($result as $value) {
- $rs[$value['exam_id']] = isset($examInfoArr[$value['exam_id']])?$examInfoArr[$value['exam_id']]:0;
- }
- }
- }
- unset($examInfoArr);
- return $rs;
- }
- /**
- * 需要处理的学校考试
- * @return array|CDbDataReader
- */
- protected function getNeedSchoolExam()
- {
- $schoolRelExam = array();
- $time = time();
- //获取要生成教师讲案的数据
- $sql = "select id,school_id,exam_group_id,class_ids,class_names from download_table_setting where download_type = 3 and status = 1 and error_msg = '' and subject_id = 12 and is_labelled>0 ";
- $result = $this->getBusConn()->createCommand($sql)->queryAll();
- //超过20分钟默认生成失败
- $sql = "update download_table_setting set status = 3,error_msg ='系统错误,建议单个生成' where status = 4 and error_msg = '' and update_time <" . ($time - 1200);
- $this->getBusConn()->createCommand($sql)->execute();
- if ($result) {
- foreach ($result as $value) {
- $schoolId = $value['school_id'];
- if (!isset($schoolRelExam[$schoolId])) {
- $schoolRelExam[$schoolId] = array();
- }
- $schoolRelExam[$schoolId][$value['exam_group_id']] = array(
- 'class_ids' => $value['class_ids'],
- 'class_names' => $value['class_names'],
- 'id' => $value['id'],
- );
- }
- }
- return $schoolRelExam;
- }
- /**
- * 更新生成状态 状态:1等待生成中,2-已生成 , 3-生成失败 4-生成中
- * @param $tableId
- * @param $status
- * @param string $errorMsg
- * @param string $zipUrl
- * @return int
- */
- protected function updateStatus($tableId, $status,$errorMsg = '',$zipUrl = '')
- {
- $time = time();
- $sql = "update download_table_setting set update_time = {$time},`status` = {$status}";
- if ($errorMsg) {
- $errorMsg = addslashes($errorMsg);
- $sql .= ",`error_msg` = '{$errorMsg}'";
- $this->showMsg(0, $errorMsg);
- }
- if ($zipUrl) {
- $sql .= ",`zip_url` = '{$zipUrl}'";
- }
- $sql .= " where id = {$tableId}";
- $bool = $this->getBusConn()->createCommand($sql)->execute();
- if ($bool === false) {
- $this->showMsg(0, '更新生成状态' . $status . '失败!!!!');
- }
- return $bool;
- }
- /**
- * 显示信息
- * @param $status
- * @param $msg
- */
- protected function showMsg($status,$msg)
- {
- echo $msg . PHP_EOL;
- }
- /**
- * client 渲染HTML
- * @param $viewName
- * @param $data
- * @return string
- */
- public function viewRender($viewName, $data)
- {
- extract($data, EXTR_PREFIX_SAME,'data');
- ob_start();
- ob_implicit_flush(0);
- $filePath=dirname(dirname(dirname(__FILE__))).'/protected/views/teaching/'.$viewName . '.php';
- require($filePath);
- return ob_get_clean();
- }
- /**
- * 生成pdf
- */
- protected function getPdf(&$pdfPathArr,$tableId,$schoolId,$examId,$classId)
- {
- $teachingPhysicsObj = new TeachingPhysics($this);
- $result = $teachingPhysicsObj->getTeachingPdf($schoolId, $examId, 1);
- if (isset($result['status']) && $result['status'] == 0) {
- $pdfPathArr[$classId] = $result['pdf_path'];
- $this->showMsg(1, '教学宝PDF生成成功!地址:'.$result['pdf_url']);
- $this->showMsg(1, ',PDF文件路径地址:'.$result['pdf_path']);
- $bool = true;
- }else{
- $errorMsg = isset($result['error']) ? $result['error'] : '生成失败!!';
- $this->showMsg(0, $errorMsg);
- $bool = $this->updateStatus($tableId, 3, $errorMsg);
- }
- return $bool;
- }
- /**
- * 打包PDF
- * @param $pdfPathArr
- * @param $filename
- * @param $examName
- * @return array
- */
- protected function zipPdf($pdfPathArr,$filename,$examName,$classNameArr)
- {
- $successArr = array();
- $examName = iconv("UTF-8","GBK//IGNORE",$examName);
- //最终生成的文件名(含路径)
- $zip = new ZipArchive();
- if ($zip->open($filename, ZIPARCHIVE::OVERWRITE)!==TRUE) {
- $this->showMsg(0, $examName . 'zip生成失败!');
- }else {
- foreach ($pdfPathArr as $classId => $val) {
- $className = isset($classNameArr[$classId]) ? $classNameArr[$classId] : '';
- $pdfname = '-'.$className.'-教师讲案';
- $pdfname = iconv("UTF-8", "GBK//IGNORE", $pdfname);
- $res = $zip->addFile($val, $examName . $pdfname . '.pdf');
- if (!$res) {
- $this->showMsg(0, '添加zip文件失败:'.$val);
- }
- $successArr[] = $res ? 1 : 0;
- }
- $zip->close();//关闭
- foreach ($pdfPathArr as $k => $val) {
- @unlink($val);
- }
- }
- return $successArr;
- }
- /**
- * 字符转换
- * @param $data
- * @return string
- */
- protected function characet($data){
- if( !empty($data) ){
- $fileType = mb_detect_encoding($data , array('UTF-8','GBK','LATIN1','BIG5')) ;
- if( $fileType != 'UTF-8'){
- $data = mb_convert_encoding($data ,'utf-8' , $fileType);
- }
- }
- return $data;
- }
- /**
- * 获取班级名称
- * @param $classAndId
- * @return array
- */
- protected function getClassName($classAndId)
- {
- $classNameArr = array();
- $classIds = explode(',',$classAndId['class_ids']);
- $classNames = explode(',',$classAndId['class_names']);
- foreach ($classIds as $key => $classId) {
- $classNameArr[$classId] = isset($classNames[$key]) ? $classNames[$key] : '';
- }
- return $classNameArr;
- }
- }
|