You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@lucy.apache.org by ma...@apache.org on 2015/12/28 21:10:55 UTC

[08/16] lucy git commit: Tune and test Go bindings for IndexReader.

Tune and test Go bindings for IndexReader.


Project: http://git-wip-us.apache.org/repos/asf/lucy/repo
Commit: http://git-wip-us.apache.org/repos/asf/lucy/commit/fe25122f
Tree: http://git-wip-us.apache.org/repos/asf/lucy/tree/fe25122f
Diff: http://git-wip-us.apache.org/repos/asf/lucy/diff/fe25122f

Branch: refs/heads/master
Commit: fe25122fadcb9115ddd0810e9986898048e5303e
Parents: c1cdb4d
Author: Marvin Humphrey <ma...@rectangular.com>
Authored: Tue Dec 8 20:33:58 2015 -0800
Committer: Marvin Humphrey <ma...@rectangular.com>
Committed: Thu Dec 10 18:22:54 2015 -0800

----------------------------------------------------------------------
 go/build.go            |  5 +++
 go/lucy/index.go       | 47 +++++++++++++++++++++++++++
 go/lucy/index_test.go  | 78 +++++++++++++++++++++++++++++++++++----------
 go/lucy/search_test.go |  9 +++---
 4 files changed, 118 insertions(+), 21 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/lucy/blob/fe25122f/go/build.go
----------------------------------------------------------------------
diff --git a/go/build.go b/go/build.go
index 801654a..fc104dc 100644
--- a/go/build.go
+++ b/go/build.go
@@ -191,6 +191,11 @@ func specClasses(parcel *cfc.Parcel) {
 	dataReaderBinding.SpecMethod("Close", "Close() error")
 	dataReaderBinding.Register()
 
+	ixReaderBinding := cfc.NewGoClass(parcel, "Lucy::Index::IndexReader")
+	ixReaderBinding.SpecMethod("Seg_Readers", "SegReaders() []SegReader")
+	ixReaderBinding.SpecMethod("Offsets", "Offsets() []int32")
+	ixReaderBinding.SpecMethod("Obtain", "Obtain(string) (DataReader, error)")
+	ixReaderBinding.Register()
 
 	docReaderBinding := cfc.NewGoClass(parcel, "Lucy::Index::DocReader")
 	docReaderBinding.SpecMethod("", "ReadDoc(int32, interface{}) error")

http://git-wip-us.apache.org/repos/asf/lucy/blob/fe25122f/go/lucy/index.go
----------------------------------------------------------------------
diff --git a/go/lucy/index.go b/go/lucy/index.go
index 18d5ba1..67d4b47 100644
--- a/go/lucy/index.go
+++ b/go/lucy/index.go
@@ -18,6 +18,7 @@ package lucy
 
 /*
 #include "Lucy/Index/Indexer.h"
+#include "Lucy/Index/IndexReader.h"
 #include "Lucy/Index/DataReader.h"
 #include "Lucy/Index/DocReader.h"
 #include "Lucy/Index/IndexManager.h"
@@ -482,3 +483,49 @@ func (d *DocReaderIMP) FetchDoc(docID int32) (doc HitDoc, err error) {
 	})
 	return doc, err
 }
+
+func OpenIndexReader(index interface{}, snapshot Snapshot, manager IndexManager) (retval IndexReader, err error) {
+	err = clownfish.TrapErr(func() {
+		indexC := (*C.cfish_Obj)(clownfish.GoToClownfish(index, unsafe.Pointer(C.CFISH_OBJ), false))
+		defer C.cfish_decref(unsafe.Pointer(indexC))
+		snapshotC := (*C.lucy_Snapshot)(clownfish.UnwrapNullable(snapshot))
+		managerC := (*C.lucy_IndexManager)(clownfish.UnwrapNullable(manager))
+		cfObj := C.lucy_IxReader_open(indexC, snapshotC, managerC)
+		retval = clownfish.WRAPAny(unsafe.Pointer(cfObj)).(IndexReader)
+	})
+	return retval, err
+}
+
+func (r *IndexReaderIMP) SegReaders() []SegReader {
+	self := (*C.lucy_IndexReader)(clownfish.Unwrap(r, "r"))
+	retvalCF := C.LUCY_IxReader_Seg_Readers(self);
+	defer C.cfish_decref(unsafe.Pointer(retvalCF))
+	if retvalCF == nil {
+		return nil
+	}
+	size := C.CFISH_Vec_Get_Size(retvalCF)
+	retval := make([]SegReader, int(size))
+	for i := 0; i < int(size); i++ {
+		elem := unsafe.Pointer(C.CFISH_Vec_Fetch(retvalCF, C.size_t(i)))
+		retval[i] = clownfish.ToGo(unsafe.Pointer(C.cfish_incref(elem))).(SegReader)
+	}
+	return retval
+}
+
+func (r *IndexReaderIMP) Offsets() []int32 {
+	self := (*C.lucy_IndexReader)(clownfish.Unwrap(r, "r"))
+	retvalCF := C.LUCY_IxReader_Offsets(self)
+	defer C.cfish_decref(unsafe.Pointer(retvalCF))
+	return i32ArrayToSlice(retvalCF)
+}
+
+func (r *IndexReaderIMP) Obtain(api string) (retval DataReader, err error) {
+	err = clownfish.TrapErr(func() {
+		self := (*C.lucy_IndexReader)(clownfish.Unwrap(r, "r"))
+		apiC := (*C.cfish_String)(clownfish.GoToClownfish(api, unsafe.Pointer(C.CFISH_STRING), false))
+		defer C.cfish_decref(unsafe.Pointer(apiC))
+		retvalCF := C.LUCY_IxReader_Obtain(self, apiC)
+		retval = clownfish.WRAPAny(unsafe.Pointer(C.cfish_incref(unsafe.Pointer(retvalCF)))).(DataReader)
+	})
+	return retval, err
+}

http://git-wip-us.apache.org/repos/asf/lucy/blob/fe25122f/go/lucy/index_test.go
----------------------------------------------------------------------
diff --git a/go/lucy/index_test.go b/go/lucy/index_test.go
index 8934167..e44bb09 100644
--- a/go/lucy/index_test.go
+++ b/go/lucy/index_test.go
@@ -400,9 +400,9 @@ func TestSortCacheMisc(t *testing.T) {
 	indexer.AddDoc(make(map[string]interface{}))
 	indexer.Commit()
 
-	searcher, _ := OpenIndexSearcher(folder)
-	segReaders := searcher.GetReader().SegReaders()
-	sortReader := segReaders[0].(SegReader).Obtain("Lucy::Index::SortReader").(SortReader)
+	ixReader, _ := OpenIndexReader(folder, nil, nil)
+	segReaders := ixReader.SegReaders()
+	sortReader := segReaders[0].Fetch("Lucy::Index::SortReader").(SortReader)
 	sortCache := sortReader.fetchSortCache("content")
 
 	if card := sortCache.GetCardinality(); card != 4 {
@@ -646,9 +646,9 @@ func TestInverterMisc(t *testing.T) {
 // Use SegLexicon to air out the Lexicon interface.
 func TestLexiconBasics(t *testing.T) {
 	folder := createTestIndex("a", "b", "c")
-	searcher, _ := OpenIndexSearcher(folder)
-	segReaders := searcher.GetReader().SegReaders()
-	lexReader := segReaders[0].(SegReader).Obtain("Lucy::Index::LexiconReader").(LexiconReader)
+	ixReader, _ := OpenIndexReader(folder, nil, nil)
+	segReaders := ixReader.SegReaders()
+	lexReader := segReaders[0].Fetch("Lucy::Index::LexiconReader").(LexiconReader)
 	segLex := lexReader.Lexicon("content", nil).(Lexicon)
 	if field := segLex.getField(); field != "content" {
 		t.Errorf("getField: %s", field)
@@ -678,9 +678,9 @@ func TestLexiconBasics(t *testing.T) {
 
 func TestPostingListBasics(t *testing.T) {
 	folder := createTestIndex("c", "b b b", "a", "b",)
-	searcher, _ := OpenIndexSearcher(folder)
-	segReaders := searcher.GetReader().SegReaders()
-	pListReader := segReaders[0].(SegReader).Obtain("Lucy::Index::PostingListReader").(PostingListReader)
+	ixReader, _ := OpenIndexReader(folder, nil, nil)
+	segReaders := ixReader.SegReaders()
+	pListReader := segReaders[0].Fetch("Lucy::Index::PostingListReader").(PostingListReader)
 	pList := pListReader.PostingList("content", nil)
 	pList.Seek("b")
 	if docFreq := pList.GetDocFreq(); docFreq != 2 {
@@ -746,16 +746,62 @@ func runDataReaderCommon(t *testing.T, reader DataReader, runAggregator bool) {
 
 func TestIndexReaderMisc(t *testing.T) {
 	folder := createTestIndex("a", "b", "c")
-	searcher, _ := OpenIndexSearcher(folder)
-	reader := searcher.GetReader()
+	reader, _ := OpenIndexReader(folder, nil, nil)
+	if segReaders := reader.SegReaders(); len(segReaders) != 1 {
+		t.Errorf("SegReaders: %#v", segReaders)
+	}
+	if offsets := reader.Offsets(); offsets[0] != 0 {
+		t.Errorf("Offsets: %#v", offsets)
+	}
+	if got, err := reader.Obtain("Lucy::Index::DocReader"); got == nil || err != nil {
+		t.Errorf("Obtain should succeed for DocReader: %#v, %v", got, err)
+	}
+	if got, err := reader.Obtain("Nope"); got != nil || err == nil {
+		t.Errorf("Obtain should fail for non-existent API name: %v", err)
+	}
+	if got := reader.Fetch("Lucy::Index::DocReader"); got == nil  {
+		t.Errorf("Fetch should succeed for DocReader")
+	}
+	if got := reader.Fetch("Nope"); got != nil {
+		t.Errorf("Fetch should return nil for non-existent API name: %v", got)
+	}
+	if got := reader.DocMax(); got != 3 {
+		t.Errorf("DocMax: %d", got);
+	}
+	if got := reader.DocCount(); got != 3 {
+		t.Errorf("DocCount: %d", got);
+	}
+	if got := reader.DelCount(); got != 0 {
+		t.Errorf("DelCount: %d", got);
+	}
 	runDataReaderCommon(t, reader, false)
 }
 
+func TestIndexReaderOpen(t *testing.T) {
+	folder := createTestIndex("a", "b", "c")
+	if got, err := OpenIndexReader(folder, nil, nil); got == nil || err != nil {
+		t.Errorf("nil Snapshot and IndexManager: %v", err)
+	}
+	snapshot := NewSnapshot()
+	snapshot.ReadFile(folder, "")
+	if got, err := OpenIndexReader(folder, snapshot, nil); got == nil || err != nil {
+		t.Errorf("With Snapshot: %v", err)
+	}
+	manager := NewIndexManager("", nil)
+	manager.SetFolder(folder)
+	if got, err := OpenIndexReader(folder, nil, manager); got == nil || err != nil {
+		t.Errorf("With IndexManager: %v", err)
+	}
+	if got, err := OpenIndexReader("no-index-here", nil, nil); got != nil || err == nil {
+		t.Errorf("Non-existent index path")
+	}
+}
+
 func TestDefaultDocReaderMisc(t *testing.T) {
 	folder := createTestIndex("a", "b", "c")
-	searcher, _ := OpenIndexSearcher(folder)
-	segReaders := searcher.GetReader().SegReaders()
-	reader := segReaders[0].(SegReader).Obtain("Lucy::Index::DocReader").(DefaultDocReader)
+	ixReader, _ := OpenIndexReader(folder, nil, nil)
+	segReaders := ixReader.SegReaders()
+	reader := segReaders[0].Fetch("Lucy::Index::DocReader").(DefaultDocReader)
 	doc := make(map[string]interface{})
 	if err := reader.ReadDoc(2, doc); err != nil {
 		t.Errorf("ReadDoc: %v", err)
@@ -765,8 +811,8 @@ func TestDefaultDocReaderMisc(t *testing.T) {
 
 func TestPolyDocReaderMisc(t *testing.T) {
 	folder := createTestIndex("a", "b", "c")
-	searcher, _ := OpenIndexSearcher(folder)
-	reader := searcher.GetReader().Obtain("Lucy::Index::DocReader").(PolyDocReader)
+	ixReader, _ := OpenIndexReader(folder, nil, nil)
+	reader := ixReader.Fetch("Lucy::Index::DocReader").(PolyDocReader)
 	doc := make(map[string]interface{})
 	if err := reader.ReadDoc(2, doc); err != nil {
 		t.Errorf("ReadDoc: %v", err)

http://git-wip-us.apache.org/repos/asf/lucy/blob/fe25122f/go/lucy/search_test.go
----------------------------------------------------------------------
diff --git a/go/lucy/search_test.go b/go/lucy/search_test.go
index 3d4fc50..5061a24 100644
--- a/go/lucy/search_test.go
+++ b/go/lucy/search_test.go
@@ -369,12 +369,11 @@ func TestNoMatchMatcherBasics(t *testing.T) {
 
 func TestRangeMatcherBasics(t *testing.T) {
 	index := createTestIndex("d", "c", "b", "a", "a", "a", "a")
-	searcher, _ := OpenIndexSearcher(index)
-	segReaders := searcher.GetReader().SegReaders()
-	segReader := segReaders[0].(SegReader)
-	sortReader := segReader.Obtain("Lucy::Index::SortReader").(SortReader)
+	ixReader, _ := OpenIndexReader(index, nil, nil)
+	segReaders := ixReader.SegReaders()
+	sortReader := segReaders[0].Fetch("Lucy::Index::SortReader").(SortReader)
 	sortCache := sortReader.fetchSortCache("content")
-	matcher := NewRangeMatcher(0, 0, sortCache, segReader.DocMax())
+	matcher := NewRangeMatcher(0, 0, sortCache, segReaders[0].DocMax())
 	if docID := matcher.Next(); docID != 4 {
 		t.Errorf("Next: %d", docID)
 	}