diff --git a/delete.go b/delete.go new file mode 100644 index 0000000..40896e8 --- /dev/null +++ b/delete.go @@ -0,0 +1,69 @@ +package simql + +import ( + "strings" +) + +// https://www.sqlite.org/lang_delete.html +type DeleteQuery struct { + table SelectTable + + where []Where + args []any +} + +func (q *DeleteQuery) Args() []any { + return q.args +} + +func (q *DeleteQuery) IsValid() bool { + if !q.table.IsValid() { + return false + } + + for _, w := range q.where { + if !w.IsValid() { + return false + } + } + + return false +} + +func (q *DeleteQuery) String() string { + strs := []string{"delete", q.table.String()} + + if len(q.where) > 0 { + strs = append(strs, "where") + + for _, w := range q.where { + strs = append(strs, w.String()) + } + } + + return strings.Join(strs, " ") +} + +func (q *DeleteQuery) Where(def string, args ...any) *DeleteQuery { + q.where = append(q.where, Where(def)) + + if len(args) > 0 { + if q.args == nil { + q.args = []any{} + } + + q.args = append(q.args, args...) + } + + return q +} + +func Delete(from string) *DeleteQuery { + q := &DeleteQuery{ + table: From(from), + + where: []Where{}, + } + + return q +} diff --git a/delete_test.go b/delete_test.go new file mode 100644 index 0000000..3985cab --- /dev/null +++ b/delete_test.go @@ -0,0 +1,47 @@ +package simql + +import ( + "testing" + + "github.com/alecthomas/assert/v2" +) + +func TestDelete(t *testing.T) { + type TestCase struct { + In *DeleteQuery + Args []any + String string + } + + testCases := []TestCase{ + { + In: Delete("customer"), + String: "delete from customer", + }, + { + In: Delete("customer as c"), + String: "delete from customer as c", + }, + { + In: Delete("customer as c"), + String: "select c.id, c.name from customer as c", + }, + { + In: Delete("customer").Where("id = ?", 1234), + Args: []any{1234}, + String: "delete from customer where id = ?", + }, + { + In: Delete("customer as c").Where("c.id = ?", 1234), + Args: []any{1234}, + String: "delete from customer as c where c.id = ?", + }, + } + + for _, testCase := range testCases { + t.Run(testCase.String, func(t *testing.T) { + assert.Equal(t, testCase.Args, testCase.In.Args(), "collected arguments incorrectly") + assert.Equal(t, testCase.String, testCase.In.String(), "stringified incorrectly") + }) + } +} diff --git a/select.go b/select.go index 0f9d5db..3a42849 100644 --- a/select.go +++ b/select.go @@ -25,38 +25,38 @@ type SelectQuery struct { offset int } -func (s *SelectQuery) Args() []any { - return s.args +func (q *SelectQuery) Args() []any { + return q.args } -func (s *SelectQuery) Columns(defs ...string) *SelectQuery { +func (q *SelectQuery) Columns(defs ...string) *SelectQuery { for _, def := range defs { - s.columns = append(s.columns, Column(def)) + q.columns = append(q.columns, Column(def)) } - return s + return q } -func (s *SelectQuery) Distinct(distinct bool) *SelectQuery { - s.distinct = distinct +func (q *SelectQuery) Distinct(distinct bool) *SelectQuery { + q.distinct = distinct - return s + return q } -func (s *SelectQuery) IsValid() bool { - for _, c := range s.columns { +func (q *SelectQuery) IsValid() bool { + for _, c := range q.columns { if !c.IsValid() { return false } } - for _, t := range s.tables { + for _, t := range q.tables { if !t.IsValid() { return false } } - for _, w := range s.where { + for _, w := range q.where { if !w.IsValid() { return false } @@ -65,53 +65,53 @@ func (s *SelectQuery) IsValid() bool { return false } -func (s *SelectQuery) LeftJoin(def string) *SelectQuery { - s.tables = append(s.tables, LeftJoin(def)) - return s +func (q *SelectQuery) LeftJoin(def string) *SelectQuery { + q.tables = append(q.tables, LeftJoin(def)) + return q } -func (s *SelectQuery) Limit(limit int) *SelectQuery { - s.limit = limit - return s +func (q *SelectQuery) Limit(limit int) *SelectQuery { + q.limit = limit + return q } -func (s *SelectQuery) InnerJoin(def string) *SelectQuery { - s.tables = append(s.tables, InnerJoin(def)) - return s +func (q *SelectQuery) InnerJoin(def string) *SelectQuery { + q.tables = append(q.tables, InnerJoin(def)) + return q } -func (s *SelectQuery) RightJoin(def string) *SelectQuery { - s.tables = append(s.tables, RightJoin(def)) - return s +func (q *SelectQuery) RightJoin(def string) *SelectQuery { + q.tables = append(q.tables, RightJoin(def)) + return q } -func (s *SelectQuery) Offset(limit int) *SelectQuery { - s.limit = limit - return s +func (q *SelectQuery) Offset(limit int) *SelectQuery { + q.limit = limit + return q } -func (s *SelectQuery) OrderBy(defs ...string) *SelectQuery { - if s.orderBy == nil { - s.orderBy = []OrderBy{} +func (q *SelectQuery) OrderBy(defs ...string) *SelectQuery { + if q.orderBy == nil { + q.orderBy = []OrderBy{} } for _, def := range defs { - s.orderBy = append(s.orderBy, OrderBy(def)) + q.orderBy = append(q.orderBy, OrderBy(def)) } - return s + return q } -func (s *SelectQuery) String() string { +func (q *SelectQuery) String() string { strs := []string{"select"} - if s.distinct { + if q.distinct { strs = append(strs, "distinct") } - if len(s.columns) > 0 { - for i, column := range s.columns { - if i < len(s.columns)-1 { + if len(q.columns) > 0 { + for i, column := range q.columns { + if i < len(q.columns)-1 { strs = append(strs, fmt.Sprintf("%s,", column)) } else { strs = append(strs, column.String()) @@ -121,23 +121,23 @@ func (s *SelectQuery) String() string { strs = append(strs, "*") } - for _, table := range s.tables { + for _, table := range q.tables { strs = append(strs, table.String()) } - if len(s.where) > 0 { + if len(q.where) > 0 { strs = append(strs, "where") - for _, w := range s.where { + for _, w := range q.where { strs = append(strs, w.String()) } } - if len(s.orderBy) > 0 { + if len(q.orderBy) > 0 { strs = append(strs, "order by") - for i, o := range s.orderBy { - if i < len(s.orderBy)-1 { + for i, o := range q.orderBy { + if i < len(q.orderBy)-1 { strs = append(strs, fmt.Sprintf("%s,", o)) } else { strs = append(strs, o.String()) @@ -145,38 +145,38 @@ func (s *SelectQuery) String() string { } } - if s.limit > 0 { - if s.offset > 0 { - strs = append(strs, fmt.Sprintf("limit %d offset %d", s.offset, s.limit)) + if q.limit > 0 { + if q.offset > 0 { + strs = append(strs, fmt.Sprintf("limit %d offset %d", q.offset, q.limit)) } else { - strs = append(strs, fmt.Sprintf("limit %d", s.limit)) + strs = append(strs, fmt.Sprintf("limit %d", q.limit)) } } return strings.Join(strs, " ") } -func (s *SelectQuery) Where(def string, args ...any) *SelectQuery { - s.where = append(s.where, Where(def)) +func (q *SelectQuery) Where(def string, args ...any) *SelectQuery { + q.where = append(q.where, Where(def)) if len(args) > 0 { - if s.args == nil { - s.args = []any{} + if q.args == nil { + q.args = []any{} } - s.args = append(s.args, args...) + q.args = append(q.args, args...) } - return s + return q } func Select(from string) *SelectQuery { - s := &SelectQuery{ + q := &SelectQuery{ columns: []Column{}, tables: []SelectTable{From(from)}, where: []Where{}, } - return s + return q }