diff --git a/rueidiscompat/adapter.go b/rueidiscompat/adapter.go index 5223d73d..bf30fbbb 100644 --- a/rueidiscompat/adapter.go +++ b/rueidiscompat/adapter.go @@ -341,7 +341,7 @@ type CoreCmdable interface { Shutdown(ctx context.Context) *StatusCmd ShutdownSave(ctx context.Context) *StatusCmd ShutdownNoSave(ctx context.Context) *StatusCmd - // TODO SlaveOf(ctx context.Context, host, port string) *StatusCmd + SlaveOf(ctx context.Context, host, port string) *StatusCmd // TODO SlowLogGet(ctx context.Context, num int64) *SlowLogCmd Time(ctx context.Context) *TimeCmd DebugObject(ctx context.Context, key string) *StringCmd @@ -379,7 +379,7 @@ type CoreCmdable interface { PubSubShardChannels(ctx context.Context, pattern string) *StringSliceCmd PubSubShardNumSub(ctx context.Context, channels ...string) *StringIntMapCmd - // TODO ClusterMyShardID(ctx context.Context) *StringCmd + ClusterMyShardID(ctx context.Context) *StringCmd ClusterSlots(ctx context.Context) *ClusterSlotsCmd ClusterShards(ctx context.Context) *ClusterShardsCmd // TODO ClusterLinks(ctx context.Context) *ClusterLinksCmd @@ -401,8 +401,6 @@ type CoreCmdable interface { ClusterFailover(ctx context.Context) *StatusCmd ClusterAddSlots(ctx context.Context, slots ...int64) *StatusCmd ClusterAddSlotsRange(ctx context.Context, min, max int64) *StatusCmd - // TODO ReadOnly(ctx context.Context) *StatusCmd - // TODO ReadWrite(ctx context.Context) *StatusCmd GeoAdd(ctx context.Context, key string, geoLocation ...GeoLocation) *IntCmd GeoPos(ctx context.Context, key string, members ...string) *GeoPosCmd @@ -420,7 +418,7 @@ type CoreCmdable interface { // TODO ACLLog(ctx context.Context, count int64) *ACLLogCmd // TODO ACLLogReset(ctx context.Context) *StatusCmd - // TODO ModuleLoadex(ctx context.Context, conf *ModuleLoadexConfig) *StringCmd + ModuleLoadex(ctx context.Context, conf *ModuleLoadexConfig) *StringCmd GearsCmdable ProbabilisticCmdable TimeseriesCmdable @@ -2733,6 +2731,12 @@ func (c *Compat) ShutdownNoSave(ctx context.Context) *StatusCmd { }) } +func (c *Compat) SlaveOf(ctx context.Context, host, port string) *StatusCmd { + cmd := c.client.B().Arbitrary("SLAVEOF").Args(host, port).Build() + resp := c.client.Do(ctx, cmd) + return newStatusCmd(resp) +} + func (c *Compat) Time(ctx context.Context) *TimeCmd { cmd := c.client.B().Time().Build() resp := c.client.Do(ctx, cmd) @@ -2940,6 +2944,12 @@ func (c *Compat) PubSubShardNumSub(ctx context.Context, channels ...string) *Str return newStringIntMapCmd(resp) } +func (c *Compat) ClusterMyShardID(ctx context.Context) *StringCmd { + cmd := c.client.B().ClusterMyshardid().Build() + resp := c.client.Do(ctx, cmd) + return newStringCmd(resp) +} + func (c *Compat) ClusterSlots(ctx context.Context) *ClusterSlotsCmd { cmd := c.client.B().ClusterSlots().Build() resp := c.client.Do(ctx, cmd) @@ -5640,6 +5650,20 @@ func (c *Compat) FTTagVals(ctx context.Context, index string, field string) *Str return newStringSliceCmd(c.client.Do(ctx, cmd)) } +func (c *Compat) ModuleLoadex(ctx context.Context, conf *ModuleLoadexConfig) *StringCmd { + cmd := c.client.B().ModuleLoadex().Path(conf.Path).Config() + for k, v := range conf.Conf { + cmd = cmd.Config(k, str(v)) + } + var resp rueidis.RedisResult + if len(conf.Args) > 0 { + resp = c.client.Do(ctx, cmd.Args(argsToSlice(conf.Args)...).Build()) + } else { + resp = c.client.Do(ctx, cmd.Build()) + } + return newStringCmd(resp) +} + func (c CacheCompat) BitCount(ctx context.Context, key string, bitCount *BitCount) *IntCmd { var resp rueidis.RedisResult if bitCount == nil { diff --git a/rueidiscompat/command.go b/rueidiscompat/command.go index 019e89ef..49abd741 100644 --- a/rueidiscompat/command.go +++ b/rueidiscompat/command.go @@ -4833,3 +4833,11 @@ func (cmd *ClientInfoCmd) from(res rueidis.RedisResult) { cmd.SetVal(info) } + +// ModuleLoadexConfig struct is used to specify the arguments for the MODULE LOADEX command of redis. +// `MODULE LOADEX path [CONFIG name value [CONFIG name value ...]] [ARGS args [args ...]]` +type ModuleLoadexConfig struct { + Path string + Conf map[string]interface{} + Args []interface{} +} diff --git a/rueidiscompat/pipeline.go b/rueidiscompat/pipeline.go index 28034ac3..e9dd6f7e 100644 --- a/rueidiscompat/pipeline.go +++ b/rueidiscompat/pipeline.go @@ -1699,6 +1699,12 @@ func (c *Pipeline) ShutdownNoSave(ctx context.Context) *StatusCmd { return ret } +func (c *Pipeline) SlaveOf(ctx context.Context, host, port string) *StatusCmd { + ret := c.comp.SlaveOf(ctx, host, port) + c.rets = append(c.rets, ret) + return ret +} + func (c *Pipeline) Time(ctx context.Context) *TimeCmd { ret := c.comp.Time(ctx) c.rets = append(c.rets, ret) @@ -1885,6 +1891,12 @@ func (c *Pipeline) PubSubShardNumSub(ctx context.Context, channels ...string) *S return ret } +func (c *Pipeline) ClusterMyShardID(ctx context.Context) *StringCmd { + ret := c.comp.ClusterMyShardID(ctx) + c.rets = append(c.rets, ret) + return ret +} + func (c *Pipeline) ClusterSlots(ctx context.Context) *ClusterSlotsCmd { ret := c.comp.ClusterSlots(ctx) c.rets = append(c.rets, ret) @@ -3030,6 +3042,12 @@ func (c *Pipeline) FTTagVals(ctx context.Context, index string, field string) *S return ret } +func (c *Pipeline) ModuleLoadex(ctx context.Context, conf *ModuleLoadexConfig) *StringCmd { + ret := c.comp.ModuleLoadex(ctx, conf) + c.rets = append(c.rets, ret) + return ret +} + // Len returns the number of queued commands. func (c *Pipeline) Len() int { return len(c.comp.client.(*proxy).cmds) diff --git a/rueidiscompat/pipeline_test.go b/rueidiscompat/pipeline_test.go index 47e42bb0..ae36819d 100644 --- a/rueidiscompat/pipeline_test.go +++ b/rueidiscompat/pipeline_test.go @@ -600,8 +600,15 @@ func TestPipeliner(t *testing.T) { p.JSONStrLen(ctx, "1", "1") p.JSONToggle(ctx, "1", "1") p.JSONType(ctx, "1", "1") + p.SlaveOf(ctx, "NO", "ONE") + p.ClusterMyShardID(ctx) + p.ModuleLoadex(ctx, &ModuleLoadexConfig{ + Path: "/", + Conf: map[string]any{"k": "v"}, + Args: []any{"1", "2"}, + }) - if n := len(p.rets); n != 477 { + if n := len(p.rets); n != 480 { t.Fatalf("unexpected pipeline calls: %v", n) } for i, cmd := range p.rets { @@ -609,7 +616,7 @@ func TestPipeliner(t *testing.T) { t.Fatalf("unexpected pipeline placeholder err(%d): %v", i, err) } } - if n := len(p.comp.client.(*proxy).cmds); n != 477 { + if n := len(p.comp.client.(*proxy).cmds); n != 480 { t.Fatalf("unexpected pipeline commands: %v", n) } var pipeline [][]string @@ -1117,5 +1124,8 @@ var golden = `[ ["JSON.STRAPPEND","1","1","1"], ["JSON.STRLEN","1","1"], ["JSON.TOGGLE","1","1"], - ["JSON.TYPE","1","1"] + ["JSON.TYPE","1","1"], + ["SLAVEOF","NO","ONE"], + ["CLUSTER","MYSHARDID"], + ["MODULE","LOADEX","/","CONFIG","k","v","ARGS","1","2"] ]`