github.com/insionng/yougam@v0.0.0-20170714101924-2bc18d833463/libraries/pingcap/go-hbase/scan_test.go (about)

     1  package hbase
     2  
     3  import (
     4  	"runtime"
     5  	"strconv"
     6  	"sync"
     7  	"time"
     8  
     9  	. "github.com/insionng/yougam/libraries/pingcap/check"
    10  )
    11  
    12  type ScanTestSuit struct {
    13  	cli       HBaseClient
    14  	tableName string
    15  }
    16  
    17  var _ = Suite(&ScanTestSuit{})
    18  
    19  func (s *ScanTestSuit) SetUpTest(c *C) {
    20  	var (
    21  		err error
    22  	)
    23  
    24  	s.cli, err = NewClient(getTestZkHosts(), "/hbase")
    25  	c.Assert(err, IsNil)
    26  
    27  	s.tableName = "test_scan"
    28  	tblDesc := NewTableDesciptor(s.tableName)
    29  	cf := newColumnFamilyDescriptor("cf", 3)
    30  	tblDesc.AddColumnDesc(cf)
    31  	s.cli.CreateTable(tblDesc, nil)
    32  }
    33  
    34  func (s *ScanTestSuit) TearDownTest(c *C) {
    35  	err := s.cli.DisableTable(s.tableName)
    36  	c.Assert(err, IsNil)
    37  
    38  	err = s.cli.DropTable(s.tableName)
    39  	c.Assert(err, IsNil)
    40  }
    41  
    42  func (s *ScanTestSuit) TestNextKey(c *C) {
    43  	inputs := []struct {
    44  		data   []byte
    45  		result []byte
    46  	}{
    47  		{nil, []byte{0}},
    48  		{[]byte{}, []byte{0}},
    49  		{[]byte{0}, []byte{1}},
    50  		{[]byte{1, 2, 3}, []byte{1, 2, 4}},
    51  		{[]byte{1, 255}, []byte{2, 0}},
    52  		{[]byte{255}, []byte{0, 0}},
    53  		{[]byte{255, 255}, []byte{0, 0, 0}},
    54  	}
    55  
    56  	for _, input := range inputs {
    57  		result := nextKey(input.data)
    58  		c.Assert(result, BytesEquals, input.result, Commentf("%v - %v - %v", input.data, input.result, result))
    59  	}
    60  }
    61  
    62  func (s *ScanTestSuit) TestScan(c *C) {
    63  	for i := 1; i <= 10000; i++ {
    64  		p := NewPut([]byte(strconv.Itoa(i)))
    65  		p.AddValue([]byte("cf"), []byte("qscan"), []byte(strconv.Itoa(i)))
    66  		ok, err := s.cli.Put(s.tableName, p)
    67  		c.Assert(ok, IsTrue)
    68  		c.Assert(err, IsNil)
    69  	}
    70  	runtime.GOMAXPROCS(runtime.NumCPU())
    71  	wg := sync.WaitGroup{}
    72  
    73  	for i := 0; i < 100; i++ {
    74  		wg.Add(1)
    75  		go func() {
    76  			defer wg.Done()
    77  			scan := NewScan([]byte(s.tableName), 100, s.cli)
    78  			defer scan.Close()
    79  			// [1, 5)
    80  			scan.StartRow = []byte("1")
    81  			scan.StopRow = []byte("5")
    82  
    83  			cnt := 0
    84  			for {
    85  				r := scan.Next()
    86  				if r == nil || scan.Closed() {
    87  					break
    88  				}
    89  				cnt++
    90  			}
    91  			c.Assert(cnt, Equals, 4445)
    92  		}()
    93  	}
    94  
    95  	wg.Wait()
    96  
    97  	for i := 1; i <= 10000; i++ {
    98  		d := NewDelete([]byte(strconv.Itoa(i)))
    99  		b, err := s.cli.Delete(s.tableName, d)
   100  		c.Assert(err, IsNil)
   101  		c.Assert(b, IsTrue)
   102  	}
   103  }
   104  
   105  func (s *ScanTestSuit) TestScanWithVersion(c *C) {
   106  	for i := 1; i <= 10000; i++ {
   107  		p := NewPut([]byte(strconv.Itoa(i)))
   108  		p.AddValue([]byte("cf"), []byte("q"), []byte(strconv.Itoa(i)))
   109  		ok, err := s.cli.Put(s.tableName, p)
   110  		c.Assert(ok, IsTrue)
   111  		c.Assert(err, IsNil)
   112  	}
   113  	// Test version put.
   114  	p := NewPut([]byte("99999"))
   115  	p.AddValue([]byte("cf"), []byte("q"), []byte("1002"))
   116  	p.AddTimestamp(1002)
   117  	ok, err := s.cli.Put(s.tableName, p)
   118  	c.Assert(ok, IsTrue)
   119  	c.Assert(err, IsNil)
   120  
   121  	p = NewPut([]byte("99999"))
   122  	p.AddValue([]byte("cf"), []byte("q"), []byte("1003"))
   123  	p.AddTimestamp(1003)
   124  	ok, err = s.cli.Put(s.tableName, p)
   125  	c.Assert(ok, IsTrue)
   126  	c.Assert(err, IsNil)
   127  
   128  	p = NewPut([]byte("99999"))
   129  	p.AddValue([]byte("cf"), []byte("q"), []byte("1001"))
   130  	p.AddTimestamp(1001)
   131  	ok, err = s.cli.Put(s.tableName, p)
   132  	c.Assert(ok, IsTrue)
   133  	c.Assert(err, IsNil)
   134  
   135  	// Test version get.
   136  	g := NewGet([]byte("99999"))
   137  	g.AddColumn([]byte("cf"), []byte("q"))
   138  	g.AddTimeRange(1001, 1004)
   139  	r, err := s.cli.Get(s.tableName, g)
   140  	c.Assert(r.Columns["cf:q"].Values, HasLen, 1)
   141  	c.Assert(string(r.SortedColumns[0].Value), Equals, "1003")
   142  	c.Assert(err, IsNil)
   143  
   144  	g = NewGet([]byte("99999"))
   145  	g.AddColumn([]byte("cf"), []byte("q"))
   146  	g.AddTimeRange(1001, 1003)
   147  	r, err = s.cli.Get(s.tableName, g)
   148  	c.Assert(r.Columns["cf:q"].Values, HasLen, 1)
   149  	c.Assert(string(r.SortedColumns[0].Value), Equals, "1002")
   150  	c.Assert(err, IsNil)
   151  
   152  	g = NewGet([]byte("99999"))
   153  	g.AddColumn([]byte("cf"), []byte("q"))
   154  	g.AddTimeRange(999, 1001)
   155  	r, err = s.cli.Get(s.tableName, g)
   156  	c.Assert(r, IsNil)
   157  	c.Assert(err, IsNil)
   158  
   159  	g = NewGet([]byte("99999"))
   160  	g.AddColumn([]byte("cf"), []byte("q"))
   161  	r, err = s.cli.Get(s.tableName, g)
   162  	c.Assert(err, IsNil)
   163  	c.Assert(r.Columns["cf:q"].Values, HasLen, 1)
   164  	c.Assert(string(r.SortedColumns[0].Value), Equals, "1003")
   165  	c.Assert(r.SortedColumns[0].Ts, Equals, uint64(1003))
   166  
   167  	g = NewGet([]byte("99999"))
   168  	g.AddColumn([]byte("cf"), []byte("q"))
   169  	g.Versions = 2
   170  	r, err = s.cli.Get(s.tableName, g)
   171  	c.Assert(r.Columns["cf:q"].Values, HasLen, 2)
   172  	value, ok := r.Columns["cf:q"].Values[1003]
   173  	c.Assert(ok, IsTrue)
   174  	c.Assert(string(value), Equals, "1003")
   175  	value, ok = r.Columns["cf:q"].Values[1002]
   176  	c.Assert(ok, IsTrue)
   177  	c.Assert(string(value), Equals, "1002")
   178  
   179  	g = NewGet([]byte("99999"))
   180  	g.AddColumn([]byte("cf"), []byte("q"))
   181  	g.Versions = 5
   182  	r, err = s.cli.Get(s.tableName, g)
   183  	c.Assert(r.Columns["cf:q"].Values, HasLen, 3)
   184  	value, ok = r.Columns["cf:q"].Values[1003]
   185  	c.Assert(ok, IsTrue)
   186  	c.Assert(string(value), Equals, "1003")
   187  	value, ok = r.Columns["cf:q"].Values[1002]
   188  	c.Assert(ok, IsTrue)
   189  	c.Assert(string(value), Equals, "1002")
   190  	value, ok = r.Columns["cf:q"].Values[1001]
   191  	c.Assert(ok, IsTrue)
   192  	c.Assert(string(value), Equals, "1001")
   193  
   194  	g = NewGet([]byte("99999"))
   195  	g.AddColumn([]byte("cf"), []byte("q"))
   196  	g.Versions = 3
   197  	g.AddTimeRange(999, 1002)
   198  	r, err = s.cli.Get(s.tableName, g)
   199  	c.Assert(r.Columns["cf:q"].Values, HasLen, 1)
   200  	c.Assert(string(r.SortedColumns[0].Value), Equals, "1001")
   201  	c.Assert(r.SortedColumns[0].Ts, Equals, uint64(1001))
   202  
   203  	// Test version scan.
   204  	// Range -> [9999, 999999)
   205  	scan := NewScan([]byte(s.tableName), 100, s.cli)
   206  	scan.StartRow = []byte("9999")
   207  	scan.StopRow = []byte("999999")
   208  
   209  	r = scan.Next()
   210  	c.Assert(r.SortedColumns, HasLen, 1)
   211  	c.Assert(string(r.SortedColumns[0].Value), Equals, "9999")
   212  
   213  	r = scan.Next()
   214  	c.Assert(r.SortedColumns, HasLen, 1)
   215  	c.Assert(string(r.SortedColumns[0].Value), Equals, "1003")
   216  
   217  	r = scan.Next()
   218  	c.Assert(r, IsNil)
   219  	scan.Close()
   220  
   221  	// Range -> [9999, 999999)
   222  	// Version -> [1000, 1002)
   223  	scan = NewScan([]byte(s.tableName), 100, s.cli)
   224  	scan.StartRow = []byte("9999")
   225  	scan.StopRow = []byte("999999")
   226  	scan.AddTimeRange(1000, 1002)
   227  
   228  	r = scan.Next()
   229  	c.Assert(r.SortedColumns, HasLen, 1)
   230  	c.Assert(string(r.SortedColumns[0].Value), Equals, "1001")
   231  
   232  	r = scan.Next()
   233  	c.Assert(r, IsNil)
   234  	scan.Close()
   235  
   236  	for i := 1; i <= 10000; i++ {
   237  		d := NewDelete([]byte(strconv.Itoa(i)))
   238  		b, err := s.cli.Delete(s.tableName, d)
   239  		c.Assert(err, IsNil)
   240  		c.Assert(b, IsTrue)
   241  	}
   242  }
   243  
   244  func (s *ScanTestSuit) TestScanCrossMultiRegions(c *C) {
   245  	origData := map[string]map[string]string{}
   246  	for i := 1; i <= 2000; i++ {
   247  		p := NewPut([]byte(strconv.Itoa(i)))
   248  		p.AddValue([]byte("cf"), []byte("qmulti"), []byte(strconv.Itoa(i)))
   249  		ok, err := s.cli.Put(s.tableName, p)
   250  		c.Assert(ok, IsTrue)
   251  		c.Assert(err, IsNil)
   252  
   253  		rowKey := string(p.Row)
   254  		origData[rowKey] = map[string]string{}
   255  		origData[rowKey]["cf:qmulti"] = string(p.Values[0][0])
   256  	}
   257  	err := s.cli.Split(s.tableName, "1024")
   258  	c.Assert(err, IsNil)
   259  	// Sleep wait Split finish.
   260  	time.Sleep(1 * time.Second)
   261  
   262  	scan := NewScan([]byte(s.tableName), 100, s.cli)
   263  	cnt := 0
   264  	for i := 1; i <= 2000; i++ {
   265  		r := scan.Next()
   266  		c.Assert(r, NotNil)
   267  		rowKey := string(r.Row)
   268  		origRow, ok := origData[rowKey]
   269  		c.Assert(ok, IsTrue)
   270  		c.Assert(origRow, NotNil)
   271  		for column := range r.Columns {
   272  			origValue, ok := origRow[column]
   273  			c.Assert(ok, IsTrue)
   274  			value := string(r.Columns[column].Value)
   275  			c.Assert(origValue, Equals, value)
   276  		}
   277  		delete(origData, rowKey)
   278  		cnt++
   279  	}
   280  	c.Assert(cnt, Equals, 2000)
   281  
   282  	for i := 1; i <= 2000; i++ {
   283  		d := NewDelete([]byte(strconv.Itoa(i)))
   284  		b, err := s.cli.Delete(s.tableName, d)
   285  		c.Assert(err, IsNil)
   286  		c.Assert(b, IsTrue)
   287  	}
   288  }
   289  
   290  func (s *ScanTestSuit) TestScanWhileSplit(c *C) {
   291  	origData := map[string]map[string]string{}
   292  	for i := 1; i <= 3000; i++ {
   293  		p := NewPut([]byte(strconv.Itoa(i)))
   294  		p.AddValue([]byte("cf"), []byte("qsplit"), []byte(strconv.Itoa(i)))
   295  		ok, err := s.cli.Put(s.tableName, p)
   296  		c.Assert(ok, IsTrue)
   297  		c.Assert(err, IsNil)
   298  
   299  		rowKey := string(p.Row)
   300  		origData[rowKey] = map[string]string{}
   301  		origData[rowKey]["cf:qsplit"] = string(p.Values[0][0])
   302  	}
   303  	scan := NewScan([]byte(s.tableName), 100, s.cli)
   304  	cnt := 0
   305  	// Scan to a random row, like 1987 or whatever.
   306  	for i := 1; i <= 1987; i++ {
   307  		r := scan.Next()
   308  		c.Assert(r, NotNil)
   309  		rowKey := string(r.Row)
   310  		origRow, ok := origData[rowKey]
   311  		c.Assert(ok, IsTrue)
   312  		c.Assert(origRow, NotNil)
   313  		for column := range r.Columns {
   314  			origValue, ok := origRow[column]
   315  			c.Assert(ok, IsTrue)
   316  			value := string(r.Columns[column].Value)
   317  			c.Assert(origValue, Equals, value)
   318  		}
   319  		delete(origData, rowKey)
   320  		cnt++
   321  	}
   322  	c.Assert(cnt, Equals, 1987)
   323  	// At this time, regions is splitting.
   324  	err := s.cli.Split(s.tableName, "2048")
   325  	c.Assert(err, IsNil)
   326  	// Sleep wait Split finish.
   327  	time.Sleep(1 * time.Second)
   328  
   329  	// Scan is go on, and get data normally.
   330  	for i := 1988; i <= 3000; i++ {
   331  		r := scan.Next()
   332  		c.Assert(r, NotNil)
   333  		rowKey := string(r.Row)
   334  		origRow, ok := origData[rowKey]
   335  		c.Assert(ok, IsTrue)
   336  		c.Assert(origRow, NotNil)
   337  		for column := range r.Columns {
   338  			origValue, ok := origRow[column]
   339  			c.Assert(ok, IsTrue)
   340  			value := string(r.Columns[column].Value)
   341  			c.Assert(origValue, Equals, value)
   342  		}
   343  		for column := range r.Columns {
   344  			origValue, ok := origRow[column]
   345  			value := string(r.Columns[column].Value)
   346  			c.Assert(ok, IsTrue)
   347  			c.Assert(origValue, Equals, value)
   348  		}
   349  		delete(origData, rowKey)
   350  		cnt++
   351  	}
   352  	c.Assert(cnt, Equals, 3000)
   353  
   354  	for i := 1; i <= 3000; i++ {
   355  		d := NewDelete([]byte(strconv.Itoa(i)))
   356  		b, err := s.cli.Delete(s.tableName, d)
   357  		c.Assert(err, IsNil)
   358  		c.Assert(b, IsTrue)
   359  	}
   360  }
   361  
   362  func (s *ScanTestSuit) TestScanClose(c *C) {
   363  	for i := 1; i <= 100; i++ {
   364  		p := NewPut([]byte(strconv.Itoa(i)))
   365  		p.AddValue([]byte("cf"), []byte("qclose"), []byte(strconv.Itoa(i)))
   366  		ok, err := s.cli.Put(s.tableName, p)
   367  		c.Assert(ok, IsTrue)
   368  		c.Assert(err, IsNil)
   369  	}
   370  	// Do not get any data.
   371  	scan := NewScan([]byte(s.tableName), 100, s.cli)
   372  	err := scan.Close()
   373  	c.Assert(err, IsNil)
   374  	r := scan.Next()
   375  	c.Assert(r, IsNil)
   376  
   377  	// Get some data.
   378  	scan = NewScan([]byte(s.tableName), 100, s.cli)
   379  	r = scan.Next()
   380  	c.Assert(r, NotNil)
   381  	// If scanner Close, then do not fetch any data even cache still has some.
   382  	err = scan.Close()
   383  	c.Assert(err, IsNil)
   384  	r = scan.Next()
   385  	c.Assert(r, IsNil)
   386  
   387  	for i := 1; i <= 100; i++ {
   388  		d := NewDelete([]byte(strconv.Itoa(i)))
   389  		b, err := s.cli.Delete(s.tableName, d)
   390  		c.Assert(err, IsNil)
   391  		c.Assert(b, IsTrue)
   392  	}
   393  }