Skip to content

Commit b7ac1f3

Browse files
authored
Merge pull request #3052 from dolthub/angela/keyless_subquery
Use IsJoin flag to check if keyless tables are actually allowed
2 parents 5b27bf7 + b2223ce commit b7ac1f3

File tree

4 files changed

+23
-8
lines changed

4 files changed

+23
-8
lines changed

enginetest/queries/update_queries.go

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -847,6 +847,21 @@ var UpdateIgnoreScripts = []ScriptTest{
847847
},
848848
},
849849
},
850+
{
851+
Name: "UPDATE with subquery in keyless tables",
852+
// https://github.com/dolthub/dolt/issues/9334
853+
SetUpScript: []string{
854+
"create table t (i int)",
855+
"insert into t values (1)",
856+
"update t set i = 10 where i in (select 1)",
857+
},
858+
Assertions: []ScriptTestAssertion{
859+
{
860+
Query: "select * from t",
861+
Expected: []sql.Row{{10}},
862+
},
863+
},
864+
},
850865
}
851866

852867
var UpdateErrorTests = []QueryErrorTest{

sql/analyzer/apply_foreign_keys.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -122,8 +122,7 @@ func applyForeignKeysToNodes(ctx *sql.Context, a *Analyzer, n sql.Node, cache *f
122122
if plan.IsEmptyTable(n.Child) {
123123
return n, transform.SameTree, nil
124124
}
125-
if n.IsJoin {
126-
uj := n.Child.(*plan.UpdateJoin)
125+
if uj, ok := n.Child.(*plan.UpdateJoin); ok {
127126
updateTargets := uj.UpdateTargets
128127
fkHandlerMap := make(map[string]sql.Node, len(updateTargets))
129128
for tableName, updateTarget := range updateTargets {

sql/analyzer/assign_update_join.go

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,7 @@ func modifyUpdateExprsForJoin(ctx *sql.Context, a *Analyzer, n sql.Node, scope *
3434
return n, transform.SameTree, nil
3535
}
3636

37-
n.IsJoin = true
38-
updateTargets, err := getUpdateTargetsByTable(us, jn)
37+
updateTargets, err := getUpdateTargetsByTable(us, jn, n.IsJoin)
3938
if err != nil {
4039
return nil, transform.SameTree, err
4140
}
@@ -53,7 +52,7 @@ func modifyUpdateExprsForJoin(ctx *sql.Context, a *Analyzer, n sql.Node, scope *
5352
}
5453

5554
// getUpdateTargetsByTable maps a set of table names and aliases to their corresponding update target Node
56-
func getUpdateTargetsByTable(node sql.Node, ij sql.Node) (map[string]sql.Node, error) {
55+
func getUpdateTargetsByTable(node sql.Node, ij sql.Node, isJoin bool) (map[string]sql.Node, error) {
5756
namesOfTableToBeUpdated := getTablesToBeUpdated(node)
5857
resolvedTables := getTablesByName(ij)
5958

@@ -73,7 +72,7 @@ func getUpdateTargetsByTable(node sql.Node, ij sql.Node) (map[string]sql.Node, e
7372
}
7473

7574
keyless := sql.IsKeyless(updatable.Schema())
76-
if keyless {
75+
if keyless && isJoin {
7776
return nil, sql.ErrUnsupportedFeature.New("error: keyless tables unsupported for UPDATE JOIN")
7877
}
7978

sql/plan/update.go

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,10 @@ var ErrUpdateUnexpectedSetResult = errors.NewKind("attempted to set field but ex
3131
// Update is a node for updating rows on tables.
3232
type Update struct {
3333
UnaryNode
34-
checks sql.CheckConstraints
35-
Ignore bool
34+
checks sql.CheckConstraints
35+
Ignore bool
36+
// IsJoin is true only for explicit UPDATE JOIN queries. It's possible for Update.IsJoin to be false and
37+
// Update.Child to be an UpdateJoin since subqueries are optimized as Joins
3638
IsJoin bool
3739
HasSingleRel bool
3840
IsProcNested bool

0 commit comments

Comments
 (0)