0、为什么选择beego框架?
   
    
     Beego
    
    
     框架是
    
    
     
      go
     
    
    
     
      语言开发的
     
    
    
     
      web
     
    
    
     
      框架(有go语言基础,能很快上手)
     
    
    
     。
    
    
     go
    
    
     语言的
    
    
     web
    
    
     框架:
    
    
     beego,gin,echo
    
    
     等等,那为什么我们选择
    
    
     beego
    
    
     呢?
    
    
     第一,
    
    
     beego
    
    
     是中国人开发的,开发文档比较详细,
    
    
     beego
    
    
     官网网址
    
    
     :
    
    
     https://beego.me/
    
    
     。第二,现在公司里面用
    
    
     beego
    
    
     的也比较多,比如今日头条,百度云盘,腾讯,阿里等。
    
   
    
     Beego不足之处:
    
   
    
     Beego
    
    
     是
    
    
     MVC
    
    
     架构。大多数代码位于Controller中,显得Controller特别臃肿。采用多文件处理(将不同模块的Controller分开处理)。对fastDFS、Redis支持度不够,可以调用接口实现或导包实现(”github.com/weilaihui/fdfs_client”;”github.com/gomodule/redigo/redis”)。
    
   
    
     
      1、MVC
     
    
    
     
      设计模式
     
    
   
    
     什么是MVC?
    
   
    
     
      
       MVC
      
     
    
    
     全名是Model View Controller,是模型(model)-视图(view)-控制器(controller)的缩写,一种软件设计典范,用一种业务逻辑、数据、界面显示分离的方法组织代码,将业务逻辑聚集到一个部件里面,在改进和个性化定制界面及用户交互的同时,不需要重新编写业务逻辑。MVC被独特的发展起来用于映射传统的输入、处理和输出功能在一个逻辑的图形化用户界面的结构中。
    
   
    
     
      Model
     
    
    
     
      (模型)
     
    
   
    
     是应用程序中用于处理应用程序数据逻辑的部分。通常模型对象负责在数据库中存取数据。
    
   
    
     
      View
     
    
    
     
      (视图)
     
    
   
    
     是应用程序中处理数据显示的部分。通常视图是依据
    
    
     
      模型数据
     
    
    
     创建的。
    
   
    
     
      Controller
     
    
    
     
      (控制器)
     
    
   
    
     是应用程序中
    
    
     
      处理用户交互
     
    
    
     的部分。通常控制器负责从视图读取数据,控制用户输入,并向模型发送数据。
    
   
    
     MVC是一个框架模式,它强制性的使应用程序的输入、处理和
    
    
     
      
       输出
      
     
    
    
     分开。使用MVC应用程序被分成三个核心部件:模型、
    
    
     
      
       视图
      
     
    
    
     、控制器。它们各自处理自己的任务。
    
   
    
     设计模式:
    
   
    
     随着Web应用的商业逻辑包含逐渐复杂的公式分析计算、决策支持等,使客户机越来越不堪重负,因此将系统的商业分离出来。单独形成一部分,这样三层结构产生了。
    
   
    
     其中‘层’是逻辑上的划分。
    
   
    
     三层体系结构是将整个系统划分为三层结构:
    
   
    (1)
    
     表现层
    
    (Presentation layer):包含表示代码、用户交互GUI、数据验证。
   
    该层用于
    
     向客户端用户提供GUI交互
    
    ,它允许用户在显示系统中输入和编辑数据,同时系统提供数据验证功能。
   
(2)业务逻辑层(Business layer):包含业务规则处理代码,即程序中与业务相关专业算法、业务政策等等。
该层用于执行业务流程和制订数据的业务规则。业务逻辑层主要面向业务应用,为表示层提供业务服务。
(3)数据持久层(Persistence layer):包含数据处理代码和数据存储代码。数据持久层主要包括数据存取服务,负责与数据库管理系统(如数据库)之间的通信。
三个层次的每一层在处理程序上有各自明确的任务,在功能实现上有清晰的区分,各层与其余层分离,但各层之间存有通信接口。
采用三层软件设计架构后,软件系统在可扩展性和可复用性方面得到极大提高,在资源分配策略设计合理运用的同时,软件的性能指标也得到提升,系统的安全性和易管东北理性也得到改善。
三层体系结构对Web应用的软件架构产生很大影响,促进了基于组件的设计思想,产生了许多开发Web层次框架的实现技术。较之两级结构来说,三层结构修改和维护上更加方便。
目前开发B/S结构的Web应用系统广泛采用这种三层体系结构。
    2、
    
     Redis
    
   
是一种高性能的Key-Value数据库
    
     NoSQL
    
    
     介绍  mysql  sqlite  sqlserver Oracle
    
   
NoSQL:一类新出现的数据库(not only sql),它的特点:
    
     1.
    
    
     不支持
    
    
     SQL
    
    
     语法
    
   
    
     2.
    
    
     存储结构跟传统关系型数据库中的那种关系表完全不同,
    
    
     nosql
    
    
     中存储的数据都是
    
    
     Key-Value
    
    
     形式
    
   
    
     3.NoSQL
    
    
     的世界中没有一种通用的语言,每种
    
    
     nosql
    
    
     数据库都有自己的
    
    
     api
    
    
     和语法,以及擅长的业务场景
    
   
- 
     
 
 NoSQL
 
 
 
 
 中的产品种类相当多
 
 
 
 :
 
    
     Mongodb
    
   
    
     Redis
    
   
    
     Hbase hadoop
    
   
    
     Cassandra hadoop
    
   
    
     NoSQL
    
    
     和SQL数据库的比较:
    
   
- 
     
 适用场景不同:
 
 
 sql
 
 
 数据库适合用于关系特别复杂的数据查询场景,
 
 
 nosql
 
 
 反之
 
- 
     
 两者在不断地取长补短,呈现融合趋势
 
    
     Redis
    
    
     简介
    
   
- 
     
 Redis
 
 
 是一个开源的使用
 
 
 ANSI C
 
 
 语言编写、支持网络、可基于内存亦可持久化的日志型、
 
 
 Key-Value
 
 
 数据库,并提供多种语言的
 
 
 API
 
 
 。从
 
 
 2010
 
 
 年
 
 
 3
 
 
 月
 
 
 15
 
 
 日起,
 
 
 Redis
 
 
 的开发工作由
 
 
 VMware
 
 
 主持。从
 
 
 2013
 
 
 年
 
 
 5
 
 
 月开始,
 
 
 Redis
 
 
 的开发由
 
 
 Pivotal
 
 
 赞助。
 
- 
     
 Redis
 
 
 是
 
 
 NoSQL
 
 
 技术阵营中的一员,它通过多种键值数据类型来适应不同场景下的存储需求,借助一些高层级的接口使用其可以胜任,如缓存、队列系统的不同角色
 
    
     Redis
    
    
     特性
    
   
- 
     
 Redis
 
 
 与其他
 
 
 key – value
 
 
 缓存产品有以下三个特点:
 
- 
     
 Redis
 
 
 支持数据的持久化,可以将内存中的数据保存在磁盘中,重启的时候可以再次加载进行使用。
 
- 
     
 Redis
 
 
 不仅仅支持简单的
 
 
 key-value
 
 
 类型的数据,同时还提供
 
 
 string list
 
 
 ,
 
 
 set
 
 
 ,
 
 
 zset
 
 
 ,
 
 
 hash
 
 
 等数据结构的存储。
 
- 
     
 Redis
 
 
 支持数据的备份,即
 
 
 master-slave
 
 
 模式的数据备份。
 
    
     Redis
    
    
     优势
    
   
- 
     
 性能极高
 
 
 – Redis
 
 
 能读的速度是
 
 
 110000
 
 
 次
 
 
 /s,
 
 
 写的速度是
 
 
 81000
 
 
 次
 
 
 /s
 
 
 。
 
- 
     
 丰富的数据类型
 
 
 – Redis
 
 
 支持二进制案例的
 
 
 Strings, Lists, Hashes, Sets
 
 
 及
 
 
 Ordered Sets
 
 
 数据类型操作。
 
- 
     
 原子
 
 
 – Redis
 
 
 的所有操作都是原子性的,同时
 
 
 Redis
 
 
 还支持对几个操作全并后的原子性执行。
 
- 
     
 丰富的特性
 
 
 – Redis
 
 
 还支持
 
 
 publish/subscribe,
 
 
 通知
 
 
 , key
 
 
 过期等等特性。
 
 
 redis
 
 
 应用场景
 
- 
     
 用来做缓存
 
 
 (ehcache/memcached)——redis
 
 
 的所有数据是放在内存中的(内存数据库)
 
- 
     
 可以在某些特定应用场景下替代传统数据库
 
 
 ——
 
 
 比如社交类的应用
 
- 
     
 在一些大型系统中,巧妙地实现一些特定的功能:
 
 
 session
 
 
 共享、购物车
 
- 
     
 只要你有丰富的想象力,
 
 
 redis
 
 
 可以用在可以给你无限的惊喜
 
 
 …….
 
    
     
      
       中文官网
      
     
    
    
     
      
       
        R
       
      
     
    
    
     
      
       
        edis
       
      
     
    
    
     
      
       
        .cn
       
      
     
    
   
    3、利用fastDFS存储图片
   
    
     什么是FastDFS
    
   
FastDFS 是用 c 语言编写的一款开源的分布式文件系统。FastDFS 为互联网量身定制, 充分考虑了冗余备份、负载均衡、线性扩容等机制,并注重高可用、高性能等指标,使用 FastDFS 很容易搭建一套高性能的文件服务器集群提供文件上传、下载等服务。
    
     
      优点:
     
    
   
    
     FastDFS 架构包括 Tracker server 和 Storage server。
    
    客户端请求 Tracker server 进行文 件上传、下载,通过 Tracker server 调度最终由 Storage server 完成文件上传和下载。
   
Tracker server 作用是负载均衡和调度,通过 Tracker server 在文件上传时可以根据一些 方法找到 Storage server 提供文件上传服务。可以将 tracker 称为追踪服务器或调度服务 器。
Storage server 作用是文件存储,客户端上传的文件最终存储在 Storage 服务器上, Storageserver 没有实现自己的文件系统而是利用操作系统 的文件系统来管理文件。可以将 storage 称为存储服务器。
    
   
服务端两个角色:
Tracker:管理集群,tracker 也可以实现集群。每个 tracker 节点地位平等。收集 Storage 集群的状态。
Storage:实际保存文件
Storage 分为多个组,每个组之间保存的文件是不同的。每 个组内部可以有多个成员,组成员内部保存的内容是一样的,组成员的地位是一致的,没有 主从的概念。
    
     
      文件上传流程
     
    
   
    
   
客户端上传文件后存储服务器将文件 ID 返回给客户端,此文件 ID 用于以后访问该文 件的索引信息。文件索引信息包括:组名,虚拟磁盘路径,数据两级目录,文件名。
    
   
    
     组名
    
    : 文件上传后所在的 storage 组名称,在文件上传成功后有 storage 服务器返回, 需要客户端自行保存。
   
    
     虚拟磁盘路径
    
    : storage 配置的虚拟路径,与磁盘选项 store_path*对应。如果配置了 store_path0 则是 M00,如果配置了 store_path1 则是 M01,以此类推。
   
    
     数据两级目录
    
    :storage 服务器在每个虚拟磁盘路径下创建的两级目录,用于存储数据 文件。
   
    
     文件名
    
    :与文件上传时不同。是由存储服务器根据特定信息生成,文件名包含:源存储 服务器 IP 地址、文件创建时间戳、文件大小、随机数和文件拓展名等信息。
   
    
     
      文件下载流程
     
    
   
    
   
    
     
      简易FastDFS架构
     
    
   
    
   
    4、beego数据操作
   
    (1)
    
     ORM使用
    
   
    对象关系映射(英语:
    
     (Object Relational Mapping
    
    ,简称
    
     ORM
    
    ,或
    
     O/RM
    
    ,或
    
     O/R mapping
    
    ),是一种程序技术,用于实现面向对象编程语言里不同类型系统的数据之间的转换
    
    
    。从效果上说,它其实是创建了一个可在编程语言里使用的–“虚拟对象数据库”。
   
    官网:
    
     https://beego.me/docs/mvc/model/orm.md
    
   
表关系如下:
type Post struct {
    Id    int
    Title string
    User  *User  `orm:"rel(fk)"`
    Tags  []*Tag `orm:"rel(m2m)"`
}type Post struct {
    Id    int
    Title string
    User  *User  `orm:"rel(fk)"`
    Tags  []*Tag `orm:"rel(m2m)"`
}
type Tag struct {
    Id    int
    Name  string
    Posts []*Post `orm:"reverse(many)"`
}
    
     QueryTable(interface{}) QuerySeter
    
    :传入表名,或者 Model 对象,返回一个
    
     QuerySeter
    
   
    
     QueryM2M(interface{}, string) QueryM2Mer
    
    :多对多关系操作
   
o := orm.NewOrm()
var qs QuerySeter
qs = o.QueryTable("user")
// 如果表没有定义过,会立刻 panic创建一个 QueryM2Mer 对象
o := orm.NewOrm()
post := Post{Id: 1}
m2m := o.QueryM2M(&post, "Tags")
// 第一个参数的对象,主键必须有值
// 第二个参数为对象需要操作的 M2M 字段
// QueryM2Mer 的 api 将作用于 Id 为 1 的 Post
    (2)高级查询
   
    官网链接:
    
     https://beego.me/docs/mvc/model/query.md
    
   
    
     RelatedSel(…interface{}) QuerySeter
    
    :关系查询
   
    
     a、一对一关系
    
   
o := orm.NewOrm()
user := User{Id: 1}
err := o.Read(&user)
    
     b、一对多关系查询
    
   
 type Address struct { //地址表
    Id int
    User *User `orm:"rel(fk)"`     //用户ID
 
}
type User struct{ //用户表
	Id 			int
	Name 		string`orm:"size(20);unique"` 		//用户名
	Address		[]*Address `orm:"reverse(many)"`
	
}
 //获取所有地址(一对多查询)
var address []models.Address
o.QueryTable("Address").RelatedSel("User").Filter("User__Name",user.Name).All(&address)
type IndexTypeGoodsBanner struct {//首页分类商品展示表
	Id 				int
	GoodsType 		*GoodsType 	`orm:"rel(fk)"`			//商品类型
	GoodsSKU  		*GoodsSKU  	`orm:"rel(fk)"`			//商品sku
	DisplayType 	int   		`orm:"default(1)"`		//展示类型 0代表文字,1代表图片
	Index 			int   		`orm:"default(0)"`		//展示顺序
}
type GoodsType struct{//商品类型表
	Id int
	Name string			//种类名称
	GoodsSKU []*GoodsSKU `orm:"reverse(many)"`
	IndexTypeGoodsBanner  []*IndexTypeGoodsBanner  `orm:"reverse(many)"`
}
type GoodsSKU struct { //商品SKU表
	Id int
	Goods     *Goods 	 `orm:"rel(fk)"` //商品SPU
	GoodsType *GoodsType `orm:"rel(fk)"`  //商品所属种类
	IndexTypeGoodsBanner []*IndexTypeGoodsBanner  `orm:"reverse(many)"`
}
//一个表和另外两个表关联查询
var text []models.IndexTypeGoodsBanner  //显示商品文字
var image []models.IndexTypeGoodsBanner //显示商品图片
//获取商品文字数据
o.QueryTable("IndexTypeGoodsBanner").RelatedSel("GoodsType", "GoodsSKU").OrderBy("Index").Filter("GoodsType", value["type"]).Filter("DisplayType", 0).All(&text)
		//获取商品图片数据
o.QueryTable("IndexTypeGoodsBanner").RelatedSel("GoodsType", "GoodsSKU").OrderBy("Index").Filter("GoodsType", value["type"]).Filter("DisplayType", 1).All(&image)
    
     c、多对多关系查询(两层循环执行):
    
   
var goodType []models.GoodsType
	o := orm.NewOrm()
	o.QueryTable("GoodsType").All(&goodType)
goods := make([]map[string]interface{}, len(goodType))
	for index, value := range goodType {
		temp := make(map[string]interface{})
		temp["type"] = value
		goods[index] = temp
	}
    
     d、更新操作:
    
   
o.QueryTable("GoodsSKU").Filter("Id", good.Id).Filter("Stock", preCount).Update(orm.Params{"Stock": good.Stock, "Sales": good.Sales})
    
     ➢
     
      了解更多Go语言知识
     
     :
    
    
     https://study.163.com/course/introduction/1210620804.htm
    
   
 
