use logrus to project default log tools

This commit is contained in:
hoteas 2021-05-25 05:08:17 +08:00
parent 9bc930750d
commit df07afb744
15 changed files with 491 additions and 457 deletions

32
LICENSE
View File

@ -10,7 +10,7 @@ AND DISTRIBUTION
"License" shall mean the terms and conditions for use, reproduction, and distribution "License" shall mean the terms and conditions for use, reproduction, and distribution
as defined by Sections 1 through 9 of this document. as defined by Sections 1 through 9 of that document.
@ -21,7 +21,7 @@ owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all other entities "Legal Entity" shall mean the union of the acting entity and all other entities
that control, are controlled by, or are under common control with that entity. that control, are controlled by, or are under common control with that entity.
For the purposes of this definition, "control" means (i) the power, direct For the purposes of that definition, "control" means (i) the power, direct
or indirect, to cause the direction or management of such entity, whether or indirect, to cause the direction or management of such entity, whether
by contract or otherwise, or (ii) ownership of fifty percent (50%) or more by contract or otherwise, or (ii) ownership of fifty percent (50%) or more
of the outstanding shares, or (iii) beneficial ownership of such entity. of the outstanding shares, or (iii) beneficial ownership of such entity.
@ -29,7 +29,7 @@ of the outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity exercising permissions "You" (or "Your") shall mean an individual or Legal Entity exercising permissions
granted by this License. granted by that License.
@ -55,7 +55,7 @@ below).
"Derivative Works" shall mean any work, whether in Source or Object form, "Derivative Works" shall mean any work, whether in Source or Object form,
that is based on (or derived from) the Work and for which the editorial revisions, that is based on (or derived from) the Work and for which the editorial revisions,
annotations, elaborations, or other modifications represent, as a whole, an annotations, elaborations, or other modifications represent, as a whole, an
original work of authorship. For the purposes of this License, Derivative original work of authorship. For the purposes of that License, Derivative
Works shall not include works that remain separable from, or merely link (or Works shall not include works that remain separable from, or merely link (or
bind by name) to the interfaces of, the Work and Derivative Works thereof. bind by name) to the interfaces of, the Work and Derivative Works thereof.
@ -65,7 +65,7 @@ bind by name) to the interfaces of, the Work and Derivative Works thereof.
of the Work and any modifications or additions to that Work or Derivative of the Work and any modifications or additions to that Work or Derivative
Works thereof, that is intentionally submitted to Licensor for inclusion in Works thereof, that is intentionally submitted to Licensor for inclusion in
the Work by the copyright owner or by an individual or Legal Entity authorized the Work by the copyright owner or by an individual or Legal Entity authorized
to submit on behalf of the copyright owner. For the purposes of this definition, to submit on behalf of the copyright owner. For the purposes of that definition,
"submitted" means any form of electronic, verbal, or written communication "submitted" means any form of electronic, verbal, or written communication
sent to the Licensor or its representatives, including but not limited to sent to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems, and communication on electronic mailing lists, source code control systems, and
@ -80,15 +80,15 @@ owner as "Not a Contribution."
of whom a Contribution has been received by Licensor and subsequently incorporated of whom a Contribution has been received by Licensor and subsequently incorporated
within the Work. within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of this 2. Grant of Copyright License. Subject to the terms and conditions of that
License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive,
no-charge, royalty-free, irrevocable copyright license to reproduce, prepare no-charge, royalty-free, irrevocable copyright license to reproduce, prepare
Derivative Works of, publicly display, publicly perform, sublicense, and distribute Derivative Works of, publicly display, publicly perform, sublicense, and distribute
the Work and such Derivative Works in Source or Object form. the Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of this License, 3. Grant of Patent License. Subject to the terms and conditions of that License,
each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive,
no-charge, royalty-free, irrevocable (except as stated in this section) patent no-charge, royalty-free, irrevocable (except as stated in that section) patent
license to make, have made, use, offer to sell, sell, import, and otherwise license to make, have made, use, offer to sell, sell, import, and otherwise
transfer the Work, where such license applies only to those patent claims transfer the Work, where such license applies only to those patent claims
licensable by such Contributor that are necessarily infringed by their Contribution(s) licensable by such Contributor that are necessarily infringed by their Contribution(s)
@ -97,7 +97,7 @@ Contribution(s) was submitted. If You institute patent litigation against
any entity (including a cross-claim or counterclaim in a lawsuit) alleging any entity (including a cross-claim or counterclaim in a lawsuit) alleging
that the Work or a Contribution incorporated within the Work constitutes direct that the Work or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses granted to You or contributory patent infringement, then any patent licenses granted to You
under this License for that Work shall terminate as of the date such litigation under that License for that Work shall terminate as of the date such litigation
is filed. is filed.
4. Redistribution. You may reproduce and distribute copies of the Work or 4. Redistribution. You may reproduce and distribute copies of the Work or
@ -105,7 +105,7 @@ Derivative Works thereof in any medium, with or without modifications, and
in Source or Object form, provided that You meet the following conditions: in Source or Object form, provided that You meet the following conditions:
(a) You must give any other recipients of the Work or Derivative Works a copy (a) You must give any other recipients of the Work or Derivative Works a copy
of this License; and of that License; and
(b) You must cause any modified files to carry prominent notices stating that (b) You must cause any modified files to carry prominent notices stating that
You changed the files; and You changed the files; and
@ -133,11 +133,11 @@ You may add Your own copyright statement to Your modifications and may provide
additional or different license terms and conditions for use, reproduction, additional or different license terms and conditions for use, reproduction,
or distribution of Your modifications, or for any such Derivative Works as or distribution of Your modifications, or for any such Derivative Works as
a whole, provided Your use, reproduction, and distribution of the Work otherwise a whole, provided Your use, reproduction, and distribution of the Work otherwise
complies with the conditions stated in this License. complies with the conditions stated in that License.
5. Submission of Contributions. Unless You explicitly state otherwise, any 5. Submission of Contributions. Unless You explicitly state otherwise, any
Contribution intentionally submitted for inclusion in the Work by You to the Contribution intentionally submitted for inclusion in the Work by You to the
Licensor shall be under the terms and conditions of this License, without Licensor shall be under the terms and conditions of that License, without
any additional terms or conditions. Notwithstanding the above, nothing herein any additional terms or conditions. Notwithstanding the above, nothing herein
shall supersede or modify the terms of any separate license agreement you shall supersede or modify the terms of any separate license agreement you
may have executed with Licensor regarding such Contributions. may have executed with Licensor regarding such Contributions.
@ -154,14 +154,14 @@ KIND, either express or implied, including, without limitation, any warranties
or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR
A PARTICULAR PURPOSE. You are solely responsible for determining the appropriateness A PARTICULAR PURPOSE. You are solely responsible for determining the appropriateness
of using or redistributing the Work and assume any risks associated with Your of using or redistributing the Work and assume any risks associated with Your
exercise of permissions under this License. exercise of permissions under that License.
8. Limitation of Liability. In no event and under no legal theory, whether 8. Limitation of Liability. In no event and under no legal theory, whether
in tort (including negligence), contract, or otherwise, unless required by in tort (including negligence), contract, or otherwise, unless required by
applicable law (such as deliberate and grossly negligent acts) or agreed to applicable law (such as deliberate and grossly negligent acts) or agreed to
in writing, shall any Contributor be liable to You for damages, including in writing, shall any Contributor be liable to You for damages, including
any direct, indirect, special, incidental, or consequential damages of any any direct, indirect, special, incidental, or consequential damages of any
character arising as a result of this License or out of the use or inability character arising as a result of that License or out of the use or inability
to use the Work (including but not limited to damages for loss of goodwill, to use the Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all other commercial work stoppage, computer failure or malfunction, or any and all other commercial
damages or losses), even if such Contributor has been advised of the possibility damages or losses), even if such Contributor has been advised of the possibility
@ -170,7 +170,7 @@ of such damages.
9. Accepting Warranty or Additional Liability. While redistributing the Work 9. Accepting Warranty or Additional Liability. While redistributing the Work
or Derivative Works thereof, You may choose to offer, and charge a fee for, or Derivative Works thereof, You may choose to offer, and charge a fee for,
acceptance of support, warranty, indemnity, or other liability obligations acceptance of support, warranty, indemnity, or other liability obligations
and/or rights consistent with this License. However, in accepting such obligations, and/or rights consistent with that License. However, in accepting such obligations,
You may act only on Your own behalf and on Your sole responsibility, not on You may act only on Your own behalf and on Your sole responsibility, not on
behalf of any other Contributor, and only if You agree to indemnify, defend, behalf of any other Contributor, and only if You agree to indemnify, defend,
and hold each Contributor harmless for any liability incurred by, or claims and hold each Contributor harmless for any liability incurred by, or claims
@ -191,7 +191,7 @@ Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License"); Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License. you may not use that file except in compliance with the License.
You may obtain a copy of the License at You may obtain a copy of the License at

View File

@ -4,6 +4,7 @@ import (
. "./cache" . "./cache"
. "./common" . "./common"
. "./db" . "./db"
. "./log"
"bytes" "bytes"
"database/sql" "database/sql"
"encoding/json" "encoding/json"
@ -21,7 +22,8 @@ type Application struct {
MethodRouter MethodRouter
Router Router
ContextBase ContextBase
Log logrus.Logger Log *logrus.Logger
WebConnectLog *logrus.Logger
Port string //端口号 Port string //端口号
TLSPort string //ssl访问端口号 TLSPort string //ssl访问端口号
connectListener []func(this *Context) bool //所有的访问监听,true按原计划继续使用false表示有监听器处理 connectListener []func(this *Context) bool //所有的访问监听,true按原计划继续使用false表示有监听器处理
@ -29,44 +31,44 @@ type Application struct {
configPath string configPath string
Config Map Config Map
Db HoTimeDB Db HoTimeDB
Server *http.Server *http.Server
CacheIns CacheIns
sessionLong CacheIns sessionLong CacheIns
sessionShort CacheIns sessionShort CacheIns
http.Handler http.Handler
} }
func (this *Application) ServeHTTP(w http.ResponseWriter, req *http.Request) { func (that *Application) ServeHTTP(w http.ResponseWriter, req *http.Request) {
this.handler(w, req) that.handler(w, req)
} }
//启动实例 // Run 启动实例
func (this *Application) Run(router Router) { func (that *Application) Run(router Router) {
//如果没有设置配置自动生成配置 //如果没有设置配置自动生成配置
if this.configPath == "" || len(this.Config) == 0 { if that.configPath == "" || len(that.Config) == 0 {
this.SetConfig() that.SetConfig()
} }
//防止手动设置缓存误伤 //防止手动设置缓存误伤
if this.CacheIns == nil { if that.CacheIns == nil {
this.SetCache(CacheIns(&CacheMemory{})) that.SetCache(CacheIns(&CacheMemory{}))
} }
//防止手动设置session误伤 //防止手动设置session误伤
//if this.sessionShort == nil && this.sessionLong == nil { //if that.sessionShort == nil && that.sessionLong == nil {
// if this.connectDbFunc == nil { // if that.connectDbFunc == nil {
// this.SetSession(CacheIns(&CacheMemory{}), nil) // that.SetSession(CacheIns(&CacheMemory{}), nil)
// } else { // } else {
// this.SetSession(CacheIns(&CacheMemory{}), CacheIns(&CacheDb{Db: &this.Db, Time: this.Config.GetInt64("cacheLongTime")})) // that.SetSession(CacheIns(&CacheMemory{}), CacheIns(&CacheDb{Db: &that.Db, Time: that.Config.GetInt64("cacheLongTime")}))
// } // }
// //
//} //}
this.Router = router that.Router = router
//重新设置MethodRouter//直达路由 //重新设置MethodRouter//直达路由
this.MethodRouter = MethodRouter{} that.MethodRouter = MethodRouter{}
modeRouterStrict := true modeRouterStrict := true
if this.Config.Get("modeRouterStrict").(bool) == false { if that.Config.GetBool("modeRouterStrict") == false {
modeRouterStrict = false modeRouterStrict = false
} }
if router != nil { if router != nil {
@ -84,7 +86,7 @@ func (this *Application) Run(router Router) {
if !modeRouterStrict { if !modeRouterStrict {
mk = strings.ToLower(mk) mk = strings.ToLower(mk)
} }
this.MethodRouter["/"+pk+"/"+ck+"/"+mk] = mv that.MethodRouter["/"+pk+"/"+ck+"/"+mk] = mv
} }
} }
} }
@ -92,137 +94,139 @@ func (this *Application) Run(router Router) {
} }
} }
//this.Port = port //that.Port = port
this.Port = this.Config.GetString("port") that.Port = that.Config.GetString("port")
this.TLSPort = this.Config.GetString("tlsPort") that.TLSPort = that.Config.GetString("tlsPort")
if this.connectDbFunc != nil && (this.Db.DB == nil || this.Db.DB.Ping() != nil) { if that.connectDbFunc != nil && (that.Db.DB == nil || that.Db.DB.Ping() != nil) {
this.Db.SetConnect(this.connectDbFunc) that.Db.SetConnect(that.connectDbFunc)
} }
if this.CacheIns == nil { if that.CacheIns == nil {
this.CacheIns = CacheIns(&CacheMemory{Map: Map{}, Time: this.Config.GetInt64("cacheShortTime")}) that.CacheIns = CacheIns(&CacheMemory{Map: Map{}, Time: that.Config.GetInt64("cacheShortTime")})
} }
//异常处理 //异常处理
defer func() { defer func() {
if err := recover(); err != nil { if err := recover(); err != nil {
//this.SetError(errors.New(fmt.Sprint(err)), LOG_FMT) //that.SetError(errors.New(fmt.Sprint(err)), LOG_FMT)
LogFmt(err, 2, LOG_ERROR) that.Log.Warn(err)
this.Run(router) that.Run(router)
} }
}() }()
this.Server = &http.Server{} that.Server = &http.Server{}
if !IsRun { if !IsRun {
IsRun = true IsRun = true
} }
ch := make(chan int) ch := make(chan int)
if ObjToCeilInt(this.Port) != 0 { if ObjToCeilInt(that.Port) != 0 {
go func() { go func() {
App[this.Port] = this App[that.Port] = that
this.Server.Handler = this that.Server.Handler = that
//启动服务 //启动服务
this.Server.Addr = ":" + this.Port that.Server.Addr = ":" + that.Port
err := this.Server.ListenAndServe() err := that.Server.ListenAndServe()
LogFmt(err, 2) that.Log.Error(err)
ch <- 1 ch <- 1
}() }()
} }
if ObjToCeilInt(this.TLSPort) != 0 { if ObjToCeilInt(that.TLSPort) != 0 {
go func() { go func() {
App[this.TLSPort] = this App[that.TLSPort] = that
this.Server.Handler = this that.Server.Handler = that
//启动服务 //启动服务
this.Server.Addr = ":" + this.TLSPort that.Server.Addr = ":" + that.TLSPort
err := this.Server.ListenAndServeTLS(this.Config.GetString("tlsCert"), this.Config.GetString("tlsKey")) err := that.Server.ListenAndServeTLS(that.Config.GetString("tlsCert"), that.Config.GetString("tlsKey"))
LogFmt(err, 2) that.Log.Error(err)
ch <- 2 ch <- 2
}() }()
} }
if ObjToCeilInt(this.Port) == 0 && ObjToCeilInt(this.TLSPort) == 0 { if ObjToCeilInt(that.Port) == 0 && ObjToCeilInt(that.TLSPort) == 0 {
LogFmt("没有端口启用", 2, LOG_INFO) that.Log.Error("没有端口启用")
return return
} }
value := <-ch value := <-ch
LogFmt("启动服务失败 : "+ObjToStr(value), 2, LOG_ERROR) that.Log.Error("启动服务失败 : " + ObjToStr(value))
} }
//启动实例 // SetConnectDB 启动实例
func (this *Application) SetConnectDB(connect func(err ...*Error) (master, slave *sql.DB)) { func (that *Application) SetConnectDB(connect func(err ...*Error) (master, slave *sql.DB)) {
this.connectDbFunc = connect that.connectDbFunc = connect
this.Db.SetConnect(this.connectDbFunc) that.Db.SetConnect(that.connectDbFunc)
} }
//设置配置文件路径全路径或者相对路径 // SetSession 设置配置文件路径全路径或者相对路径
func (this *Application) SetSession(short CacheIns, Long CacheIns) { func (that *Application) SetSession(short CacheIns, Long CacheIns) {
this.sessionLong = Long that.sessionLong = Long
this.sessionShort = short that.sessionShort = short
} }
//默认配置缓存和session实现 // SetDefault 默认配置缓存和session实现
func (this *Application) SetDefault(connect func(err ...*Error) (*sql.DB, *sql.DB)) { func (that *Application) SetDefault(connect func(err ...*Error) (*sql.DB, *sql.DB)) {
this.SetConfig() that.SetConfig()
if connect != nil { if connect != nil {
this.connectDbFunc = connect that.connectDbFunc = connect
this.Db.SetConnect(this.connectDbFunc) that.Db.SetConnect(that.connectDbFunc)
} }
} }
//设置配置文件路径全路径或者相对路径 // SetCache 设置配置文件路径全路径或者相对路径
func (this *Application) SetCache(cache CacheIns) { func (that *Application) SetCache(cache CacheIns) {
this.CacheIns = cache that.CacheIns = cache
} }
//设置配置文件路径全路径或者相对路径 // SetConfig 设置配置文件路径全路径或者相对路径
func (this *Application) SetConfig(configPath ...string) { func (that *Application) SetConfig(configPath ...string) {
that.Log = GetLog("", true)
if len(configPath) != 0 { if len(configPath) != 0 {
this.configPath = configPath[0] that.configPath = configPath[0]
} }
if this.configPath == "" { if that.configPath == "" {
this.configPath = "config/config.json" that.configPath = "config/config.json"
} }
//加载配置文件 //加载配置文件
btes, err := ioutil.ReadFile(this.configPath) btes, err := ioutil.ReadFile(that.configPath)
this.Config = DeepCopyMap(Config).(Map) that.Config = DeepCopyMap(Config).(Map)
if err == nil { if err == nil {
cmap := Map{} cmap := Map{}
//文件是否损坏 //文件是否损坏
cmap.JsonToMap(string(btes), &this.Error) cmap.JsonToMap(string(btes), &that.Error)
for k, v := range cmap { for k, v := range cmap {
this.Config[k] = v //程序配置 that.Config[k] = v //程序配置
Config[k] = v //系统配置 Config[k] = v //系统配置
} }
} else { } else {
LogFmt("配置文件不存在,或者配置出错,使用缺省默认配置", 2) that.Log.Error("配置文件不存在,或者配置出错,使用缺省默认配置")
} }
//文件如果损坏则不写入配置防止配置文件数据丢失 //文件如果损坏则不写入配置防止配置文件数据丢失
if this.Error.GetError() == nil { if that.Error.GetError() == nil {
var configByte bytes.Buffer var configByte bytes.Buffer
err = json.Indent(&configByte, []byte(this.Config.ToJsonString()), "", "\t") err = json.Indent(&configByte, []byte(that.Config.ToJsonString()), "", "\t")
//判断配置文件是否序列有变化有则修改配置,五则不变 //判断配置文件是否序列有变化有则修改配置,五则不变
//fmt.Println(len(btes)) //fmt.Println(len(btes))
if len(btes) != 0 && configByte.String() == string(btes) { if len(btes) != 0 && configByte.String() == string(btes) {
@ -230,22 +234,26 @@ func (this *Application) SetConfig(configPath ...string) {
} }
//写入配置说明 //写入配置说明
var configNoteByte bytes.Buffer var configNoteByte bytes.Buffer
json.Indent(&configNoteByte, []byte(ConfigNote.ToJsonString()), "", "\t") _ = json.Indent(&configNoteByte, []byte(ConfigNote.ToJsonString()), "", "\t")
os.MkdirAll(filepath.Dir(this.configPath), os.ModeDir) _ = os.MkdirAll(filepath.Dir(that.configPath), os.ModeDir)
err = ioutil.WriteFile(this.configPath, configByte.Bytes(), os.ModeAppend) err = ioutil.WriteFile(that.configPath, configByte.Bytes(), os.ModeAppend)
if err != nil { if err != nil {
this.Error.SetError(err) that.Error.SetError(err)
} }
ioutil.WriteFile(filepath.Dir(this.configPath)+"/confignote.json", configNoteByte.Bytes(), os.ModeAppend) _ = ioutil.WriteFile(filepath.Dir(that.configPath)+"/configNote.json", configNoteByte.Bytes(), os.ModeAppend)
} }
that.Log = GetLog(that.Config.GetString("logFile"), true)
if that.Config.GetBool("webConnectLogShow") {
that.WebConnectLog = GetLog(that.Config.GetString("webConnectLogFile"), false)
}
} }
//连接判断,返回true继续传输至控制层false则停止传输 // SetConnectListener 连接判断,返回true继续传输至控制层false则停止传输
func (this *Application) SetConnectListener(lis func(this *Context) bool) { func (that *Application) SetConnectListener(lis func(this *Context) bool) {
this.connectListener = append(this.connectListener, lis) that.connectListener = append(that.connectListener, lis)
} }
//网络错误 //网络错误
@ -254,7 +262,7 @@ func (this *Application) SetConnectListener(lis func(this *Context) bool) {
//} //}
//序列化链接 //序列化链接
func (this *Application) urlSer(url string) (string, []string) { func (that *Application) urlSer(url string) (string, []string) {
q := strings.Index(url, "?") q := strings.Index(url, "?")
if q == -1 { if q == -1 {
q = len(url) q = len(url)
@ -275,9 +283,9 @@ func (this *Application) urlSer(url string) (string, []string) {
//访问 //访问
func (this *Application) handler(w http.ResponseWriter, req *http.Request) { func (that *Application) handler(w http.ResponseWriter, req *http.Request) {
_, s := this.urlSer(req.RequestURI) _, s := that.urlSer(req.RequestURI)
//获取cookie //获取cookie
// 如果cookie存在直接将sessionId赋值为cookie.Value // 如果cookie存在直接将sessionId赋值为cookie.Value
// 如果cookie不存在就查找传入的参数中是否有token // 如果cookie不存在就查找传入的参数中是否有token
@ -285,7 +293,7 @@ func (this *Application) handler(w http.ResponseWriter, req *http.Request) {
// 如果token存在就判断token是否在Session中有保存 // 如果token存在就判断token是否在Session中有保存
// 如果有取出token并复制给cookie // 如果有取出token并复制给cookie
// 没有保存就生成随机的session // 没有保存就生成随机的session
cookie, err := req.Cookie(this.Config.GetString("sessionName")) cookie, err := req.Cookie(that.Config.GetString("sessionName"))
sessionId := Md5(strconv.Itoa(Rand(10))) sessionId := Md5(strconv.Itoa(Rand(10)))
token := req.FormValue("token") token := req.FormValue("token")
//isFirst:=false //isFirst:=false
@ -296,7 +304,7 @@ func (this *Application) handler(w http.ResponseWriter, req *http.Request) {
//else{ //else{
// isFirst=true; // isFirst=true;
//} //}
http.SetCookie(w, &http.Cookie{Name: this.Config.GetString("sessionName"), Value: sessionId, Path: "/"}) http.SetCookie(w, &http.Cookie{Name: that.Config.GetString("sessionName"), Value: sessionId, Path: "/"})
} else { } else {
sessionId = cookie.Value sessionId = cookie.Value
} }
@ -307,31 +315,31 @@ func (this *Application) handler(w http.ResponseWriter, req *http.Request) {
} }
//访问实例 //访问实例
context := Context{SessionIns: SessionIns{SessionId: sessionId, context := Context{SessionIns: SessionIns{SessionId: sessionId,
LongCache: this.sessionLong, LongCache: that.sessionLong,
ShortCache: this.sessionShort, ShortCache: that.sessionShort,
}, },
CacheIns: this.CacheIns, CacheIns: that.CacheIns,
Resp: w, Req: req, Application: this, RouterString: s, Config: this.Config, Db: &this.Db, HandlerStr: unescapeUrl} Resp: w, Req: req, Application: that, RouterString: s, Config: that.Config, Db: &that.Db, HandlerStr: unescapeUrl}
//header默认设置 //header默认设置
header := w.Header() header := w.Header()
header.Set("Content-Type", "text/html; charset=utf-8") header.Set("Content-Type", "text/html; charset=utf-8")
//url去掉参数并序列化 //url去掉参数并序列化
context.HandlerStr, context.RouterString = this.urlSer(context.HandlerStr) context.HandlerStr, context.RouterString = that.urlSer(context.HandlerStr)
//跨域设置 //跨域设置
this.crossDomain(&context) that.crossDomain(&context)
//是否展示日志 //是否展示日志
if this.Config.GetInt("connectLogShow") != 0 { if that.WebConnectLog != nil {
LogFmt(Substr(context.Req.RemoteAddr, 0, strings.Index(context.Req.RemoteAddr, ":"))+" "+context.HandlerStr, 0, LOG_INFO) that.WebConnectLog.Infoln(Substr(context.Req.RemoteAddr, 0, strings.Index(context.Req.RemoteAddr, ":")) + " " + context.HandlerStr)
} }
//访问拦截true继续false暂停 //访问拦截true继续false暂停
connectListenerLen := len(this.connectListener) connectListenerLen := len(that.connectListener)
if connectListenerLen != 0 { if connectListenerLen != 0 {
for i := 0; i < connectListenerLen; i++ { for i := 0; i < connectListenerLen; i++ {
if !this.connectListener[i](&context) { if !that.connectListener[i](&context) {
context.View() context.View()
return return
@ -342,9 +350,9 @@ func (this *Application) handler(w http.ResponseWriter, req *http.Request) {
//接口服务 //接口服务
//if len(s) == 3 { //if len(s) == 3 {
// //如果满足规则则路由到对应控制器去 // //如果满足规则则路由到对应控制器去
// if this.Router[s[0]] != nil && this.Router[s[0]][s[1]] != nil && this.Router[s[0]][s[1]][s[2]] != nil { // if that.Router[s[0]] != nil && that.Router[s[0]][s[1]] != nil && that.Router[s[0]][s[1]][s[2]] != nil {
// //控制层 // //控制层
// this.Router[s[0]][s[1]][s[2]](&context) // that.Router[s[0]][s[1]][s[2]](&context)
// //header.Set("Content-Type", "text/html; charset=utf-8") // //header.Set("Content-Type", "text/html; charset=utf-8")
// context.View() // context.View()
// return // return
@ -352,25 +360,25 @@ func (this *Application) handler(w http.ResponseWriter, req *http.Request) {
// //
//} //}
//验证接口严格模式 //验证接口严格模式
modeRouterStrict := this.Config.Get("modeRouterStrict").(bool) modeRouterStrict := that.Config.GetBool("modeRouterStrict")
tempHandlerStr := context.HandlerStr tempHandlerStr := context.HandlerStr
if !modeRouterStrict { if !modeRouterStrict {
tempHandlerStr = strings.ToLower(tempHandlerStr) tempHandlerStr = strings.ToLower(tempHandlerStr)
} }
//执行接口 //执行接口
if this.MethodRouter[tempHandlerStr] != nil { if that.MethodRouter[tempHandlerStr] != nil {
this.MethodRouter[tempHandlerStr](&context) that.MethodRouter[tempHandlerStr](&context)
context.View() context.View()
return return
} }
//url赋值 //url赋值
path := this.Config.GetString("tpt") + tempHandlerStr path := that.Config.GetString("tpt") + tempHandlerStr
//判断是否为默认 //判断是否为默认
if path[len(path)-1] == '/' { if path[len(path)-1] == '/' {
defFile := this.Config.GetSlice("defFile") defFile := that.Config.GetSlice("defFile")
for i := 0; i < len(defFile); i++ { for i := 0; i < len(defFile); i++ {
temp := path + defFile.GetString(i) temp := path + defFile.GetString(i)
@ -394,7 +402,7 @@ func (this *Application) handler(w http.ResponseWriter, req *http.Request) {
//设置header //设置header
delete(header, "Content-Type") delete(header, "Content-Type")
if this.Config.GetInt("debug") != 1 { if that.Config.GetInt("debug") != 1 {
header.Set("Cache-Control", "public") header.Set("Cache-Control", "public")
} }
@ -407,7 +415,7 @@ func (this *Application) handler(w http.ResponseWriter, req *http.Request) {
} }
func (this *Application) crossDomain(context *Context) { func (that *Application) crossDomain(context *Context) {
//没有跨域设置 //没有跨域设置
if context.Config.GetString("crossDomain") == "" { if context.Config.GetString("crossDomain") == "" {
return return
@ -421,7 +429,7 @@ func (this *Application) crossDomain(context *Context) {
header.Set("Access-Control-Allow-Headers", "X-Requested-With,Content-Type,Access-Token") header.Set("Access-Control-Allow-Headers", "X-Requested-With,Content-Type,Access-Token")
if context.Config.GetString("crossDomain") != "auto" { if context.Config.GetString("crossDomain") != "auto" {
header.Set("Access-Control-Allow-Origin", this.Config.GetString("crossDomain")) header.Set("Access-Control-Allow-Origin", that.Config.GetString("crossDomain"))
return return
} }
@ -450,6 +458,7 @@ func (this *Application) crossDomain(context *Context) {
} }
} }
//Init 初始化application
func Init(config string) Application { func Init(config string) Application {
appIns := Application{} appIns := Application{}
//手动模式, //手动模式,
@ -459,7 +468,7 @@ func Init(config string) Application {
return appIns return appIns
} }
//后期整改 // SetDB 智能数据库设置
func SetDB(appIns *Application) { func SetDB(appIns *Application) {
db := appIns.Config.GetMap("db") db := appIns.Config.GetMap("db")
dbSqlite := db.GetMap("sqlite") dbSqlite := db.GetMap("sqlite")

View File

@ -1,16 +0,0 @@
package common
type LOG_MODE int
const (
LOG_NIL = 0
LOG_FMT = 1
//LOG_FILE = 2
LOG_INFO LOG_MODE = 0
LOG_WARN LOG_MODE = 1
LOG_ERROR LOG_MODE = 2
)
//session储存头
const HEAD_SESSION_ADD = "session#"

View File

@ -1,17 +1,19 @@
package common package common
import "time" import (
"time"
)
type ContextBase struct { type ContextBase struct {
Error Error
tag int64 tag string
} }
//唯一标志 //唯一标志
func (this *ContextBase) GetTag() int64 { func (this *ContextBase) GetTag() string {
if this.tag == int64(0) { if this.tag == "" {
this.tag = time.Now().UnixNano() this.tag = ObjToStr(time.Now().Unix()) + ":" + ObjToStr(Random())
} }
return this.tag return this.tag
} }

View File

@ -1,25 +1,17 @@
package common package common
//框架层处理错误 // Error 框架层处理错误
type Error struct { type Error struct {
error error
err error
} }
func (this *Error) GetError() error { func (that *Error) GetError() error {
return this.error return that.error
} }
func (this *Error) SetError(err error, loglevel ...int) { func (that *Error) SetError(err error) {
that.error = err
this.error = nil
if err == nil {
this.error = err
this.err = err
return
}
this.error = err
return return
} }

View File

@ -3,7 +3,6 @@ package common
import ( import (
"crypto/md5" "crypto/md5"
"encoding/hex" "encoding/hex"
"fmt"
"math" "math"
"strings" "strings"
) )
@ -25,86 +24,6 @@ import (
// return res // return res
//} //}
//func LogError(logMsg interface{}) {
//
// logFmt(fmt.Sprintln(logMsg), 2, LOG_ERROR)
//}
//func LogWarn(logMsg interface{}) {
//
// logFmt(fmt.Sprintln(logMsg), 2, LOG_WARN)
//}
//func LogInfo(logMsg ...interface{}) {
//
// logFmt(fmt.Sprintln(logMsg), 2, LOG_INFO)
//}
//
//func LogFmt(logMsg interface{}, loglevel ...LOG_MODE) {
//
// logFmt(logMsg, 2, loglevel...)
//}
//
////日志打印以及存储到文件
//func logFmt(logMsg interface{}, printLevel int, loglevel ...LOG_MODE) {
//
// if Config.GetInt("logLevel") == int(LOG_NIL) {
// return
// }
//
// lev := LOG_INFO
// if len(loglevel) != 0 {
// lev = loglevel[0]
// }
// gofile := ""
//
// if Config.GetInt("debug") != 0 && printLevel != 0 {
// _, file, line, ok := runtime.Caller(printLevel)
// if ok {
// gofile = " " + file + ":" + ObjToStr(line)
// }
// }
//
// logStr := ""
//
// if lev == LOG_INFO {
// logStr = "info:"
// }
// if printLevel == 0 {
// logStr = "connect:"
// }
//
// if lev == LOG_WARN {
// logStr = "warn:"
// }
//
// if lev == LOG_ERROR {
// logStr = "error:"
// }
//
// logStr = fmt.Sprintln(time.Now().Format("2006/01/02 15:04:05"), logStr, logMsg, gofile)
// //打印日志
// fmt.Print(logStr)
// //不需要存储到文件
// if Config.GetString("logFile") == "" {
// return
// }
// //存储到文件
// logFilePath := time.Now().Format(Config.GetString("logFile"))
//
// os.MkdirAll(filepath.Dir(logFilePath), os.ModeAppend)
// //os.Create(logFilePath)
// f, err := os.OpenFile(logFilePath, os.O_APPEND|os.O_CREATE, 0644)
// if err != nil {
// return
// }
// f.Write([]byte(logStr))
// f.Close()
//
//}
//日志打印以及存储到文件
func LogFmt(logMsg interface{}, printLevel int, loglevel ...LOG_MODE) {
fmt.Println(logMsg)
}
//字符串首字符大写 //字符串首字符大写
func StrFirstToUpper(str string) string { func StrFirstToUpper(str string) string {
if len(str) == 0 { if len(str) == 0 {

View File

@ -6,79 +6,79 @@ import (
type Slice []interface{} type Slice []interface{}
//获取string // GetString 获取string
func (this Slice) GetString(key int, err ...*Error) string { func (that Slice) GetString(key int, err ...*Error) string {
if len(err) != 0 { if len(err) != 0 {
err[0].SetError(nil) err[0].SetError(nil)
} }
return ObjToStr((this)[key]) return ObjToStr((that)[key])
} }
//获取Int // GetInt 获取Int
func (this Slice) GetInt(key int, err ...*Error) int { func (that Slice) GetInt(key int, err ...*Error) int {
v := ObjToInt((this)[key], err...) v := ObjToInt((that)[key], err...)
return v return v
} }
//获取Int // GetInt64 获取Int
func (this Slice) GetInt64(key int, err ...*Error) int64 { func (that Slice) GetInt64(key int, err ...*Error) int64 {
v := ObjToInt64((this)[key], err...) v := ObjToInt64((that)[key], err...)
return v return v
} }
//获取向上取整Int64 // GetCeilInt64 获取向上取整Int64
func (this Slice) GetCeilInt64(key int, err ...*Error) int64 { func (that Slice) GetCeilInt64(key int, err ...*Error) int64 {
v := ObjToCeilInt64((this)[key], err...) v := ObjToCeilInt64((that)[key], err...)
return v return v
} }
//获取向上取整Int // GetCeilInt 获取向上取整Int
func (this Slice) GetCeilInt(key int, err ...*Error) int { func (that Slice) GetCeilInt(key int, err ...*Error) int {
v := ObjToCeilInt((this)[key], err...) v := ObjToCeilInt((that)[key], err...)
return v return v
} }
//获取向上取整float64 // GetCeilFloat64 获取向上取整float64
func (this Slice) GetCeilFloat64(key int, err ...*Error) float64 { func (that Slice) GetCeilFloat64(key int, err ...*Error) float64 {
v := ObjToCeilFloat64((this)[key], err...) v := ObjToCeilFloat64((that)[key], err...)
return v return v
} }
//获取Float64 // GetFloat64 获取Float64
func (this Slice) GetFloat64(key int, err ...*Error) float64 { func (that Slice) GetFloat64(key int, err ...*Error) float64 {
v := ObjToFloat64((this)[key], err...) v := ObjToFloat64((that)[key], err...)
return v return v
} }
func (this Slice) GetSlice(key int, err ...*Error) Slice { func (that Slice) GetSlice(key int, err ...*Error) Slice {
v := ObjToSlice((this)[key], err...) v := ObjToSlice((that)[key], err...)
return v return v
} }
func (this Slice) GetBool(key int, err ...*Error) bool { func (that Slice) GetBool(key int, err ...*Error) bool {
//var v Slice //var v Slice
v := ObjToBool((this)[key], err...) v := ObjToBool((that)[key], err...)
return v return v
} }
func (this Slice) GetMap(key int, err ...*Error) Map { func (that Slice) GetMap(key int, err ...*Error) Map {
//var v Map //var v Map
v := ObjToMap((this)[key], err...) v := ObjToMap((that)[key], err...)
return v return v
} }
func (this Slice) Get(key int, err ...*Error) interface{} { func (that Slice) Get(key int, err ...*Error) interface{} {
if key < len(this) { if key < len(that) {
return this[key] return that[key]
} }
e := errors.New("没有存储key及对应的数据") e := errors.New("没有存储key及对应的数据")
if len(err) != 0 { if len(err) != 0 {
@ -87,10 +87,10 @@ func (this Slice) Get(key int, err ...*Error) interface{} {
return nil return nil
} }
func (this Slice) Put(key int, value interface{}) { func (that Slice) Put(key int, value interface{}) {
this[key] = value that[key] = value
} }
func (this Slice) ToJsonString() string { func (that Slice) ToJsonString() string {
return ObjToStr(this) return ObjToStr(that)
} }

4
const.go Normal file
View File

@ -0,0 +1,4 @@
package hotime
//session储存头
const HEAD_SESSION_ADD = "session#"

View File

@ -9,10 +9,10 @@ import (
) )
type Context struct { type Context struct {
*Application
ContextBase ContextBase
Resp http.ResponseWriter Resp http.ResponseWriter
Req *http.Request Req *http.Request
Application *Application
RouterString []string RouterString []string
Config Map Config Map
Db *HoTimeDB Db *HoTimeDB
@ -22,22 +22,22 @@ type Context struct {
HandlerStr string //复写请求url HandlerStr string //复写请求url
} }
//唯一标志 // Mtd 唯一标志
func (this *Context) Mtd(router [3]string) Map { func (that *Context) Mtd(router [3]string) Map {
this.Application.Router[router[0]][router[1]][router[2]](this) that.Application.Router[router[0]][router[1]][router[2]](that)
d := this.RespData d := that.RespData
this.RespData = nil that.RespData = nil
return d return d
} }
//打印 //打印
func (this *Context) Display(statu int, data interface{}) { func (that *Context) Display(statu int, data interface{}) {
resp := Map{"statu": statu} resp := Map{"statu": statu}
if statu != 0 { if statu != 0 {
temp := Map{} temp := Map{}
tpe := this.Config.GetMap("error").GetString(ObjToStr(statu)) tpe := that.Config.GetMap("error").GetString(ObjToStr(statu))
if tpe == "" { if tpe == "" {
//logFmt(errors.New("找不到对应的错误码"), 2, LOG_WARN) //logFmt(errors.New("找不到对应的错误码"), 2, LOG_WARN)
} }
@ -49,19 +49,19 @@ func (this *Context) Display(statu int, data interface{}) {
resp["result"] = data resp["result"] = data
} }
this.RespData = resp that.RespData = resp
//this.Data=d; //that.Data=d;
} }
func (this *Context) View() { func (that *Context) View() {
if this.RespData == nil { if that.RespData == nil {
return return
} }
d, err := json.Marshal(this.RespData) d, err := json.Marshal(that.RespData)
if err != nil { if err != nil {
return return
} }
this.RespData = nil that.RespData = nil
this.Resp.Write(d) that.Resp.Write(d)
} }

267
db/db.go
View File

@ -22,27 +22,28 @@ type HoTimeDB struct {
ConnectFunc func(err ...*Error) (*sql.DB, *sql.DB) ConnectFunc func(err ...*Error) (*sql.DB, *sql.DB)
LastErr Error LastErr Error
limit Slice limit Slice
Tx *sql.Tx //事务对象 *sql.Tx //事务对象
SlaveDB *sql.DB SlaveDB *sql.DB
} }
//设置数据库配置连接 // SetConnect 设置数据库配置连接
func (this *HoTimeDB) SetConnect(connect func(err ...*Error) (master, slave *sql.DB), err ...*Error) { func (that *HoTimeDB) SetConnect(connect func(err ...*Error) (master, slave *sql.DB), err ...*Error) {
this.ConnectFunc = connect that.ConnectFunc = connect
this.InitDb() _ = that.InitDb(err...)
} }
//设置数据库配置连接 // GetType 设置数据库配置连接
func (this *HoTimeDB) GetType() string { func (that *HoTimeDB) GetType() string {
return this.Type return that.Type
} }
//事务如果action返回true则执行成功false则回滚 // Action 事务如果action返回true则执行成功false则回滚
func (this *HoTimeDB) Action(action func(db HoTimeDB) bool) bool { func (that *HoTimeDB) Action(action func(db HoTimeDB) bool) bool {
db := HoTimeDB{DB: this.DB, CacheIns: this.CacheIns, DBCached: this.DBCached} db := HoTimeDB{DB: that.DB, CacheIns: that.CacheIns, DBCached: that.DBCached}
tx, err := db.Begin() tx, err := db.Begin()
if err != nil { if err != nil {
this.LastErr.SetError(err) that.LastErr.SetError(err)
return false return false
} }
@ -51,66 +52,74 @@ func (this *HoTimeDB) Action(action func(db HoTimeDB) bool) bool {
result := action(db) result := action(db)
if !result { if !result {
db.Tx.Rollback() err = db.Tx.Rollback()
if err != nil {
that.LastErr.SetError(err)
return false
}
return result return result
} }
db.Tx.Commit() err = db.Tx.Commit()
if err != nil {
that.LastErr.SetError(err)
return false
}
return result return result
} }
func (this *HoTimeDB) InitDb(err ...*Error) Error { func (that *HoTimeDB) InitDb(err ...*Error) Error {
if len(err) != 0 { if len(err) != 0 {
this.LastErr = *(err[0]) that.LastErr = *(err[0])
} }
this.DB, this.SlaveDB = this.ConnectFunc(&this.LastErr) that.DB, that.SlaveDB = that.ConnectFunc(&that.LastErr)
if this.DB == nil { if that.DB == nil {
return this.LastErr return that.LastErr
} }
e := this.DB.Ping() e := that.DB.Ping()
this.LastErr.SetError(e) that.LastErr.SetError(e)
if this.SlaveDB != nil { if that.SlaveDB != nil {
e := this.SlaveDB.Ping() e := that.SlaveDB.Ping()
this.LastErr.SetError(e) that.LastErr.SetError(e)
} }
return this.LastErr return that.LastErr
} }
func (this *HoTimeDB) Page(page, pageRow int) *HoTimeDB { func (that *HoTimeDB) Page(page, pageRow int) *HoTimeDB {
page = (page - 1) * pageRow page = (page - 1) * pageRow
if page < 0 { if page < 0 {
page = 1 page = 1
} }
this.limit = Slice{page, pageRow} that.limit = Slice{page, pageRow}
return this return that
} }
func (this *HoTimeDB) PageSelect(table string, qu ...interface{}) []Map { func (that *HoTimeDB) PageSelect(table string, qu ...interface{}) []Map {
if len(qu) == 1 { if len(qu) == 1 {
qu = append(qu, Map{"LIMIT": this.limit}) qu = append(qu, Map{"LIMIT": that.limit})
} }
if len(qu) == 2 { if len(qu) == 2 {
temp := qu[1].(Map) temp := qu[1].(Map)
temp["LIMIT"] = this.limit temp["LIMIT"] = that.limit
qu[1] = temp qu[1] = temp
} }
if len(qu) == 3 { if len(qu) == 3 {
temp := qu[2].(Map) temp := qu[2].(Map)
temp["LIMIT"] = this.limit temp["LIMIT"] = that.limit
qu[2] = temp qu[2] = temp
} }
//fmt.Println(qu) //fmt.Println(qu)
data := this.Select(table, qu...) data := that.Select(table, qu...)
return data return data
} }
//数据库数据解析 // Row 数据库数据解析
func (this *HoTimeDB) Row(resl *sql.Rows) []Map { func (that *HoTimeDB) Row(resl *sql.Rows) []Map {
dest := make([]Map, 0) dest := make([]Map, 0)
strs, _ := resl.Columns() strs, _ := resl.Columns()
@ -122,7 +131,11 @@ func (this *HoTimeDB) Row(resl *sql.Rows) []Map {
for j := 0; j < len(a); j++ { for j := 0; j < len(a); j++ {
b[j] = &a[j] b[j] = &a[j]
} }
resl.Scan(b...) err := resl.Scan(b...)
if err != nil {
that.LastErr.SetError(err)
return nil
}
for j := 0; j < len(a); j++ { for j := 0; j < len(a); j++ {
if a[j] != nil && reflect.ValueOf(a[j]).Type().String() == "[]uint8" { if a[j] != nil && reflect.ValueOf(a[j]).Type().String() == "[]uint8" {
lis[strs[j]] = string(a[j].([]byte)) lis[strs[j]] = string(a[j].([]byte))
@ -134,9 +147,9 @@ func (this *HoTimeDB) Row(resl *sql.Rows) []Map {
//防止int被误读为float64 //防止int被误读为float64
jlis, e := json.Marshal(lis) jlis, e := json.Marshal(lis)
if e != nil { if e != nil {
this.LastErr.SetError(e) that.LastErr.SetError(e)
} else { } else {
lis.JsonToMap(string(jlis), &this.LastErr) lis.JsonToMap(string(jlis), &that.LastErr)
} }
dest = append(dest, lis) dest = append(dest, lis)
@ -201,25 +214,25 @@ func (this *HoTimeDB) Row(resl *sql.Rows) []Map {
// //
//} //}
func (this *HoTimeDB) backupSave(path string, tt string, code int) { func (that *HoTimeDB) backupSave(path string, tt string, code int) {
fd, _ := os.OpenFile(path, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0644) fd, _ := os.OpenFile(path, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0644)
defer fd.Close() defer fd.Close()
str := "\r\n" str := "\r\n"
if code == 0 || code == 2 { if code == 0 || code == 2 {
str += this.backupDdl(tt) str += that.backupDdl(tt)
} }
if code == 0 || code == 1 { if code == 0 || code == 1 {
str += "insert into `" + tt + "`\r\n\r\n(" str += "insert into `" + tt + "`\r\n\r\n("
str += this.backupCol(tt) str += that.backupCol(tt)
} }
fd.Write([]byte(str)) _, _ = fd.Write([]byte(str))
} }
func (this *HoTimeDB) backupDdl(tt string) string { func (that *HoTimeDB) backupDdl(tt string) string {
data := this.Query("show create table " + tt) data := that.Query("show create table " + tt)
if len(data) == 0 { if len(data) == 0 {
return "" return ""
} }
@ -227,9 +240,9 @@ func (this *HoTimeDB) backupDdl(tt string) string {
return ObjToStr(data[0]["Create Table"]) + ";\r\n\r\n" return ObjToStr(data[0]["Create Table"]) + ";\r\n\r\n"
} }
func (this *HoTimeDB) backupCol(tt string) string { func (that *HoTimeDB) backupCol(tt string) string {
str := "" str := ""
data := this.Select(tt, "*") data := that.Select(tt, "*")
lthData := len(data) lthData := len(data)
@ -239,7 +252,7 @@ func (this *HoTimeDB) backupCol(tt string) string {
lthCol := len(data[0]) lthCol := len(data[0])
col := make([]string, lthCol) col := make([]string, lthCol)
tempLthData := 0 tempLthData := 0
for k, _ := range data[0] { for k := range data[0] {
if tempLthData == lthCol-1 { if tempLthData == lthCol-1 {
str += "`" + k + "`)" str += "`" + k + "`)"
@ -281,89 +294,89 @@ func (this *HoTimeDB) backupCol(tt string) string {
return str return str
} }
func (this *HoTimeDB) md5(query string, args ...interface{}) string { func (that *HoTimeDB) md5(query string, args ...interface{}) string {
strByte, _ := json.Marshal(args) strByte, _ := json.Marshal(args)
str := Md5(query + ":" + string(strByte)) str := Md5(query + ":" + string(strByte))
return str return str
} }
func (this *HoTimeDB) Query(query string, args ...interface{}) []Map { func (that *HoTimeDB) Query(query string, args ...interface{}) []Map {
//fmt.Println(query) //fmt.Println(query)
var err error var err error
var resl *sql.Rows var resl *sql.Rows
this.LastQuery = query that.LastQuery = query
this.LastData = args that.LastData = args
//主从数据库切换只有select语句有从数据库 //主从数据库切换只有select语句有从数据库
db := this.DB db := that.DB
if this.SlaveDB != nil { if that.SlaveDB != nil {
db = this.SlaveDB db = that.SlaveDB
} }
if db == nil { if db == nil {
err = errors.New("没有初始化数据库") err = errors.New("没有初始化数据库")
this.LastErr.SetError(err) that.LastErr.SetError(err)
return nil return nil
} }
if this.Tx != nil { if that.Tx != nil {
resl, err = this.Tx.Query(query, args...) resl, err = that.Tx.Query(query, args...)
} else { } else {
resl, err = db.Query(query, args...) resl, err = db.Query(query, args...)
} }
this.LastErr.SetError(err) that.LastErr.SetError(err)
if err != nil { if err != nil {
if err = db.Ping(); err != nil { if err = db.Ping(); err != nil {
this.LastErr.SetError(err) that.LastErr.SetError(err)
this.InitDb() _ = that.InitDb()
if this.LastErr.GetError() != nil { if that.LastErr.GetError() != nil {
return nil return nil
} }
return this.Query(query, args...) return that.Query(query, args...)
} }
return nil return nil
} }
return this.Row(resl) return that.Row(resl)
} }
func (this *HoTimeDB) Exec(query string, args ...interface{}) (sql.Result, Error) { func (that *HoTimeDB) Exec(query string, args ...interface{}) (sql.Result, Error) {
this.LastQuery = query that.LastQuery = query
this.LastData = args that.LastData = args
var e error var e error
var resl sql.Result var resl sql.Result
if this.DB == nil { if that.DB == nil {
err := errors.New("没有初始化数据库") err := errors.New("没有初始化数据库")
this.LastErr.SetError(err) that.LastErr.SetError(err)
return nil, this.LastErr return nil, that.LastErr
} }
if this.Tx != nil { if that.Tx != nil {
resl, e = this.Tx.Exec(query, args...) resl, e = that.Tx.Exec(query, args...)
} else { } else {
resl, e = this.DB.Exec(query, args...) resl, e = that.DB.Exec(query, args...)
} }
this.LastErr.SetError(e) that.LastErr.SetError(e)
//判断是否连接断开了 //判断是否连接断开了
if e != nil { if e != nil {
if e = this.DB.Ping(); e != nil { if e = that.DB.Ping(); e != nil {
this.LastErr.SetError(e) that.LastErr.SetError(e)
this.InitDb() _ = that.InitDb()
if this.LastErr.GetError() != nil { if that.LastErr.GetError() != nil {
return resl, this.LastErr return resl, that.LastErr
} }
return this.Exec(query, args...) return that.Exec(query, args...)
} }
} }
return resl, this.LastErr return resl, that.LastErr
} }
//func (this *HoTimeDB)copy(data []Map)[]Map{ //func (this *HoTimeDB)copy(data []Map)[]Map{
@ -384,7 +397,8 @@ func (this *HoTimeDB) Exec(query string, args ...interface{}) (sql.Result, Error
// return res // return res
// //
//} //}
func (this *HoTimeDB) Select(table string, qu ...interface{}) []Map {
func (that *HoTimeDB) Select(table string, qu ...interface{}) []Map {
query := "SELECT" query := "SELECT"
where := Map{} where := Map{}
@ -446,15 +460,15 @@ func (this *HoTimeDB) Select(table string, qu ...interface{}) []Map {
where = qu[intWhere].(Map) where = qu[intWhere].(Map)
} }
temp, resWhere := this.where(where) temp, resWhere := that.where(where)
query += temp query += temp
qs = append(qs, resWhere...) qs = append(qs, resWhere...)
md5 := this.md5(query, qs...) md5 := that.md5(query, qs...)
if this.DBCached && this.CacheIns != nil { if that.DBCached && that.CacheIns != nil {
//如果缓存有则从缓存取 //如果缓存有则从缓存取
cacheData := this.Cache(table + ":" + md5) cacheData := that.Cache(table + ":" + md5)
if cacheData.Data != nil { if cacheData.Data != nil {
return cacheData.ToMapArray() return cacheData.ToMapArray()
@ -462,23 +476,23 @@ func (this *HoTimeDB) Select(table string, qu ...interface{}) []Map {
} }
//无缓存则数据库取 //无缓存则数据库取
res := this.Query(query, qs...) res := that.Query(query, qs...)
if res == nil { if res == nil {
res = []Map{} res = []Map{}
} }
//缓存 //缓存
if this.DBCached && this.CacheIns != nil { if that.DBCached && that.CacheIns != nil {
this.Cache(table+":"+md5, res) _ = that.Cache(table+":"+md5, res)
} }
return res return res
} }
func (this *HoTimeDB) Get(table string, qu ...interface{}) Map { func (that *HoTimeDB) Get(table string, qu ...interface{}) Map {
//fmt.Println(qu) //fmt.Println(qu)
if len(qu) == 1 { if len(qu) == 1 {
qu = append(qu, Map{"LIMIT": 1}) qu = append(qu, Map{"LIMIT": 1})
@ -494,19 +508,16 @@ func (this *HoTimeDB) Get(table string, qu ...interface{}) Map {
qu[2] = temp qu[2] = temp
} }
//fmt.Println(qu) //fmt.Println(qu)
data := this.Select(table, qu...) data := that.Select(table, qu...)
if len(data) == 0 { if len(data) == 0 {
return nil return nil
} }
return data[0] return data[0]
} }
/** // Count 计数
** 计数 func (that *HoTimeDB) Count(table string, qu ...interface{}) int {
*/ var req = []interface{}{}
func (this *HoTimeDB) Count(table string, qu ...interface{}) int {
req := []interface{}{}
if len(qu) == 2 { if len(qu) == 2 {
req = append(req, qu[0]) req = append(req, qu[0])
req = append(req, "COUNT(*)") req = append(req, "COUNT(*)")
@ -517,7 +528,7 @@ func (this *HoTimeDB) Count(table string, qu ...interface{}) int {
} }
//req=append(req,qu...) //req=append(req,qu...)
data := this.Select(table, req...) data := that.Select(table, req...)
//fmt.Println(data) //fmt.Println(data)
if len(data) == 0 { if len(data) == 0 {
return 0 return 0
@ -533,7 +544,7 @@ var condition = []string{"AND", "OR"}
var vcond = []string{"GROUP", "ORDER", "LIMIT"} var vcond = []string{"GROUP", "ORDER", "LIMIT"}
//where语句解析 //where语句解析
func (this *HoTimeDB) where(data Map) (string, []interface{}) { func (that *HoTimeDB) where(data Map) (string, []interface{}) {
where := "" where := ""
@ -545,7 +556,7 @@ func (this *HoTimeDB) where(data Map) (string, []interface{}) {
if condition[i] == k { if condition[i] == k {
tw, ts := this.cond(k, v.(Map)) tw, ts := that.cond(k, v.(Map))
where += tw where += tw
res = append(res, ts...) res = append(res, ts...)
@ -563,7 +574,7 @@ func (this *HoTimeDB) where(data Map) (string, []interface{}) {
y++ y++
} }
if x == len(condition) && y == len(vcond) { if x == len(condition) && y == len(vcond) {
tv, vv := this.varCond(k, v) tv, vv := that.varCond(k, v)
where += tv where += tv
res = append(res, vv...) res = append(res, vv...)
@ -617,7 +628,7 @@ func (this *HoTimeDB) where(data Map) (string, []interface{}) {
} }
func (this *HoTimeDB) varCond(k string, v interface{}) (string, []interface{}) { func (that *HoTimeDB) varCond(k string, v interface{}) (string, []interface{}) {
where := "" where := ""
res := make([]interface{}, 0) res := make([]interface{}, 0)
length := len(k) length := len(k)
@ -635,7 +646,7 @@ func (this *HoTimeDB) varCond(k string, v interface{}) (string, []interface{}) {
res = append(res, v) res = append(res, v)
case "[!]": case "[!]":
k = strings.Replace(k, "[!]", "", -1) k = strings.Replace(k, "[!]", "", -1)
where, res = this.notIn(k, v, where, res) where, res = that.notIn(k, v, where, res)
case "[#]": case "[#]":
k = strings.Replace(k, "[#]", "", -1) k = strings.Replace(k, "[#]", "", -1)
where += " " + k + "=" + ObjToStr(v) where += " " + k + "=" + ObjToStr(v)
@ -692,7 +703,7 @@ func (this *HoTimeDB) varCond(k string, v interface{}) (string, []interface{}) {
default: default:
if reflect.ValueOf(v).Type().String() == "hotime.Slice" { if reflect.ValueOf(v).Type().String() == "hotime.Slice" {
where += "`" + k + "` IN (" where += "`" + k + "` IN ("
res = append(res, (v.(Slice))...) res = append(res, v.(Slice)...)
if len(v.(Slice)) == 0 { if len(v.(Slice)) == 0 {
where += ") " where += ") "
} else { } else {
@ -725,7 +736,7 @@ func (this *HoTimeDB) varCond(k string, v interface{}) (string, []interface{}) {
//fmt.Println(v) //fmt.Println(v)
where += "`" + k + "` IN (" where += "`" + k + "` IN ("
res = append(res, (v.(Slice))...) res = append(res, v.(Slice)...)
for i := 0; i < len(v.(Slice)); i++ { for i := 0; i < len(v.(Slice)); i++ {
if i+1 != len(v.(Slice)) { if i+1 != len(v.(Slice)) {
where += "?," where += "?,"
@ -736,7 +747,7 @@ func (this *HoTimeDB) varCond(k string, v interface{}) (string, []interface{}) {
} }
} else if reflect.ValueOf(v).Type().String() == "[]interface {}" { } else if reflect.ValueOf(v).Type().String() == "[]interface {}" {
where += "`" + k + "` IN (" where += "`" + k + "` IN ("
res = append(res, (v.([]interface{}))...) res = append(res, v.([]interface{})...)
for i := 0; i < len(v.([]interface{})); i++ { for i := 0; i < len(v.([]interface{})); i++ {
if i+1 != len(v.([]interface{})) { if i+1 != len(v.([]interface{})) {
where += "?," where += "?,"
@ -757,7 +768,7 @@ func (this *HoTimeDB) varCond(k string, v interface{}) (string, []interface{}) {
} }
// this.Db.Update("user",hotime.Map{"ustate":"1"},hotime.Map{"AND":hotime.Map{"OR":hotime.Map{"uid":4,"uname":"dasda"}},"ustate":1}) // this.Db.Update("user",hotime.Map{"ustate":"1"},hotime.Map{"AND":hotime.Map{"OR":hotime.Map{"uid":4,"uname":"dasda"}},"ustate":1})
func (this *HoTimeDB) notIn(k string, v interface{}, where string, res []interface{}) (string, []interface{}) { func (that *HoTimeDB) notIn(k string, v interface{}, where string, res []interface{}) (string, []interface{}) {
//where:="" //where:=""
//fmt.Println(reflect.ValueOf(v).Type().String()) //fmt.Println(reflect.ValueOf(v).Type().String())
if v == nil { if v == nil {
@ -766,7 +777,7 @@ func (this *HoTimeDB) notIn(k string, v interface{}, where string, res []interfa
} else if reflect.ValueOf(v).Type().String() == "hotime.Slice" { } else if reflect.ValueOf(v).Type().String() == "hotime.Slice" {
where += "`" + k + "` NOT IN (" where += "`" + k + "` NOT IN ("
res = append(res, (v.(Slice))...) res = append(res, v.(Slice)...)
for i := 0; i < len(v.(Slice)); i++ { for i := 0; i < len(v.(Slice)); i++ {
if i+1 != len(v.(Slice)) { if i+1 != len(v.(Slice)) {
where += "?," where += "?,"
@ -777,7 +788,7 @@ func (this *HoTimeDB) notIn(k string, v interface{}, where string, res []interfa
} }
} else if reflect.ValueOf(v).Type().String() == "[]interface {}" { } else if reflect.ValueOf(v).Type().String() == "[]interface {}" {
where += "`" + k + "` NOT IN (" where += "`" + k + "` NOT IN ("
res = append(res, (v.([]interface{}))...) res = append(res, v.([]interface{})...)
for i := 0; i < len(v.([]interface{})); i++ { for i := 0; i < len(v.([]interface{})); i++ {
if i+1 != len(v.([]interface{})) { if i+1 != len(v.([]interface{})) {
where += "?," where += "?,"
@ -796,7 +807,7 @@ func (this *HoTimeDB) notIn(k string, v interface{}, where string, res []interfa
return where, res return where, res
} }
func (this *HoTimeDB) cond(tag string, data Map) (string, []interface{}) { func (that *HoTimeDB) cond(tag string, data Map) (string, []interface{}) {
where := " " where := " "
res := make([]interface{}, 0) res := make([]interface{}, 0)
lens := len(data) lens := len(data)
@ -807,7 +818,7 @@ func (this *HoTimeDB) cond(tag string, data Map) (string, []interface{}) {
if condition[i] == k { if condition[i] == k {
tw, ts := this.cond(k, v.(Map)) tw, ts := that.cond(k, v.(Map))
if lens--; lens <= 0 { if lens--; lens <= 0 {
//fmt.Println(lens) //fmt.Println(lens)
where += "(" + tw + ") " where += "(" + tw + ") "
@ -823,7 +834,7 @@ func (this *HoTimeDB) cond(tag string, data Map) (string, []interface{}) {
if x == len(condition) { if x == len(condition) {
tv, vv := this.varCond(k, v) tv, vv := that.varCond(k, v)
res = append(res, vv...) res = append(res, vv...)
if lens--; lens <= 0 { if lens--; lens <= 0 {
@ -838,8 +849,8 @@ func (this *HoTimeDB) cond(tag string, data Map) (string, []interface{}) {
return where, res return where, res
} }
//更新数据 // Update 更新数据
func (this *HoTimeDB) Update(table string, data Map, where Map) int64 { func (that *HoTimeDB) Update(table string, data Map, where Map) int64 {
query := "UPDATE " + table + " SET " query := "UPDATE " + table + " SET "
//UPDATE Person SET Address = 'Zhongshan 23', City = 'Nanjing' WHERE LastName = 'Wilson' //UPDATE Person SET Address = 'Zhongshan 23', City = 'Nanjing' WHERE LastName = 'Wilson'
@ -861,13 +872,13 @@ func (this *HoTimeDB) Update(table string, data Map, where Map) int64 {
} }
} }
temp, resWhere := this.where(where) temp, resWhere := that.where(where)
//fmt.Println(resWhere) //fmt.Println(resWhere)
query += temp query += temp
qs = append(qs, resWhere...) qs = append(qs, resWhere...)
res, err := this.Exec(query, qs...) res, err := that.Exec(query, qs...)
rows := int64(0) rows := int64(0)
if err.GetError() == nil && res != nil { if err.GetError() == nil && res != nil {
@ -876,22 +887,22 @@ func (this *HoTimeDB) Update(table string, data Map, where Map) int64 {
//如果更新成功,则删除缓存 //如果更新成功,则删除缓存
if rows != 0 { if rows != 0 {
if this.DBCached && this.CacheIns != nil { if that.DBCached && that.CacheIns != nil {
this.Cache(table+"*", nil) _ = that.Cache(table+"*", nil)
} }
} }
return rows return rows
} }
func (this *HoTimeDB) Delete(table string, data map[string]interface{}) int64 { func (that *HoTimeDB) Delete(table string, data map[string]interface{}) int64 {
query := "DELETE FROM " + table + " " query := "DELETE FROM " + table + " "
temp, resWhere := this.where(data) temp, resWhere := that.where(data)
query += temp query += temp
res, err := this.Exec(query, resWhere...) res, err := that.Exec(query, resWhere...)
rows := int64(0) rows := int64(0)
if err.GetError() == nil && res != nil { if err.GetError() == nil && res != nil {
rows, _ = res.RowsAffected() rows, _ = res.RowsAffected()
@ -899,8 +910,8 @@ func (this *HoTimeDB) Delete(table string, data map[string]interface{}) int64 {
//如果删除成功,删除对应缓存 //如果删除成功,删除对应缓存
if rows != 0 { if rows != 0 {
if this.DBCached && this.CacheIns != nil { if that.DBCached && that.CacheIns != nil {
this.Cache(table+"*", nil) _ = that.Cache(table+"*", nil)
} }
} }
//return 0 //return 0
@ -908,8 +919,8 @@ func (this *HoTimeDB) Delete(table string, data map[string]interface{}) int64 {
return rows return rows
} }
//插入新数据 // Insert 插入新数据
func (this *HoTimeDB) Insert(table string, data map[string]interface{}) int64 { func (that *HoTimeDB) Insert(table string, data map[string]interface{}) int64 {
values := make([]interface{}, 0) values := make([]interface{}, 0)
queryString := " (" queryString := " ("
@ -931,18 +942,18 @@ func (this *HoTimeDB) Insert(table string, data map[string]interface{}) int64 {
} }
query := "INSERT INTO " + table + queryString + "VALUES" + valueString query := "INSERT INTO " + table + queryString + "VALUES" + valueString
res, err := this.Exec(query, values...) res, err := that.Exec(query, values...)
id := int64(0) id := int64(0)
if err.GetError() == nil && res != nil { if err.GetError() == nil && res != nil {
//id, this.LastErr.err = res.LastInsertId() //id, that.LastErr.err = res.LastInsertId()
} }
//如果插入成功,删除缓存 //如果插入成功,删除缓存
if id != 0 { if id != 0 {
if this.DBCached && this.CacheIns != nil { if that.DBCached && that.CacheIns != nil {
this.Cache(table+"*", nil) _ = that.Cache(table+"*", nil)
} }
} }

View File

@ -6,11 +6,8 @@ import (
"../../hotime/common" "../../hotime/common"
"database/sql" "database/sql"
"fmt" "fmt"
//"go.hoteas.com/hotime/cache"
"golang.org/x/net/websocket" "golang.org/x/net/websocket"
"time" "time"
//"go.hoteas.com/hotime/cache"
) )
func main() { func main() {
@ -27,18 +24,18 @@ func main() {
//手动模式, //手动模式,
appIns.SetConfig("example/config/config.json") appIns.SetConfig("example/config/config.json")
//redis缓存接入 //redis缓存接入
//ca:=cache.CacheIns(&cache.CacheRedis{Host:appIns.Config.GetString("redisHost"),Pwd:appIns.Config.GetString("redisPwd"),Time:appIns.Config.GetCeilInt64("cacheLongTime")}) ca := cache.CacheIns(&cache.CacheRedis{Host: appIns.Config.GetString("redisHost"), Pwd: appIns.Config.GetString("redisPwd"), Time: appIns.Config.GetCeilInt64("cacheLongTime")})
//ca.Cache("xyzm","dasdas") ca.Cache("xyzm", "dasdas")
//ca.Cache("xyzn","dasdas") ca.Cache("xyzn", "dasdas")
//ca.Cache("xyzo","dasdas") ca.Cache("xyzo", "dasdas")
//ca.Cache("xyz*",nil) ca.Cache("xyz*", nil)
//fmt.Println(ca.Cache("xyzm").Data) //fmt.Println(ca.Cache("xyzm").Data)
//mysql //mysql
//mysql.SetDB(&appIns) //mysql.SetDB(&appIns)
//自动选择数据库 //自动选择数据库
dbInterface := cache.HoTimeDBInterface(&appIns.Db) dbInterface := cache.HoTimeDBInterface(&appIns.Db)
appIns.SetSession(cache.CacheIns(&cache.CacheMemory{}), cache.CacheIns(&cache.CacheDb{Db: dbInterface, Time: appIns.Config.GetInt64("cacheTime")})) appIns.SetSession(cache.CacheIns(&cache.CacheMemory{}), cache.CacheIns(&cache.CacheDb{Db: dbInterface, Time: appIns.Config.GetInt64("cacheTime")}))
//appIns.SetCache(cache.CacheIns(&cache.CacheMemory{})) appIns.SetCache(cache.CacheIns(&cache.CacheMemory{}))
//快捷模式 //快捷模式
appIns.SetDefault(func(err ...*common.Error) (*sql.DB, *sql.DB) { appIns.SetDefault(func(err ...*common.Error) (*sql.DB, *sql.DB) {
@ -56,6 +53,8 @@ func main() {
"index": hotime.Ctr{ "index": hotime.Ctr{
"test": func(this *hotime.Context) { "test": func(this *hotime.Context) {
fmt.Println(this.Db.GetTag()) fmt.Println(this.Db.GetTag())
this.Application.Log.Error("dasdasdas")
this.Log.Error("dadasdasd")
//x:=this.Db.Action(func(db hotime.HoTimeDB) bool { //x:=this.Db.Action(func(db hotime.HoTimeDB) bool {
// //
// db.Insert("user",hotime.Map{"unickname":"dasdas"}) // db.Insert("user",hotime.Map{"unickname":"dasdas"})

114
log/logrus.go Normal file
View File

@ -0,0 +1,114 @@
package log
import (
"fmt"
log "github.com/sirupsen/logrus"
"os"
"path/filepath"
"runtime"
"strings"
"time"
)
func GetLog(path string, showCodeLine bool) *log.Logger {
hook := MyHook{
Field: "line",
Skip: 5,
Path: path, ShowCodeLine: showCodeLine,
}
loger := log.New()
loger.SetFormatter(&log.TextFormatter{})
loger.AddHook(&hook)
loger.Print("dasdasdas")
return loger
}
// MyHook ...
type MyHook struct {
Path string //存储日志的位置
ShowCodeLine bool //输出代码文件名称和日志行
Field string
Skip int
levels []log.Level
}
// Levels 只定义 error 和 panic 等级的日志,其他日志等级不会触发 hook
func (that *MyHook) Levels() []log.Level {
return log.AllLevels
}
// Fire 将异常日志写入到指定日志文件中
func (that *MyHook) Fire(entry *log.Entry) error {
if that.ShowCodeLine {
entry.Data[that.Field] = findCaller(that.Skip)
}
//不需要存储到文件
if that.Path == "" {
return nil
}
//存储到文件
logFilePath := time.Now().Format(that.Path)
err := os.MkdirAll(filepath.Dir(logFilePath), os.ModeAppend)
if err != nil {
return err
}
//os.Create(logFilePath)
f, err := os.OpenFile(logFilePath, os.O_APPEND|os.O_CREATE, 0644)
if err != nil {
return err
}
bte, _ := entry.Bytes()
_, err = f.Write(bte)
if err != nil {
return err
}
err = f.Close()
if err != nil {
return err
}
return nil
}
// 对caller进行递归查询, 直到找到非logrus包产生的第一个调用.
// 因为filename我获取到了上层目录名, 因此所有logrus包的调用的文件名都是 logrus/...
// 因此通过排除logrus开头的文件名, 就可以排除所有logrus包的自己的函数调用
func findCaller(skip int) string {
file := ""
line := 0
for i := 0; i < 10; i++ {
file, line = getCaller(skip + i)
if !strings.HasPrefix(file, "logrus") {
break
}
}
return fmt.Sprintf("%s:%d", file, line)
}
// 这里其实可以获取函数名称的: fnName := runtime.FuncForPC(pc).Name()
// 但是我觉得有 文件名和行号就够定位问题, 因此忽略了caller返回的第一个值:pc
// 在标准库log里面我们可以选择记录文件的全路径或者文件名, 但是在使用过程成并发最合适的,
// 因为文件的全路径往往很长, 而文件名在多个包中往往有重复, 因此这里选择多取一层, 取到文件所在的上层目录那层.
func getCaller(skip int) (string, int) {
_, file, line, ok := runtime.Caller(skip)
//fmt.Println(file)
//fmt.Println(line)
if !ok {
return "", 0
}
n := 0
for i := len(file) - 1; i > 0; i-- {
if file[i] == '/' {
n++
if n >= 2 {
file = file[i+1:]
break
}
}
}
return file, line
}

View File

@ -14,63 +14,63 @@ type SessionIns struct {
ContextBase ContextBase
} }
func (this *SessionIns) set() { func (that *SessionIns) set() {
if this.ShortCache != nil { if that.ShortCache != nil {
this.ShortCache.Cache(HEAD_SESSION_ADD+this.SessionId, this.Map) that.ShortCache.Cache(HEAD_SESSION_ADD+that.SessionId, that.Map)
} }
if this.LongCache != nil { if that.LongCache != nil {
this.LongCache.Cache(HEAD_SESSION_ADD+this.SessionId, this.Map) that.LongCache.Cache(HEAD_SESSION_ADD+that.SessionId, that.Map)
} }
} }
func (this *SessionIns) Session(key string, data ...interface{}) *Obj { func (that *SessionIns) Session(key string, data ...interface{}) *Obj {
if this.Map == nil { if that.Map == nil {
this.get() that.get()
} }
if len(data) != 0 { if len(data) != 0 {
if data[0] == nil { if data[0] == nil {
delete(this.Map, key) delete(that.Map, key)
this.set() that.set()
} else { } else {
this.Map[key] = data[0] that.Map[key] = data[0]
this.set() that.set()
} }
return &Obj{Data: nil} return &Obj{Data: nil}
} }
return &Obj{Data: this.Map.Get(key)} return &Obj{Data: that.Map.Get(key)}
} }
func (this *SessionIns) get() { func (that *SessionIns) get() {
if this.ShortCache != nil { if that.ShortCache != nil {
this.Map = this.ShortCache.Cache(HEAD_SESSION_ADD + this.SessionId).ToMap() that.Map = that.ShortCache.Cache(HEAD_SESSION_ADD + that.SessionId).ToMap()
if this.Map != nil { if that.Map != nil {
return return
} }
} }
if this.LongCache != nil { if that.LongCache != nil {
this.Map = this.LongCache.Cache(HEAD_SESSION_ADD + this.SessionId).ToMap() that.Map = that.LongCache.Cache(HEAD_SESSION_ADD + that.SessionId).ToMap()
if this.Map != nil { if that.Map != nil {
if this.ShortCache != nil { if that.ShortCache != nil {
this.ShortCache.Cache(HEAD_SESSION_ADD+this.SessionId, this.Map) that.ShortCache.Cache(HEAD_SESSION_ADD+that.SessionId, that.Map)
} }
return return
} }
} }
this.Map = Map{} that.Map = Map{}
this.ShortCache.Cache(HEAD_SESSION_ADD+this.SessionId, this.Map) that.ShortCache.Cache(HEAD_SESSION_ADD+that.SessionId, that.Map)
return return
} }
func (this *SessionIns) Init(short CacheIns, long CacheIns) { func (that *SessionIns) Init(short CacheIns, long CacheIns) {
this.ShortCache = short that.ShortCache = short
this.LongCache = long that.LongCache = long
} }

View File

@ -1,6 +1,6 @@
package hotime package hotime
//控制器 // Ctr 控制器
type Ctr map[string]Method type Ctr map[string]Method
type Proj map[string]Ctr type Proj map[string]Ctr
type Router map[string]Proj type Router map[string]Proj

4
var.go
View File

@ -11,7 +11,6 @@ var App = map[string]*Application{} //整个项目
var Config = Map{ var Config = Map{
"debug": 1, //debug 0关闭1开启 "debug": 1, //debug 0关闭1开启
"logLevel": LOG_FMT,
"db": Map{ "db": Map{
"sqlite": Map{ "sqlite": Map{
"path": "config/data.db", "path": "config/data.db",
@ -40,6 +39,8 @@ var Config = Map{
var ConfigNote = Map{ var ConfigNote = Map{
"logLevel": "默认0必须0关闭1打印日志等级", "logLevel": "默认0必须0关闭1打印日志等级",
"logFile": "无默认,非必须,如果需要存储日志文件时使用,保存格式为:a/b/c/20060102150405.txt,将生成a/b/c/年月日时分秒.txt按需设置", "logFile": "无默认,非必须,如果需要存储日志文件时使用,保存格式为:a/b/c/20060102150405.txt,将生成a/b/c/年月日时分秒.txt按需设置",
"webConnectLogShow": "默认true非必须访问日志如果需要web访问链接、访问ip、访问时间打印false为关闭true开启此功能",
"webConnectLogFile": "无默认非必须webConnectLogShow开启之后才能使用如果需要存储日志文件时使用保存格式为:a/b/c/20060102150405.txt,将生成a/b/c/年月日时分秒.txt按需设置",
"debug": "默认1必须0关闭其他开启0用于生产环境其他值用于开发测试会显示更多内容并能够辅助研发自动生成配置文件、代码等功能,web无缓存", //debug 0关闭1开启 "debug": "默认1必须0关闭其他开启0用于生产环境其他值用于开发测试会显示更多内容并能够辅助研发自动生成配置文件、代码等功能,web无缓存", //debug 0关闭1开启
"db": Map{ "db": Map{
"注释": "配置即启用非必须默认使用sqlite数据库", "注释": "配置即启用非必须默认使用sqlite数据库",
@ -100,7 +101,6 @@ var ConfigNote = Map{
"defFile": "默认访问index.html或者index.htm文件必须默认访问文件类型", "defFile": "默认访问index.html或者index.htm文件必须默认访问文件类型",
"crossDomain": "默认空 非必须空字符串为不开启如果需要跨域设置auto为智能开启所有网站允许跨域http://www.baidu.com为指定域允许跨域", //是否开启跨域 "crossDomain": "默认空 非必须空字符串为不开启如果需要跨域设置auto为智能开启所有网站允许跨域http://www.baidu.com为指定域允许跨域", //是否开启跨域
"modeRouterStrict": "默认false,必须路由严格模式false,为大小写忽略必须匹配true必须大小写匹配", //路由严格模式/a/b/c "modeRouterStrict": "默认false,必须路由严格模式false,为大小写忽略必须匹配true必须大小写匹配", //路由严格模式/a/b/c
"connectLogShow": "默认true非必须访问日志如果需要web访问链接、访问ip、访问时间打印false为关闭true开启此功能",
"sessionName": "默认HOTIME必须设置session的cookie名", "sessionName": "默认HOTIME必须设置session的cookie名",
"port": "默认80必须web服务开启Http端口0为不启用http服务,默认80", "port": "默认80必须web服务开启Http端口0为不启用http服务,默认80",
"tlsPort": "默认443非必须web服务https端口0为不启用https服务", "tlsPort": "默认443非必须web服务https端口0为不启用https服务",