优化体验

This commit is contained in:
Minho
2017-05-26 14:19:27 +08:00
parent a562499b83
commit bb9ba8c4b6
23 changed files with 794 additions and 275 deletions

View File

@@ -17,6 +17,8 @@
<link href="/static/css/jstree.css" rel="stylesheet">
{{if eq .Model.Editor "markdown"}}
<link href="{{cdncss "/static/editor.md/css/editormd.preview.css"}}" rel="stylesheet">
<link href="{{cdncss "/static/prettify/themes/atelier-estuary-dark.min.css"}}" rel="stylesheet">
<link href="/static/css/markdown.preview.css" rel="stylesheet">
{{else}}
<link href="{{cdncss "/static/highlight/styles/zenburn.css"}}" rel="stylesheet">
{{end}}
@@ -226,196 +228,20 @@
<script type="text/javascript" src="{{cdnjs "/static/nprogress/nprogress.js"}}"></script>
<script type="text/javascript" src="{{cdnjs "/static/highlight/highlight.js"}}"></script>
<script type="text/javascript" src="{{cdnjs "/static/highlight/highlightjs-line-numbers.min.js"}}"></script>
<script type="text/javascript" src="/static/js/jquery.highlight.js"></script>
<script type="text/javascript" src="/static/js/kancloud.js"></script>
<script type="text/javascript">
var events = $("body");
var catalog = null;
function initHighlighting() {
$('pre code').each(function (i, block) {
hljs.highlightBlock(block);
});
hljs.initLineNumbersOnLoad();
}
function loadDocument($url,$id,$callback) {
$.ajax({
url : $url,
type : "GET",
beforeSend :function (xhr) {
var body = events.data('body_' + $id);
var title = events.data('title_' + $id);
var doc_title = events.data('doc_title_' + $id);
if(body && title && doc_title){
if (typeof $callback === "function") {
body = $callback(body);
}
$("#page-content").html(body);
$("title").text(title);
$("#article-title").text(doc_title);
events.trigger('article.open',$url,true);
return false;
}
NProgress.start();
},
success : function (res) {
if(res.errcode === 0){
var body = res.data.body;
var doc_title = res.data.doc_title;
var title = res.data.title;
$body = body;
if (typeof $callback === "function" ){
$body = $callback(body);
}
$("#page-content").html($body);
$("title").text(title);
$("#article-title").text(doc_title);
events.data('body_' + $id,body);
events.data('title_' + $id,title);
events.data('doc_title_' + $id,doc_title);
events.trigger('article.open',$url,false);
}else{
layer.msg("加载失败");
}
},
complete : function () {
NProgress.done();
}
});
}
$(function () {
$(".view-backtop").on("click", function () {
$('.manual-right').animate({ scrollTop: '0px' }, 200);
});
$(".manual-right").scroll(function () {
var top = $(".manual-right").scrollTop();
if(top > 100){
$(".view-backtop").addClass("active");
}else{
$(".view-backtop").removeClass("active");
}
});
window.isFullScreen = false;
initHighlighting();
$("#sidebar").jstree({
'plugins':["wholerow","types"],
"types": {
"default" : {
"icon" : false //
}
},
'core' : {
'check_callback' : true,
"multiple" : false ,
'animation' : 0
}
}).on('select_node.jstree',function (node,selected,event) {
$(".m-manual").removeClass('manual-mobile-show-left');
var url = selected.node.a_attr.href;
if(url === window.location.href){
return false;
}
loadDocument(url,selected.node.id);
});
$("#slidebar").on("click",function () {
$(".m-manual").addClass('manual-mobile-show-left');
});
$(".manual-mask").on("click",function () {
$(".m-manual").removeClass('manual-mobile-show-left');
});
$(".manual-fullscreen-switch").on("click",function () {
isFullScreen = !isFullScreen;
if (isFullScreen) {
$(".m-manual").addClass('manual-fullscreen-active');
} else {
$(".m-manual").removeClass('manual-fullscreen-active');
}
});
events.on('article.open', function (event, url,init) {
if ('pushState' in history) {
if (init == false) {
history.replaceState({ }, '', url);
init = true;
} else {
history.pushState({ }, '', url);
}
} else {
location.hash = url;
}
initHighlighting();
});
$(".navg-item[data-mode]").on("click",function () {
var mode = $(this).data('mode');
$(this).siblings().removeClass('active').end().addClass('active');
$(".m-manual").removeClass("manual-mode-view manual-mode-collect manual-mode-search").addClass("manual-mode-" + mode);
});
/**
*
*/
$("#searchForm").ajaxForm({
beforeSubmit : function () {
var keyword = $.trim($("#searchForm").find("input[name='keyword']").val());
if(keyword === ""){
$(".search-empty").show();
$("#searchList").html("");
return false;
}
$("#btnSearch").attr("disabled","disabled").find("i").removeClass("fa-search").addClass("loading");
window.keyword = keyword;
},
success :function (res) {
var html = "";
if(res.errcode === 0){
for(var i in res.data){
var item = res.data[i];
html += '<li><a href="javascript:;" title="'+ item.doc_name +'" data-id="'+ item.doc_id+'"> '+ item.doc_name +' </a></li>';
}
}
if(html !== ""){
$(".search-empty").hide();
}else{
$(".search-empty").show();
}
$("#searchList").html(html);
},
complete : function () {
$("#btnSearch").removeAttr("disabled").find("i").removeClass("loading").addClass("fa-search");
}
});
$("#searchList").on("click","a",function () {
var id = $(this).attr("data-id");
var url = "{{urlfor "DocumentController.Read" ":key" .Model.Identify ":id" ""}}/" + id;
$(this).parent("li").siblings().find("a").removeClass("active");
$(this).addClass("active");
loadDocument(url,id,function (body) {
if(body !== ""){
console.log(window.keyword);
body = body.replace(new RegExp(window.keyword,"g"),'<em class="search-highlight">' + window.keyword + '</em>');
}
return body;
});
$(function () {
$("#searchList").on("click","a",function () {
var id = $(this).attr("data-id");
var url = "{{urlfor "DocumentController.Read" ":key" .Model.Identify ":id" ""}}/" + id;
$(this).parent("li").siblings().find("a").removeClass("active");
$(this).addClass("active");
loadDocument(url,id,function (body) {
return $(body).highlight(window.keyword);
});
});
});
</script>
</body>
</html>

View File

@@ -29,6 +29,8 @@
<link href="{{cdncss "/static/highlight/styles/zenburn.css"}}" rel="stylesheet">
<link href="{{cdncss "/static/webuploader/webuploader.css"}}" rel="stylesheet">
<link href="/static/css/markdown.css" rel="stylesheet">
<link href="{{cdncss "/static/prettify/themes/atelier-estuary-dark.min.css"}}" rel="stylesheet">
<link href="/static/css/markdown.preview.css" rel="stylesheet">
<!-- HTML5 shim and Respond.js for IE8 support of HTML5 elements and media queries -->
<!-- WARNING: Respond.js doesn't work if you view the page via file:// -->
<!--[if lt IE 9]>
@@ -77,7 +79,9 @@
<a href="javascript:;" data-toggle="tooltip" data-title="添加表格"><i class="fa fa-table item" name="table" unselectable="on"></i></a>
<a href="javascript:;" data-toggle="tooltip" data-title="引用"><i class="fa fa-quote-right item" name="quote" unselectable="on"></i></a>
<a href="javascript:;" data-toggle="tooltip" data-title="GFM 任务列表"><i class="fa fa-tasks item" name="tasks" aria-hidden="true"></i></a>
<a href="javascript:;" data-toggle="tooltip" data-title="附件"><i class="fa fa-paperclip last" aria-hidden="true" name="attachment"></i></a>
<a href="javascript:;" data-toggle="tooltip" data-title="附件"><i class="fa fa-paperclip item" aria-hidden="true" name="attachment"></i></a>
<a href="javascript:;" data-toggle="tooltip" data-title="模板"><i class="fa fa-tachometer last" name="template"></i></a>
</div>
<div class="editormd-group pull-right">
@@ -225,6 +229,57 @@
</div>
</div>
<div class="modal fade" id="documentTemplateModal" tabindex="-1" role="dialog" aria-labelledby="请选择模板类型" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h4 class="modal-title" id="modal-title">请选择模板类型</h4>
</div>
<div class="modal-body template-list">
<div class="container">
<div class="section">
<a data-type="normal" href="javascript:;"><i class="fa fa-file-o"></i></a>
<h3><a data-type="normal" href="javascript:;">普通文档</a></h3>
<ul>
<li>默认类型</li>
<li>简单的文本文档</li>
</ul>
</div>
<div class="section">
<a data-type="api" href="javascript:;"><i class="fa fa-file-code-o"></i></a>
<h3><a data-type="api" href="javascript:;">API文档</a></h3>
<ul>
<li>用于API文档速写</li>
<li>支持代码高亮</li>
</ul>
</div>
<div class="section">
<a data-type="code" href="javascript:;"><i class="fa fa-book"></i></a>
<h3><a data-type="code" href="javascript:;">数据字典</a></h3>
<ul>
<li>用于数据字典显示</li>
<li>表格支持</li>
</ul>
</div>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">取消</button>
</div>
</div>
</div>
</div>
<template id="template-normal">
{{template "document/template_normal.tpl"}}
</template>
<template id="template-api">
{{template "document/template_api.tpl"}}
</template>
<template id="template-code">
{{template "document/template_code.tpl"}}
</template>
<script src="{{cdnjs "/static/jquery/1.12.4/jquery.min.js"}}"></script>
<script src="{{cdnjs "/static/vuejs/vue.min.js"}}" type="text/javascript"></script>
<script src="{{cdnjs "/static/bootstrap/js/bootstrap.min.js"}}"></script>
@@ -233,10 +288,6 @@
<script src="{{cdnjs "/static/editor.md/editormd.js"}}" type="text/javascript"></script>
<script src="{{cdnjs "/static/layer/layer.js"}}" type="text/javascript" ></script>
<script src="{{cdnjs "/static/js/jquery.form.js"}}" type="text/javascript"></script>
<script type="text/javascript">
</script>
<script src="/static/js/editor.js" type="text/javascript"></script>
<script src="/static/js/markdown.js" type="text/javascript"></script>
<script type="text/javascript">

View File

@@ -0,0 +1,71 @@
#### 简要描述:
- 用户登录接口
#### 接口版本:
|版本号|制定人|制定日期|修订日期|
|:---- |:---|:----- |----- |
|2.1.0 |秦亮 |2017-03-20 | xxxx-xx-xx |
#### 请求URL:
- http://xx.com/api/login
#### 请求方式:
- GET
- POST
#### 请求头:
|参数名|是否必须|类型|说明|
|:---- |:---|:----- |----- |
|Content-Type |是 |string |请求类型: application/json |
|Content-MD5 |是 |string | 请求内容签名 |
#### 请求参数:
|参数名|是否必须|类型|说明|
|:---- |:---|:----- |----- |
|username |是 |string |用户名 |
|password |是 |string | 密码 |
#### 返回示例:
**正确时返回:**
```
{
"errcode": 0,
"data": {
"uid": "1",
"account": "admin",
"nickname": "Minho",
"group_level": 0 ,
"create_time": "1436864169",
"last_login_time": "0",
}
}
```
**错误时返回:**
```
{
"errcode": 500,
"errmsg": "invalid appid"
}
```
#### 返回参数说明:
|参数名|类型|说明|
|:----- |:-----|----- |
|group_level |int |用户组id1超级管理员2普通用户 |
#### 备注:
- 更多返回错误代码请看首页的错误代码描述

View File

@@ -0,0 +1,13 @@
### 数据库字典
#### 用户表,储存用户信息
|字段|类型|空|默认|注释|
|:---- |:------- |:--- |-- -|------ |
|uid |int(10) |否 | | |
|username |varchar(20) |否 | | 用户名 |
|password |varchar(50) |否 | | 密码 |
|name |varchar(15) |是 | | 昵称 |
|reg_time |int(11) |否 | 0 | 注册时间 |
#### 备注:无

View File

@@ -0,0 +1,208 @@
# MinDoc 简介
[![Build Status](https://travis-ci.org/lifei6671/godoc.svg?branch=master)](https://travis-ci.org/lifei6671/godoc)
MinDoc 是一款针对IT团队开发的简单好用的文档管理系统。
MinDoc 的前身是 SmartWiki 文档系统。SmartWiki 是基于 PHP 框架 laravel 开发的一款文档管理系统。因 PHP 的部署对普通用户来说太复杂,所以改用 Golang 开发。可以方便用户部署和实用。
开发缘起是公司IT部门需要一款简单实用的项目接口文档管理和分享的系统。其功能和界面源于 kancloud 。
可以用来储存日常接口文档,数据库字典,手册说明等文档。内置项目管理,用户管理,权限管理等功能,能够满足大部分中小团队的文档管理需求。
演示站点: [http://doc.iminho.me](http://doc.iminho.me)
# 安装与使用
**如果你的服务器上没有安装golang程序请手动设置一个环境变量如下键名为 ZONEINFO值为MinDoc跟目录下的/lib/time/zoneinfo.zip 。**
**Windows 教程:** [https://github.com/lifei6671/godoc/blob/master/README_WIN.md](docs/README_WIN.md)
**Linux 教程:**  [https://github.com/lifei6671/godoc/blob/master/README_LINUX.md](docs/README_LINUX.md)
**PDF 导出配置教程**  [https://github.com/lifei6671/godoc/blob/master/docs/README_LINUX.md](docs/WKHTMLTOPDF.md)
对于没有Golang使用经验的用户可以从 [https://github.com/lifei6671/godoc/releases](https://github.com/lifei6671/godoc/releases) 这里下载编译完的程序。
如果有Golang开发经验建议通过编译安装。
```bash
git clone https://github.com/lifei6671/godoc.git
go get -d ./...
go build -ldflags "-w"
```
MinDoc 使用MySQL储存数据且编码必须是`utf8mb4_general_ci`。请在安装前,把数据库配置填充到项目目录下的 conf/app.conf 中。
如果conf目录下不存在 app.conf 请重命名 app.conf.example 为 app.conf。
如果 MinDoc 根目录下存在 install.lock 文件表示已经初始化过数据库,想要重新初始化数据库,只需要删除该文件重新启动程序即可。
**默认程序会自动创建表同时初始化一个超级管理员用户admin 密码123456 。请登录后重新设置密码。**
## Linux 下后台运行
在 Linux 如果想让程序后台运行可以执行如下命令:
```bash
#使程序后台运行
nohup ./godoc &
```
该命令会使程序后台执行,但是服务器重启后不会自动启动服务。
使用 supervisor 做服务,可以使服务器重启后自动重启 MinDoc。
## Windows 下后台运行
Windows 下后台运行需要借助 CMD 命令行命令:
```bash
#在MinDoc跟目录下新建一个slave.vbs文件
Set ws = CreateObject("Wscript.Shell")
ws.run "cmd /c start.bat",vbhide
#再建一个start.bat文件
@echo off
godoc_windows_amd64.exe
```
启动时双击slave.vbs即可等待程序初始化完数据库会在该目录下创建一个install.lock文件标识已安装成功。
如果是自己编译可以用以下命令即可编译出不依赖cmd命令的后台运行的程序
```bash
go build -ldflags "-H=windowsgui"
```
通过该命令编译的Golang程序在Windows上默认后台运行。
请将将 MinDoc 加入开机启动列表,使程序开机启动。
## 密码找回功能
密码找回功能依赖邮件服务,因此,需要配置邮件服务才能使用该功能,该配置位于 `conf/app.conf` 中:
```bash
#邮件配置
#是否启用邮件
enable_mail=true
#smtp服务器的账号
smtp_user_name=admin@iminho.me
#smtp服务器的地址
smtp_host=smtp.ym.163.com
#密码
smtp_password=1q2w3e__ABC
#端口号
smtp_port=25
#邮件发送人的地址
form_user_name=admin@iminho.me
#邮件有效期30分钟
mail_expired=30
```
# 使用Docker部署
如果是Docker用户可参考项目内置的Dockerfile文件编译镜像。
在启动镜像时需要提供如下的环境变量:
```ini
MYSQL_PORT_3306_TCP_ADDR MySQL地址
MYSQL_PORT_3306_TCP_PORT MySQL端口号
MYSQL_INSTANCE_NAME MySQL数据库名称
MYSQL_USERNAME MySQL账号
MYSQL_PASSWORD MySQL密码
HTTP_PORT 程序监听的端口号
```
举个栗子
```bash
docker run -p 8181:8181 -e MYSQL_PORT_3306_TCP_ADDR=127.0.0.1 -e MYSQL_PORT_3306_TCP_PORT=3306 -e MYSQL_INSTANCE_NAME=mindoc_db -e MYSQL_USERNAME=root -e MYSQL_PASSWORD=123456 -e httpport=8181 -d daocloud.io/lifei6671/godoc:latest
```
# 项目截图
**创建项目**
![创建项目](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501204438.png)
**项目列表**
![项目列表](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501203542.png)
**项目概述**
![项目概述](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501203619.png)
**项目成员**
![项目成员](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501203637.png)
**项目设置**
![项目设置](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501203656.png)
**基于Editor.md开发的Markdown编辑器**
![基于Editor.md开发的Markdown编辑器](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501203854.png)
**基于wangEditor开发的富文本编辑器**
![基于wangEditor开发的富文本编辑器](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501204651.png)
**项目预览**
![项目预览](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501204609.png)
**超级管理员后台**
![超级管理员后台](https://raw.githubusercontent.com/lifei6671/godoc/master/uploads/20170501204710.png)
# 使用的技术
- beego 1.8.1
- mysql 5.6
- editor.md
- bootstrap 3.2
- jquery 库
- layer 弹出层框架
- webuploader 文件上传框架
- Nprogress 库
- jstree 树状结构库
- font awesome 字体库
- cropper 图片剪裁库
- layer 弹出层框架
- highlight 代码高亮库
- to-markdown HTML转Markdown库
- wangEditor 富文本编辑器
# 主要功能
- 项目管理,可以对项目进行编辑更改,成员添加等。
- 文档管理,添加和删除文档等。
- 评论管理,可以管理文档评论和自己发布的评论。
- 用户管理,添加和禁用用户,个人资料更改等。
- 用户权限管理 实现用户角色的变更。
- 项目加密可以设置项目公开状态私有项目需要通过Token访问。
- 站点配置,可开启匿名访问、验证码等。
# 参与开发
我们欢迎您在 MinDoc 项目的 GitHub 上报告 issue 或者 pull request。
如果您还不熟悉GitHub的Fork and Pull开发模式您可以阅读GitHub的文档https://help.github.com/articles/using-pull-requests 获得更多的信息。
# 关于作者
一个不纯粹的PHPer一个不自由的 gopher 。

View File

@@ -47,7 +47,7 @@
<div class="form-group">
<label>用户密码</label>
<input type="password" class="form-control" name="password1" placeholder="用户密码" maxlength="50">
<p style="color: #999;font-size: 12px;">不修改密码请留空</p>
<p style="color: #999;font-size: 12px;">不修改密码请留空,只支持本地用户修改密码</p>
</div>
<div class="form-group">
<label>确认密码</label>

View File

@@ -40,21 +40,21 @@
</div>
</div>
<div class="box-body manager">
<div class="dashboard-item">
<a href="{{urlfor "ManagerController.Books"}}" class="dashboard-item">
<span class="fa fa-book" aria-hidden="true"></span>
<span class="fa-class">项目数量</span>
<span class="fa-class">{{.Model.BookNumber}}</span>
</div>
</a>
<div class="dashboard-item">
<span class="fa fa-file-text-o" aria-hidden="true"></span>
<span class="fa-class">文章数量</span>
<span class="fa-class">{{.Model.DocumentNumber}}</span>
</div>
<div class="dashboard-item">
<span class="fa fa-users" aria-hidden="true"></span>
<span class="fa-class">会员数量</span>
<span class="fa-class">{{.Model.MemberNumber}}</span>
</div>
<a href="{{urlfor "ManagerController.Users"}}" class="dashboard-item">
<span class="fa fa-users" aria-hidden="true"></span>
<span class="fa-class">会员数量</span>
<span class="fa-class">{{.Model.MemberNumber}}</span>
</a>
<!--
{{/*
<div class="dashboard-item">

View File

@@ -29,7 +29,9 @@
<div class="page-left">
<ul class="menu">
<li class="active"><a href="{{urlfor "SettingController.Index"}}" class="item"><i class="fa fa-sitemap" aria-hidden="true"></i> 基本信息</a> </li>
{{if ne .Member.AuthMethod "ldap"}}
<li><a href="{{urlfor "SettingController.Password"}}" class="item"><i class="fa fa-user" aria-hidden="true"></i> 修改密码</a> </li>
{{end}}
</ul>
</div>
<div class="page-right">