mirror of
https://source.quilibrium.com/quilibrium/ceremonyclient.git
synced 2024-12-27 00:55:17 +00:00
137 lines
3.3 KiB
Go
137 lines
3.3 KiB
Go
|
// Copyright 2019 The LevelDB-Go and Pebble Authors. All rights reserved. Use
|
||
|
// of this source code is governed by a BSD-style license that can be found in
|
||
|
// the LICENSE file.
|
||
|
|
||
|
package tool
|
||
|
|
||
|
import (
|
||
|
"bytes"
|
||
|
"fmt"
|
||
|
"os"
|
||
|
"path/filepath"
|
||
|
"strings"
|
||
|
"testing"
|
||
|
"time"
|
||
|
|
||
|
"github.com/cockroachdb/datadriven"
|
||
|
"github.com/cockroachdb/errors"
|
||
|
"github.com/cockroachdb/pebble/internal/base"
|
||
|
"github.com/cockroachdb/pebble/internal/testkeys"
|
||
|
"github.com/cockroachdb/pebble/vfs"
|
||
|
"github.com/spf13/cobra"
|
||
|
"github.com/stretchr/testify/require"
|
||
|
)
|
||
|
|
||
|
func runTests(t *testing.T, path string) {
|
||
|
paths, err := filepath.Glob(path)
|
||
|
require.NoError(t, err)
|
||
|
|
||
|
root := filepath.Dir(path)
|
||
|
for {
|
||
|
next := filepath.Dir(root)
|
||
|
if next == "." {
|
||
|
break
|
||
|
}
|
||
|
root = next
|
||
|
}
|
||
|
|
||
|
normalize := func(name string) string {
|
||
|
if os.PathSeparator == '/' {
|
||
|
return name
|
||
|
}
|
||
|
return strings.Replace(name, "/", string(os.PathSeparator), -1)
|
||
|
}
|
||
|
|
||
|
for _, path := range paths {
|
||
|
name, err := filepath.Rel(root, path)
|
||
|
require.NoError(t, err)
|
||
|
|
||
|
fs := vfs.NewMem()
|
||
|
t.Run(name, func(t *testing.T) {
|
||
|
datadriven.RunTest(t, path, func(t *testing.T, d *datadriven.TestData) string {
|
||
|
args := []string{d.Cmd}
|
||
|
for _, arg := range d.CmdArgs {
|
||
|
args = append(args, arg.String())
|
||
|
}
|
||
|
args = append(args, strings.Fields(d.Input)...)
|
||
|
|
||
|
// The testdata files contain paths with "/" path separators, but we
|
||
|
// might be running on a system with a different path separator
|
||
|
// (e.g. Windows). Copy the input data into a mem filesystem which
|
||
|
// always uses "/" for the path separator.
|
||
|
for i := range args {
|
||
|
src := normalize(args[i])
|
||
|
dest := vfs.Default.PathBase(src)
|
||
|
if ok, err := vfs.Clone(vfs.Default, fs, src, dest); err != nil {
|
||
|
return err.Error()
|
||
|
} else if ok {
|
||
|
args[i] = fs.PathBase(args[i])
|
||
|
}
|
||
|
}
|
||
|
|
||
|
var buf bytes.Buffer
|
||
|
var secs int64
|
||
|
timeNow = func() time.Time { secs++; return time.Unix(secs, 0) }
|
||
|
|
||
|
defer func() {
|
||
|
timeNow = time.Now
|
||
|
}()
|
||
|
|
||
|
// Register a test comparer and merger so that we can check the
|
||
|
// behavior of tools when the comparer and merger do not match.
|
||
|
comparer := func() *Comparer {
|
||
|
c := *base.DefaultComparer
|
||
|
c.Name = "test-comparer"
|
||
|
c.FormatKey = func(key []byte) fmt.Formatter {
|
||
|
return fmtFormatter{
|
||
|
fmt: "test formatter: %s",
|
||
|
v: key,
|
||
|
}
|
||
|
}
|
||
|
c.FormatValue = func(_, value []byte) fmt.Formatter {
|
||
|
return fmtFormatter{
|
||
|
fmt: "test value formatter: %s",
|
||
|
v: value,
|
||
|
}
|
||
|
}
|
||
|
return &c
|
||
|
}()
|
||
|
altComparer := func() *Comparer {
|
||
|
c := *base.DefaultComparer
|
||
|
c.Name = "alt-comparer"
|
||
|
return &c
|
||
|
}()
|
||
|
merger := func() *Merger {
|
||
|
m := *base.DefaultMerger
|
||
|
m.Name = "test-merger"
|
||
|
return &m
|
||
|
}()
|
||
|
openErrEnhancer := func(err error) error {
|
||
|
if errors.Is(err, base.ErrCorruption) {
|
||
|
return base.CorruptionErrorf("%v\nCustom message in case of corruption error.", err)
|
||
|
}
|
||
|
return err
|
||
|
}
|
||
|
|
||
|
tool := New(
|
||
|
DefaultComparer(comparer),
|
||
|
Comparers(altComparer, testkeys.Comparer),
|
||
|
Mergers(merger),
|
||
|
FS(fs),
|
||
|
OpenErrEnhancer(openErrEnhancer),
|
||
|
)
|
||
|
|
||
|
c := &cobra.Command{}
|
||
|
c.AddCommand(tool.Commands...)
|
||
|
c.SetArgs(args)
|
||
|
c.SetOut(&buf)
|
||
|
c.SetErr(&buf)
|
||
|
if err := c.Execute(); err != nil {
|
||
|
return err.Error()
|
||
|
}
|
||
|
return buf.String()
|
||
|
})
|
||
|
})
|
||
|
}
|
||
|
}
|