Skip to content

Commit

Permalink
store/tikv,util/logutil: add a function to convert proto.Message to h…
Browse files Browse the repository at this point in the history
…ex format (pingcap#11550)
  • Loading branch information
tiancaiamao authored and sre-bot committed Aug 9, 2019
1 parent d51a3e0 commit 31a8e21
Show file tree
Hide file tree
Showing 4 changed files with 149 additions and 4 deletions.
9 changes: 5 additions & 4 deletions store/tikv/split_region.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ package tikv
import (
"bytes"
"context"
"encoding/hex"

"github.com/pingcap/errors"
"github.com/pingcap/kvproto/pkg/kvrpcpb"
Expand Down Expand Up @@ -45,7 +46,7 @@ func (s *tikvStore) SplitRegion(splitKey kv.Key, scatter bool) (regionID uint64,
}
if bytes.Equal(splitKey, loc.StartKey) {
logutil.BgLogger().Info("skip split region",
zap.Binary("at", splitKey))
zap.String("at", hex.EncodeToString(splitKey)))
return 0, nil
}
res, err := sender.SendReq(bo, req, loc.Region, readTimeoutShort)
Expand All @@ -65,9 +66,9 @@ func (s *tikvStore) SplitRegion(splitKey kv.Key, scatter bool) (regionID uint64,
}
splitRegion := res.Resp.(*kvrpcpb.SplitRegionResponse)
logutil.BgLogger().Info("split region complete",
zap.Binary("at", splitKey),
zap.Stringer("new region left", splitRegion.GetLeft()),
zap.Stringer("new region right", splitRegion.GetRight()))
zap.String("at", hex.EncodeToString(splitKey)),
zap.Stringer("new region left", logutil.Hex(splitRegion.GetLeft())),
zap.Stringer("new region right", logutil.Hex(splitRegion.GetRight())))
left := splitRegion.GetLeft()
if left == nil {
return 0, nil
Expand Down
78 changes: 78 additions & 0 deletions util/logutil/hex.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
// Copyright 2019 PingCAP, Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by aprettyPrintlicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// See the License for the specific language governing permissions and
// limitations under the License.

package logutil

import (
"bytes"
"encoding/hex"
"fmt"
"io"
"reflect"
"strings"

"github.com/golang/protobuf/proto"
)

// Hex defines a fmt.Stringer for proto.Message.
// We can't define the String() method on proto.Message, but we can wrap it.
func Hex(msg proto.Message) fmt.Stringer {
return hexStringer{msg}
}

type hexStringer struct {
proto.Message
}

func (h hexStringer) String() string {
val := reflect.ValueOf(h.Message)
var w bytes.Buffer
prettyPrint(&w, val)
return w.String()
}

func prettyPrint(w io.Writer, val reflect.Value) {
tp := val.Type()
switch val.Kind() {
case reflect.Slice:
elemType := tp.Elem()
if elemType.Kind() == reflect.Uint8 {
fmt.Fprintf(w, "%s", hex.EncodeToString(val.Bytes()))
} else {
fmt.Fprintf(w, "%s", val.Interface())
}
case reflect.Struct:
fmt.Fprintf(w, "{")
for i := 0; i < val.NumField(); i++ {
fv := val.Field(i)
ft := tp.Field(i)
if strings.HasPrefix(ft.Name, "XXX_") {
continue
}
if i != 0 {
fmt.Fprintf(w, " ")
}
fmt.Fprintf(w, "%s:", ft.Name)
prettyPrint(w, fv)
}
fmt.Fprintf(w, "}")
case reflect.Ptr:
if val.IsNil() {
fmt.Fprintf(w, "%v", val.Interface())
} else {
prettyPrint(w, reflect.Indirect(val))
}
default:
fmt.Fprintf(w, "%v", val.Interface())
}
}
64 changes: 64 additions & 0 deletions util/logutil/hex_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
// Copyright 2017 PingCAP, Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// See the License for the specific language governing permissions and
// limitations under the License.

package logutil_test

import (
"bytes"
"encoding/hex"
"reflect"

. "github.com/pingcap/check"
"github.com/pingcap/kvproto/pkg/metapb"
"github.com/pingcap/tidb/kv"
"github.com/pingcap/tidb/util/logutil"
)

var _ = Suite(&testHexSuite{})

type testHexSuite struct{}

func (s *testHexSuite) SetUpSuite(c *C) {}

func (s *testHexSuite) SetUpTest(c *C) {}

func (s *testHexSuite) TestHex(c *C) {
var region metapb.Region
region.Id = 6662
region.StartKey = []byte{'t', 200, '\\', 000, 000, 000, '\\', 000, 000, 000, 37, '-', 000, 000, 000, 000, 000, 000, 000, 37}
region.EndKey = []byte("3asg3asd")

c.Assert(logutil.Hex(&region).String(), Equals, "{Id:6662 StartKey:74c85c0000005c000000252d0000000000000025 EndKey:3361736733617364 RegionEpoch:<nil> Peers:[]}")
}

func (s *testHexSuite) TestPrettyPrint(c *C) {
var buf bytes.Buffer

byteSlice := []byte("asd2fsdafs中文3af")
logutil.PrettyPrint(&buf, reflect.ValueOf(byteSlice))
c.Assert(buf.String(), Equals, "61736432667364616673e4b8ade69687336166")
c.Assert(buf.String(), Equals, hex.EncodeToString(byteSlice))
buf.Reset()

// Go reflect can't distinguish uint8 from byte!
intSlice := []uint8{1, 2, 3, uint8('a'), uint8('b'), uint8('c'), uint8('\'')}
logutil.PrettyPrint(&buf, reflect.ValueOf(intSlice))
c.Assert(buf.String(), Equals, "01020361626327")
buf.Reset()

var ran kv.KeyRange
ran.StartKey = kv.Key("_txxey23_i263")
ran.EndKey = nil
logutil.PrettyPrint(&buf, reflect.ValueOf(ran))
c.Assert(buf.String(), Equals, "{StartKey:5f747878657932335f69323633 EndKey:}")
}
2 changes: 2 additions & 0 deletions util/logutil/log_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@ const (
zapLogWithKeyValPattern = `\[\d\d\d\d/\d\d/\d\d \d\d:\d\d:\d\d.\d\d\d\ (\+|-)\d\d:\d\d\] \[(FATAL|ERROR|WARN|INFO|DEBUG)\] \[([\w_%!$@.,+~-]+|\\.)+:\d+\] \[.*\] \[ctxKey=.*\] (\[.*=.*\]).*\n`
)

var PrettyPrint = prettyPrint

func Test(t *testing.T) {
TestingT(t)
}
Expand Down

0 comments on commit 31a8e21

Please sign in to comment.