// SeekFirst returns an iterator which points to the first entry of the KV index. func (c *index) SeekFirst(r kv.Retriever) (iter table.IndexIterator, err error) { it, err := r.Seek(c.prefix) if err != nil { return nil, errors.Trace(err) } return &indexIter{it: it, idx: c, prefix: c.prefix}, nil }
// ScanMetaWithPrefix scans metadata with the prefix. func ScanMetaWithPrefix(retriever kv.Retriever, prefix kv.Key, filter func(kv.Key, []byte) bool) error { iter, err := retriever.Seek(prefix) if err != nil { return errors.Trace(err) } defer iter.Close() for { if err != nil { return errors.Trace(err) } if iter.Valid() && iter.Key().HasPrefix(prefix) { if !filter(iter.Key(), iter.Value()) { break } err = iter.Next() if err != nil { return errors.Trace(err) } } else { break } } return nil }
func iterRecords(retriever kv.Retriever, t table.Table, startKey kv.Key, cols []*table.Column, fn table.RecordIterFunc) error { it, err := retriever.Seek(startKey) if err != nil { return errors.Trace(err) } defer it.Close() if !it.Valid() { return nil } log.Debugf("startKey:%q, key:%q, value:%q", startKey, it.Key(), it.Value()) colMap := make(map[int64]*types.FieldType, len(cols)) for _, col := range cols { colMap[col.ID] = &col.FieldType } prefix := t.RecordPrefix() for it.Valid() && it.Key().HasPrefix(prefix) { // first kv pair is row lock information. // TODO: check valid lock // get row handle handle, err := tablecodec.DecodeRowKey(it.Key()) if err != nil { return errors.Trace(err) } rowMap, err := tablecodec.DecodeRow(it.Value(), colMap) if err != nil { return errors.Trace(err) } data := make([]types.Datum, 0, len(cols)) for _, col := range cols { if col.IsPKHandleColumn(t.Meta()) { data = append(data, types.NewIntDatum(handle)) } else { data = append(data, rowMap[col.ID]) } } more, err := fn(handle, data, cols) if !more || err != nil { return errors.Trace(err) } rk := t.RecordKey(handle) err = kv.NextUntil(it, util.RowKeyPrefixFilter(rk)) if err != nil { return errors.Trace(err) } } return nil }
// Seek searches KV index for the entry with indexedValues. func (c *index) Seek(r kv.Retriever, indexedValues []types.Datum) (iter table.IndexIterator, hit bool, err error) { key, _, err := c.GenIndexKey(indexedValues, 0) if err != nil { return nil, false, errors.Trace(err) } it, err := r.Seek(key) if err != nil { return nil, false, errors.Trace(err) } // check if hit hit = false if it.Valid() && it.Key().Cmp(key) == 0 { hit = true } return &indexIter{it: it, idx: c, prefix: c.prefix}, hit, nil }
func iterRecords(retriever kv.Retriever, t table.Table, startKey kv.Key, cols []*table.Column, fn table.RecordIterFunc) error { it, err := retriever.Seek(startKey) if err != nil { return errors.Trace(err) } defer it.Close() if !it.Valid() { return nil } log.Debugf("startKey:%q, key:%q, value:%q", startKey, it.Key(), it.Value()) prefix := t.RecordPrefix() for it.Valid() && it.Key().HasPrefix(prefix) { // first kv pair is row lock information. // TODO: check valid lock // get row handle handle, err := tables.DecodeRecordKeyHandle(it.Key()) if err != nil { return errors.Trace(err) } data, err := rowWithCols(retriever, t, handle, cols) if err != nil { return errors.Trace(err) } more, err := fn(handle, data, cols) if !more || err != nil { return errors.Trace(err) } rk := t.RecordKey(handle, nil) err = kv.NextUntil(it, util.RowKeyPrefixFilter(rk)) if err != nil { return errors.Trace(err) } } return nil }