mirror of
https://github.com/dolthub/dolt.git
synced 2026-04-22 11:29:06 -05:00
Adds our_diff_type and their_diff_type to dolt_conflicts_table_name (#3748)
* add our_diff_type and their_diff_type to dolt_conflicts_table_name * pr comments * [ga-format-pr] Run go/utils/repofmt/format_repo.sh and go/Godeps/update.sh Co-authored-by: druvv <druvv@users.noreply.github.com>
This commit is contained in:
@@ -167,6 +167,11 @@ func TestSystemTableTags(t *testing.T) {
|
||||
assert.Equal(t, doltSchemasMin+3, schema.DoltSchemasFragmentTag)
|
||||
assert.Equal(t, doltSchemasMin+4, schema.DoltSchemasExtraTag)
|
||||
})
|
||||
t.Run("dolt_conflicts_ tags", func(t *testing.T) {
|
||||
doltConflictsMin := sysTableMin + uint64(7000)
|
||||
assert.Equal(t, doltConflictsMin+0, schema.DoltConflictsOurDiffTypeTag)
|
||||
assert.Equal(t, doltConflictsMin+1, schema.DoltConflictsTheirDiffTypeTag)
|
||||
})
|
||||
}
|
||||
|
||||
func TestEmptyInMemoryRepoCreation(t *testing.T) {
|
||||
|
||||
@@ -39,11 +39,18 @@ const (
|
||||
baseStr = "base"
|
||||
)
|
||||
|
||||
const (
|
||||
ConflictDiffTypeAdded = "added"
|
||||
ConflictDiffTypeModified = "modified"
|
||||
ConflictDiffTypeRemoved = "removed"
|
||||
)
|
||||
|
||||
// ConflictReader is a class providing a NextConflict function which can be used in a pipeline as a pipeline.SourceFunc,
|
||||
// or it can be used to read each conflict
|
||||
type ConflictReader struct {
|
||||
confItr types.MapIterator
|
||||
joiner *rowconv.Joiner
|
||||
sch schema.Schema
|
||||
nbf *types.NomsBinFormat
|
||||
}
|
||||
|
||||
@@ -76,6 +83,16 @@ func NewConflictReader(ctx context.Context, tbl *doltdb.Table) (*ConflictReader,
|
||||
return nil, err
|
||||
}
|
||||
|
||||
readerSch := joiner.GetSchema()
|
||||
readerSch, err = readerSch.AddColumn(schema.NewColumn("our_diff_type", schema.DoltConflictsOurDiffTypeTag, types.StringKind, false), nil)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
readerSch, err = readerSch.AddColumn(schema.NewColumn("their_diff_type", schema.DoltConflictsTheirDiffTypeTag, types.StringKind, false), nil)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
_, confIdx, err := tbl.GetConflicts(ctx)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
@@ -91,7 +108,7 @@ func NewConflictReader(ctx context.Context, tbl *doltdb.Table) (*ConflictReader,
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &ConflictReader{confItr, joiner, tbl.Format()}, nil
|
||||
return &ConflictReader{confItr: confItr, joiner: joiner, sch: readerSch, nbf: tbl.Format()}, nil
|
||||
}
|
||||
|
||||
func tagMappingConverter(ctx context.Context, vrw types.ValueReadWriter, src, dest schema.Schema) (*rowconv.RowConverter, error) {
|
||||
@@ -106,7 +123,7 @@ func tagMappingConverter(ctx context.Context, vrw types.ValueReadWriter, src, de
|
||||
|
||||
// GetSchema gets the schema of the rows that this reader will return
|
||||
func (cr *ConflictReader) GetSchema() schema.Schema {
|
||||
return cr.joiner.GetSchema()
|
||||
return cr.sch
|
||||
}
|
||||
|
||||
// GetJoiner returns the joiner used to join a row with its base, and merge versions
|
||||
@@ -162,6 +179,11 @@ func (cr *ConflictReader) NextConflict(ctx context.Context) (row.Row, pipeline.I
|
||||
|
||||
joinedRow, err := cr.joiner.Join(namedRows)
|
||||
|
||||
ourDiffType := getDiffType(conflict.Base, conflict.Value)
|
||||
theirDiffType := getDiffType(conflict.Base, conflict.MergeValue)
|
||||
joinedRow, err = joinedRow.SetColVal(schema.DoltConflictsOurDiffTypeTag, types.String(ourDiffType), cr.sch)
|
||||
joinedRow, err = joinedRow.SetColVal(schema.DoltConflictsTheirDiffTypeTag, types.String(theirDiffType), cr.sch)
|
||||
|
||||
if err != nil {
|
||||
return nil, pipeline.NoProps, err
|
||||
}
|
||||
@@ -169,6 +191,16 @@ func (cr *ConflictReader) NextConflict(ctx context.Context) (row.Row, pipeline.I
|
||||
return joinedRow, pipeline.NoProps, nil
|
||||
}
|
||||
|
||||
func getDiffType(base types.Value, other types.Value) string {
|
||||
if types.IsNull(base) {
|
||||
return ConflictDiffTypeAdded
|
||||
} else if types.IsNull(other) {
|
||||
return ConflictDiffTypeRemoved
|
||||
}
|
||||
|
||||
return ConflictDiffTypeModified
|
||||
}
|
||||
|
||||
// GetKeyForConflicts returns the pk for a conflict row
|
||||
func (cr *ConflictReader) GetKeyForConflict(ctx context.Context, r row.Row) (types.Value, error) {
|
||||
rows, err := cr.joiner.Split(r)
|
||||
|
||||
@@ -137,7 +137,10 @@ func (j *Joiner) Split(r row.Row) (map[string]row.Row, error) {
|
||||
}
|
||||
|
||||
_, err := r.IterCols(func(tag uint64, val types.Value) (stop bool, err error) {
|
||||
schemaNameAndTag := j.revTagMap[tag]
|
||||
schemaNameAndTag, ok := j.revTagMap[tag]
|
||||
if !ok {
|
||||
return false, nil
|
||||
}
|
||||
colVals[schemaNameAndTag.str][schemaNameAndTag.u64] = val
|
||||
|
||||
return false, nil
|
||||
|
||||
@@ -99,3 +99,9 @@ const (
|
||||
DoltConstraintViolationsTypeTag = 0
|
||||
DoltConstraintViolationsInfoTag = math.MaxUint64
|
||||
)
|
||||
|
||||
// Tags for the dolt_conflicts_table_name table
|
||||
const (
|
||||
DoltConflictsOurDiffTypeTag = iota + SystemTableReservedMin + uint64(7000)
|
||||
DoltConflictsTheirDiffTypeTag
|
||||
)
|
||||
|
||||
@@ -22,6 +22,7 @@ import (
|
||||
|
||||
"github.com/dolthub/dolt/go/libraries/doltcore/doltdb"
|
||||
"github.com/dolthub/dolt/go/libraries/doltcore/doltdb/durable"
|
||||
"github.com/dolthub/dolt/go/libraries/doltcore/merge"
|
||||
"github.com/dolthub/dolt/go/libraries/doltcore/schema"
|
||||
"github.com/dolthub/dolt/go/libraries/doltcore/sqle/index"
|
||||
"github.com/dolthub/dolt/go/libraries/doltcore/sqle/sqlutil"
|
||||
@@ -122,6 +123,7 @@ type prollyConflictRowIter struct {
|
||||
|
||||
var _ sql.RowIter = &prollyConflictRowIter{}
|
||||
|
||||
// base_cols, our_cols, our_diff_type, their_cols, their_diff_type
|
||||
func newProllyConflictRowIter(ctx *sql.Context, ct ProllyConflictsTable) (*prollyConflictRowIter, error) {
|
||||
idx, err := ct.tbl.GetRowData(ctx)
|
||||
if err != nil {
|
||||
@@ -145,12 +147,12 @@ func newProllyConflictRowIter(ctx *sql.Context, ct ProllyConflictsTable) (*proll
|
||||
var o, t, n int
|
||||
if !keyless {
|
||||
o = b + kd.Count() + baseVD.Count()
|
||||
t = o + kd.Count() + oursVD.Count()
|
||||
n = t + kd.Count() + theirsVD.Count()
|
||||
t = o + kd.Count() + oursVD.Count() + 1
|
||||
n = t + kd.Count() + theirsVD.Count() + 1
|
||||
} else {
|
||||
o = b + baseVD.Count() - 1
|
||||
t = o + oursVD.Count() - 1
|
||||
n = t + theirsVD.Count() - 1
|
||||
t = o + oursVD.Count()
|
||||
n = t + theirsVD.Count()
|
||||
}
|
||||
|
||||
return &prollyConflictRowIter{
|
||||
@@ -230,6 +232,7 @@ func (itr *prollyConflictRowIter) putConflictRowVals(ctx *sql.Context, c conf, r
|
||||
r[itr.o+itr.kd.Count()+i] = f
|
||||
}
|
||||
}
|
||||
r[itr.o+itr.kd.Count()+itr.oursVD.Count()] = getDiffType(c.bV, c.oV)
|
||||
|
||||
if c.tV != nil {
|
||||
for i := 0; i < itr.theirsVD.Count(); i++ {
|
||||
@@ -240,10 +243,22 @@ func (itr *prollyConflictRowIter) putConflictRowVals(ctx *sql.Context, c conf, r
|
||||
r[itr.t+itr.kd.Count()+i] = f
|
||||
}
|
||||
}
|
||||
r[itr.t+itr.kd.Count()+itr.theirsVD.Count()] = getDiffType(c.bV, c.tV)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func getDiffType(base val.Tuple, other val.Tuple) string {
|
||||
if base == nil {
|
||||
return merge.ConflictDiffTypeAdded
|
||||
} else if other == nil {
|
||||
return merge.ConflictDiffTypeRemoved
|
||||
}
|
||||
|
||||
// There has to be some edit, otherwise it wouldn't be a conflict...
|
||||
return merge.ConflictDiffTypeModified
|
||||
}
|
||||
|
||||
func (itr *prollyConflictRowIter) putKeylessConflictRowVals(ctx *sql.Context, c conf, r sql.Row) error {
|
||||
if c.bV != nil {
|
||||
for i := 0; i < itr.baseVD.Count()-1; i++ {
|
||||
@@ -264,6 +279,7 @@ func (itr *prollyConflictRowIter) putKeylessConflictRowVals(ctx *sql.Context, c
|
||||
r[itr.o+i] = f
|
||||
}
|
||||
}
|
||||
r[itr.o+itr.oursVD.Count()-1] = getDiffType(c.bV, c.oV)
|
||||
|
||||
if c.tV != nil {
|
||||
for i := 0; i < itr.theirsVD.Count()-1; i++ {
|
||||
@@ -274,6 +290,7 @@ func (itr *prollyConflictRowIter) putKeylessConflictRowVals(ctx *sql.Context, c
|
||||
r[itr.t+i] = f
|
||||
}
|
||||
}
|
||||
r[itr.t+itr.theirsVD.Count()-1] = getDiffType(c.bV, c.tV)
|
||||
|
||||
return nil
|
||||
}
|
||||
@@ -478,7 +495,7 @@ func (cd *prollyConflictDeleter) Close(ctx *sql.Context) error {
|
||||
}
|
||||
|
||||
func CalculateConflictSchema(base, ours, theirs schema.Schema) (schema.Schema, error) {
|
||||
cols := make([]schema.Column, 1+ours.GetAllCols().Size()+theirs.GetAllCols().Size()+base.GetAllCols().Size())
|
||||
cols := make([]schema.Column, 3+ours.GetAllCols().Size()+theirs.GetAllCols().Size()+base.GetAllCols().Size())
|
||||
|
||||
// the commit hash or working set hash of the right side during merge
|
||||
cols[0] = schema.NewColumn("from_root_ish", 0, types.StringKind, false)
|
||||
@@ -517,10 +534,13 @@ func CalculateConflictSchema(base, ours, theirs schema.Schema) (schema.Schema, e
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
cols[i] = schema.NewColumn("our_diff_type", uint64(i), types.StringKind, false)
|
||||
i++
|
||||
err = putWithPrefix("their_", theirs)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
cols[i] = schema.NewColumn("their_diff_type", uint64(i), types.StringKind, false)
|
||||
|
||||
return schema.UnkeyedSchemaFromCols(schema.NewColCollection(cols...)), nil
|
||||
}
|
||||
|
||||
@@ -692,6 +692,12 @@ func TestDoltMerge(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestDoltConflictsTableNameTable(t *testing.T) {
|
||||
for _, script := range DoltConflictDiffTypeScripts {
|
||||
enginetest.TestScript(t, newDoltHarness(t), script)
|
||||
}
|
||||
}
|
||||
|
||||
// tests new format behavior for keyless merges that create CVs and conflicts
|
||||
func TestKeylessDoltMergeCVsAndConflicts(t *testing.T) {
|
||||
if !types.IsFormat_DOLT_1(types.Format_Default) {
|
||||
|
||||
@@ -1624,6 +1624,50 @@ var KeylessMergeCVsAndConflictsScripts = []queries.ScriptTest{
|
||||
},
|
||||
}
|
||||
|
||||
var DoltConflictDiffTypeScripts = []queries.ScriptTest{
|
||||
{
|
||||
Name: "conflict diff types",
|
||||
SetUpScript: []string{
|
||||
"SET dolt_allow_commit_conflicts = on;",
|
||||
"CREATE table t (pk int PRIMARY KEY, col1 int);",
|
||||
"INSERT INTO t VALUES (1, 1);",
|
||||
"INSERT INTO t VALUES (2, 2);",
|
||||
"INSERT INTO t VALUES (3, 3);",
|
||||
"CALL DOLT_COMMIT('-am', 'create table with row');",
|
||||
|
||||
"CALL DOLT_CHECKOUT('-b', 'other');",
|
||||
"UPDATE t set col1 = 3 where pk = 1;",
|
||||
"UPDATE t set col1 = 0 where pk = 2;",
|
||||
"DELETE FROM t where pk = 3;",
|
||||
"INSERT INTO t VALUES (4, -4);",
|
||||
"CALL DOLT_COMMIT('-am', 'right edit');",
|
||||
|
||||
"CALL DOLT_CHECKOUT('main');",
|
||||
"UPDATE t set col1 = 2 where pk = 1;",
|
||||
"DELETE FROM t where pk = 2;",
|
||||
"UPDATE t set col1 = 0 where pk = 3;",
|
||||
"INSERT INTO t VALUES (4, 4);",
|
||||
"CALL DOLT_COMMIT('-am', 'left edit');",
|
||||
},
|
||||
Assertions: []queries.ScriptTestAssertion{
|
||||
{
|
||||
Query: "CALL DOLT_MERGE('other');",
|
||||
Expected: []sql.Row{{0, 1}},
|
||||
},
|
||||
{
|
||||
Query: "SELECT base_pk, base_col1, our_pk, our_col1, our_diff_type, their_pk, their_col1, their_diff_type" +
|
||||
" from dolt_conflicts_t ORDER BY COALESCE(base_pk, our_pk, their_pk) ASC;",
|
||||
Expected: []sql.Row{
|
||||
{1, 1, 1, 2, "modified", 1, 3, "modified"},
|
||||
{2, 2, nil, nil, "removed", 2, 0, "modified"},
|
||||
{3, 3, 3, 0, "modified", nil, nil, "removed"},
|
||||
{nil, nil, 4, 4, "added", 4, -4, "added"},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
// MergeArtifactsScripts tests new format merge behavior where
|
||||
// existing violations and conflicts are merged together.
|
||||
var MergeArtifactsScripts = []queries.ScriptTest{
|
||||
|
||||
Reference in New Issue
Block a user