golang(4)使用beego + ace admin 开发后台系统 CRUD

1,关于ace admin


ace admin 是一个非常好的后台系统ui。
集成了很多的好东西。非常的方便开发后天系统,而且能很漂亮。
上面有一堆的例子。非常的漂亮。
http://ace.jeka.by/

之前还是收费的。后来在github 上面放了一个项目。
但是没有源码。是压缩之后的代码。而且,付费地址也不再了。
是一个过期了的模板 3 年前的了。
github 地址:
https://github.com/bopoda/ace
项目已经没有人维护了。也没有源码了,原来的购买地址都没有了。做公司的后天系统没啥问题了。
比起其他的也没感觉上不潮但比起原生的 bootstrap 要好看点。
已经不错了,还要啥自行车呢。
我写了一个 go-admin 的demo :
项目地址:
https://github.com/freewebsys/go-admin
代码都上传上去了。

2,做一个 golang的后台管理足够了


项目使用beego 进行开发,使用beego开发还是非常的快速的。
将项目 ace 代码 assets 下面的 4个 文件夹拷贝到 beego 项目的 static 文件夹下面:

  1.  
    css
  2.  
    font-awesome
  3.  
    images
  4.  
    js
  • 1
  • 2
  • 3
  • 4

项目几算导入了。其他两个文件夹不加也罢。

3,model 存储对象


存储对象一个用户表的设计:

  1.  
    CREATE TABLE `user_info` (
  2.  
    `id` bigint(20) NOT NULL AUTO_INCREMENT,
  3.  
    `user_name` varchar(200) DEFAULT NULL,
  4.  
    `password` varchar(200) DEFAULT NULL,
  5.  
    `name` varchar(200) DEFAULT NULL,
  6.  
    `birth_date` varchar(200) DEFAULT NULL,
  7.  
    `gender` int(1) DEFAULT NULL,
  8.  
    `email` varchar(200) DEFAULT NULL,
  9.  
    `phone` varchar(200) DEFAULT NULL,
  10.  
    `status` tinyint(1) NOT NULL ,
  11.  
    `create_time` datetime NOT NULL,
  12.  
    `update_time` datetime NOT NULL,
  13.  
    UNIQUE KEY `user_name` (`key`),
  14.  
    PRIMARY KEY (`id`)
  15.  
    ENGINE=InnoDB DEFAULT CHARSET=utf8;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15

一个简单的用户表
对应的数据操作:

  1.  
    package models
  2.  
     
  3.  
    import (
  4.  
    "github.com/astaxie/beego/orm"
  5.  
    "github.com/astaxie/beego/logs"
  6.  
    "time"
  7.  
    )
  8.  
     
  9.  
    type UserInfo struct {
  10.  
    Id int64 `orm:"auto"`
  11.  
    UserName string `orm:"size(255)"` //登录名
  12.  
    Password string `orm:"size(255)"` //密码
  13.  
    Name string `orm:"size(255)"` //用户名
  14.  
    BirthDate string `orm:"size(255)"` //生日
  15.  
    Gender int8 //性别
  16.  
    Email string `orm:"size(255)"` //Email
  17.  
    Phone string `orm:"size(255)"` //电话
  18.  
    Status int8 //状态
  19.  
    CreateTime time.Time //创建时间
  20.  
    UpdateTime time.Time //更新时间
  21.  
    }
  22.  
     
  23.  
    func init() {
  24.  
    orm.RegisterModel(new(UserInfo))
  25.  
    }
  26.  
     
  27.  
    //创建&更新
  28.  
    func SaveUserInfoById(m *UserInfo) (err error) {
  29.  
    o := orm.NewOrm()
  30.  
    var num int64
  31.  
    if m.Id == 0 {
  32.  
    m.CreateTime = time.Now()
  33.  
    m.UpdateTime = time.Now()
  34.  
    if num, err = o.Insert(m); err == nil {
  35.  
    logs.Info("Number of records insert in database:", num)
  36.  
    }
  37.  
    else {
  38.  
    var tmp *UserInfo
  39.  
    tmp, err = GetUserInfoById(m.Id)
  40.  
     
  41.  
    if err == nil {
  42.  
     
  43.  
    //修改几个参数的名称。
  44.  
    tmp.UserName = m.UserName
  45.  
    tmp.Name = m.Name
  46.  
    tmp.BirthDate = m.BirthDate
  47.  
    tmp.Gender = m.Gender
  48.  
    tmp.Email = m.Email
  49.  
    tmp.Phone = m.Phone
  50.  
    tmp.Status = m.Status
  51.  
    tmp.UpdateTime = time.Now()
  52.  
     
  53.  
    if num, err = o.Update(tmp); err == nil {
  54.  
    logs.Info("Number of records updated in database:", num)
  55.  
    }
  56.  
    }
  57.  
    }
  58.  
    return
  59.  
    }
  60.  
     
  61.  
    //删除
  62.  
    func DeleteUserInfo(id int64(err error) {
  63.  
    o := orm.NewOrm()
  64.  
    v := UserInfo{Id: id}
  65.  
    if err = o.Read(&v, "Id"); err == nil {
  66.  
    if num, err := o.Delete(&UserInfo{Id: id}); err == nil {
  67.  
    logs.Info("Number of records deleted in database:", num)
  68.  
    }
  69.  
    }
  70.  
    return
  71.  
    }
  72.  
     
  73.  
    //按id查询
  74.  
    func GetUserInfoById(id int64(v *UserInfo, err error) {
  75.  
    o := orm.NewOrm()
  76.  
    v = &UserInfo{Id: id}
  77.  
    if err = o.Read(v, "Id"); err == nil {
  78.  
    return v, nil
  79.  
    }
  80.  
    return nil, err
  81.  
    }
  82.  
     
  83.  
    //查询数据
  84.  
    func QueryAllUserInfo() (dataList []interface{}, err error) {
  85.  
    var list []UserInfo
  86.  
    o := orm.NewOrm()
  87.  
    qs := o.QueryTable(new(UserInfo))
  88.  
    //查询
  89.  
    //查询数据
  90.  
    if _, err = qs.All(&list); err == nil {
  91.  
    for _, v := range list {
  92.  
    dataList = append(dataList, v)
  93.  
    }
  94.  
    return dataList, nil
  95.  
    }
  96.  
    return nil, err
  97.  
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97

参考了bee go 自动生成的代码。但是发现beego 升级了之后模板变了。
其中特别要主要 := 的坑,如果稍不留神就会替换掉对象在一个作用域下,而且不会报错呢。

4,controller 控制


  1.  
    package controllers
  2.  
     
  3.  
    import (
  4.  
    "github.com/astaxie/beego/logs"
  5.  
    "github.com/astaxie/beego"
  6.  
    "github.com/freewebsys/go-admin/models"
  7.  
    )
  8.  
     
  9.  
    type UserInfoController struct {
  10.  
    beego.Controller
  11.  
    }
  12.  
     
  13.  
    //修改
  14.  
    func (c *UserInfoController) Edit() {
  15.  
    //获得id
  16.  
    id, _ := c.GetInt64("Id", 0)
  17.  
    userInfo, err := models.GetUserInfoById(id)
  18.  
    if err == nil {
  19.  
    c.Data["UserInfo"] = userInfo
  20.  
    else {
  21.  
    tmpUserInfo := &models.UserInfo{}
  22.  
    tmpUserInfo.Status = -1
  23.  
    tmpUserInfo.Gender = -1
  24.  
    c.Data["UserInfo"] = tmpUserInfo
  25.  
    }
  26.  
    c.TplName = "userInfo/edit.html"
  27.  
    }
  28.  
     
  29.  
    //删除
  30.  
    func (c *UserInfoController) Delete() {
  31.  
    //获得id
  32.  
    id, _ := c.GetInt64("Id", 0)
  33.  
    if err := models.DeleteUserInfo(id); err == nil {
  34.  
    c.Data["json"] = "ok"
  35.  
    else {
  36.  
    c.Data["json"] = "error"
  37.  
    }
  38.  
    c.ServeJSON()
  39.  
    }
  40.  
     
  41.  
    //保存
  42.  
    func (c *UserInfoController) Save() {
  43.  
    //自动解析绑定到对象中
  44.  
    userInfo := models.UserInfo{}
  45.  
    if err := c.ParseForm(&userInfo); err == nil {
  46.  
    if err := models.SaveUserInfoById(&userInfo); err == nil {
  47.  
    c.Data["json"] = ""
  48.  
    else {
  49.  
    c.Data["json"] = "error"
  50.  
    }
  51.  
    else {
  52.  
    c.Data["json"] = "error"
  53.  
    }
  54.  
    c.ServeJSON()
  55.  
    }
  56.  
     
  57.  
    //返回全部数据
  58.  
    func (c *UserInfoController) List() {
  59.  
     
  60.  
    dataList, err := models.QueryAllUserInfo()
  61.  
    if err == nil {
  62.  
    c.Data["List"] = dataList
  63.  
    }
  64.  
    logs.Info("dataList :", dataList)
  65.  
    c.TplName = "userInfo/list.html"
  66.  
     
  67.  
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68

5,view 展示


展示列表:
参考:http://ace.jeka.by/tables.html

  1.  
    <table id="simple-table" class="table table-bordered table-hover">
  2.  
    <tr>
  3.  
    <th>Id</th>
  4.  
    <th>姓名</th>
  5.  
    <th>生日</th>
  6.  
    <th>性别</th>
  7.  
    <th>Email</th>
  8.  
    <th>电话</th>
  9.  
    <th>状态</th>
  10.  
    <th>创建时间</th>
  11.  
    <th>更新时间</th>
  12.  
    <th>操作</th>
  13.  
    </tr>
  14.  
    {{range .List}}
  15.  
    <tr>
  16.  
     
  17.  
    <td>{{.Id}}</td>
  18.  
    <td>{{.Name}}</td>
  19.  
    <td>{{.BirthDate}}</td>
  20.  
    <td>{{.Gender}}</td>
  21.  
    <td>{{.Email}}</td>
  22.  
    <td>{{.Phone}}</td>
  23.  
    <td>{{.Status}}</td>
  24.  
    <td>{{date .CreateTime "2006-01-02 15:04:05"}}</td>
  25.  
    <td>{{date .UpdateTime "2006-01-02 15:04:05"}}</td>
  26.  
     
  27.  
    <td>
  28.  
    <div class="hidden-sm hidden-xs btn-group">
  29.  
    <button class="btn btn-xs btn-info" onclick="showEditWindow('{{.Id}}');">
  30.  
    <i class="ace-icon fa fa-pencil bigger-120"></i>
  31.  
    </button>
  32.  
    <button class="btn btn-xs btn-danger" onclick="deleteConfirm('{{.Id}}');">
  33.  
    <i class="ace-icon fa fa-trash-o bigger-120"></i>
  34.  
    </button>
  35.  
    </div>
  36.  
    </td>
  37.  
    </tr>
  38.  
    {{end}}
  39.  
    </table>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39

特别注意对时间字段的格式化:{{date .UpdateTime “2006-01-02 15:04:05”}} 不是java习惯的 yyyy-MM-dd
感觉上一点也不好记。是按照老外的习惯记住的 1 2 3 4 5 6 的规则命名的。

创建& 编辑:

将对象放到 data里面,然后做展示编辑。

  1.  
    <div class="col-sm-9">
  2.  
    <input type="text" id="UserName" name="UserName" placeholder="登录名" class="col-xs-10 col-sm-5"
  3.  
    value="{{.UserInfo.UserName}}"/>
  4.  
    </div>
  • 1
  • 2
  • 3
  • 4

其中编辑使用div 窗口弹出参考:
http://ace.jeka.by/form-elements.html
http://ace.jeka.by/content-slider.html
并且页面进行校验:

使用的教研框架:http://jqueryvalidation.org/

  1.  
    jQuery(function ($) {
  2.  
    $('#saveForm').validate({
  3.  
    errorElement: 'div',
  4.  
    errorClass: 'help-block',
  5.  
    focusInvalid: false,
  6.  
    ignore: "",
  7.  
    rules: {
  8.  
    UserName: {
  9.  
    required: true,
  10.  
    }
  11.  
    },
  12.  
    highlight: function (e) {
  13.  
    $(e).closest('.form-group').removeClass('has-info').addClass('has-error');
  14.  
    },
  15.  
    success: function (e) {
  16.  
    $(e).closest('.form-group').removeClass('has-error');//.addClass('has-info');
  17.  
    $(e).remove();
  18.  
    }
  19.  
    });
  20.  
    });
  21.  
    //保存,之前进行校验
  22.  
    function save() {
  23.  
    if ($('#saveForm').valid()) {
  24.  
    $.post("/admin/userInfo/save", $("#saveForm").serialize(),
  25.  
    function (data) {
  26.  
    window.location.reload();
  27.  
    });
  28.  
    }
  29.  
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29

7,拦截器


  1.  
    //增加拦截器。
  2.  
    var filterAdmin = func(ctx *context.Context) {
  3.  
    url := ctx.Input.URL()
  4.  
    logs.Info("##### filter url : %s", url)
  5.  
    //TODO 如果判断用户未登录。
  6.  
     
  7.  
    }
  8.  
    beego.InsertFilter("/admin/*", beego.BeforeExec, filterAdmin)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

可以针对 /admin/* 进行拦截

8,关闭防火墙


在 mac 上面发现总是要允许端口,开发比较讨厌,请关闭防火墙:

这里写图片描述

6,总结


beego 开发一个admin系统还是挺快的。
因为beego 可以自动检查代码改的,自动重启,开发速度还是很快的。
并且因为beego的编译启动还是非常的快速的。
所以开发速度还是挺快的。golang的代码还需要适应下。上手还是挺快的。1,2个星期就能开发一个小系统。
做个用户权限,登录啥的都非常方便。

本文的原文连接是: http://blog.csdn.net/freewebsys/article/details/68955060 未经博主允许不得转载。
博主地址是:http://blog.csdn.net/freewebsys

 
posted @ 2021-07-05 19:24  dreamw  阅读(258)  评论(0编辑  收藏  举报