Repository: ariga/atlas
Pull request #2322 (2023-11-28 08:45:30)

sql/sqlcheck: fix alert message for unique index report in case of multiple columns


Patch:
diff --git a/sql/sqlcheck/datadepend/datadepend.go b/sql/sqlcheck/datadepend/datadepend.go
index 1dab1518..39e7fb90 100644
--- a/sql/sqlcheck/datadepend/datadepend.go
+++ b/sql/sqlcheck/datadepend/datadepend.go
@@ -8,6 +8,7 @@ import (
 	"context"
 	"errors"
 	"fmt"
+	"strings"
 
 	"ariga.io/atlas/schemahcl"
 	"ariga.io/atlas/sql/internal/sqlx"
@@ -87,22 +88,27 @@ func (a *Analyzer) Diagnostics(_ context.Context, p *sqlcheck.Pass) (diags []sql
 			for _, c := range m.Changes {
 				switch c := c.(type) {
 				case *schema.AddIndex:
-					column := func() *schema.Column {
+					names := func() []string {
+						var names []string
 						for i := range c.I.Parts {
 							// We consider a column a non-new column if
 							// it was not added in this migration file.
 							if column := c.I.Parts[i].C; column != nil && p.File.ColumnSpan(m.T, column)&sqlcheck.SpanAdded == 0 {
-								return column
+								names = append(names, fmt.Sprintf("%q", column.Name))
 							}
 						}
-						return nil
+						return names
 					}()
-					// A unique index was added on an existing column.
-					if c.I.Unique && column != nil {
+					// A unique index was added on an existing columns.
+					if c.I.Unique && len(names) > 0 {
+						s := fmt.Sprintf("columns %s contain", strings.Join(names, ", "))
+						if len(names) == 1 {
+							s = fmt.Sprintf("column %s contains", names[0])
+						}
 						diags = append(diags, sqlcheck.Diagnostic{
 							Code: codeAddUniqueI,
 							Pos:  sc.Stmt.Pos,
-							Text: fmt.Sprintf("Adding a unique index %q on table %q might fail in case column %q contains duplicate entries", c.I.Name, m.T.Name, column.Name),
+							Text: fmt.Sprintf("Adding a unique index %q on table %q might fail in case %s duplicate entries", c.I.Name, m.T.Name, s),
 						})
 					}
 				case *schema.ModifyIndex:


Test patch:
diff --git a/sql/sqlcheck/datadepend/datadepend_test.go b/sql/sqlcheck/datadepend/datadepend_test.go
index fefad1fb..01e46055 100644
--- a/sql/sqlcheck/datadepend/datadepend_test.go
+++ b/sql/sqlcheck/datadepend/datadepend_test.go
@@ -38,6 +38,8 @@ func TestAnalyzer_AddUniqueIndex(t *testing.T) {
 									AddColumns(
 										schema.NewColumn("a"),
 										schema.NewColumn("b"),
+										schema.NewColumn("c"),
+										schema.NewColumn("d"),
 									),
 								Changes: []schema.Change{
 									// Ignore new created columns.
@@ -48,11 +50,19 @@ func TestAnalyzer_AddUniqueIndex(t *testing.T) {
 										I: schema.NewUniqueIndex("idx_a").
 											AddColumns(schema.NewColumn("a")),
 									},
-									// Report on existing columns.
+									// Report on existing column.
 									&schema.AddIndex{
 										I: schema.NewUniqueIndex("idx_b").
 											AddColumns(schema.NewColumn("b")),
 									},
+									// Report on existing columns.
+									&schema.AddIndex{
+										I: schema.NewUniqueIndex("idx_c_d").
+											AddColumns(
+												schema.NewColumn("c"),
+												schema.NewColumn("d"),
+											),
+									},
 								},
 							},
 						},
@@ -69,8 +79,9 @@ func TestAnalyzer_AddUniqueIndex(t *testing.T) {
 	err = az.Analyze(context.Background(), pass)
 	require.NoError(t, err)
 	require.Equal(t, "data dependent changes detected", report.Text)
-	require.Len(t, report.Diagnostics, 1)
+	require.Len(t, report.Diagnostics, 2)
 	require.Equal(t, `Adding a unique index "idx_b" on table "users" might fail in case column "b" contains duplicate entries`, report.Diagnostics[0].Text)
+	require.Equal(t, `Adding a unique index "idx_c_d" on table "users" might fail in case columns "c", "d" contain duplicate entries`, report.Diagnostics[1].Text)
 }
 
 func TestAnalyzer_ModifyUniqueIndex(t *testing.T) {