|
@@ -8,6 +8,7 @@ import (
|
|
|
"strconv"
|
|
"strconv"
|
|
|
"strings"
|
|
"strings"
|
|
|
|
|
|
|
|
|
|
+ "github.com/runningwater/go-redis/aof"
|
|
|
"github.com/runningwater/go-redis/config"
|
|
"github.com/runningwater/go-redis/config"
|
|
|
"github.com/runningwater/go-redis/interface/resp"
|
|
"github.com/runningwater/go-redis/interface/resp"
|
|
|
"github.com/runningwater/go-redis/lib/logger"
|
|
"github.com/runningwater/go-redis/lib/logger"
|
|
@@ -15,22 +16,38 @@ import (
|
|
|
)
|
|
)
|
|
|
|
|
|
|
|
type Database struct {
|
|
type Database struct {
|
|
|
- dbSet []*DB
|
|
|
|
|
|
|
+ dbSet []*DB
|
|
|
|
|
+ aofHandler *aof.Handler
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
func NewDatabase() *Database {
|
|
func NewDatabase() *Database {
|
|
|
if config.Properties.Databases == 0 {
|
|
if config.Properties.Databases == 0 {
|
|
|
config.Properties.Databases = 16
|
|
config.Properties.Databases = 16
|
|
|
}
|
|
}
|
|
|
- dbs := &Database{}
|
|
|
|
|
- dbs.dbSet = make([]*DB, config.Properties.Databases)
|
|
|
|
|
- for i := range dbs.dbSet {
|
|
|
|
|
|
|
+ database := &Database{}
|
|
|
|
|
+ database.dbSet = make([]*DB, config.Properties.Databases)
|
|
|
|
|
+ // 初始化数据库集合
|
|
|
|
|
+ for i := range database.dbSet {
|
|
|
db := NewDB()
|
|
db := NewDB()
|
|
|
db.index = i
|
|
db.index = i
|
|
|
- dbs.dbSet[i] = db
|
|
|
|
|
|
|
+ database.dbSet[i] = db
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
- return dbs
|
|
|
|
|
|
|
+ if config.Properties.AppendOnly {
|
|
|
|
|
+ aofHandler, err := aof.NewAofHandler(database)
|
|
|
|
|
+ if err != nil {
|
|
|
|
|
+ panic(err)
|
|
|
|
|
+ }
|
|
|
|
|
+ database.aofHandler = aofHandler
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ for _, db := range database.dbSet {
|
|
|
|
|
+ d := db
|
|
|
|
|
+ d.addAof = func(line CmdLine) {
|
|
|
|
|
+ database.aofHandler.AddAof(d.index, line)
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ return database
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
func (d *Database) Exec(client resp.Connection, args [][]byte) resp.Reply {
|
|
func (d *Database) Exec(client resp.Connection, args [][]byte) resp.Reply {
|
|
@@ -64,15 +81,30 @@ func (d *Database) AfterClientClose(client resp.Connection) {
|
|
|
|
|
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-// select db 命令
|
|
|
|
|
|
|
+// execSelect 处理数据库选择命令
|
|
|
|
|
+//
|
|
|
|
|
+// 参数:
|
|
|
|
|
+//
|
|
|
|
|
+// c: 客户端连接对象,用于执行数据库切换操作
|
|
|
|
|
+// database: 数据库实例,包含所有可用的数据库集合
|
|
|
|
|
+// args: 命令参数,第一个参数为要选择的数据库索引
|
|
|
|
|
+//
|
|
|
|
|
+// 返回值:
|
|
|
|
|
+//
|
|
|
|
|
+// resp.Reply: 执行结果回复,成功返回OK,失败返回错误信息
|
|
|
func execSelect(c resp.Connection, database *Database, args [][]byte) resp.Reply {
|
|
func execSelect(c resp.Connection, database *Database, args [][]byte) resp.Reply {
|
|
|
|
|
+ // 解析数据库索引参数
|
|
|
dbIndex, err := strconv.Atoi(string(args[0]))
|
|
dbIndex, err := strconv.Atoi(string(args[0]))
|
|
|
if err != nil {
|
|
if err != nil {
|
|
|
return reply.NewErrReply("ERR invalid DB index")
|
|
return reply.NewErrReply("ERR invalid DB index")
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
|
|
+ // 验证数据库索引范围
|
|
|
if dbIndex >= len(database.dbSet) {
|
|
if dbIndex >= len(database.dbSet) {
|
|
|
return reply.NewErrReply("ERR DB index is out of range")
|
|
return reply.NewErrReply("ERR DB index is out of range")
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
|
|
+ // 执行数据库切换操作
|
|
|
c.SelectDB(dbIndex)
|
|
c.SelectDB(dbIndex)
|
|
|
return reply.NewOkReply()
|
|
return reply.NewOkReply()
|
|
|
}
|
|
}
|