From 169eebe421598cefeb5ab99d9c43d64a86693265 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jos=C3=A9=20Carlos=20Nieto?= <jose.carlos@menteslibres.net>
Date: Sun, 8 Jun 2014 08:46:03 -0500
Subject: [PATCH] Making some values public for easy initialization and adding
 sort by multiple columns.

---
 util/sqlgen/column.go    |  4 ++--
 util/sqlgen/database.go  |  4 ++--
 util/sqlgen/default.go   |  7 +++++--
 util/sqlgen/layout.go    |  2 ++
 util/sqlgen/main.go      |  2 ++
 util/sqlgen/main_test.go | 39 +++++++++++++++++++++++++++++++--------
 util/sqlgen/order_by.go  | 27 ++++++++++++++++++++++++---
 util/sqlgen/table.go     |  4 ++--
 util/sqlgen/value.go     |  6 +++---
 9 files changed, 73 insertions(+), 22 deletions(-)

diff --git a/util/sqlgen/column.go b/util/sqlgen/column.go
index 282fe579..7909654f 100644
--- a/util/sqlgen/column.go
+++ b/util/sqlgen/column.go
@@ -5,11 +5,11 @@ import (
 )
 
 type Column struct {
-	v string
+	Value string
 }
 
 func (self Column) String() string {
-	chunks := strings.Split(self.v, Layout.ColumnSeparator)
+	chunks := strings.Split(self.Value, Layout.ColumnSeparator)
 
 	for i := range chunks {
 		chunks[i] = mustParse(Layout.IdentifierQuote, Raw{chunks[i]})
diff --git a/util/sqlgen/database.go b/util/sqlgen/database.go
index 6d77c955..e61f1f36 100644
--- a/util/sqlgen/database.go
+++ b/util/sqlgen/database.go
@@ -5,9 +5,9 @@ import (
 )
 
 type Database struct {
-	v string
+	Value string
 }
 
 func (self Database) String() string {
-	return mustParse(Layout.IdentifierQuote, Raw{fmt.Sprintf(`%v`, self.v)})
+	return mustParse(Layout.IdentifierQuote, Raw{fmt.Sprintf(`%v`, self.Value)})
 }
diff --git a/util/sqlgen/default.go b/util/sqlgen/default.go
index baf78211..2924c611 100644
--- a/util/sqlgen/default.go
+++ b/util/sqlgen/default.go
@@ -17,9 +17,11 @@ const (
 	defaultClauseOperator  = ` {{.}} `
 	defaultColumnValue     = `{{.Column}} {{.Operator}} {{.Value}}`
 
+	defaultSortByColumnLayout = `{{.Column}} {{.Sort}}`
+
 	defaultOrderByLayout = `
-		{{if .Columns}}
-			ORDER BY {{.Columns}} {{.Sort}}
+		{{if .SortColumns}}
+			ORDER BY {{.SortColumns}}
 		{{end}}
 	`
 
@@ -76,6 +78,7 @@ const (
 			({{.Columns}})
 		VALUES
 			({{.Values}})
+		{{.Extra}}
 	`
 
 	defaultTruncateLayout = `
diff --git a/util/sqlgen/layout.go b/util/sqlgen/layout.go
index 9e928191..c4bc6159 100644
--- a/util/sqlgen/layout.go
+++ b/util/sqlgen/layout.go
@@ -15,6 +15,7 @@ type layout struct {
 	ClauseGroup         string
 	ClauseOperator      string
 	ColumnValue         string
+	SortByColumnLayout  string
 	WhereLayout         string
 	OrderByLayout       string
 	InsertLayout        string
@@ -42,6 +43,7 @@ var Layout = layout{
 	defaultClauseGroup,
 	defaultClauseOperator,
 	defaultColumnValue,
+	defaultSortByColumnLayout,
 	defaultWhereLayout,
 	defaultOrderByLayout,
 	defaultInsertLayout,
diff --git a/util/sqlgen/main.go b/util/sqlgen/main.go
index fabdf6ff..35c61094 100644
--- a/util/sqlgen/main.go
+++ b/util/sqlgen/main.go
@@ -21,6 +21,7 @@ const (
 type (
 	Limit  int
 	Offset int
+	Extra  string
 )
 
 func mustParse(text string, data interface{}) string {
@@ -45,6 +46,7 @@ type Statement struct {
 	Values
 	ColumnValues
 	OrderBy
+	Extra
 	Where
 }
 
diff --git a/util/sqlgen/main_test.go b/util/sqlgen/main_test.go
index c3431854..5ff0d214 100644
--- a/util/sqlgen/main_test.go
+++ b/util/sqlgen/main_test.go
@@ -228,8 +228,8 @@ func TestSelectFieldsFromWithOrderBy(t *testing.T) {
 			{"baz"},
 		},
 		OrderBy: OrderBy{
-			Columns: Columns{
-				{"foo"},
+			SortColumns: SortColumns{
+				SortColumn{Column: Column{"foo"}},
 			},
 		},
 		Table: Table{"table name"},
@@ -251,10 +251,9 @@ func TestSelectFieldsFromWithOrderBy(t *testing.T) {
 			{"baz"},
 		},
 		OrderBy: OrderBy{
-			Columns: Columns{
-				{"foo"},
+			SortColumns{
+				SortColumn{Column{"foo"}, Sort{SqlSortAsc}},
 			},
-			Sort: Sort{SqlSortAsc},
 		},
 		Table: Table{"table name"},
 	}
@@ -275,10 +274,9 @@ func TestSelectFieldsFromWithOrderBy(t *testing.T) {
 			{"baz"},
 		},
 		OrderBy: OrderBy{
-			Columns: Columns{
-				{"foo"},
+			SortColumns{
+				{Column{"foo"}, Sort{SqlSortDesc}},
 			},
-			Sort: Sort{SqlSortDesc},
 		},
 		Table: Table{"table name"},
 	}
@@ -289,6 +287,31 @@ func TestSelectFieldsFromWithOrderBy(t *testing.T) {
 	if s != e {
 		t.Fatalf("Got: %s, Expecting: %s", s, e)
 	}
+
+	// ORDER BY many fields
+	stmt = Statement{
+		Type: SqlSelect,
+		Columns: Columns{
+			{"foo"},
+			{"bar"},
+			{"baz"},
+		},
+		OrderBy: OrderBy{
+			SortColumns{
+				{Column{"foo"}, Sort{SqlSortDesc}},
+				{Column{"bar"}, Sort{SqlSortAsc}},
+				{Column{"baz"}, Sort{SqlSortDesc}},
+			},
+		},
+		Table: Table{"table name"},
+	}
+
+	s = trim(stmt.Compile())
+	e = `SELECT "foo", "bar", "baz" FROM "table name" ORDER BY "foo" DESC, "bar" ASC, "baz" DESC`
+
+	if s != e {
+		t.Fatalf("Got: %s, Expecting: %s", s, e)
+	}
 }
 
 func TestSelectFieldsFromWhere(t *testing.T) {
diff --git a/util/sqlgen/order_by.go b/util/sqlgen/order_by.go
index 198b33bd..754dee3e 100644
--- a/util/sqlgen/order_by.go
+++ b/util/sqlgen/order_by.go
@@ -1,12 +1,33 @@
 package sqlgen
 
-type OrderBy struct {
-	Columns
+import "strings"
+
+type SortColumn struct {
+	Column
 	Sort
 }
 
+type SortColumns []SortColumn
+
+func (self SortColumns) String() string {
+	l := len(self)
+	s := make([]string, 0, l)
+	for i := 0; i < l; i++ {
+		s = append(s, self[i].String())
+	}
+	return strings.Join(s, Layout.IdentifierSeparator)
+}
+
+func (self SortColumn) String() string {
+	return mustParse(Layout.SortByColumnLayout, self)
+}
+
+type OrderBy struct {
+	SortColumns
+}
+
 func (self OrderBy) String() string {
-	if self.Columns.Len() > 0 {
+	if len(self.SortColumns) > 0 {
 		return mustParse(Layout.OrderByLayout, self)
 	}
 	return ""
diff --git a/util/sqlgen/table.go b/util/sqlgen/table.go
index ddd3006a..d8093472 100644
--- a/util/sqlgen/table.go
+++ b/util/sqlgen/table.go
@@ -5,9 +5,9 @@ import (
 )
 
 type Table struct {
-	v string
+	Value string
 }
 
 func (self Table) String() string {
-	return mustParse(Layout.IdentifierQuote, Raw{fmt.Sprintf(`%v`, self.v)})
+	return mustParse(Layout.IdentifierQuote, Raw{fmt.Sprintf(`%v`, self.Value)})
 }
diff --git a/util/sqlgen/value.go b/util/sqlgen/value.go
index 859c8fcd..2f77a7c6 100644
--- a/util/sqlgen/value.go
+++ b/util/sqlgen/value.go
@@ -8,14 +8,14 @@ import (
 type Values []Value
 
 type Value struct {
-	v interface{}
+	Value interface{}
 }
 
 func (self Value) String() string {
-	if raw, ok := self.v.(Raw); ok {
+	if raw, ok := self.Value.(Raw); ok {
 		return raw.Raw
 	}
-	return mustParse(Layout.ValueQuote, Raw{fmt.Sprintf(`%v`, self.v)})
+	return mustParse(Layout.ValueQuote, Raw{fmt.Sprintf(`%v`, self.Value)})
 }
 
 func (self Values) String() string {
-- 
GitLab