예제 #1
0
func (self *ReplicaClient) Get(key string, value *string) error {
	newkey := colon.Escape(self.name) + "::" + key + "valu" // <- key should escape as well! NVM

	var mylist trib.List
	mylist.L = make([]string, 0)
	// get the list of logs of the key
	for index, ad := range self.addr {
		tempclient := &client{ad}
		err1 := tempclient.ListGet(newkey, &mylist)
		if err1 == nil {
			break
		} else if index < len(self.addr)-1 {
			continue
		} else {
			return err1
		}
	}

	s := ""
	if len(mylist.L) == 0 {
		*value = s
		return nil
	}

	// add dedup
	mylist.L = removeDuplicates(mylist.L)

	loglist := make(LogSlice, len(mylist.L))

	// decode the logs
	for index, l := range mylist.L {
		loglist[index] = DecodeLog(l)
	}

	sort.Sort(loglist)

	index := len(loglist) - 1
	result := loglist[index].Val
	*value = result
	return nil
}
예제 #2
0
func (self *client) ListGet(key string, list *trib.List) error {
	// connect to the server
	conn, e := rpc.DialHTTP("tcp", self.addr)
	if e != nil {
		return e
	}

	// perform the call
	list.L = nil
	e = conn.Call("Storage.ListGet", key, list)
	if e != nil {
		conn.Close()
		return e
	}
	if list.L == nil {
		list.L = []string{}
	}

	// close the connection
	return conn.Close()
}
예제 #3
0
func (self *Storage) ListGet(key string, ret *trib.List) error {
	self.listLock.Lock()
	defer self.listLock.Unlock()

	if lst, found := self.lists[key]; !found {
		ret.L = []string{}
	} else {
		ret.L = make([]string, 0, lst.Len())
		for i := lst.Front(); i != nil; i = i.Next() {
			ret.L = append(ret.L, i.Value.(string))
		}
	}

	if Logging {
		log.Printf("ListGet(%q) => %d", key, len(ret.L))
		for i, s := range ret.L {
			log.Printf("  %d: %q", i, s)
		}
	}

	return nil
}
예제 #4
0
func (self *FrontServer) Following(who string) ([]string, error) {
	_, e := self.findUser(who)
	if e != nil {
		return nil, e
	}
	client := self.storageClient.Bin(who)
	followingUsers := trib.List{L: []string{}}
	if e := client.ListGet("Followings", &followingUsers); e != nil {
		return nil, e
	}

	followingUsers.L = removeDuplicates(followingUsers.L)
	return followingUsers.L, nil
}
예제 #5
0
func (self *Storage) ListKeys(p *trib.Pattern, r *trib.List) error {
	self.listLock.Lock()
	defer self.listLock.Unlock()

	ret := make([]string, 0, len(self.lists))
	for k := range self.lists {
		if p.Match(k) {
			ret = append(ret, k)
		}
	}

	r.L = ret

	if Logging {
		log.Printf("ListKeys(%q, %q) => %d", p.Prefix, p.Suffix, len(r.L))
		for i, s := range r.L {
			log.Printf("  %d: %q", i, s)
		}
	}

	return nil
}
예제 #6
0
func (self *FrontServer) Home(user string) ([]*trib.Trib, error) {
	self.lock.Lock()
	defer self.lock.Unlock()
	_, e := self.findUser(user)
	if e != nil {
		return nil, e
	}
	followingUsers, e := self.Following(user)
	if e != nil {
		return nil, e
	}
	followingUsers = append(followingUsers, user)
	wholeRawList := trib.List{L: []string{}}
	for _, followed := range followingUsers {
		client := self.storageClient.Bin(followed)
		rawList := trib.List{L: []string{}}
		if e := client.ListGet("Tribs", &rawList); e != nil {
			return nil, e
		}
		wholeRawList.L = append(wholeRawList.L, rawList.L...)
	}
	size := len(wholeRawList.L)
	tribList := make([]*trib.Trib, size)
	for i, entry := range wholeRawList.L {
		if e := json.Unmarshal([]byte(entry), &tribList[i]); e != nil {
			return nil, e
		}
	}
	// sort by logic clock
	sort.Sort(byClock(tribList))
	l := len(tribList)
	start := 0
	if l > trib.MaxTribFetch {
		start = l - trib.MaxTribFetch
	}

	return tribList[start:], nil
}
예제 #7
0
func (self *ReplicaClient) ListKeys(p *trib.Pattern, list *trib.List) error {
	// escape colon
	binName := colon.Escape(self.name)
	p.Prefix = binName + "::" + p.Prefix
	p.Suffix = p.Suffix + "list"

	// RPC call
	// get the list of logs of the key

	// a list used as temp storage
	tmpList := trib.List{make([]string, 0)}
	for index, ad := range self.addr {
		tempclient := &client{ad}
		err1 := tempclient.ListKeys(p, &tmpList)
		if err1 == nil {
			break
		} else if index < len(self.addr)-1 {
			continue
		} else {
			return err1
		}
	}

	blockCh := make(chan string, len(tmpList.L))
	for _, str := range tmpList.L {
		go func(str string) {
			tmpList2 := trib.List{make([]string, 0)}
			s1 := colon.Escape(self.name) + "::"
			s2 := "list"
			str = strings.TrimPrefix(str, s1)
			str = strings.TrimSuffix(str, s2)
			_ = self.ListGet(str, &tmpList2) // ignore this err?
			if len(tmpList2.L) != 0 {
				blockCh <- str
			} else {
				blockCh <- ""
			}
		}(str)
	}

	list.L = make([]string, 0, len(tmpList.L))
	for _ = range tmpList.L {
		result := <-blockCh
		if result != "" {
			list.L = append(list.L, result)
		}
	}

	// unescape and trim
	if len(list.L) > 0 {
		for i, str := range list.L {
			//str = colon.Unescape(str)
			s1 := colon.Escape(self.name) + "::"
			s2 := "valu"
			str = strings.TrimPrefix(str, s1)
			str = strings.TrimSuffix(str, s2)
			list.L[i] = str
		}
	}
	return nil
}
예제 #8
0
func (self *ReplicaClient) ListGet(key string, list *trib.List) error {

	newkey := colon.Escape(self.name) + "::" + key + "list"

	var mylist trib.List
	mylist.L = make([]string, 0)

	// get the list of logs of the key
	for index, ad := range self.addr {
		tempclient := &client{ad}
		err1 := tempclient.ListGet(newkey, &mylist)
		if err1 == nil {
			break
		} else if index < len(self.addr)-1 {
			continue
		} else {
			return err1
		}
	}

	if len(mylist.L) == 0 {
		list.L = make([]string, 0)
		return nil
	}

	// add dedup
	mylist.L = removeDuplicates(mylist.L)

	loglist := make(LogSlice, len(mylist.L))

	// decode the logs
	for index, l := range mylist.L {
		loglist[index] = DecodeLog(l)
	}

	sort.Sort(loglist)

	var templist trib.List
	//get the real list
	for _, log := range loglist {
		if log.Op == "append" {
			templist.L = append(templist.L, log.Val)
		} else { // remove?
			newList := trib.List{[]string{}}
			for _, entry := range templist.L {
				if log.Val != entry {
					newList.L = append(newList.L, entry)
				}
			}
			templist.L = newList.L
			/*i := 0
			for _, l := range templist.L{
				if l == log.Val {
					if i < len(templist.L) {
						templist.L = append(templist.L[:i], templist.L[i+1:]...)
					} else {
						templist.L = templist.L[:i]
					}
				} else {
					i++
				}
			}*/
		}
	}
	*list = templist
	return nil
}