用beego开发服务端应用

  • 说明
  • Quick Start
  • 开发文档
  • 目录结构说明
  • 使用配置文件
  • beego默认参数
  • 路由设置
  • 需要特别注意的NSAfter()
  • 使用数据库
  • 数据库迁移(migration)
  • beego.Controller处理http请求
  • 参考
  • 说明

    beego是国内团队开源的golang开发框架,是一个关注度和使用量都比价高的项目。

    Quick Start

    beego快速入门中给出一个很简单的例子。

    安装

    首先需要安装beego和bee工具:

    $ go get -u github.com/astaxie/beego
    $ go get -u github.com/beego/bee

    为了能够直接使用bee命令,需要将$GOPATH/bin添加到$PATH变量中。

    创建应用

    创建一个名为hello的应用,可以选择web应用,或者api应用:

    $ bee new hello     //创建一个web应用
    $ bee api hello //创建一个api应用

    执行结束后,会在当前目录下创建名为hello的目录:

    .
    |____hello
    | |____conf
    | | |____app.conf
    | |____controllers
    | | |____default.go
    | |____main.go
    | |____models
    | |____routers
    | | |____router.go
    | |____static
    | | |____css
    | | |____img
    | | |____js
    | | | |____reload.min.js
    | |____tests
    | | |____default_test.go
    | |____views
    | | |____index.tpl

    编译运行

    进入hello目录中,执行bee run,就会完成编译、运行:

    $ cd hello/
    $ bee run
    ______
    | ___ \
    | |_/ / ___ ___
    | ___ \ / _ \ / _ \
    | |_/ /| __/| __/
    \____/ \___| \___| v1.9.1
    2017/10/23 14:33:05 INFO ▶ 0001 Using 'hello' as 'appname'
    2017/10/23 14:33:05 INFO ▶ 0002 Initializing watcher...
    2017/10/23 14:33:06 SUCCESS ▶ 0003 Built Successfully!
    2017/10/23 14:33:06 INFO ▶ 0004 Restarting 'hello'...
    2017/10/23 14:33:06 SUCCESS ▶ 0005 './hello' is running...
    2017/10/23 14:33:06 [I] [asm_amd64.s:2197] http server Running on http://:8080

    打包发布

    项目打包发布:

    $ bee pack

    代码生成

    生成models:

    bee generate model user -fields="name:string,age:int"

    生成controller:

    bee generate controller user

    生成view:

    bee generate view user

    生成文档:

    bee generate docs

    开发文档

    beego开发文档中对beego做了很详细的说明。

    目录结构说明

    .
    |____hello
    | |____conf <- 配置文件
    | | |____app.conf
    | |____controllers <- 控制器,即http请求的handler
    | | |____default.go
    | |____main.go <- main函数
    | |____models
    | |____routers <- 路由,将url关联到controllers
    | | |____router.go
    | |____static <- 静态文件
    | | |____css
    | | |____img
    | | |____js
    | | | |____reload.min.js
    | |____tests <- 测试
    | | |____default_test.go
    | |____views <- 页面模版,controller中可以直接渲染对应的tpl文件
    | | |____index.tpl

    使用配置文件

    beego参数配置中讲解如何使用配置文件、如何配置参数。

    beego默认解析应用目录下的conf/app.conf文件,配置项可以通过beego.AppConfig.*读取:

    beego.AppConfig.String("mysqluser")

    beego.Appconfig包含多个方法:

    Set(key, val string) error
    String(key string) string
    Strings(key string) []string
    Int(key string) (int, error)
    Int64(key string) (int64, error)
    Bool(key string) (bool, error)
    Float(key string) (float64, error)
    DefaultString(key string, defaultVal string) string
    DefaultStrings(key string, defaultVal []string)
    DefaultInt(key string, defaultVal int) int
    DefaultInt64(key string, defaultVal int64) int64
    DefaultBool(key string, defaultVal bool) bool
    DefaultFloat(key string, defaultVal float64) float64
    DIY(key string) (interface{}, error)
    GetSection(section string) (map[string]string, error)
    SaveConfigFile(filename string) error

    配置文件中可以配置section,通过runmode指定要使用的section,例如:

    appname = beepkg
    httpaddr = "127.0.0.1"
    httpport = 9090
    runmode ="dev"
    autorender = false
    recoverpanic = false
    viewspath = "myview" [dev]
    httpport = 8080
    [prod]
    httpport = 8088
    [test]
    httpport = 8888

    对于section的配置项,通过下面的方式读取,模式::配置参数名:

    beego.AppConfig.String(“dev::mysqluser”)

    配置文件中可以使用环境变量:

    runmode  = "${ProRunMode||dev}"
    httpport = "${ProPort||9090}"

    加载特定的配置文件,可以加载多个配置文件,key不能冲突:

    beego.LoadAppConfig("ini", "conf/app2.conf")
    beego.LoadAppConfig("ini", "conf/app3.conf")

    beego默认参数

    beego的默认参数全部保存在beego.BConfig中。,可以访问、修改所有的配置信息。

    在配置文件中设置的同名的key(不区分大小写)的值会覆盖默认值,例如:

    appname = hello
    httpport = 8080
    runmode = dev [dev]
    AutoRender=false #会覆盖beego.BConfig.WebConfig.AutoRender的默认值 [test] [prod]

    App配置:

    beego.BConfig.AppName = "beego"
    beego.BConfig.RunMode = "dev"
    beego.BConfig.RouterCaseSensitive = true
    beego.BConfig.ServerName = "beego"
    beego.BConfig.RecoverPanic = true
    beego.BConfig.EnableGzip = false
    beego.BConfig.MaxMemory = 1 << 26
    beego.BConfig.EnableErrorsShow = true
    beego.BConfig.EnableErrorsRender = true

    Web配置:

    beego.BConfig.WebConfig.AutoRender = true
    beego.BConfig.WebConfig.EnableDocs = true
    beego.BConfig.WebConfig.FlashName = "BEEGO_FLASH"
    beego.BConfig.WebConfig.FlashSeperator = "BEEGOFLASH"
    beego.BConfig.WebConfig.DirectoryIndex = false
    beego.BConfig.StaticDir = static
    beego.BConfig.WebConfig.StaticExtensionsToGzip = []string{".css", ".js"}
    beego.BConfig.WebConfig.TemplateLeft="
    beego.BConfig.WebConfig.TemplateRight="
    beego.BConfig.WebConfig.ViewsPath="views"
    beego.BConfig.WebConfig.EnableXSRF = false
    beego.BConfig.WebConfig.XSRFKEY = "beegoxsrf"
    beego.BConfig.WebConfig.XSRFExpire = 0

    监听配置:

    beego.BConfig.Listen.Graceful=false
    beego.BConfig.Listen.ServerTimeOut=0
    beego.BConfig.Listen.ListenTCP4 = "tcp4"
    beego.BConfig.Listen.EnableHTTP = true
    beego.BConfig.Listen.HTTPAddr = ""
    beego.BConfig.Listen.HTTPPort = 8080
    beego.BConfig.Listen.EnableHTTPS = false
    beego.BConfig.Listen.HTTPSAddr = ""
    beego.BConfig.Listen.HTTPSPort = 10443
    beego.BConfig.Listen.HTTPSCertFile = "conf/ssl.crt"
    beego.BConfig.Listen.HTTPSKeyFile = "conf/ssl.key"
    beego.BConfig.Listen.EnableAdmin = false
    beego.BConfig.Listen.AdminAddr = "localhost"
    beego.BConfig.Listen.AdminPort = 8088
    beego.BConfig.Listen.EnableFcgi = false
    beego.BConfig.Listen.EnableStdIo = false

    Session配置:

    beego.BConfig.WebConfig.Session.SessionOn = false
    beego.BConfig.WebConfig.Session.SessionProvider = ""
    beego.BConfig.WebConfig.Session.SessionName = "beegosessionID"
    beego.BConfig.WebConfig.Session.SessionGCMaxLifetime = 3600
    beego.BConfig.WebConfig.SessionProviderConfig
    beego.BConfig.WebConfig.Session.SessionCookieLifeTime = 3600
    beego.BConfig.WebConfig.Session.SessionAutoSetCookie = true
    beego.BConfig.WebConfig.Session.SessionDomain = ""

    Log配置:

    beego.BConfig.Log.AccessLogs = false
    beego.BConfig.Log.FileLineNum = true
    beego.BConfig.Log.Outputs = map[string]string{"console": ""}

    路由设置

    beego支持三种路由: 基础路由、正则路由、自动路由。

    路由的表述方式

    支持用正则的方式书写路由,参考了sinatra的路由实现。

     路由规则                           可以匹配
    /api/?:id ----> /api/, /api/123 id=123
    /api/:id ----> /api/123 id=123
    /api/:id([0-9]+) ----> /api/123 id=123
    /user/:username([\w]+) ----> /user/abc username=abc
    /download/*.* ----> /download/file/api.xml path=file/api ext=xml
    /download/ceshi/* ----> /download/cechis/file/api.json splat=file/api.json
    /:id:int ----> 等同于/:id([0-9]+)
    /:hi:string ----> 等同于/:hi([\w]+)
    /cms_:id([0-9]+).html ----> /cms_123.html id=123

    可以通过*context.Context的Input.Param()方法读取路由中的变量:

    ctx.Input.Param(":id")

    在Controller中,通过下面的方式获取路由中的变量,this是controller:

    this.Ctx.Input.Param(":id")
    this.Ctx.Input.Param(":username")
    this.Ctx.Input.Param(":splat")
    this.Ctx.Input.Param(":path")
    this.Ctx.Input.Param(":ext")

    直接设置路由

    routers/router.go中设置,可以使用下面的基础函数直接设置路由:

    beego.Get(router, beego.FilterFunc)
    beego.Post(router, beego.FilterFunc)
    beego.Put(router, beego.FilterFunc)
    beego.Head(router, beego.FilterFunc)
    beego.Options(router, beego.FilterFunc)
    beego.Delete(router, beego.FilterFunc)
    beego.Any(router, beego.FilterFunc)

    例如:

    //响应post /alice
    beego.Post("/alice",func(ctx *context.Context){
    ctx.Output.Body([]byte("bob"))
    }) //响应到/foo的所有http请求
    beego.Any("/foo",func(ctx *context.Context){
    ctx.Output.Body([]byte("bar"))
    })

    以注册handler的方式设置路由

    也可以使用beego.Handler(router, http.Handler)设置路由的handler:

    beego.Handler("/rpc", s)

    beego.Handler默认是完全匹配,不是前缀匹配。可以自定义http请求方法和处理函数的映射关系:

    beego.Router("/api/list",&RestController{},"*:ListFood")
    beego.Router("/api/create",&RestController{},"post:CreateFood")
    beego.Router("/api/update",&RestController{},"put:UpdateFood")
    beego.Router("/api/delete",&RestController{},"delete:DeleteFood")

    自定义映射关系的格式为”请求方法:函数名”,请求方法有下面几种:

    *: 包含以下所有的函数,优先级低于下面的方法
    get: GET 请求
    post: POST 请求
    put: PUT 请求
    delete: DELETE 请求
    patch: PATCH 请求
    options: OPTIONS 请求
    head: HEAD 请求

    自动注册路由

    另外还有beego.AutoRouter($controllers.ObjectController{}),会自动通过反射为Object中的方法生成路由。

    通过注解注册路由

    在controller的方法上面加上router注释,router.go中通过beego.Include(&Controller)引入controller的时候会自动注册路由。

    例如:

    // CMS API
    type CMSController struct {
    beego.Controller
    } func (c *CMSController) URLMapping() {
    c.Mapping("StaticBlock", c.StaticBlock)
    c.Mapping("AllBlock", c.AllBlock)
    } // @router /staticblock/:key [get]
    func (this *CMSController) StaticBlock() { } // @router /all/:key [get]
    func (this *CMSController) AllBlock() { }

    然后在router.go中:

    beego.Include(&CMSController{})

    beego会自动进行源码分析,如果是dev模式,会在routers/commentXXX.go文件。

    使用namespace管理路由

    namespace支持前套,并且可以对包含其中对路由进行前置过滤、条件判断。

    namespace接口如下:

    NewNamespace(prefix string, funcs …interface{})     初始化 namespace 对象
    NSCond(cond namespaceCond) 支持满足条件才namespace
    NSBefore(filiterList …FilterFunc)
    NSAfter(filiterList …FilterFunc)
    NSInclude(cList …ControllerInterface)
    NSRouter(rootpath string, c ControllerInterface, mappingMethods …string)
    NSGet(rootpath string, f FilterFunc)
    NSPost(rootpath string, f FilterFunc)
    NSDelete(rootpath string, f FilterFunc)
    NSPut(rootpath string, f FilterFunc)
    NSHead(rootpath string, f FilterFunc)
    NSOptions(rootpath string, f FilterFunc)
    NSPatch(rootpath string, f FilterFunc)
    NSAny(rootpath string, f FilterFunc)
    NSHandler(rootpath string, h http.Handler)
    NSAutoRouter(c ControllerInterface)
    NSAutoPrefix(prefix string, c ControllerInterface)

    示例:

    //初始化 namespace
    ns :=
    beego.NewNamespace("/v1",
    beego.NSCond(func(ctx *context.Context) bool {
    if ctx.Input.Domain() == "api.beego.me" {
    return true
    }
    return false
    }),
    beego.NSBefore(auth),
    beego.NSGet("/notallowed", func(ctx *context.Context) {
    ctx.Output.Body([]byte("notAllowed"))
    }),
    beego.NSRouter("/version", &AdminController{}, "get:ShowAPIVersion"),
    beego.NSRouter("/changepassword", &UserController{}),
    beego.NSNamespace("/shop",
    beego.NSBefore(sentry),
    beego.NSGet("/:id", func(ctx *context.Context) {
    ctx.Output.Body([]byte("notAllowed"))
    }),
    ),
    beego.NSNamespace("/cms",
    beego.NSInclude(
    &controllers.MainController{},
    &controllers.CMSController{},
    &controllers.BlockController{},
    ),
    ),
    )
    //注册 namespace
    beego.AddNamespace(ns)

    注册了以下的路由:

    GET /v1/notallowed
    GET /v1/version
    GET /v1/changepassword
    POST /v1/changepassword
    GET /v1/shop/123
    GET /v1/cms/ 对应 MainController、CMSController、BlockController 中得注解路由

    需要特别注意的NSAfter()

    NSAfter()注册的filter函数会在请求处理结束的时候被调用,但是要注意在bee 1.9.0中:

    beego.NSAfter does not work after controller.ServeJSON

    相关的issue:

    注解路由无法进入NSBefore controller.ServeJSON should work will with beego.NSAfter

    可以用github: study-beego里的的代码试验一下。

    使用数据库

    beego仿照Digango ORM和SQLAlchemy实现beego ORM,当前支持三个驱动:

    MySQL:github.com/go-sql-driver/mysql
    PostgreSQL:github.com/lib/pq
    Sqlite3:github.com/mattn/go-sqlite3

    beego生成的model文件中,会自动将model注册到orm,例如:

    bee generate model user -fields="name:string,age:int"

    生成的代码models/user.go中会在init()中注册:

    func init() {
    orm.RegisterModel(new(User))
    }

    因此只需要手工书写orm初始化的代码,譬如在main.go中:

    func init() {
    orm.RegisterDataBase("default", "mysql", "root:@tcp(127.0.0.1:3306)/mysql?charset=utf8", 30)
    }

    数据库迁移(migration)

    数据库迁移功能可以数据库进行升级、回滚操作。

    生成迁移文件,user是表名,fields是表结构:

    bee generate migration user -driver=mysql -fields="name:string,age:int"

    运行后,生成了文件:

    |____database
    | |____migrations
    | | |____20171024_154037_user.go

    在数据库中创建了名为study-beego的数据库后,执行下面的命令:

    bee migrate -driver=mysql -conn="root:@tcp(127.0.0.1:3306)/study-beego"

    study-beego中的表将会被创建或者更新,并在名为migrations的表中记录更新。

    migrate的子命令refreshrollback执行失败,原因不明。

    beego.Controller处理http请求

    注意,在1.9.0中,需要在配置中设置copyrequestbody=true以后,c.Ctx.Input.RequestBody中才有数据。

    func (c *UserController) Post() {
    var v models.User
    json.Unmarshal(c.Ctx.Input.RequestBody, &v)
    fmt.Println(v)
    if _, err := models.AddUser(&v); err == nil {
    c.Ctx.Output.SetStatus(201)
    c.Data["json"] = v
    } else {
    c.Data["json"] = err.Error()
    }
    c.ServeJSON()
    }

用beego开发服务端应用的更多相关文章

  1. WebService-03-使用CXF开发服务端和客户端

    写在前面的话 前面两节说了使用Java提供的包开发服务端和客户端,现在使用CXF来开发,CXF提供了两个类发而服务,一个是ServerFactoryBean,另一个是JaxWsServerFactor ...

  2. nodejs 开发服务端 child_process 调试方法(1)

    由于最近正在做一个服务端项目,采用了nodejs引擎开发,主要是master-worker工作机制;主进程可以直接调试,但是子进程调试好像有点麻烦,我没有找到好的方法; worker这里,我分拆成了几 ...

  3. 【笔记6-支付及订单模块】从0开始 独立完成企业级Java电商网站开发(服务端)

    支付模块 实际开发工作中经常会遇见如下场景,一个支付模块,一个订单模块,有一定依赖,一个同事负责支付模块,另一个同事负责订单模块,但是开发支付模块的时候要依赖订单模块的相关类 ,方法,或者工具类,这些 ...

  4. nodejs 开发服务端 部署到 iis 服务器环境 -- iisnode 安装问题解决记录

    开发环境 nodejs: v10.15.3 windows: 10 iis: 10 需求: 用Nodejs开发了服务端,要部署到IIS 需要在IIS服务器上安装iisnode,结果遇到问题:安装不上 ...

  5. Delphi 三层框架开发 服务端开发

    采用Delphi7+SQL2008 一.创建数据库和表 CREATE TABLE [dbo].[tb_Department]( [FKey] [uniqueidentifier] NOT NULL, ...

  6. maven版cxf集合spring开发服务端(二)

    一.新建一个maven项目 二.pom.xml引入依赖 <dependency> <groupId>org.apache.cxf</groupId> <art ...

  7. maven版cxf集合jetty开发服务端(一)

    一.首先新建一个maven项目 二.pom.xml引入依赖 <dependency> <groupId>org.apache.cxf</groupId> <a ...

  8. 【笔记7-部署发布】从0开始 独立完成企业级Java电商网站开发(服务端)

    阿里云服务 购买 连接 购买域名 域名备案 域名解析 源配置步骤 资源地址 http://learning.happymmall.com/ 配置阿里云的yum源 1.备份 mv /etc/yum.re ...

  9. 【笔记4-商品模块】从0开始 独立完成企业级Java电商网站开发(服务端)

    分类管理模块 数据表结构设计 分类表 CREATE TABLE.mmall_ category' ( 'id' int(11) NOT NULL AUTO_ INCREMENT COMMENT ' 类 ...

随机推荐

  1. How to configure ODBC DSN in Client to access remote DB2 for Windows

      How to configure ODBC DSN in Client to access remote DB2 for Windows MA Gen feng (Guangdong Unito ...

  2. 解析Json字符串的三种方法

    在很多时候,我们的需要将类似 json 格式的字符串数据转为json, 下面将介绍日常中使用的三种解析json字符串的方法 1.首先,我们先看一下什么是 json 格式字符串数据,很简单,就是 jso ...

  3. 排序算法入门之希尔排序(java实现)

    希尔排序是对插入排序的改进.插入排序是前面元素已经有序了,移动元素是一个一个一次往后移动,当插入的元素比前面排好序的所有元素都小时,则需要将前面所有元素都往后移动.希尔排序有了自己的增量,可以理解为插 ...

  4. WebLogic域配置策略

    WebLogic域配置策略--手动和模板选项,第一部分 域含有BEA WebLogic Server实例的配置信息.它包含有关服务器.集群和机器的配置信息.域还含有关于资源,例如Java数据库连接(J ...

  5. 三大框架:Struts+Hibernate+Spring

    三大框架:Struts+Hibernate+Spring Java三大框架主要用来做WEN应用. Struts主要负责表示层的显示 Spring利用它的IOC和AOP来处理控制业务(负责对数据库的操作 ...

  6. xmlrpc

    xmlrpc编辑 官方URL:http://ws.apache.org/xmlrpc/xmlrpc2/index.html 本词条缺少名片图,补充相关内容使词条更完整,还能快速升级,赶紧来编辑吧! x ...

  7. AS3中的mouseEnabled与mouseChild

    InteractiveObject类的一个属性,InteractiveObject类是用户可以使用鼠标和键盘与之交互的所有显示对象的抽象基类.我们不能直接实例化InteractiveObject类.m ...

  8. Tracert(跟踪路由)是路由跟踪实用程序,用于确定 IP 数据包访问目标所采取的路径。

    Tracert(跟踪路由)是路由跟踪实用程序,用于确定 IP 数据包访问目标所采取的路径.   Tracert 命令用 IP 生存时间 (TTL) 字段和 ICMP 错误消息来确定从一个主机到网络上其 ...

  9. Django之AppConfig源码学习

    class AppConfig(object) 这个基类描述了一个Django应用以及它的配置信息. 属性: name:django应用的完整python路径,eg.'django.contrib.a ...

  10. cannot import name '_imaging' 与No module named PIL解决方法

    今天学习廖雪峰的python 第三方模块pillow一章. 直接使用from PIL import Image 会报"No module named PIL",显然这是没有安装pi ...