用beego寫一個友情連接

beego框架和bee工具的安裝很是簡單,惟一須要注意的是Mac平臺go1.8版本沒法運行bee工具,說是官方包形成的bug,須要使用更高版本,好比個人Mac本地版本是:javascript

zhgxun-pro:~ zhgxun$ go version
go version go1.8.3 darwin/amd64

如今來看如何用beego框架編寫一個友情連接。html

一、建立表java

CREATE TABLE `link` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `type` tinyint(1) NOT NULL DEFAULT 1 COMMENT '類型1官網2手冊3其它',
  `title` varchar(120) NOT NULL COMMENT '標題',
  `url` varchar(255) NOT NULL COMMENT '地址',
  `content` varchar(255) NOT NULL COMMENT '描述',
  `status` tinyint(1) NOT NULL DEFAULT '1' COMMENT '狀態1可用2不可用',
  `ctime` int(11) DEFAULT '0' COMMENT '建立時間',
  `utime` int(11) NOT NULL DEFAULT '0' COMMENT '更新時間',
  PRIMARY KEY (`id`),
  KEY `type`(`type`),
  KEY `title`(`title`),
  KEY `status`(`status`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8 COMMENT='友情連接';

二、編寫模型python

// 友情連接
package models

import (
    "time"

    "github.com/astaxie/beego/orm"
)

type Link struct {
    Id      int64
    Type    int
    Title   string
    Url     string
    Content string
    Status  int
    Ctime   int64
    Utime   int64
}

// LinkStatus 友情連接狀態
func LinkStatus() map[int]string {
    return map[int]string{
        1: "可用",
        2: "不可用",
    }
}

// LinkStatusDesc 友情連接狀態描述
func LinkStatusDesc(id int) string {
    if desc, ok := LinkStatus()[id]; ok {
        return desc
    }
    return "未知"
}

// LinkTypeList 類型
func LinkTypeList() map[int]string {
    return map[int]string{
        1: "官網",
        2: "手冊",
        3: "其它",
    }
}

// LinkTypeDesc 類型描述
func LinkTypeDesc(id int) string {
    if desc, ok := LinkTypeList()[id]; ok {
        return desc
    }
    return "未知"
}

// LinkSave 添加友情連接
func LinkSave(l *Link) (int64, error) {
    o := orm.NewOrm()
    l.Status = 1
    l.Ctime = time.Now().Unix()
    l.Utime = time.Now().Unix()
    return o.Insert(l)
}

// LinkUpdate 更新友情連接
func LinkUpdate(l *Link) (int64, error) {
    o := orm.NewOrm()
    l.Utime = time.Now().Unix()
    if _, err := o.Update(l); err != nil {
        return l.Id, err
    }
    return l.Id, nil
}

// LinkList 友情連接列表
func LinkList() []*Link {
    var link Link
    var links []*Link
    o := orm.NewOrm()
    o.QueryTable(link).RelatedSel().Filter("Status", 1).All(&links)
    return links
}

// LinkInfo 友情連接詳情
func LinkInfo(id int64) (Link, error) {
    var l Link
    o := orm.NewOrm()
    err := o.QueryTable(l).RelatedSel().Filter("Id", id).One(&l)
    return l, err
}

三、註冊模型mysql

package main

import (
    _ "github.com/go-sql-driver/mysql"

    "github.com/astaxie/beego"
    "github.com/astaxie/beego/orm"

    "step/models"
    _ "step/routers"
)

func init() {
    orm.RegisterDataBase("default", "mysql", "root:@/step")
    orm.RegisterModel(
        new(models.Link),
    )
}

func main() {
    beego.Run()
}

四、註冊路由git

package routers

import (
    "github.com/astaxie/beego"

    "step/controllers"
)

func init() {
    // 友情連接
    beego.Router("/link", &controllers.LinkController{}, "GET:Index")
    beego.Router("/link/create", &controllers.LinkController{}, "GET,POST:Create")
    beego.Router("/link/:id([0-9]+)", &controllers.LinkController{}, "GET,POST:View")
    beego.Router("/link/update/:id([0-9]+)", &controllers.LinkController{}, "GET,POST:Update")
    beego.Router("/link/delete/:id([0-9]+)", &controllers.LinkController{}, "GET:Delete")
}

五、控制器github

// 友情連接
package controllers

import (
    "fmt"
    "strconv"
    "strings"

    "github.com/astaxie/beego"

    "step/models"
)

type LinkController struct {
    beego.Controller
}

// Index 友情連接列表
func (l *LinkController) Index() {
    l.Data["links"] = models.LinkList()
    l.Data["types"] = models.LinkTypeList()
    l.Data["status"] = models.LinkStatus()
    l.Layout = "base.html"
    l.TplName = "link/index.html"
}

// Create 添加友情連接
func (l *LinkController) Create() {
    if l.Ctx.Request.Method == "POST" {
        typeId, err := strconv.Atoi(strings.TrimSpace(l.Input().Get("type")))
        if err != nil {
            l.Redirect("/link/create", 302)
        }
        title := l.Input().Get("title")
        url := l.Input().Get("url")
        content := l.Input().Get("content")
        if typeId <= 0 {
            l.Redirect("/link/create", 302)
        }
        if strings.TrimSpace(title) == "" {
            l.Redirect("/link/create", 302)
        }
        if strings.TrimSpace(url) == "" {
            l.Redirect("/link/create", 302)
        }
        if strings.TrimSpace(content) == "" {
            l.Redirect("/link/create", 302)
        }
        var id int64
        if id, err = models.LinkSave(&models.Link{
            Type:    typeId,
            Title:   title,
            Url:     url,
            Content: content,
        }); err != nil {
            l.Redirect("/link/create", 302)
        }
        l.Redirect("/link/"+strconv.FormatInt(id, 10), 302)
    }

    l.Data["isNewRecord"] = true
    l.Data["link"] = models.Link{}
    l.Data["types"] = models.LinkTypeList()
    l.Layout = "base.html"
    l.TplName = "link/create.html"
}

// View 友情連接詳情
func (l *LinkController) View() {
    id, err := strconv.Atoi(l.Ctx.Input.Param(":id"))
    if err != nil || id <= 0 {
        l.Redirect("/link", 302)
    }
    link, err := models.LinkInfo(int64(id))
    if err != nil {
        l.Redirect("/link ", 302)
    }
    l.Data["link"] = link
    l.Data["type"] = models.LinkTypeDesc(link.Type)
    l.Data["status"] = models.LinkStatusDesc(link.Status)
    l.Layout = "base.html"
    l.TplName = "link/view.html"
}

// Update 編輯友情連接
func (l *LinkController) Update() {
    id, err := strconv.Atoi(l.Ctx.Input.Param(":id"))
    if err != nil || id <= 0 {
        l.Redirect("/link", 302)
    }
    link, err := models.LinkInfo(int64(id))
    if err != nil {
        l.Redirect("/link ", 302)
    }
    
    if l.Ctx.Request.Method == "POST" {
        typeId, err := strconv.Atoi(strings.TrimSpace(l.Input().Get("type")))
        if err != nil {
            l.Redirect("/link/update/"+strconv.FormatInt(int64(id), 10), 302)
        }
        link.Type = typeId
        link.Title = strings.TrimSpace(l.Input().Get("title"))
        link.Url = strings.TrimSpace(l.Input().Get("url"))
        link.Content = strings.TrimSpace(l.Input().Get("content"))
        var newId int64
        if newId, err = models.LinkUpdate(&link); err != nil {
            l.Redirect("/link/update/"+strconv.FormatInt(newId, 10), 302)
        }
        l.Redirect("/link/"+strconv.FormatInt(newId, 10), 302)
    }
    
    l.Data["isNewRecord"] = false
    l.Data["link"] = link
    l.Data["types"] = models.LinkTypeList()
    l.Layout = "base.html"
    l.TplName = "link/update.html"
}

// Delete 刪除友情連接
func (l *LinkController) Delete() {
    id, err := strconv.Atoi(l.Ctx.Input.Param(":id"))
    if err != nil || id <= 0 {
        l.Redirect("/link", 302)
    }
    link, err := models.LinkInfo(int64(id))
    if err != nil {
        l.Redirect("/link", 302)
    }
    link.Status = 2
    if _, err := models.LinkUpdate(&link); err != nil {
        fmt.Println(err)
    }
    l.Redirect("/link", 302)
}

六、模板web

6.1 列表 index.htmlsql

<ol class="breadcrumb">
    <li><a href="#">首頁</a></li>
    <li><a href="#">內容管理</a></li>
    <li class="active">友情連接</li>
</ol>

<p>
    <a class="btn btn-primary" href="/link/create">添加</a>
</p>

<p class="text-info">共搜索到 <a class="text-success">{{.links | len}}</a> 條符合條件的記錄。</p>
<table class="table table-bordered table-striped">
    <thead>
        <tr>
            <th width="10%">ID</th>
            <th width="10%">類型</th>
            <th width="20%">名稱</th>
            <th width="35%">描述</th>
            <th width="10%">狀態</th>
            <th width="15%">操做</th>
        </tr>
    </thead>
    <tbody>
        {{range .links}}
        <tr>
            <td>{{.Id}}</td>
            <td>{{index $.types .Type}}</td>
            <td>{{.Title}}</td>
            <td>{{.Content}}</td>
            <td>{{index $.status .Status}}</td>
            <td>
                <a href="/link/{{.Id}}">查看</a>&nbsp;&nbsp;|
                <a href="/link/update/{{.Id}}">編輯</a>&nbsp;&nbsp;|
                <a href="javascript:if(confirm('肯定刪除嗎?')) location.href='/link/delete/{{.Id}}'">刪除</a>
            </td>
        </tr>
        {{end}}
    </tbody>
</table>

6.2 添加 create.html框架

<ol class="breadcrumb">
    <li><a href="#">首頁</a></li>
    <li><a href="#">內容管理</a></li>
    <li><a href="/link">友情連接</a></li>
    <li class="active">添加</li>
</ol>

{{template "link/from.html" .}}

6.3 表單from.html

<form method="post" action="/link/{{if .isNewRecord}}create{{else}}update/{{.link.Id}}{{end}}">
    <div class="form-group">
        <label for="type">類型</label>
        <select class="form-control" id="type" name="type">
            {{range $index, $type := .types}}
            <option id="type_{{$index}}"  value="{{$index}}">{{$type}}</option>
            {{end}}
        </select>
    </div>
    <div class="form-group">
        <label for="title">標題</label>
        <input type="text" class="form-control" id="title" name="title" value="{{.link.Title}}" placeholder="請輸入標題">
    </div>
    <div class="form-group">
        <label for="url">地址</label>
        <input type="text" class="form-control" id="url" name="url" value="{{.link.Url}}" placeholder="請輸入標題">
    </div>
    <div class="form-group">
        <label for="content">描述</label>
        <textarea class="form-control" id="content" name="content" cols="15" rows="4">{{.link.Content}}</textarea>
    </div>
    <div class="form-group">
        <button type="submit" class="btn btn-primary">{{if .isNewRecord}}添加{{else}}編輯{{end}}</button>
    </div>
</form>
<script type="text/javascript">
    $(function () {
        $("#type_{{.link.Type}}").attr("selected", "selected");
    });
</script>

6.4 編輯 update.html

<ol class="breadcrumb">
    <li><a href="#">首頁</a></li>
    <li><a href="#">內容管理</a></li>
    <li><a href="/link">友情連接</a></li>
    <li class="active">編輯</li>
</ol>

{{template "link/from.html" .}}

6.5 查看 view.html

<ol class="breadcrumb">
    <li><a href="#">首頁</a></li>
    <li><a href="#">內容管理</a></li>
    <li><a href="/link">友情連接</a></li>
    <li class="active">詳情</li>
</ol>

<p>
    <a class="btn btn-primary" href="/link/create">添加</a>
    <a class="btn btn-info" href="/link/update/{{.link.Id}}">修改</a>
    <a class="btn btn-danger" href="/link/delete/{{.link.Id}}">刪除</a>
</p>

<table class="table table-bordered table-responsive">
    <thead>
    <tr>
        <th width="10%">屬性</th>
        <th width="90%">名稱</th>
    </tr>
    </thead>
    <tbody>
    <tr>
        <td>Id</td>
        <td>{{.link.Id}}</td>
    </tr>
    <tr>
        <td>類型</td>
        <td>{{.type}}</td>
    </tr>
    <tr>
        <td>名字</td>
        <td>{{.link.Title}}</td>
    </tr>
    <tr>
        <td>說明</td>
        <td>{{.link.Content}}</td>
    </tr>
    <tr>
        <td>狀態</td>
        <td>{{.status}}</td>
    </tr>
    </tbody>
</table>

七、效果展現
列表
列表

添加
添加

修改
修改

詳情
詳情

八、說明

《Go語言程序設計》一書7.7節中提到:

"Go語言目前沒有一個權威的web框架,就像Ruby語言有Rails和python有Django。這並非說這樣的框架不存在,而是Go語言標準庫中的構建模塊就已經很是靈活以致於這些框架都是沒必要要的。此外,儘管在一個項目早期使用框架是很是方便的,可是它們帶來額外的複雜度會使長期的維護更加困難。"

和使用PHP成熟的WEB開發框架好比YII2比較起來,確實顯得無比笨拙。固然還能夠作更多的封裝,在這裏就不作這些處理,僅僅是體驗一下用go來編寫一個簡單的友情連接,你就會知道對於通常功能的實現,有一個完善的框架是多麼的便捷和美好。沒有嘗試過用bee的自動生成工具生成的代碼有多棒,但至少應該比上面的代碼看起來要聰明一些纔好。

相關文章
相關標籤/搜索
本站公眾號
   歡迎關注本站公眾號,獲取更多信息