Merge remote-tracking branch 'origin/pr/15'

This commit is contained in:
Noah Watkins 2016-03-26 11:52:02 -07:00
commit 8c0703f5e2
2 changed files with 120 additions and 1 deletions

View File

@ -547,3 +547,75 @@ func (ioctx *IOContext) CleanOmap(oid string) error {
return GetRadosError(int(ret))
}
type Iter struct {
ctx C.rados_list_ctx_t
err error
entry string
}
type IterToken uint32
// Return a Iterator object that can be used to list the object names in the current pool
func (ioctx *IOContext) Iter() (*Iter, error) {
iter := Iter{}
if cerr := C.rados_objects_list_open(ioctx.ioctx, &iter.ctx); cerr < 0 {
return nil, GetRadosError(cerr)
}
return &iter, nil
}
// Returns a token marking the current position of the iterator. To be used in combination with Iter.Seek()
func (iter *Iter) Token() IterToken {
return IterToken(C.rados_objects_list_get_pg_hash_position(iter.ctx))
}
func (iter *Iter) Seek(token IterToken) {
C.rados_objects_list_seek(iter.ctx, C.uint32_t(token))
}
// Next retrieves the next object name in the pool/namespace iterator.
// Upon a successful invocation (return value of true), the Value method should
// be used to obtain the name of the retrieved object name. When the iterator is
// exhausted, Next returns false. The Err method should used to verify whether the
// end of the iterator was reached, or the iterator received an error.
//
// Example:
// iter := pool.Iter()
// defer iter.Close()
// for iter.Next() {
// fmt.Printf("%v\n", iter.Value())
// }
// return iter.Err()
//
func (iter *Iter) Next() bool {
var c_entry *C.char
if cerr := C.rados_objects_list_next(iter.ctx, &c_entry, nil); cerr < 0 {
iter.err = GetRadosError(cerr)
return false
}
iter.entry = C.GoString(c_entry)
return true
}
// Returns the current value of the iterator (object name), after a successful call to Next.
func (iter *Iter) Value() string {
if iter.err != nil {
return ""
}
return iter.entry
}
// Checks whether the iterator has encountered an error.
func (iter *Iter) Err() error {
if iter.err == RadosErrorNotFound {
return nil
}
return iter.err
}
// Closes the iterator cursor on the server. Be aware that iterators are not closed automatically
// at the end of iteration.
func (iter *Iter) Close() {
C.rados_objects_list_close(iter.ctx)
}

View File

@ -492,7 +492,7 @@ func TestMonCommand(t *testing.T) {
conn.Shutdown()
}
func TestObjectIterator(t *testing.T) {
func TestObjectListObjects(t *testing.T) {
conn, _ := rados.NewConn()
conn.ReadDefaultConfigFile()
conn.Connect()
@ -533,6 +533,53 @@ func TestObjectIterator(t *testing.T) {
assert.Equal(t, objectList, createdList)
}
func TestObjectIterator(t *testing.T) {
conn, _ := rados.NewConn()
conn.ReadDefaultConfigFile()
conn.Connect()
poolname := GetUUID()
err := conn.MakePool(poolname)
assert.NoError(t, err)
ioctx, err := conn.OpenIOContext(poolname)
assert.NoError(t, err)
objectList := []string{}
iter, err := ioctx.Iter()
assert.NoError(t, err)
for iter.Next() {
objectList = append(objectList, iter.Value())
}
iter.Close()
assert.NoError(t, iter.Err())
assert.True(t, len(objectList) == 0)
createdList := []string{}
for i := 0; i < 200; i++ {
oid := GetUUID()
bytes_in := []byte("input data")
err = ioctx.Write(oid, bytes_in, 0)
assert.NoError(t, err)
createdList = append(createdList, oid)
}
assert.True(t, len(createdList) == 200)
iter, err = ioctx.Iter()
assert.NoError(t, err)
for iter.Next() {
objectList = append(objectList, iter.Value())
}
iter.Close()
assert.NoError(t, iter.Err())
assert.Equal(t, len(objectList), len(createdList))
sort.Strings(objectList)
sort.Strings(createdList)
assert.Equal(t, objectList, createdList)
}
func TestNewConnWithUser(t *testing.T) {
_, err := rados.NewConnWithUser("admin")
assert.Equal(t, err, nil)