コード例 #1
0
func (self redisCacheProvider) Pop(group string) (uint64, error) {
	if len(group) == 0 {
		errorMsg := fmt.Sprint("The group name is INVALID!")
		base.Logger().Errorln(errorMsg)
		return 0, errors.New(errorMsg)
	}
	rwSign := getRWSign(group)
	rwSign.RSet()
	defer rwSign.RUnset()
	conn := redisPool.Get()
	defer conn.Close()
	value, err := conn.Do("RPOP", group)
	if err != nil {
		errorMsg := fmt.Sprintf("Redis Error <RPOP %s>: %s\n ", group, err.Error())
		base.Logger().Error(errorMsg)
		return 0, errors.New(errorMsg)
	}
	if value == nil {
		errorMsg := fmt.Sprintf("Empty List! (group=%s)", group)
		return 0, &base.EmptyListError{errorMsg}
	}
	baValue := value.([]uint8)
	number, err := strconv.ParseUint(string(baValue), 10, 64)
	if err != nil {
		errorMsg := fmt.Sprintf("Converting Error (value=%s): %s\n ", value, err.Error())
		base.Logger().Error(errorMsg)
		return 0, errors.New(errorMsg)
	}
	return number, nil
}
コード例 #2
0
ファイル: server.go プロジェクト: hyper-carrot/go_idcenter
func main() {
	flag.Parse()
	http.HandleFunc("/id", doForId)
	base.Logger().Infof("Starting id center http server (port=%d)...\n", serverPort)
	err := http.ListenAndServe(":"+fmt.Sprintf("%d", serverPort), nil)
	if err != nil {
		base.Logger().Fatalln("Listen and serve error: ", err)
	} else {
		base.Logger().Infoln("The id center http server is started.")
	}
}
コード例 #3
0
ファイル: server.go プロジェクト: hyper-carrot/go_idcenter
func pushResponse(bufrw *bufio.ReadWriter, content interface{}, group string, op string) {
	literals := fmt.Sprintf("%v", content)
	_, err := bufrw.Write([]byte(literals))
	if err == nil {
		err = bufrw.Flush()
	}
	if err != nil {
		base.Logger().Errorf("Pushing response error (content=%v, group=%s, op=%s): %s\n", literals, group, op, err)
	} else {
		base.Logger().Errorf("The response '%v' has been pushed. (group=%s, op=%s)\n", literals, group, op)
	}
}
コード例 #4
0
ファイル: manager.go プロジェクト: hyper-carrot/go_idcenter
func (self *IdCenterManager) Clear(group string) (bool, error) {
	defer func() {
		if err := recover(); err != nil {
			debug.PrintStack()
			errorMsg := fmt.Sprintf("Occur FATAL error when clear (group=%v): %s", group, err)
			base.Logger().Fatalln(errorMsg)
		}
	}()
	storageProvider := self.getStorageProvider()
	spResult, spErr := storageProvider.Clear(group)
	cacheProvider := self.getCacheProvider()
	cpResult, cpErr := cacheProvider.Clear(group)
	if spErr != nil || cpErr != nil {
		var errorMsgBuffer bytes.Buffer
		errorMsgBuffer.WriteString("Clear Failing:")
		if spErr != nil {
			errorMsgBuffer.WriteString(fmt.Sprintf("%s: %s; ", reflect.TypeOf(storageProvider).Name(), spErr))
		}
		if cpErr != nil {
			errorMsgBuffer.WriteString(fmt.Sprintf("%s: %s; ", reflect.TypeOf(cacheProvider).Name(), cpErr))
		}
		errorMsgBuffer.WriteString("\n")
		return false, errors.New(errorMsgBuffer.String())
	}
	return (spResult && cpResult), nil
}
コード例 #5
0
ファイル: manager.go プロジェクト: hyper-carrot/go_idcenter
func RegisterProvider(provider base.Provider) error {
	defer func() {
		if err := recover(); err != nil {
			debug.PrintStack()
			errorMsg := fmt.Sprintf("Occur FATAL error when register provider (provider=%v): %s", provider, err)
			base.Logger().Fatalln(errorMsg)
		}
	}()
	if provider == nil {
		panicMsg := "IdCenter: The provider is nil!\n"
		base.Logger().Fatal(panicMsg)
		panic(panicMsg)
	}
	name := provider.Name()
	if len(name) == 0 {
		panicMsg := "IdCenter: The name of provider is nil!\n"
		base.Logger().Fatal(panicMsg)
		panic(panicMsg)
	}
	switch t := interface{}(provider).(type) {
	case base.CacheProvider:
		if _, contains := cacheProviderMap[name]; contains {
			errorMsg := fmt.Sprintf("IdCenter: Repetitive cache provider name '%s'!\n", name)
			base.Logger().Error(errorMsg)
			return errors.New(errorMsg)
		}
		cp, ok := interface{}(provider).(base.CacheProvider)
		if !ok {
			errorMsg := fmt.Sprintf("IdCenter: Incorrect cache provider type! (name '%s')\n", name)
			base.Logger().Error(errorMsg)
			return errors.New(errorMsg)
		}
		cacheProviderMap[name] = cp
	case base.StorageProvider:
		if _, contains := storageProviderMap[name]; contains {
			errorMsg := fmt.Sprintf("IdCenter: Repetitive storage provider name '%s'!\n", name)
			base.Logger().Error(errorMsg)
			return errors.New(errorMsg)
		}
		sp, ok := interface{}(provider).(base.StorageProvider)
		if !ok {
			errorMsg := fmt.Sprintf("IdCenter: Incorrect cache provider type! (name '%s')\n", name)
			base.Logger().Error(errorMsg)
			return errors.New(errorMsg)
		}
		storageProviderMap[name] = sp
	default:
		panicMsg := fmt.Sprintf("IdCenter: Unexpected Provider type '%v'! (name=%s)\n", t, name)
		base.Logger().Fatal(panicMsg)
		panic(panicMsg)
	}
	return nil
}
コード例 #6
0
ファイル: server.go プロジェクト: hyper-carrot/go_idcenter
func doForId(w http.ResponseWriter, r *http.Request) {
	hj, ok := w.(http.Hijacker)
	var errorMsg string
	if !ok {
		errorMsg = "The Web Server does not support Hijacking! "
		http.Error(w, errorMsg, http.StatusInternalServerError)
		base.Logger().Errorf(errorMsg)
		return
	}
	conn, bufrw, err := hj.Hijack()
	if err != nil {
		errorMsg = "Internal error!"
		http.Error(w, errorMsg, http.StatusInternalServerError)
		base.Logger().Errorf(errorMsg+" Hijacking Error: %s\n", err)
		return
	}
	defer conn.Close()
	r.ParseForm()
	group := r.FormValue("group")
	op := r.FormValue("op")
	base.Logger().Infof("Receive a request for id (group=%s, op=%s))...\n", group, op)
	var respContent interface{}
	if op == "clear" {
		result, err := idCenterManager.Clear(group)
		if err != nil {
			errorMsg = fmt.Sprintf("Clear id group error: %s", err)
			base.Logger().Errorln(errorMsg)
		}
		respContent = interface{}(result)
	} else {
		currentId, err := idCenterManager.GetId(group)
		if err != nil {
			errorMsg = fmt.Sprintf("Get id error: %s", err)
			base.Logger().Errorln(errorMsg)
		}
		respContent = interface{}(currentId)
	}
	if len(errorMsg) > 0 {
		respContent = interface{}("Internal error!")
	}
	pushResponse(bufrw, respContent, group, op)
}
コード例 #7
0
func (self redisCacheProvider) Clear(group string) (bool, error) {
	if len(group) == 0 {
		errorMsg := fmt.Sprint("The group name is INVALID!")
		base.Logger().Errorln(errorMsg)
		return false, errors.New(errorMsg)
	}
	rwSign := getRWSign(group)
	rwSign.RSet()
	defer rwSign.RUnset()
	conn := redisPool.Get()
	defer conn.Close()
	effectedKeys, err := redis.Int(conn.Do("DEL", group))
	if err != nil {
		errorMsg := fmt.Sprintf("Redis Error <DEL %s>: %s\n ", group, err.Error())
		base.Logger().Error(errorMsg)
		return false, errors.New(errorMsg)
	}
	base.Logger().Infof("Redis Cache Provider: The group '%s' is cleared. (affectedKeys=%v)", group, (effectedKeys > 0))
	return true, nil
}
コード例 #8
0
func (self redisCacheProvider) BuildList(group string, begin uint64, end uint64) (bool, error) {
	if len(group) == 0 {
		errorMsg := fmt.Sprint("The group name is INVALID!")
		base.Logger().Errorln(errorMsg)
		return false, errors.New(errorMsg)
	}
	rwSign := getRWSign(group)
	rwSign.Set()
	defer rwSign.Unset()
	if (begin <= 0) || (end <= 0) || (begin >= end) {
		errorMsg := fmt.Sprintf("Invalid Parameter(s)! (begin=%d, end=%d)\n", begin, end)
		base.Logger().Error(errorMsg)
		return false, errors.New(errorMsg)
	}
	conn := redisPool.Get()
	defer conn.Close()
	exists, err := redis.Bool(conn.Do("EXISTS", group))
	if err != nil {
		errorMsg := fmt.Sprintf("Redis Error <EXISTS %s>: %s\n ", group, err.Error())
		base.Logger().Errorf(errorMsg)
		return false, errors.New(errorMsg)
	}
	if exists {
		effectedKeys, err := redis.Int(conn.Do("DEL", group))
		if err != nil {
			errorMsg := fmt.Sprintf("Redis Error <DEL %s>: %s\n ", group, err.Error())
			base.Logger().Error(errorMsg)
			return false, errors.New(errorMsg)
		}
		if effectedKeys < 1 {
			warningMsg := fmt.Sprintf("Redis warning <DEL %s>: seemingly failed.\n ", group)
			base.Logger().Warn(warningMsg)
		}
	}
	for i := begin; i < end; i++ {
		length, err := redis.Int(conn.Do("LPUSH", group, i))
		if err != nil {
			errorMsg := fmt.Sprintf("Redis Error <LPUSH %s %d> (total_length=%d): %s\n ", group, i, length, err.Error())
			base.Logger().Error(errorMsg)
			return false, errors.New(errorMsg)
		}
	}
	base.Logger().Infof("The list of group '%s' is builded. (begin=%d, end=%d)\n", group, begin, end)
	return true, nil

}
コード例 #9
0
func initializeForCacheProvider(parameter RedisParameter) error {
	redisServerAddr := fmt.Sprintf("%v:%v", parameter.Ip, parameter.Port)
	base.Logger().Infof("Initialize redis cache provider (parameter=%v)...", parameter)
	redisPool = &redis.Pool{
		MaxIdle:     int(parameter.PoolSize),
		IdleTimeout: 240 * time.Second,
		Dial: func() (redis.Conn, error) {
			c, err := redis.Dial("tcp", redisServerAddr)
			if err != nil {
				return nil, err
			}
			if len(parameter.Password) > 0 {
				if _, err := c.Do("AUTH", parameter.Password); err != nil {
					c.Close()
					return nil, err
				}
			}
			return c, err
		},
	}
	rwSignMap = make(map[string]*go_lib.RWSign)
	iRedisCacheProvider = &redisCacheProvider{parameter.Name}
	return nil
}
コード例 #10
0
ファイル: manager.go プロジェクト: hyper-carrot/go_idcenter
func UnregisterProvider(provider base.Provider) {
	defer func() {
		if err := recover(); err != nil {
			debug.PrintStack()
			errorMsg := fmt.Sprintf("Occur FATAL error when unregister provider (provider=%v): %s", provider, err)
			base.Logger().Fatalln(errorMsg)
		}
	}()
	if provider == nil {
		panicMsg := "IdCenter: The provider is nil!\n"
		base.Logger().Fatal(panicMsg)
		panic(panicMsg)
	}
	name := provider.Name()
	if len(name) == 0 {
		panicMsg := "IdCenter: The name of provider is nil!\n"
		base.Logger().Fatal(panicMsg)
		panic(panicMsg)
	}
	switch t := interface{}(provider).(type) {
	case base.CacheProvider:
		_, contains := cacheProviderMap[name]
		if contains {
			delete(cacheProviderMap, name)
		} else {
			base.Logger().Warnf("IdCenter: The cache Provider named '%s' is NOTEXISTENT!\n", name)
		}
	case base.StorageProvider:
		_, contains := storageProviderMap[name]
		if contains {
			delete(storageProviderMap, name)
		} else {
			base.Logger().Warnf("IdCenter: The storage Provider named '%s' is NOTEXISTENT!\n", name)
		}
	default:
		panicMsg := fmt.Sprintf("IdCenter: Unexpected Provider type '%v'! (name=%s)\n", t, name)
		base.Logger().Fatal(panicMsg)
		panic(panicMsg)
	}
	return
}
コード例 #11
0
ファイル: manager.go プロジェクト: hyper-carrot/go_idcenter
func (self *IdCenterManager) GetId(group string) (uint64, error) {
	defer func() {
		if err := recover(); err != nil {
			debug.PrintStack()
			errorMsg := fmt.Sprintf("Occur FATAL error when get id (group=%v): %s", group, err)
			base.Logger().Fatalln(errorMsg)
		}
	}()
	cacheProvider := self.getCacheProvider()
	storageProvider := self.getStorageProvider()
	id, err := cacheProvider.Pop(group)
	if err != nil {
		switch err.(type) {
		case *base.EmptyListError:
			warningMsg := fmt.Sprintf("Warning: The list of group '%s' is empty.", group)
			base.Logger().Warn(warningMsg)
		default:
			errorMsg := fmt.Sprintf("Occur error when pop id for group '%s': %s\n", group, err.Error())
			base.Logger().Error(errorMsg)
			return 0, err
		}
	}
	if id > 0 {
		return id, nil
	}
	base.Logger().Infof("Prepare check & build id list for group '%s'...\n", group)
	groupInfo, err := storageProvider.Get(group)
	if err != nil {
		errorMsg := fmt.Sprintf("Occur error when get group (name='%s') info : %s\n", group, err.Error())
		base.Logger().Error(errorMsg)
		return 0, err
	}
	if groupInfo == nil {
		currentStart := self.Start
		if currentStart <= 0 {
			currentStart = DEFAULT_START
		}
		currentStep := self.Step
		if currentStep <= 0 {
			currentStep = DEFAULT_STEP
		}
		ok, err := storageProvider.BuildInfo(group, currentStart, currentStep)
		if err != nil {
			errorMsg := fmt.Sprintf("Occur error when initialize group '%s': %s", group, err.Error())
			base.Logger().Errorln(errorMsg)
			return 0, err
		}
		if !ok {
			warnMsg := fmt.Sprintf("Building group info is FAILING. Maybe the group already exists. (group=%v)", group)
			base.Logger().Warnln(warnMsg)
		}
	}
	idRange, err := storageProvider.Propel(group)
	if err != nil {
		errorMsg := fmt.Sprintf("Occur error when propel id for group '%s': %s\n", group, err.Error())
		base.Logger().Error(errorMsg)
		return 0, err
	}
	currentBegin := idRange.Begin
	currentEnd := idRange.End
	ok, err := cacheProvider.BuildList(group, currentBegin, currentEnd)
	if err != nil {
		errorMsg := fmt.Sprintf("Occur error when build id list for group '%s': %s\n", group, err.Error())
		base.Logger().Error(errorMsg)
		return 0, err
	}
	if !ok {
		warnMsg := fmt.Sprintf("Building id list is FAILING. (group=%v)", group)
		base.Logger().Warnln(warnMsg)
	}
	id, err = cacheProvider.Pop(group)
	if err != nil {
		switch err.(type) {
		case *base.EmptyListError:
			warningMsg := fmt.Sprintf("Warning: The list of group '%s' is empty.", group)
			base.Logger().Warn(warningMsg)
		default:
			errorMsg := fmt.Sprintf("Occur error when pop id for group '%s': %s\n", group, err.Error())
			base.Logger().Error(errorMsg)
			return 0, err
		}
	}
	return id, nil
}
コード例 #12
0
ファイル: server.go プロジェクト: hyper-carrot/go_idcenter
func init() {
	flag.IntVar(&serverPort, "port", 9092, "the server (http listen) port")
	iConfig = go_lib.Config{Path: base.CONFIG_FILE_NAME}
	err := iConfig.ReadConfig(false)
	if err != nil {
		errorMsg := fmt.Sprintf("Config Loading error: %s", err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	configRedisPort := iConfig.Dict["redis_server_port"]
	redisPort, err := strconv.Atoi(configRedisPort)
	if err != nil {
		errorMsg := fmt.Sprintf("The redis server port '%v' is INVALID! Error: %s", configRedisPort, err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	configRedisPoolSize := iConfig.Dict["redis_server_pool_size"]
	redisPoolSize, err := strconv.Atoi(configRedisPoolSize)
	if err != nil {
		errorMsg := fmt.Sprintf("The redis server pool size '%v' is INVALID! Error: %s", redisPoolSize, err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	cacheParameter := provider.RedisParameter{
		Name:     "Redis Cache Provider",
		Ip:       iConfig.Dict["redis_server_ip"],
		Port:     redisPort,
		Password: iConfig.Dict["redis_server_password"],
		PoolSize: uint16(redisPoolSize),
	}
	rcp := manager.NewRedisCacheProvider(cacheParameter)
	err = manager.RegisterProvider(interface{}(rcp).(base.Provider))
	if err != nil {
		errorMsg := fmt.Sprintf("Redis Cache provider register error: %s", err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	configMysqlPort := iConfig.Dict["mysql_server_port"]
	mysqlPort, err := strconv.Atoi(configMysqlPort)
	if err != nil {
		errorMsg := fmt.Sprintf("The mysql server port '%v' is INVALID! Error: %s", configMysqlPort, err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	configMysqlPoolSize := iConfig.Dict["mysql_server_pool_size"]
	mysqlPoolSize, err := strconv.Atoi(configMysqlPoolSize)
	if err != nil {
		errorMsg := fmt.Sprintf("The mysql server pool size '%v' is INVALID! Error: %s", configMysqlPoolSize, err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	storageParameter := provider.MysqlParameter{
		Name:     "Mysql Storage Provider",
		Ip:       iConfig.Dict["redis_server_ip"],
		Port:     mysqlPort,
		DbName:   iConfig.Dict["mysql_server_db_name"],
		User:     iConfig.Dict["mysql_server_user"],
		Password: iConfig.Dict["mysql_server_password"],
		PoolSize: uint16(mysqlPoolSize),
	}
	msp := manager.NewMysqlStorageProvider(storageParameter)
	err = manager.RegisterProvider(interface{}(msp).(base.Provider))
	if err != nil {
		errorMsg := fmt.Sprintf("MySQL Storage provider register error: %s", err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	configIdStart := iConfig.Dict["id_start"]
	idStart, err := strconv.Atoi(configIdStart)
	if err != nil {
		errorMsg := fmt.Sprintf("The start number of id '%v' is INVALID! Error: %s", configIdStart, err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	configIdStep := iConfig.Dict["id_step"]
	idStep, err := strconv.Atoi(configIdStep)
	if err != nil {
		errorMsg := fmt.Sprintf("The step number of id '%v' is INVALID! Error: %s", configIdStep, err)
		base.Logger().Fatalf(errorMsg)
		panic(errors.New(errorMsg))
	}
	idCenterManager = manager.IdCenterManager{
		CacheProviderName:   rcp.Name(),
		StorageProviderName: msp.Name(),
		Start:               uint64(idStart),
		Step:                uint32(idStep),
	}
}