Skip to content
This repository has been archived by the owner on Jul 24, 2024. It is now read-only.

Commit

Permalink
analyze: analyze table after restore (#605)
Browse files Browse the repository at this point in the history
  • Loading branch information
3pointer authored Nov 26, 2020
1 parent 602ed18 commit 1a7a2f3
Show file tree
Hide file tree
Showing 15 changed files with 182 additions and 43 deletions.
3 changes: 0 additions & 3 deletions cmd/backup.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ package cmd
import (
"github.com/pingcap/log"
"github.com/pingcap/tidb/ddl"
"github.com/pingcap/tidb/session"
"github.com/spf13/cobra"
"go.uber.org/zap"

Expand Down Expand Up @@ -56,8 +55,6 @@ func NewBackupCommand() *cobra.Command {

// Do not run ddl worker in BR.
ddl.RunWorker = false
// Do not run stat worker in BR.
session.DisableStats4Test()

summary.SetUnit(summary.BackupUnit)
return nil
Expand Down
4 changes: 0 additions & 4 deletions cmd/restore.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ package cmd

import (
"github.com/pingcap/log"
"github.com/pingcap/tidb/session"
"github.com/spf13/cobra"
"go.uber.org/zap"

Expand Down Expand Up @@ -82,9 +81,6 @@ func NewRestoreCommand() *cobra.Command {
utils.LogBRInfo()
task.LogArguments(c)

// Do not run stat worker in BR.
session.DisableStats4Test()

summary.SetUnit(summary.RestoreUnit)
return nil
},
Expand Down
6 changes: 3 additions & 3 deletions go.mod1
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,10 @@ require (
github.com/pingcap/check v0.0.0-20200212061837-5e12011dc712
github.com/pingcap/errors v0.11.5-0.20201029093017-5a7df2af2ac7
github.com/pingcap/failpoint v0.0.0-20200702092429-9f69995143ce
github.com/pingcap/kvproto v0.0.0-20201113092725-08f2872278eb
github.com/pingcap/kvproto v0.0.0-20201120081251-756b1447ba12
github.com/pingcap/log v0.0.0-20201112100606-8f1e84a3abc8
github.com/pingcap/parser v0.0.0-20201112105242-773b8b74f44e
github.com/pingcap/tidb v1.1.0-beta.0.20201119091753-38bbb0dd2197
github.com/pingcap/parser v0.0.0-20201123080035-8f4c6ab94e11
github.com/pingcap/tidb v1.1.0-beta.0.20201125030655-07ff41d0c43e
github.com/pingcap/tidb-tools v4.0.5-0.20200820092506-34ea90c93237+incompatible
github.com/pingcap/tipb v0.0.0-20201026044621-45e60c77588f
github.com/prometheus/client_golang v1.5.1
Expand Down
11 changes: 6 additions & 5 deletions go.sum1
Original file line number Diff line number Diff line change
Expand Up @@ -753,8 +753,9 @@ github.com/pingcap/kvproto v0.0.0-20200411081810-b85805c9476c/go.mod h1:IOdRDPLy
github.com/pingcap/kvproto v0.0.0-20200417092353-efbe03bcffbd/go.mod h1:IOdRDPLyda8GX2hE/jO7gqaCV/PNFh8BZQCQZXfIOqI=
github.com/pingcap/kvproto v0.0.0-20200420075417-e0c6e8842f22/go.mod h1:IOdRDPLyda8GX2hE/jO7gqaCV/PNFh8BZQCQZXfIOqI=
github.com/pingcap/kvproto v0.0.0-20200810113304-6157337686b1/go.mod h1:IOdRDPLyda8GX2hE/jO7gqaCV/PNFh8BZQCQZXfIOqI=
github.com/pingcap/kvproto v0.0.0-20201113092725-08f2872278eb h1:K3r4KjVQeD4nLnfj44ibdLIXnUh58aQpkgVNWuBO9z0=
github.com/pingcap/kvproto v0.0.0-20201113092725-08f2872278eb/go.mod h1:IOdRDPLyda8GX2hE/jO7gqaCV/PNFh8BZQCQZXfIOqI=
github.com/pingcap/kvproto v0.0.0-20201120081251-756b1447ba12 h1:f33y/pngBI525jqytoSZevpmmq43XiIHoeElx3BppNQ=
github.com/pingcap/kvproto v0.0.0-20201120081251-756b1447ba12/go.mod h1:IOdRDPLyda8GX2hE/jO7gqaCV/PNFh8BZQCQZXfIOqI=
github.com/pingcap/log v0.0.0-20191012051959-b742a5d432e9 h1:AJD9pZYm72vMgPcQDww9rkZ1DnWfl0pXV3BOWlkYIjA=
github.com/pingcap/log v0.0.0-20191012051959-b742a5d432e9/go.mod h1:4rbK1p9ILyIfb6hU7OG2CiWSqMXnp3JMbiaVJ6mvoY8=
github.com/pingcap/log v0.0.0-20200117041106-d28c14d3b1cd h1:CV3VsP3Z02MVtdpTMfEgRJ4T9NGgGTxdHpJerent7rM=
Expand All @@ -765,8 +766,8 @@ github.com/pingcap/log v0.0.0-20201112100606-8f1e84a3abc8 h1:M+DNpOu/I3uDmwee6vc
github.com/pingcap/log v0.0.0-20201112100606-8f1e84a3abc8/go.mod h1:4rbK1p9ILyIfb6hU7OG2CiWSqMXnp3JMbiaVJ6mvoY8=
github.com/pingcap/parser v0.0.0-20190506092653-e336082eb825/go.mod h1:1FNvfp9+J0wvc4kl8eGNh7Rqrxveg15jJoWo/a0uHwA=
github.com/pingcap/parser v0.0.0-20200422082501-7329d80eaf2c/go.mod h1:9v0Edh8IbgjGYW2ArJr19E+bvL8zKahsFp+ixWeId+4=
github.com/pingcap/parser v0.0.0-20201112105242-773b8b74f44e h1:TCSZlqvNP2Ipt0xUwZ5Z6ehmKo1dlk5KCU1SOLXUYL4=
github.com/pingcap/parser v0.0.0-20201112105242-773b8b74f44e/go.mod h1:GbEr2PgY72/4XqPZzmzstlOU/+il/wrjeTNFs6ihsSE=
github.com/pingcap/parser v0.0.0-20201123080035-8f4c6ab94e11 h1:CpYV3/Mp42Szvt8ne6g2ojLtBmsUq6o86JazeAj4pIo=
github.com/pingcap/parser v0.0.0-20201123080035-8f4c6ab94e11/go.mod h1:GbEr2PgY72/4XqPZzmzstlOU/+il/wrjeTNFs6ihsSE=
github.com/pingcap/pd v2.1.5+incompatible/go.mod h1:nD3+EoYes4+aNNODO99ES59V83MZSI+dFbhyr667a0E=
github.com/pingcap/pd/v4 v4.0.0-rc.1.0.20200422143320-428acd53eba2/go.mod h1:s+utZtXDznOiL24VK0qGmtoHjjXNsscJx3m1n8cC56s=
github.com/pingcap/sysutil v0.0.0-20200206130906-2bfa6dc40bcd/go.mod h1:EB/852NMQ+aRKioCpToQ94Wl7fktV+FNnxf3CX/TTXI=
Expand All @@ -776,8 +777,8 @@ github.com/pingcap/sysutil v0.0.0-20200715082929-4c47bcac246a/go.mod h1:EB/852NM
github.com/pingcap/sysutil v0.0.0-20201021075216-f93ced2829e2 h1:b2G/eqDeywtdJF3w9nIUdqMmXChsmpLvf4FzUxJ9Vmk=
github.com/pingcap/sysutil v0.0.0-20201021075216-f93ced2829e2/go.mod h1:EB/852NMQ+aRKioCpToQ94Wl7fktV+FNnxf3CX/TTXI=
github.com/pingcap/tidb v1.1.0-beta.0.20200423094549-0ad7ce6cdae6/go.mod h1:KJXj2xHYfl1x4zcusC2JEANzVci+ietFOMh/CAmrYdw=
github.com/pingcap/tidb v1.1.0-beta.0.20201119091753-38bbb0dd2197 h1:J6vZT3DALFLPmJSKYi5kFkLvayNqq7Oo6ongGQSpTc8=
github.com/pingcap/tidb v1.1.0-beta.0.20201119091753-38bbb0dd2197/go.mod h1:yAq/uipWkDY0PDXdRCgs0uQs8lV9isdWcIdRYWtk+mU=
github.com/pingcap/tidb v1.1.0-beta.0.20201125030655-07ff41d0c43e h1:EHjW6Jjcy7rGUqbOiGfoyzhWVxry38zC3xFQFUw27EU=
github.com/pingcap/tidb v1.1.0-beta.0.20201125030655-07ff41d0c43e/go.mod h1:nmENlVbrMlaj+Tw0nPI/aQThVFficGJ/citl9OA/B3A=
github.com/pingcap/tidb-insight v0.3.1/go.mod h1:HZ6cGBYxViftTKLbl/V4moRol79bifZzI9ImGavJms0=
github.com/pingcap/tidb-lightning v4.0.9-0.20201106041742-a1ac97827a27+incompatible h1:y6cwuJJo8tLeHjgjODpwCSqNAv1g+9WUtcsFOHu/7ag=
github.com/pingcap/tidb-lightning v4.0.9-0.20201106041742-a1ac97827a27+incompatible/go.mod h1:UrN2l06neiEfkass87Tjvv5JFIMsOMb2DT7P7s+fwMc=
Expand Down
16 changes: 16 additions & 0 deletions pkg/backup/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -250,12 +250,15 @@ func BuildBackupRangeAndSchema(
storage kv.Storage,
tableFilter filter.Filter,
backupTS uint64,
ignoreStats bool,
) ([]rtree.Range, *Schemas, error) {
info, err := dom.GetSnapshotInfoSchema(backupTS)
if err != nil {
return nil, nil, errors.Trace(err)
}

h := dom.StatsHandle()

ranges := make([]rtree.Range, 0)
backupSchemas := newBackupSchemas()
for _, dbInfo := range info.AllSchemas() {
Expand Down Expand Up @@ -332,9 +335,22 @@ func BuildBackupRangeAndSchema(
return nil, nil, errors.Trace(err)
}

var stats []byte
if !ignoreStats {
jsonTable, err := h.DumpStatsToJSON(dbInfo.Name.String(), tableInfo, nil)
if err != nil {
return nil, nil, errors.Trace(err)
}
stats, err = json.Marshal(jsonTable)
if err != nil {
return nil, nil, errors.Trace(err)
}
}

schema := kvproto.Schema{
Db: dbData,
Table: tableData,
Stats: stats,
}
backupSchemas.pushPending(schema, dbInfo.Name.L, tableInfo.Name.L)

Expand Down
10 changes: 5 additions & 5 deletions pkg/backup/schema_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,23 +61,23 @@ func (s *testBackupSchemaSuite) TestBuildBackupRangeAndSchema(c *C) {
testFilter, err := filter.Parse([]string{"test.t1"})
c.Assert(err, IsNil)
_, backupSchemas, err := backup.BuildBackupRangeAndSchema(
s.mock.Domain, s.mock.Storage, testFilter, math.MaxUint64)
s.mock.Domain, s.mock.Storage, testFilter, math.MaxUint64, false)
c.Assert(err, IsNil)
c.Assert(backupSchemas, IsNil)

// Database is not exist.
fooFilter, err := filter.Parse([]string{"foo.t1"})
c.Assert(err, IsNil)
_, backupSchemas, err = backup.BuildBackupRangeAndSchema(
s.mock.Domain, s.mock.Storage, fooFilter, math.MaxUint64)
s.mock.Domain, s.mock.Storage, fooFilter, math.MaxUint64, false)
c.Assert(err, IsNil)
c.Assert(backupSchemas, IsNil)

// Empty database.
noFilter, err := filter.Parse([]string{"*.*"})
c.Assert(err, IsNil)
_, backupSchemas, err = backup.BuildBackupRangeAndSchema(
s.mock.Domain, s.mock.Storage, noFilter, math.MaxUint64)
s.mock.Domain, s.mock.Storage, noFilter, math.MaxUint64, false)
c.Assert(err, IsNil)
c.Assert(backupSchemas, IsNil)

Expand All @@ -87,7 +87,7 @@ func (s *testBackupSchemaSuite) TestBuildBackupRangeAndSchema(c *C) {
tk.MustExec("insert into t1 values (10);")

_, backupSchemas, err = backup.BuildBackupRangeAndSchema(
s.mock.Domain, s.mock.Storage, testFilter, math.MaxUint64)
s.mock.Domain, s.mock.Storage, testFilter, math.MaxUint64, false)
c.Assert(err, IsNil)
c.Assert(backupSchemas.Len(), Equals, 1)
updateCh := new(simpleProgress)
Expand All @@ -107,7 +107,7 @@ func (s *testBackupSchemaSuite) TestBuildBackupRangeAndSchema(c *C) {
tk.MustExec("insert into t2 values (11);")

_, backupSchemas, err = backup.BuildBackupRangeAndSchema(
s.mock.Domain, s.mock.Storage, noFilter, math.MaxUint64)
s.mock.Domain, s.mock.Storage, noFilter, math.MaxUint64, false)
c.Assert(err, IsNil)
c.Assert(backupSchemas.Len(), Equals, 2)
updateCh.reset()
Expand Down
5 changes: 3 additions & 2 deletions pkg/conn/conn.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,6 @@ import (
"time"

"github.com/pingcap/errors"
"github.com/pingcap/kvproto/pkg/backup"
"github.com/pingcap/kvproto/pkg/metapb"
"github.com/pingcap/log"
"github.com/pingcap/tidb/domain"
"github.com/pingcap/tidb/store/tikv"
Expand All @@ -22,6 +20,9 @@ import (
"google.golang.org/grpc/credentials"
"google.golang.org/grpc/keepalive"

"github.com/pingcap/kvproto/pkg/backup"
"github.com/pingcap/kvproto/pkg/metapb"

berrors "github.com/pingcap/br/pkg/errors"
"github.com/pingcap/br/pkg/glue"
"github.com/pingcap/br/pkg/logutil"
Expand Down
15 changes: 14 additions & 1 deletion pkg/gluetidb/glue.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,20 @@ type tidbSession struct {

// GetDomain implements glue.Glue.
func (Glue) GetDomain(store kv.Storage) (*domain.Domain, error) {
return session.GetDomain(store)
se, err := session.CreateSession(store)
if err != nil {
return nil, err
}
dom, err := session.GetDomain(store)
if err != nil {
return nil, err
}
// create stats handler for backup and restore.
err = dom.UpdateTableStatsLoop(se)
if err != nil {
return nil, err
}
return dom, nil
}

// CreateSession implements glue.Glue.
Expand Down
43 changes: 28 additions & 15 deletions pkg/restore/batcher_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -68,52 +68,65 @@ func newDrySender() *drySender {
}
}

type recordCurrentTableManager map[int64]bool
type recordCurrentTableManager struct {
lock sync.Mutex
m map[int64]bool
}

func (manager recordCurrentTableManager) Close(ctx context.Context) {
if len(manager) > 0 {
func (manager *recordCurrentTableManager) Close(ctx context.Context) {
manager.lock.Lock()
defer manager.lock.Unlock()
if len(manager.m) > 0 {
log.Panic("When closing, there are still some tables doesn't be sent",
zap.Any("tables", manager))
zap.Any("tables", manager.m))
}
}

func newMockManager() recordCurrentTableManager {
return make(recordCurrentTableManager)
func newMockManager() *recordCurrentTableManager {
return &recordCurrentTableManager{
m: make(map[int64]bool),
}
}

func (manager recordCurrentTableManager) Enter(_ context.Context, tables []restore.CreatedTable) error {
func (manager *recordCurrentTableManager) Enter(_ context.Context, tables []restore.CreatedTable) error {
manager.lock.Lock()
defer manager.lock.Unlock()
for _, t := range tables {
log.Info("entering", zap.Int64("table ID", t.Table.ID))
manager[t.Table.ID] = true
manager.m[t.Table.ID] = true
}
return nil
}

func (manager recordCurrentTableManager) Leave(_ context.Context, tables []restore.CreatedTable) error {
func (manager *recordCurrentTableManager) Leave(_ context.Context, tables []restore.CreatedTable) error {
manager.lock.Lock()
defer manager.lock.Unlock()
for _, t := range tables {
if !manager[t.Table.ID] {
if !manager.m[t.Table.ID] {
return errors.Errorf("Table %d is removed before added", t.Table.ID)
}
log.Info("leaving", zap.Int64("table ID", t.Table.ID))
delete(manager, t.Table.ID)
delete(manager.m, t.Table.ID)
}
return nil
}

func (manager recordCurrentTableManager) Has(tables ...restore.TableWithRange) bool {
func (manager *recordCurrentTableManager) Has(tables ...restore.TableWithRange) bool {
manager.lock.Lock()
defer manager.lock.Unlock()
ids := make([]int64, 0, len(tables))
currentIDs := make([]int64, 0, len(manager))
currentIDs := make([]int64, 0, len(manager.m))
for _, t := range tables {
ids = append(ids, t.Table.ID)
}
for id, contains := range manager {
for id, contains := range manager.m {
if contains {
currentIDs = append(currentIDs, id)
}
}
log.Info("testing", zap.Int64s("should has ID", ids), zap.Int64s("has ID", currentIDs))
for _, i := range ids {
if !manager[i] {
if !manager.m[i] {
return false
}
}
Expand Down
30 changes: 30 additions & 0 deletions pkg/restore/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import (
"github.com/pingcap/parser/model"
"github.com/pingcap/tidb/domain"
"github.com/pingcap/tidb/kv"
"github.com/pingcap/tidb/statistics/handle"
"github.com/pingcap/tidb/store/tikv/oracle"
"github.com/pingcap/tidb/tablecodec"
"github.com/pingcap/tidb/util/codec"
Expand Down Expand Up @@ -80,6 +81,12 @@ type Client struct {
backend *backup.StorageBackend
switchModeInterval time.Duration
switchCh chan struct{}

// statHandler and dom are used for analyze table after restore.
// it will backup stats with #dump.DumpStatsToJSON
// and restore stats with #dump.LoadStatsFromJSON
statsHandler *handle.Handle
dom *domain.Domain
}

// NewRestoreClient returns a new RestoreClient.
Expand All @@ -94,6 +101,16 @@ func NewRestoreClient(
if err != nil {
return nil, errors.Trace(err)
}
dom, err := g.GetDomain(store)
if err != nil {
return nil, errors.Trace(err)
}

var statsHandle *handle.Handle
// tikv.Glue will return nil, tidb.Glue will return available domain
if dom != nil {
statsHandle = dom.StatsHandle()
}

return &Client{
pdClient: pdClient,
Expand All @@ -102,6 +119,8 @@ func NewRestoreClient(
tlsConf: tlsConf,
keepaliveConf: keepaliveConf,
switchCh: make(chan struct{}),
dom: dom,
statsHandler: statsHandle,
}, nil
}

Expand Down Expand Up @@ -775,6 +794,17 @@ func (rc *Client) execChecksum(ctx context.Context, tbl CreatedTable, kvClient k
)
return errors.Annotate(berrors.ErrRestoreChecksumMismatch, "failed to validate checksum")
}
if table.Stats != nil {
log.Info("start loads analyze after validate checksum",
zap.Stringer("db name", tbl.OldTable.DB.Name),
zap.Stringer("name", tbl.OldTable.Info.Name),
zap.Int64("old id", tbl.OldTable.Info.ID),
zap.Int64("new id", tbl.Table.ID),
)
if err := rc.statsHandler.LoadStatsFromJSON(rc.dom.InfoSchema(), table.Stats); err != nil {
log.Error("analyze table failed", zap.Any("table", table.Stats), zap.Error(err))
}
}
return nil
}

Expand Down
Loading

0 comments on commit 1a7a2f3

Please sign in to comment.