func (gd *GlobalDataHelper) GlobalDataAddRowValues(sender rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { var index int var name string var row int var val []datatype.Any if err := ParseArgs(msg, &index, &name, &row, &val); err != nil { log.LogError(err) return share.ERR_ARGS_ERROR, nil } args := make([]interface{}, len(val)) for k, v := range val { args[k] = v.Val } index, err := gd.AddRowValues(index, name, row, args...) if err != nil { log.LogError(err) } if index == -1 { log.LogError("add record row failed") } return 0, nil }
func (b *BaseProxy) SyncPlayerBak(mailbox rpc.Mailbox, info map[ObjectID]ObjectID) error { //同步数据 player := App.players.GetPlayer(mailbox) if player == nil { log.LogError("player not found") } for k, v := range info { ent := App.GetEntity(k) if ent == nil { log.LogError("object not found") continue } ent.SetExtraData("linkObj", v) } var err error if player.Quit { App.players.RemovePlayer(mailbox) err = server.MailTo(&mailbox, &player.Base, "AreaBridge.RemovePlayerBak", "ok", ) } return err }
func (t *Thread) work(id int) { log.LogMessage(t.TAG, " thread work, id:", id) var start_time time.Time var delay time.Duration warninglvl := 50 * time.Millisecond for { select { case rpc := <-t.Queue[id]: log.LogMessage(t.TAG, " thread:", id, rpc.GetSrc(), " call:", rpc.GetMethod()) start_time = time.Now() err := rpc.Call() if err != nil { log.LogError("rpc error:", err) } delay = time.Now().Sub(start_time) if delay > warninglvl { log.LogWarning("rpc call ", rpc.GetMethod(), " delay:", delay.Nanoseconds()/1000000, "ms") } err = rpc.Done() if err != nil { log.LogError("rpc error:", err) } rpc.Free() break default: if t.Quit { log.LogMessage(t.TAG, " thread ", id, " quit") return } time.Sleep(time.Millisecond) } } }
//进程rpc处理 func RpcProcess(ch chan *rpc.RpcCall) { var start_time time.Time var delay time.Duration for { select { case call := <-ch: if call.IsThreadWork() { busy = true } else { log.LogDebug(call.GetSrc(), " rpc call:", call.GetMethod()) start_time = time.Now() err := call.Call() if err != nil { log.LogError(err) } delay = time.Now().Sub(start_time) if delay > warninglvl { log.LogWarning("rpc call ", call.GetMethod(), " delay:", delay.Nanoseconds()/1000000, "ms") } err = call.Done() if err != nil { log.LogError(err) } call.Free() busy = true } default: return } } }
//数据库加载回调 func (gd *GlobalDataHelper) OnLoadGlobalData(msg *rpc.Message) { ret := GetReplyError(msg) if ret == share.ERR_REPLY_FAILED { log.LogError("global data is empty") if err := gd.createDataSet(); err != nil { log.LogError("create global data error:", err) } return } if ret != share.ERR_REPLY_SUCCEED { log.LogError("global data load error, errcode:", ret) return } var callbackparams share.DBParams var savedata share.DbSave if err := ParseArgs(msg, &callbackparams, &savedata); err != nil { log.LogError("load global data error:", err) return } ent, err := core.CreateFromDb(&savedata) if err != nil { log.LogError("create global data set failed, err:", err) } if gd.dataset != nil { core.Destroy(gd.dataset.GetObjId()) } gd.dataset = ent gd.ready = true gd.OnDataReady() log.LogMessage("load global succeed") }
func Start(startapp string, name string, appuid int32, typ string, startargs string) error { ferr, err := os.Create(fmt.Sprintf("log/%s_err.log", name)) if err != nil { log.LogError(err) return err } fout, err := os.Create(fmt.Sprintf("log/%s_trace.log", name)) if err != nil { log.LogError(err) return err } cmd := exec.Command(startapp, "-m", fmt.Sprintf("%s:%d", context.Host, context.Port), "-l", context.LocalIP, "-o", context.OuterIP, "-d", strconv.Itoa(int(appuid)), "-t", typ, "-s", startargs) cmd.Stdout = fout cmd.Stderr = ferr err = cmd.Start() if err != nil { log.LogFatalf(err) return err } log.TraceInfo("master", "app start ", typ, ",", strconv.Itoa(int(appuid))) atomic.AddInt32(&Load, 1) context.waitGroup.Wrap(func() { cmd.Wait() ferr.Close() fout.Close() log.LogMessage(name, " is quit") atomic.AddInt32(&Load, -1) }) return nil }
func (d *DbBridge) CreateRoleBack(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { r := server.NewMessageReader(msg) errstr, err := r.ReadString() if server.Check(err) { return 0, nil } if errstr != "ok" { server.Check(server.Error(nil, &mailbox, "Role.Error", share.ERROR_CREATE_ROLE_ERROR)) return 0, nil } player := App.Players.GetPlayer(mailbox.Id) if player == nil { log.LogError("player not found, id:", mailbox.Id) //角色没有找到 return 0, nil } if player.State != STATE_LOGGED { log.LogError("player state not logged") return 0, nil } server.Check(d.getUserInfo(mailbox, player.Account)) return 0, nil }
func (c *Client) Start() { log.LogMessage("client start:", c.id) conn, err := net.Dial("tcp", "172.30.9.101:5391") if err != nil { log.LogError(err) return } c.buf = make([]byte, 1024*16) mid, data, err := util.ReadPkg(conn, c.buf) if err != nil { log.LogError(err) log.LogError("quit client ", c.id) return } l := &s2c.Login{} err = ParseProto(mid, data, l) if err != nil { log.LogError(err) log.LogError("quit client ", c.id) return } conn.Close() c.Login(l.GetHost(), l.GetPort()) }
func (s *Session) GetBaseAndId(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { r := server.NewMessageReader(msg) user, err := r.ReadString() if server.Check(err) { return 0, nil } s.l.Lock() defer s.l.Unlock() s.serial++ if s.serial < 0 { s.serial = 0 } bases := server.GetAppIdsByType("base") sort.Sort(sort.StringSlice(bases)) if len(bases) > 0 { idx := s.serial % len(bases) baseid := bases[idx] s.id++ if base := server.GetAppByName(baseid); base != nil { server.Check(base.Call(&mailbox, "Login.AddClient", user)) return 0, nil } log.LogError(server.ErrNotFoundApp) return 0, nil } log.LogError(server.ErrNotFoundApp) return 0, nil }
//交换子对象的位置 func (k *Kernel) Exchange(src Entityer, dest Entityer) bool { if src == nil || dest == nil || src.GetParent() == nil || dest.GetParent() == nil || !src.GetParent().GetObjId().Equal(dest.GetParent().GetObjId()) { log.LogError("parent not equal") return false } parent := src.GetParent() err := parent.SwapChild(src.GetIndex(), dest.GetIndex()) if err != nil { log.LogError(err) return false } if viewid := parent.GetExtraData("viewportid"); viewid != nil { root := parent.GetRoot() vp := k.FindViewport(root) if vp != nil { vp.ViewportNotifyExchange(viewid.(int32), int32(dest.GetIndex()), viewid.(int32), int32(src.GetIndex())) } } return true }
//当前服务器增加entity func (t *TeleportHelper) TeleportPlayerByBase(sender rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { reply = CreateMessage(sender) var playerinfo *datatype.EntityInfo var args []interface{} if err := ParseArgs(msg, &args); err != nil || len(args) < 1 { log.LogError(err) return share.ERR_ARGS_ERROR, reply } var ok bool if playerinfo, ok = args[0].(*datatype.EntityInfo); !ok { log.LogError("args parse error") return share.ERR_ARGS_ERROR, reply } pl, err := core.CreateFromArchive(playerinfo, nil) if err != nil { log.LogError(err) return share.ERR_FUNC_BEGIN + 1, reply } var params []interface{} if len(args) > 1 { params = args[1].([]interface{}) } if !core.apper.OnTeleportFromBase(params, pl) { core.Destroy(pl.GetObjId()) return share.ERR_REPLY_FAILED, reply } return share.ERR_REPLY_SUCCEED, reply }
func (b *BaseProxy) RemovePlayer(mailbox rpc.Mailbox, reason int) error { //同步数据 player := App.players.GetPlayer(mailbox) if player == nil { log.LogError("player not found") } player.Save(true) var err error if player.Entity.GetExtraData("saveData") == nil { log.LogError("player save data is nil") return err } err = server.MailTo(&App.MailBox, &player.Base, "Sync.SyncPlayer", map[string]interface{}{ "mailbox": player.Mailbox, "data": player.Entity.GetExtraData("saveData")}, ) player.Entity.RemoveExtraData("saveData") return err }
func (s *GlobalData_Save) Load(eq ExecQueryer, dbId uint64, extfield string, extobjs ...interface{}) error { sql, a := s.Query(dbId) sql = fmt.Sprintf(sql, extfield) r, err := eq.Query(sql, a...) if err != nil { log.LogError("load error:", err) return err } defer r.Close() if !r.Next() { log.LogError("load error:", sql, a) return ErrSqlRowError } args := []interface{}{&dbId, &s.Capacity, &s.ConfigId, &s.Name, &s.Test1, &s.Test2} if extobjs != nil { args = append(args, extobjs...) } if err = r.Scan(args...); err != nil { log.LogError("load error:", err) return err } if err = s.TestRec_r.Load(eq, dbId); err != nil { log.LogError("load error:", err) return err } return nil }
func (rec *GlobalDataTestRec) Load(eq ExecQueryer, dbId uint64) error { rec.Rows = rec.Rows[:0] sql := "SELECT `r_testrec` FROM `tbl_globaldata` WHERE `id`=? LIMIT 1" r, err := eq.Query(sql, dbId) if err != nil { log.LogError("load record GlobalDataTestRec error:", err) return err } defer r.Close() if !r.Next() { log.LogError("load record GlobalDataTestRec error:", sql, dbId) return ErrSqlRowError } var json []byte if err = r.Scan(&json); err != nil { log.LogError("load record GlobalDataTestRec error:", err) return err } if json == nil || len(json) < 2 { log.LogWarning("load record GlobalDataTestRec error: nil") return nil } err = rec.Unmarshal(json) if err != nil { log.LogError("unmarshal record GlobalDataTestRec error:", err) return err } return nil }
func (this *Database) ExecSql(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { var sqlstr string var callback string var callbackparams share.DBParams if server.Check(server.ParseArgs(msg, &sqlstr, &callback, &callbackparams)) { return 0, nil } sqlconn := db.sql var r sql.Result var err error app := server.GetAppById(mailbox.App) if app == nil { log.LogError(server.ErrAppNotFound) return 0, nil } if r, err = sqlconn.Exec(sqlstr); err != nil { log.LogError("sql:", sqlstr) server.Check(app.Call(nil, callback, callbackparams, 0, err.Error())) return 0, nil } eff, _ := r.RowsAffected() server.Check(app.Call(nil, callback, callbackparams, eff, "")) return 0, nil }
func (this *Database) QuerySql(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { var sqlstr string var callback string var callbackparams share.DBParams if server.Check(server.ParseArgs(msg, &sqlstr, &callback, &callbackparams)) { return 0, nil } sqlconn := db.sql var r *sql.Rows var err error app := server.GetAppById(mailbox.App) if app == nil { log.LogError(server.ErrAppNotFound) return 0, nil } if r, err = sqlconn.Query(sqlstr); err != nil { log.LogError(err) return 0, nil } defer r.Close() var cols []string cols, err = r.Columns() if err != nil { server.Check(app.Call(nil, callback, callbackparams, []share.DBRow{share.DBRow{"error": []byte(err.Error())}})) return 0, nil } result := make([]interface{}, len(cols)) for k := range result { result[k] = new([]byte) } arrresult := make([]share.DBRow, 0, 100) for r.Next() { err = r.Scan(result...) if err != nil { log.LogError("sql:", sqlstr) server.Check(app.Call(nil, callback, callbackparams, []share.DBRow{share.DBRow{"error": []byte(err.Error())}})) return 0, nil } mapresult := make(share.DBRow, len(cols)) for k, v := range cols { mapresult[v] = *result[k].(*[]byte) } arrresult = append(arrresult, mapresult) if len(arrresult) == 100 { break } } server.Check(app.Call(nil, callback, callbackparams, arrresult)) return 0, nil }
/* 查询表格的字段信息 */ func (conn *MySql) QueryTblInfo(tbl_schema, tbl_name string) (fields TblField, empty bool, err error) { rowcount, e := conn.Query("select count(*) from information_schema.columns where table_schema=? and table_name=? limit 0, 1", tbl_schema, tbl_name) if e != nil { log.LogError(err.Error()) err = e return } defer rowcount.Close() if !rowcount.Next() { return } var count int rowcount.Scan(&count) if count <= 0 { empty = true return } fields.FieldList = make([]Field, count) inforows, e2 := conn.Query("select column_name, column_type, is_nullable, extra from information_schema.columns where table_schema=? and table_name=?", tbl_schema, tbl_name) if e2 != nil { log.LogError(err.Error()) err = e2 return } defer inforows.Close() var colname, coltype, isnull string var extra sql.NullString index := 0 for inforows.Next() { e := inforows.Scan(&colname, &coltype, &isnull, &extra) if e != nil { log.LogError(e.Error()) err = e return } fields.FieldList[index] = Field{colname, coltype, isnull == "YES", extra.Valid && (extra.String == "auto_increment")} index++ } indexinfo, e := conn.queryTblIndex(tbl_schema, tbl_name) if e != nil { err = e return } fields.IndexInfo = indexinfo return }
func (this *Database) UpdateRow(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { var tbl string var values map[string]interface{} var condition string var callback string var callbackparams share.DBParams if server.Check(server.ParseArgs(msg, &tbl, &values, &condition, &callback, &callbackparams)) { return 0, nil } sqlconn := db.sql var r sql.Result var err error app := server.GetAppById(mailbox.App) if app == nil { log.LogError(server.ErrAppNotFound) return 0, nil } if condition != "" { condition = fmt.Sprintf("WHERE %s", condition) } args := make([]interface{}, 0, len(values)) var sql bytes.Buffer sql.WriteString("UPDATE `") sql.WriteString(tbl) sql.WriteString("` SET") split := " " for k, v := range values { sql.WriteString(split) split = ", " sql.WriteString("`") sql.WriteString(k) sql.WriteString("`") sql.WriteString("=?") args = append(args, v) } sqlstr := fmt.Sprintf("%s %s", sql.String(), condition) if r, err = sqlconn.Exec(sqlstr, args...); err != nil { log.LogError("sql:", sqlstr) if callback == "_" { log.LogError(err) return 0, nil } server.Check(app.Call(nil, callback, callbackparams, 0, err.Error())) return 0, nil } if callback == "_" { return 0, nil } eff, _ := r.RowsAffected() server.Check(app.Call(nil, callback, callbackparams, eff, "")) return 0, nil }
func (p *PlayerList) AddPlayer(mailbox rpc.Mailbox, data *EntityInfo) *AreaPlayer { if _, dup := p.players[mailbox.Uid]; dup { log.LogError("player already added,", mailbox) return nil } ent, err := App.CreateFromArchive(data, map[string]interface{}{ "mailbox": mailbox, "base": rpc.Mailbox{App: mailbox.App}, "sync": true}) if err != nil { log.LogError(err) return nil } nameinter, err := ent.Get("Name") if err != nil { log.LogError(err) App.Destroy(ent.GetObjId()) return nil } name := nameinter.(string) if _, dup := p.namelist[name]; dup { log.LogError("player name conflict") App.Destroy(ent.GetObjId()) return nil } pl := &AreaPlayer{} pl.Mailbox = mailbox pl.Base = rpc.Mailbox{App: mailbox.App} pl.Name = name pl.Entity = ent pl.Deleted = false pl.Quit = false p.players[mailbox.Uid] = pl p.namelist[name] = mailbox cell := App.GetCell(1) if w, ok := ent.(inter.Watcher); ok { w.SetRange(2) } pl.Cell = cell App.PlaceObj( cell.scene, ent, Vector3{ util.RandRangef(0, cell.width), 0, util.RandRangef(0, cell.height)}, 0) log.LogDebug("Add player:", mailbox) return pl }
func (a *Areas) GetArea(mailbox rpc.Mailbox, id string) error { a.l.Lock() defer a.l.Unlock() log.LogMessage("GetArea") app := server.GetAppByName(mailbox.App) if app == nil { return server.ErrAppNotFound } if areainfo, exist := a.areas[id]; exist { if areainfo.Status == AREA_CREATED { return app.Call(&mailbox, "AreaBridge.GetAreaBak", areainfo.AppId) } else { a.pending[id].PushBack(mailbox) return nil } } a.lastareaid++ appid := fmt.Sprintf("area_%d", a.lastareaid) data, err := share.CreateAppMsg("area", id, appid, fmt.Sprintf(`{ "id":"%s", "host":"127.0.0.1", "port":0, "areaid":"%s"}`, appid, id), App.Name, ) if err != nil { log.LogError(err) return app.Call(&mailbox, "AreaBridge.GetAreaBak", "") } err = App.SendToMaster(data) if err != nil { log.LogError(err) return app.Call(&mailbox, "AreaBridge.GetAreaBak", "") } ar := &area{} ar.AppId = appid ar.Status = AREA_CREATING a.areas[id] = ar l := list.New() l.PushBack(mailbox) a.pending[id] = l log.LogMessage(a) return nil }
func (this *SceneBeat) Add(obj Entityer, beat string, t time.Duration, count int32, param interface{}) bool { oid := obj.GetObjId() if this.find(oid, beat) != nil { log.LogError("heartbeat already add", beat) return false } if t < time.Millisecond { log.LogError("heartbeat duration must above 1 millisecond,", t) return false } if count == 0 { log.LogError("heartbeat count must above 0 or -1") return false } tick := this.getTick() this.serial++ tick.serial = this.serial tick.Name = beat tick.Oid = oid tick.ent = obj tick.Params = param tick.Last = time.Now() tick.Interval = t tick.Count = count tick.deleted = false if hb, ok := this.heartbeats[int64(t)]; ok { hb.Add(tick) } else { hb = &beatSlot{} hb.info = list.New() hb.Add(tick) this.heartbeats[int64(t)] = hb } if beats, ok := this.beatHash[oid.Index]; ok { beats[beat] = &beatIndex{t, tick} } else { b := make(map[string]*beatIndex, 10) b[beat] = &beatIndex{t, tick} this.beatHash[oid.Index] = b } return true }
func (gd *GlobalDataHelper) GlobalDataClearRecord(sender rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { var index int var name string if err := ParseArgs(msg, &index, &name); err != nil { log.LogError(err) return share.ERR_ARGS_ERROR, nil } err := gd.ClearRecord(index, name) if err != nil { log.LogError(err) } return 0, nil }
func (gd *GlobalDataHelper) GlobalDataDelRow(sender rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { var index int var name string var row int if err := ParseArgs(msg, &index, &name, &row); err != nil { log.LogError(err) return share.ERR_ARGS_ERROR, nil } err := gd.DelRow(index, name, row) if err != nil { log.LogError(err) } return 0, nil }
func createRpc(ch chan *rpc.RpcCall) *rpc.Server { rpc, err := rpc.CreateRpcService(remotes, handlers, ch) if err != nil { log.LogFatalf(err) } id := 0 var collection RpcCollection for service, _ := range handlers { if service != "C2SHelper" { id++ sid := id * 100 info := rpc.GetRpcInfo("C2S" + service) for _, m := range info { sid++ rinfo := RpcInfo{service, m, int16(sid)} collection.Infos = append(collection.Infos, rinfo) } } } if len(collection.Infos) > 0 { t, err := template.New("maker").Parse(tpl) if err != nil { log.LogError(err.Error()) } if err != nil { log.LogError("template", err) } //save file file, err := os.Create("interface/" + core.Name + "_rpc.xml") if err != nil { log.LogError("writer", err) return rpc } defer file.Close() writer := bufio.NewWriter(file) err = t.Execute(writer, collection) if err != nil { log.LogError("writer", err) } writer.Flush() } return rpc }
func (fsm *FSM) CallState(e Event) { if function, ok := fsm.method[fsm.state]; ok { returnValues := function.Func.Call([]reflect.Value{fsm.rcvr, reflect.ValueOf(e.event), reflect.ValueOf(e.param), reflect.ValueOf(e.timeout)}) nextstate := returnValues[0].String() timeout := returnValues[1].Int() errInter := returnValues[2].Interface() errmsg := "" if errInter != nil { errmsg = errInter.(error).Error() } if nextstate == "stop" { fsm.Stop(errmsg) return } if errmsg != "" { log.LogError(errmsg) } fsm.state = nextstate if timeout > 0 { go fsm.DelayCall(timeout) } } }
func (a *Account) Login(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { args := &c2s.Enterbase{} if server.Check(server.ParseProto(msg, args)) { return 0, nil } if App.Login.checkClient(args.GetUser(), args.GetKey()) { if pl := App.Players.AddPlayer(mailbox.Id); pl != nil { log.LogMessage("add player:", mailbox) pl.Account = args.GetUser() pl.State = STATE_LOGGED if args.GetRolename() != "" { pl.ChooseRole = args.GetRolename() server.Check(App.DbBridge.selectUser(mailbox, pl.Account, args.GetRolename(), int(args.GetRoleindex()))) return 0, nil } server.Check(App.DbBridge.getUserInfo(mailbox, args.GetUser())) return 0, nil } log.LogError("player add failed", mailbox) return 0, nil } else { log.LogDebug(args.GetUser(), args.GetKey()) err := &s2c.Error{} err.ErrorNo = proto.Int32(share.ERROR_LOGIN_FAILED) server.Check(server.MailTo(nil, &mailbox, "Login.Error", err)) return 0, nil } }
//删除信件 func (l *LetterSystem) DeleteLetter(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { args := &c2s.Reqoperatemail{} if server.Check(server.ParseProto(msg, args)) { return 0, nil } p := App.Players.GetPlayer(mailbox.Id) if p == nil { log.LogError("player not found, id:", mailbox.Id) //角色没有找到 return 0, nil } player := p.Entity.(*entity.Player) if len(args.Mails) == 0 { return 0, nil } for _, sno := range args.Mails { row := player.MailBox_r.FindSerial_no(uint64(sno)) if row == -1 { return 0, nil } player.MailBox_r.Del(row) } return 0, nil }
func (m *Master) Start() { context = m if !m.Agent { log.TraceInfo("master", "start") tcpListener, err := net.Listen("tcp", fmt.Sprintf("%s:%d", m.Host, m.Port)) if err != nil { log.LogError(err) log.LogFatalf(err) } m.tcpListener = tcpListener tcpserver := &tcp_server{} m.waitGroup.Wrap(func() { util.TCPServer(m.tcpListener, tcpserver) }) } if !m.Agent && m.ConsolePort != 0 { StartConsoleServer(m) log.LogMessage("console start at:", m.ConsolePort) } if m.Agent { log.TraceInfo("master agent", "start") m.agent = &Agent{} m.agent.Connect(m.Host, m.Port, true, m.ConnectToMaster) } else { m.agentlist = NewAgentList() m.waitfor = true if m.WaitAgents == 0 { m.waitfor = false StartApp(m) } } }
func (d *DbBridge) RoleInUse(mailbox rpc.Mailbox, msg *rpc.Message) (errcode int32, reply *rpc.Message) { r := server.NewMessageReader(msg) serverid, err := r.ReadString() if server.Check(err) { return 0, nil } player := App.Players.GetPlayer(mailbox.Id) if player == nil { return 0, nil } if serverid == App.Name { server.Check(App.Players.SwitchPlayer(player)) return 0, nil } app := server.GetAppByName(serverid) if app == nil { log.LogError(server.ErrAppNotFound) return 0, nil } app.Call(&mailbox, "Login.SwitchPlayer", player.Account) return 0, nil }
func (s *BaseScene_Save) InsertOrUpdate(eq ExecQueryer, insert bool, dbId uint64, extfields string, extplacehold string, extobjs ...interface{}) error { var sql string var args []interface{} if insert { sql = "INSERT INTO `tbl_basescene`(`id`,`capacity`,`configid`,`p_name`%s ) VALUES(?,?,?,?%s) " args = []interface{}{dbId, s.Capacity, s.ConfigId, s.Name} sql = fmt.Sprintf(sql, extfields, extplacehold) if extobjs != nil { args = append(args, extobjs...) } } else { sql = "UPDATE `tbl_basescene` SET %s`capacity`=?, `configid`=?,`p_name`=? WHERE `id` = ?" if extobjs != nil { args = append(args, extobjs...) } args = append(args, []interface{}{s.Capacity, s.ConfigId, s.Name, dbId}...) sql = fmt.Sprintf(sql, extfields) } if _, err := eq.Exec(sql, args...); err != nil { log.LogError("InsertOrUpdate error:", sql, args) return err } return nil }