信步漫談之Wiki知識庫——搭建dokuwiki



1 目標

  • 搭建 DokuWiki 知識庫和遇到的問題解決方式
  • DokuWiki 的使用方式
  • 擴展插件支持 markdown 語法

2 資源

系統:CentOS 7.7.1908-Minimal(本文服務器地址:192.168.64.100)
DokuWiki 版本:2020-07-29(下載最后穩定版路徑:https://download.dokuwiki.org/src/dokuwiki/dokuwiki-stable.tgz)
PHP 版本:7.3.27

3 環境准備

  • 關閉防火牆
# systemctl stop firewalld.service
# systemctl disable firewalld.service
  • 啟用epel和remi存儲庫以使用最新的PHP 7.x版本
# yum -y install http://rpms.remirepo.net/enterprise/remi-release-7.rpm
# yum -y install epel-release
  • 禁用安裝php5.4以從remi存儲庫安裝php7.3
# yum-config-manager --disable remi-php54
# yum-config-manager --enable remi-php73
  • 安裝 PHP
# yum -y install httpd
# yum -y install php php-gd php-xml
  • 啟動並啟用服務
# systemctl start httpd
# systemctl enable httpd
  • 重新啟動Apache Web服務器
# systemctl restart httpd
  • 關閉SELinux
    1. 打開 /etc/selinux/config 文件
    SELINUX=enforcing
    修改為
    SELINUX=disabled
    
    1. 重啟服務器生效

4 DokuWiki 安裝

  • 將下載的 DokuWiki 安裝包上傳到 /opt/dokuwiki 目錄,解壓到 /var/www/html 目錄下,重命名為 wiki
# cd /opt/dokuwiki
# tar -zxvf dokuwiki-stable.tgz -C /var/www/html
# cd /var/www/html
# mv dokuwiki-2020-07-29/ wiki
  • 修改 wiki 文件夾權限
# chown -R apache:apache wiki
  • 重啟 httpd 服務
# systemctl restart httpd

5 DokuWiki 初始配置

  • 訪問 DokuWiki 的安裝程序(http://192.168.1.100/wiki/install.php),並根據提示進行安裝配置
    1. 右上角選擇語言
    2. 填寫維基名稱、用戶、密碼、郵箱
    3. 選擇“初始的 ACL 政策”為“任何人都有讀權限,只有注冊用戶有寫和上傳權限”
    4. 保存,完成安裝
  • 統一編碼
    1. 查看當前系統編碼(命令:locale),此處查看是 UTF-8
    2. 打開 wiki/conf/local.php 文件
    3. 在最后一行加上編碼配置
    $conf['fnencode']='utf-8';
    

6 DokuWiki 使用方式

7 DokuWiki 插件優化

  • 導航欄添加樹形風格,指定新增詞條的命名空間
    1. 新增頁面插件(Add New Page)
    2. 導航菜單插件(IndexMenu Plugin)
      • 新建wiki/data/pages/sidebar.txt,內容如下
      ===== 導航目錄 =====
      {{indexmenu>..|navbar}}
      ===== 添加新頁面 =====
      {{NEWPAGE}}
      
  • 兼容 markdown 語法
    1. Markdown插件(Markdown Page Plugin)
    2. 安裝插件后,在新增編輯詞條時,<markdown> 標簽內的內容將按 markdown 的語法進行解析

8 完全替換為 markdown 語法編輯器

寫在前面,嘗試過這種完全替換為 markdown 語法編輯器的方法,並補充了原作者的一些遺漏之處,總體實現的效果還是不錯的,有實時展示的編輯窗口,也支持圖片上傳引用。

  • 下載 editor.md
  • 解壓到 wiki/lib/editor.md(切記,此處不是寫錯,是 lib 目錄下,不是 lib/plugins 目錄,這是個坑,我踩過。。。)
  • 修改 wiki/inc/form.php 里的函數 form_wikitext($attrs),修改return結果,代碼中 id="editormd" 是后面 editor.md 實例需要的 id
    function form_wikitext($attrs) {
    	// mandatory attributes
    	unset($attrs['name']);
    	unset($attrs['id']);
    	$text = str_replace("<markdown>\n",'',$attrs['_text']);
    	$text = str_replace("\n</markdown>",'',$text);
    	return '<div id="editormd" contenteditable="true"><textarea name="wikitext">'.DOKU_LF.formText($text).'</textarea></div>';
    }
    
  • 修改 wiki/inc/parser/xhtml.php 里的函數 cdata
    function cdata($text) {
    	//$this->doc .= $this->_xmlEntities($text);
    	return $this->doc.=$text;
    }
    
    修改原因:因為以前是純字符編輯器,會將一些特殊符號進行過濾,比如:<>等等.而替換之后的xheditor本身已經做了一次過濾了,再次過濾就會導致字符<變成&lt,因此去掉這段之后,就只過濾一次
  • 修改 wiki/inc/Action/Save.php 的以下內容
    saveWikiText($ID,con($PRE,$TEXT,$SUF,true),$SUM,$INPUT->bool('minor')); //use pretty mode for con
    
    替換成
    saveWikiText($ID,con($PRE,"<markdown>\n".$TEXT."\n</markdown>",$SUF,true),$SUM,$INPUT->bool('minor')); //use pretty mode for con
    
  • 修改 wiki/lib/tpl/dokuwiki/main.php,添加 editor.md 包
    1. head 節點中添加
    <link rel="stylesheet" href="<?php echo DOKU_BASE;?>lib/editor.md/css/editormd.min.css" />
    
    1. body 節點下添加(直接加在 <body> 的節點下方)
    <script src="<?php echo DOKU_BASE;?>lib/editor.md/examples/js/jquery.min.js"></script>
    <script src="<?php echo DOKU_BASE;?>lib/editor.md/editormd.js"></script>
    <script type="text/javascript">
    $ = jQuery
    	var testEditor;
    	$(function(md) {
    	if (document.getElementById("editormd")) {
    		testEditor = editormd("editormd", {
    			width: "100%",
    			height: 740,
    			path: '<?php echo DOKU_BASE;?>lib/editor.md/lib/',
    			syncScrolling : "single",
    			imageUpload: true,
    			imageFormats: ["jpg", "jpeg", "gif", "png", "bmp", "webp"],
    			imageUploadURL: "<?php echo DOKU_BASE;?>uploadimg.php",
    			onload: function() {}
    		});
    	}
    	});
    
    	window.onload = function() {
    		//document.getElementById("editormd").addEventListener('paste', function (event) {
    		$("#editormd").on('paste', function(event) {
    			//console.log(event);
    			var items = (event.clipboardData || event.originalEvent.clipboardData).items;
    			for (var index in items) {
    				var item = items[index];
    				//console.log(item);
    				if (item.kind === 'file') {
    					var blob = item.getAsFile();                        
    					var reader = new FileReader();
    					reader.onload = function(event) {                            
    						var base64 = event.target.result;
    						console.log(base64);
    						//ajax上傳圖片
    						$.post("<?php echo DOKU_BASE;?>uploadimg.php", {
    							screenshots: base64
    						}, function(rets) {
    							ret = JSON.parse(rets);
    							//layer.msg(ret.msg);
    							console.log(ret);
    							if (ret.success === 1) {
    								//新一行的圖片顯示
    								testEditor.insertValue("\n![](" + ret.url + ")");
    							} else {
    								alert("截圖上傳失敗:" + ret.message);
    							}
    						});
    					};
    					reader.readAsDataURL(blob);
    				}
    			}
    		});
    	}
    </script>
    
  • 圖片上傳支持
    將如下代碼保存到 uploadimg.php 文件,放到 wiki 根目錄下,代碼中添加了權限校驗和兼容 dokuwiki 獲取圖片 url
    <?php
    if(!defined('DOKU_INC')) define('DOKU_INC', dirname(__FILE__).'/');
    require_once(DOKU_INC.'inc/init.php');
    
    $INFO = pageinfo();
    $hostpath=getBaseURL(false);
    $attachDir='/data/media/editor/';//上傳文件保存路徑,結尾不要帶/
    $maxAttachSize = 2*1024*1024;  //最大上傳大小,默認是2M
    
    function upEditorImg(){
    	global $hostpath, $attachDir, $maxAttachSize;
    	//獲取文件的大小
    	$file_size=$_FILES['editormd-image-file']['size'];
    	//echo "$file_size $maxAttachSize";
    	if($file_size > $maxAttachSize) {
    		echo '{"success":0,"message":"不能上傳大於2M的文件"}';
    		return false;
    	}
    
    	//獲取文件類型
    	$file_type=$_FILES['editormd-image-file']['type'];
    	if($file_type!="image/jpeg" && $file_type!='image/pjpeg' && $file_type!="image/png") {
    		echo '{"success":0,"message":"圖片格式異常"}';
    		return false;
    	}
    
    	//判斷是否上傳成功(是否使用post方式上傳)
    	if(is_uploaded_file($_FILES['editormd-image-file']['tmp_name'])) {
    		//把文件轉存到你希望的目錄(不要使用copy函數)
    		$uploaded_file=$_FILES['editormd-image-file']['tmp_name'];
    
    		//我們給每個用戶動態的創建一個文件夾
    		$save_path=$_SERVER['DOCUMENT_ROOT'].$hostpath.$attachDir;
    		//判斷該用戶文件夾是否已經有這個文件夾
    		if(!file_exists($save_path)) {
    			mkdir($save_path);
    		}
    
    		//$move_to_file=$save_path."/".$_FILES['editormd-image-file']['name'];
    		$file_true_name=$_FILES['editormd-image-file']['name'];
    		$move_file_name=time().rand(1,1000).substr($file_true_name,strrpos($file_true_name,"."));
    		$move_to_file=$save_path.$move_file_name;
    		//echo "$uploaded_file   $move_to_file";
    		if(move_uploaded_file($uploaded_file,iconv("utf-8","gb2312",$move_to_file))) {
    			//echo $_FILES['editormd-image-file']['name']."上傳成功";
    			//echo '{"success":1,"message":"上傳成功", "url":"'.$hostpath.$attachDir.$move_file_name.'"}';
    			$result=array(
    			  'success'=> 1,
    			  'message'=>'上傳成功',
    			  'url'=>'editor:'.$move_file_name
    			);
    			echo json_encode($result);
    		} else {
    			//echo "上傳失敗";
    			echo '{"success":0,"message":"服務器保存文件失敗"}';
    		}
    	} else {
    		//echo "上傳失敗";
    		echo '{"success":0,"message":"上傳失敗"}';
    		return false;
    	}
    }
    
    //$_POST= [screenshots] => data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAI0AAACcCAYAAABC1CibAAAL6UlEQVR4Ae2dbUiU6RrH...
    function upEditorScreenshots(){
    	global $hostpath, $attachDir, $maxAttachSize;
    
    	$content = $_POST['screenshots'];
    
    	if (preg_match('/^data:image\/(\w+);base64,(\S+)/', $content, $result)) {
    		$file_type = $result[1];
    		$base64data = $result[2];
    
    		//echo "$file_type $base64data";
    		$save_path = $_SERVER['DOCUMENT_ROOT'].$hostpath.$attachDir;
    		if (!is_dir($save_path)) {
    			mkdir($save_path, 0777);
    		}
    
    		$filedata = base64_decode($base64data);
    		$filename = time().rand(1,1000).".".$file_type;
    		if (!file_put_contents($save_path . $filename, $filedata)) {
    			echo '{"success":0,"message":"服務器保存文件失敗"}';
    			return false;
    		}
    		unset($filedata);
    
    		echo '{"success":1,"message":"上傳成功", "url":"editor:'.$move_file_name.$filename.'"}';
    		return true;
    	} else {
    		echo '{"success":0,"message":"圖片格式異常"}';
    		return false;
    	}
    }
    
    //print_r($_POST);
    //print_r($_FILES);
    
    if(isset($_FILES['editormd-image-file'])){
    	global $INFO;
    	if($INFO['writable'] && !$INFO['locked']) {
    		upEditorImg();
    	} else {
    	echo '{"success":0,"message":"沒有權限"}';
    	}
    	exit();
    }
    
    if(isset($_POST['screenshots'])){
    	global $INFO;
    	if($INFO['writable'] && !$INFO['locked']) {
    		upEditorScreenshots();
    	} else  {
    	echo '{"success":0,"message":",沒有權限"}';
    	}
    	exit();
    }
    ?>
    
  • 修改圖片加載地址
    修改 wiki/lib/editor.md/lib/marked.min.js 文件中 img 標簽生成的方法,在以下
    var out='<img src="'+href+'" alt="'+text+'"';
    
    代碼前添加
    if(href.indexOf(':')>0&&href.indexOf("/")<0){href='/lib/exe/fetch.php?cache=&media='+href;}
    

9 遇到的問題及解決

  • 安裝過程提示:yum-config-manager: command not found
    原因:系統默認沒有安裝這個命令
    解決:這個命令在 yum-utils 包里,通過命令 yum -y install yum-utils 安裝即可
  • 訪問 DokuWiki 的地址時,提示如下
    DokuWiki Setup Error
    The datadir ('pages') at ./data/pages is not found, isn't accessible or writable. You should check your config and permission settings. Or maybe you want to run the installer?
    
    原因:
    1. SELinux沒有關閉
    2. wiki 目錄沒有修改文件夾權限為 apache 用戶

10 相關知識

  • 在 DokuWiki 安裝配置完成后,配置信息存放在 wiki/conf/local.php 文件中,如果語言等忘記修改,可直接修改該文件即可
    <?php
    /**
     * Dokuwiki's Main Configuration File - Local Settings
     * Auto-generated by install script
     * Date: Sun, 14 Feb 2021 02:56:54 +0000
     */
    $conf['title'] = 'Alfred知識庫';
    $conf['lang'] = 'zh';
    $conf['license'] = 'cc-by-sa';
    $conf['useacl'] = 1;
    $conf['superuser'] = '@admin';
    $conf['disableactions'] = 'register';
    $conf['fnencode']='utf-8';
    
  • DokuWiki 的插件官網下載地址:https://www.dokuwiki.org/plugins

11 參考資料(感謝)


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM