Get Redis variable in different package in Golang

huangapple go评论92阅读模式
英文:

Get Redis variable in different package in Golang

问题

我正在使用go-redis/redisgo-redis/cache来缓存Go对象。

import (
    "communication/MQ_pkg"
    "gopkg.in/go-redis/cache.v3"
    "gopkg.in/vmihailenco/msgpack.v2"
)

obj := &VAR_STRUCT{}    

Codec.Set(&cache.Item{
    Key:    key,
    Object: obj,
})

在上述代码中,obj是一个具有Go映射(键值对)的结构体。通过上述代码,我设置了一个键并将值保存在其中。这段代码位于common包中。
现在,我想在不导入该包的情况下在不同的包(比如GetRedis_pkg)中访问它。有没有办法可以做到这一点?
并且,我能否通过使用Redis键来访问该结构体中的特定映射?

我导入了gopkg.in/go-redis/cache.v3来在我的代码中使用Redis。

英文:

I'm using go-redis/redis and go-redis/cache to cache Go objects.

import (
	"communication/MQ_pkg"

	"gopkg.in/go-redis/cache.v3"
	"gopkg.in/vmihailenco/msgpack.v2"
)

obj := &VAR_STRUCT{}    	

Codec.Set(&cache.Item{
    		Key:    key,
    		Object: obj,
    	})

where obj is an structure having go maps(key value pair)
By Using above code i am setting a key and saving values into it. This is in package common.
Now i want to access this in different package say GetRedis_pkg without importing pkg. Is there are any way i can do that.
And can i access particular map inside that that structure by any means using redis key
imorted gopkg.in/go-redis/cache.v3 to use redis in my code

答案1

得分: 1

是的,您可以通过使用一个共同的Codec实例来访问相同的映射,用于设置和获取操作。为此,您需要实现一个单例实例生成器。最好是一个线程安全的实现。这样,您将节省大量资源并确保连接的正确性。这对于保持客户端的唯一性以防止错误和节省资源非常重要。

单例编解码器

package singleton

import (
    "sync"
    "gopkg.in/go-redis/cache.v5"
    "gopkg.in/redis.v5"
)

var codec *cache.Codec
var once sync.Once

func GetInstance() *cache.Codec {
    once.Do(func() {
        client := redis.NewClient(&redis.Options{
            Addr:     "localhost:6379",
            Password: "", // 未设置密码
            DB:       0,  // 使用默认数据库
        })

        codec = &cache.Codec{
            Redis: client,

            Marshal: func(v interface{}) ([]byte, error) {
                return msgpack.Marshal(v)
            },
            Unmarshal: func(b []byte, v interface{}) error {
                return msgpack.Unmarshal(b, v)
            },
        }
    })
    return codec
}

使用编解码器实例设置键

package setter

import (
    "github.com/Me/myapp/singleton"
    "sync"
)

func Set(keys []string, vals []SomeObj, wg *sync.WaitGroup) {
    for i, k := range keys {
        wg.Add(1)
        // 单例是线程安全的,可以与goroutine一起使用
        go func() {
            codec := singleton.GetInstance()

            codec.Set(&cache.Item{
                Key:        k,
                Object:     vals[i],
                Expiration: time.Hour,
            })
            wg.Done()
        }()
    }
}

使用相同的编解码器实例获取对象

package getter

import (
    "github.com/Me/myapp/singleton"
    "sync"
)

func Get(keys []string, wg *sync.WaitGroup) chan SomeObj {
    wanted_objs := make(chan *SomeObj)
    for i, k := range keys {
        wg.Add(1)
        // 单例是线程安全的,可以与goroutine一起使用
        go func() {
            codec := singleton.GetInstance()
            wanted := new(SomeObj)
            if err := codec.Get(key, wanted); err == nil {
                wanted_objs <- wanted
            }
        }()
    }
    return wanted_objs
}
英文:

Yes, you can access the same map by using a common Codec instance for both packages and both of set and get operations. For this purposes you need to implement a singleton instance producer. Desirably it should be a thread safe implementation. In this way you will save a lot of resource and guarantee connection correctness. This is significant to keep a client the only to prevent bugs and save resource.

> Client is a Redis client representing a pool of zero or more underlying connections. It's safe for concurrent use by multiple goroutines.

###Singleton codec

package singleton
                           
import (                       
    &quot;sync&quot;                     
    &quot;gopkg.in/go-redis/cache.v5&quot;
    &quot;gopkg.in/redis.v5&quot;
)                                                            
                           
var codec *cache.Codec        
var once sync.Once             
                           
func GetInstance() *cache.Codec {
    once.Do(func() {           
        client := redis.NewClient(&amp;redis.Options{
            Addr:     &quot;localhost:6379&quot;,
            Password: &quot;&quot;, // no password set
            DB:       0,  // use default DB
        })

        codec = &amp;cache.Codec{
            Redis: client,

            Marshal: func(v interface{}) ([]byte, error) {
                return msgpack.Marshal(v)
            },
            Unmarshal: func(b []byte, v interface{}) error {
                return msgpack.Unmarshal(b, v)
            },
        }
    })                         
    return codec            
}        

###Set key using codec instance
package setter

import (                                         
    &quot;github.com/Me/myapp/singleton&quot;  
    &quot;sync&quot;                              
)                                       
                                    
func Set(keys []string, vals []SomeObj, wg *sync.WaitGroup){
    for i, k := range keys {            
        wg.Add(1)
        // singleton is thread safe and could be used with goroutines                       
        go func() {                     
            codec := single.GetInstance()

            codec.Set(&amp;cache.Item{
                Key:        k,
                Object:     vals[i],
                Expiration: time.Hour,
            })
            wg.Done()                   
        }()                             
    }                                   
}                                       

Get object using the same codec instance

package getter                           
                                    
import (                                         
    &quot;github.com/Me/myapp/singleton&quot;  
    &quot;sync&quot;                              
)                                       

func Set(keys []string, wg *sync.WaitGroup) chan SomeObj {
    wanted_objs := make(chan *SomeObj)
    for i, k := range keys {            
        wg.Add(1)
        // singleton is thread safe and could be used with goroutines                       
        go func() {                     
            codec := singleton.GetInstance()
            wanted := new(SomeObj)
            if err := codec.Get(key, wanted); err == nil {
                wanted_objs &lt;- wanted
            }
        }()
    }
    return wanted_objs
}

huangapple
  • 本文由 发表于 2016年12月30日 15:42:38
  • 转载请务必保留本文链接:https://go.coder-hub.com/41392558.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定