| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398 |
- <?php
- /**
- * The control file of extension module of ZenTaoPMS.
- *
- * @copyright Copyright 2009-2023 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
- * @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
- * @author Chunsheng Wang <chunsheng@cnezsoft.com>
- * @package extension
- * @version $Id$
- * @link https://www.zentao.net
- */
- class extension extends control
- {
- /**
- * 插件列表页面。
- * Browse extensions.
- *
- * @param string $status
- * @access public
- * @return void
- */
- public function browse($status = 'installed')
- {
- $this->extensionZen->checkSafe();
- $versions = array();
- $extensions = $this->extension->getLocalExtensions($status);
- if($extensions && $status == 'installed')
- {
- /* Get latest release from remote. */
- $extCodes = helper::safe64Encode(join(',', array_keys($extensions)));
- $results = $this->extension->getExtensionsByAPI('bycode', $extCodes, $recTotal = 0, $recPerPage = 1000, $pageID = 1);
- if(isset($results->extensions))
- {
- $remoteReleases = $results->extensions;
- foreach($remoteReleases as $release)
- {
- if(!isset($extensions[$release->code])) continue;
- $extension = $extensions[$release->code];
- $extension->viewLink = $release->viewLink;
- if(isset($release->latestRelease) && $extension->version != $release->latestRelease->releaseVersion && $this->extension->checkVersion($release->latestRelease->zentaoCompatible))
- {
- $upgradeLink = inlink('upgrade', "extension=$release->code&downLink=&md5=&type=$release->type");
- $upgradeLink = ($release->latestRelease->charge || !$release->latestRelease->public) ? $release->latestRelease->downLink : $upgradeLink;
- $extension->upgradeLink = $upgradeLink;
- }
- }
- }
- }
- $this->view->title = $this->lang->extension->browse;
- $this->view->tab = $status;
- $this->view->extensions = $extensions;
- $this->view->versions = $versions;
- $this->display();
- }
- /**
- * 从禅道官网的插件市场获得插件。
- * Obtain extensions from the community.
- *
- * @param string $type
- * @param string $param
- * @param int $recTotal
- * @param int $recPerPage
- * @param int $pageID
- * @access public
- * @return void
- */
- public function obtain($type = 'byUpdatedTime', $param = '', $recTotal = 0, $recPerPage = 10, $pageID = 1)
- {
- $this->extensionZen->checkSafe();
- /* Init vars. */
- $type = strtolower($type);
- $moduleID = $type == 'bymodule' ? (int)base64_decode($param) : 0;
- $extensions = array();
- $pager = null;
- /* Set the key. */
- if($type == 'bysearch') $param = helper::safe64Encode($this->post->key ? $this->post->key : '');
- /* Get results from the api. */
- $results = $this->extension->getExtensionsByAPI($type, $param, $recTotal, $recPerPage, $pageID);
- if($results)
- {
- $this->app->loadClass('pager', $static = true);
- $pager = new pager($results->dbPager->recTotal, $results->dbPager->recPerPage, $results->dbPager->pageID);
- $extensions = (array)$results->extensions;
- }
- $this->view->title = $this->lang->extension->obtain;
- $this->view->moduleTree = $this->extension->getModulesByAPI();
- $this->view->extensions = $extensions;
- $this->view->installeds = $this->extension->getLocalExtensions('installed,deactivated');
- $this->view->pager = $pager;
- $this->view->tab = 'obtain';
- $this->view->type = $type;
- $this->view->moduleID = $moduleID;
- $this->display();
- }
- /**
- * 上传插件页面。
- * Upload an extension
- *
- * @access public
- * @return void
- */
- public function upload()
- {
- if($_FILES)
- {
- /* 检查上传附件的错误信息。 */
- if(!array_filter($_FILES['files']['name'])) return $this->send(array('result' => 'fail', 'message' => $this->lang->extension->errorFileNotEmpty));
- $tmpName = $_FILES['files']['tmp_name'][0];
- $fileName = $_FILES['files']['name'][0];
- $dest = $this->app->getTmpRoot() . "extension/$fileName";
- /* 创建目录并将上传的插件包移动到该目录下。 */
- if(!is_dir(dirname($dest))) mkdir(dirname($dest));
- if(!move_uploaded_file($tmpName, $dest))
- {
- /* 如果文件移动失败则返回错误信息。 */
- $downloadPath = $this->app->getTmpRoot() . 'extension/';
- $errorMessage = strip_tags(sprintf($this->lang->extension->errorDownloadPathNotWritable, $downloadPath, $downloadPath));
- return $this->send(array('result' => 'fail', 'message' => $errorMessage));
- }
- /* 解压插件包, 失败则删除插件包并返回错误信息。 */
- $extension = basename($fileName, '.zip');
- $return = $this->extensionZen->extractPackage($extension);
- if($return->result != 'ok')
- {
- unlink($dest);
- return $this->send(array('result' => 'fail', 'callback' => 'zui.Modal.alert({message: {html:"' . sprintf($this->lang->extension->errorExtracted, $fileName, $return->error) . '"}});'));
- }
- $info = $this->extension->parseExtensionCFG($extension);
- if(isset($info->code) && $info->code != $extension)
- {
- /* 如果插件包的插件代号和插件包名字不一致,则删除解压文件并将上传的插件包改名为插件代号。 */
- $classFile = $this->app->loadClass('zfile');
- $classFile->removeDir($this->extension->pkgRoot . $extension); // 这里删掉也没事,后续安装升级的时候会再次解压。
- rename($this->app->getTmpRoot() . "/extension/$fileName", $this->app->getTmpRoot() . "/extension/{$info->code}.zip");
- $extension = $info->code;
- }
- /* 判断是否已经安装过此插件,安装过做升级操作,否则做安装操作。 */
- $info = $this->extension->getInfoFromDB($extension);
- $type = (!empty($info) && ($info->status == 'installed' || $info->status == 'deactivated')) ? 'upgrade' : 'install';
- $link = $type == 'install' ? inlink('install', "extension=$extension") : inlink('upgrade', "extension=$extension");
- return $this->send(array('result' => 'success', 'callback' => array('name' => 'loadInModal', 'params' => $link)));
- }
- $this->extensionZen->checkSafe();
- $this->view->maxUploadSize = strtoupper(ini_get('upload_max_filesize'));;
- $this->display();
- }
- /**
- * 安装插件页面。
- * Install a extension
- *
- * @param string $extension
- * @param string $downLink
- * @param string $md5
- * @param string $type
- * @param string $overridePackage
- * @param string $ignoreCompatible
- * @param string $overrideFile
- * @param string $agreeLicense
- * @param string $upgrade
- * @access public
- * @return void
- */
- public function install($extension, $downLink = '', $md5 = '', $type = '', $overridePackage = 'no', $ignoreCompatible = 'no', $overrideFile = 'no', $agreeLicense = 'no', $upgrade = 'no')
- {
- $this->extensionZen->checkSafe();
- set_time_limit(0);
- $installTitle = $upgrade == 'no' ? $this->lang->extension->install : $this->lang->extension->upgrade;
- $installType = $upgrade == 'no' ? $this->lang->extension->installExt : $this->lang->extension->upgradeExt;
- $this->view->title = $installTitle . $extension;
- $this->view->installType = $installType;
- $this->view->upgrade = $upgrade;
- $this->view->error = '';
- /* 插件安装前的合规校验。 */
- $ignoreLink = inlink('install', "extension=$extension&downLink=&md5=$md5&type=$type&overridePackage=$overridePackage&ignoreCompatible=yes&overrideFile=$overrideFile&agreeLicense=$agreeLicense&upgrade=$upgrade");
- $overrideLink = inlink('install', "extension=$extension&downLink=&md5=$md5&type=$type&overridePackage=$overridePackage&ignoreCompatible=$ignoreCompatible&overrideFile=yes&agreeLicense=$agreeLicense&upgrade=$upgrade");
- $this->extensionZen->checkExtension($extension, $ignoreCompatible, $ignoreLink, $overrideFile, $overrideLink, $installType);
- if($this->view->error) return $this->display();
- if($upgrade == 'yes')
- {
- $newInfo = $this->extension->parseExtensionCFG($extension);
- $this->post->upgradeVersion = isset($newInfo->version) ? $newInfo->version : '';
- $oldInfo = $this->extension->getInfoFromDB($extension);
- $this->post->installedVersion = $oldInfo ? $oldInfo->version : '';
- }
- /* 打印授权协议同意表单。 */
- /* Print the license form. */
- if($agreeLicense == 'no')
- {
- $extensionInfo = $this->extension->getInfoFromPackage($extension);
- $license = $this->extension->processLicense($extensionInfo->license);
- $agreeLink = inlink('install', "extension=$extension&downLink=&md5=$md5&type=$type&overridePackage=$overridePackage&ignoreCompatible=$ignoreCompatible&overrideFile=$overrideFile&agreeLicense=yes&upgrade=$upgrade");
- $this->view->license = $license;
- $this->view->author = $extensionInfo->author;
- $this->view->agreeLink = $agreeLink;
- return $this->display();
- }
- /* 安装插件。 */
- $this->extensionZen->copyHookFiles($extension);
- $this->extensionZen->installExtension($extension, $type, $upgrade);
- $this->display();
- }
- /**
- * 卸载插件页面。
- * Uninstall an extension.
- *
- * @param string $extension
- * @param string $confirm
- * @access public
- * @return void
- */
- public function uninstall($extension, $confirm = 'no')
- {
- $this->extensionZen->checkSafe();
- /* Determine whether need to back up. */
- $info = $this->extension->getInfoFromDB($extension);
- $dbFile = $this->extension->getDBFile($extension, 'uninstall');
- if($confirm == 'no')
- {
- $this->view->title = $this->lang->extension->waring;
- $this->view->confirm = 'no';
- $this->view->code = $extension;
- return $this->display();
- }
- /* 相关依赖插件检查。 */
- $dependsExts = $this->extensionZen->getDependsByDB($extension);
- if($dependsExts)
- {
- $this->view->error = sprintf($this->lang->extension->errorUninstallDepends, join(' ', $dependsExts));
- return $this->display();
- }
- /* 卸载前的钩子加载。 */
- $this->extensionZen->copyHookFiles($extension);
- $preUninstallHook = $this->extensionZen->getHookFile($extension, 'preuninstall');
- if($preUninstallHook && $info->status == 'installed') include $preUninstallHook;
- if(file_exists($dbFile)) $this->view->backupFile = $this->extensionZen->backupDB($extension);
- $this->extension->executeDB($extension, 'uninstall');
- $this->extension->updateExtension(array('code' => $extension, 'status' => 'available'));
- $this->extensionZen->togglePackageDisable($extension, 'disabled');
- $this->view->title = $this->lang->extension->uninstallFinished;
- $this->view->removeCommands = $this->extension->removePackage($extension);
- /* 卸载后的钩子加载。 */
- $postUninstallHook = $this->extensionZen->getHookFile($extension, 'postuninstall');
- if($postUninstallHook && $info->status == 'installed') include $postUninstallHook;
- $this->display();
- }
- /**
- * 激活插件页面。
- * Activate an extension;
- *
- * @param string $extension
- * @param string $ignore yes|no
- * @access public
- * @return void
- */
- public function activate($extension, $ignore = 'no')
- {
- $this->extensionZen->checkSafe();
- if($ignore == 'no')
- {
- $return = $this->extensionZen->checkFileConflict($extension);
- if($return->result != 'ok')
- {
- $ignoreLink = inlink('activate', "extension=$extension&ignore=yes");
- $resetLink = inlink('browse', 'type=deactivated');
- $this->view->error = sprintf($this->lang->extension->errorFileConflicted, $return->error, $ignoreLink, $resetLink);
- return $this->display();
- }
- }
- $this->extensionZen->togglePackageDisable($extension, 'active');
- $this->extensionZen->copyPackageFiles($extension);
- $this->extension->updateExtension(array('code' => $extension, 'status' => 'installed'));
- $this->view->title = $this->lang->extension->activateFinished;
- $this->display();
- }
- /**
- * 禁用插件页面。
- * Deactivate an extension
- *
- * @param string $extension
- * @access public
- * @return void
- */
- public function deactivate($extension)
- {
- $this->extensionZen->checkSafe();
- $this->extension->updateExtension(array('code' => $extension, 'status' => 'deactivated'));
- $this->extensionZen->togglePackageDisable($extension, 'disabled');
- $this->view->title = $this->lang->extension->deactivateFinished;
- $this->view->removeCommands = $this->extension->removePackage($extension);
- $this->display();
- }
- /**
- * 清除插件页面。
- * Erase an extension.
- *
- * @param string $extension
- * @access public
- * @return void
- */
- public function erase($extension)
- {
- $this->extensionZen->checkSafe();
- $this->view->removeCommands = $this->extension->erasePackage($extension);
- $this->view->title = $this->lang->extension->eraseFinished;
- $this->display();
- }
- /**
- * 升级插件页面。
- * Update extension.
- *
- * @param string $extension
- * @param string $downLink
- * @param string $md5
- * @param string $type
- * @access public
- * @return void
- */
- public function upgrade($extension, $downLink = '', $md5 = '', $type = '')
- {
- $this->extensionZen->checkSafe();
- $this->extension->removePackage($extension);
- $this->locate(inlink('install', "extension=$extension&downLink=&md5=$md5&type=$type&overridePackage=no&ignoreCompatible=yes&overrideFile=no&agreeLicense=no&upgrade=yes"));
- }
- /**
- * 查看插件的目录结构。
- * Browse the structure of extension.
- *
- * @param string $extension
- * @access public
- * @return void
- */
- public function structure($extension)
- {
- $this->extensionZen->checkSafe();
- $this->view->extension = $this->extension->getInfoFromDB($extension);
- $this->display();
- }
- /**
- * 安全验证页面。
- * Security verification.
- *
- * @param string $statusFile
- * @access public
- * @return void
- */
- public function safe($statusFile)
- {
- $statusFile = str_replace('\\', '/', helper::safe64Decode($statusFile));
- $okFile = str_replace($this->app->getBasePath(), '', $statusFile);
- $this->view->error = sprintf($this->lang->noticeOkFile, $okFile, $statusFile);
- $this->view->title = $this->lang->extension->browse;
- $this->display();
- }
- }
|