...

Source file src/github.com/doug-martin/goqu/v9/sqlgen/delete_sql_generator_test.go

Documentation: github.com/doug-martin/goqu/v9/sqlgen

     1  package sqlgen_test
     2  
     3  import (
     4  	"testing"
     5  
     6  	"github.com/doug-martin/goqu/v9/exp"
     7  	"github.com/doug-martin/goqu/v9/internal/errors"
     8  	"github.com/doug-martin/goqu/v9/internal/sb"
     9  	"github.com/doug-martin/goqu/v9/sqlgen"
    10  	"github.com/stretchr/testify/suite"
    11  )
    12  
    13  type (
    14  	deleteTestCase struct {
    15  		clause     exp.DeleteClauses
    16  		sql        string
    17  		isPrepared bool
    18  		args       []interface{}
    19  		err        string
    20  	}
    21  	deleteSQLGeneratorSuite struct {
    22  		baseSQLGeneratorSuite
    23  	}
    24  )
    25  
    26  func (dsgs *deleteSQLGeneratorSuite) assertCases(dsg sqlgen.DeleteSQLGenerator, testCases ...deleteTestCase) {
    27  	for _, tc := range testCases {
    28  		b := sb.NewSQLBuilder(tc.isPrepared)
    29  		dsg.Generate(b, tc.clause)
    30  		switch {
    31  		case len(tc.err) > 0:
    32  			dsgs.assertErrorSQL(b, tc.err)
    33  		case tc.isPrepared:
    34  			dsgs.assertPreparedSQL(b, tc.sql, tc.args)
    35  		default:
    36  			dsgs.assertNotPreparedSQL(b, tc.sql)
    37  		}
    38  	}
    39  }
    40  
    41  func (dsgs *deleteSQLGeneratorSuite) TestDialect() {
    42  	opts := sqlgen.DefaultDialectOptions()
    43  	d := sqlgen.NewDeleteSQLGenerator("test", opts)
    44  	dsgs.Equal("test", d.Dialect())
    45  
    46  	opts2 := sqlgen.DefaultDialectOptions()
    47  	d2 := sqlgen.NewDeleteSQLGenerator("test2", opts2)
    48  	dsgs.Equal("test2", d2.Dialect())
    49  }
    50  
    51  func (dsgs *deleteSQLGeneratorSuite) TestGenerate() {
    52  	dc := exp.NewDeleteClauses().
    53  		SetFrom(exp.NewIdentifierExpression("", "test", ""))
    54  
    55  	dsgs.assertCases(
    56  		sqlgen.NewDeleteSQLGenerator("test", sqlgen.DefaultDialectOptions()),
    57  		deleteTestCase{clause: dc, sql: `DELETE FROM "test"`},
    58  		deleteTestCase{clause: dc, sql: `DELETE FROM "test"`, isPrepared: true},
    59  	)
    60  
    61  	opts2 := sqlgen.DefaultDialectOptions()
    62  	opts2.DeleteClause = []byte("delete")
    63  
    64  	dsgs.assertCases(
    65  		sqlgen.NewDeleteSQLGenerator("test", opts2),
    66  		deleteTestCase{clause: dc, sql: `delete FROM "test"`},
    67  		deleteTestCase{clause: dc, sql: `delete FROM "test"`, isPrepared: true},
    68  	)
    69  }
    70  
    71  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_withUnsupportedFragment() {
    72  	opts := sqlgen.DefaultDialectOptions()
    73  	opts.DeleteSQLOrder = []sqlgen.SQLFragmentType{sqlgen.InsertBeingSQLFragment}
    74  	dc := exp.NewDeleteClauses().
    75  		SetFrom(exp.NewIdentifierExpression("", "test", ""))
    76  
    77  	dsgs.assertCases(
    78  		sqlgen.NewDeleteSQLGenerator("test", opts),
    79  		deleteTestCase{clause: dc, err: `goqu: unsupported DELETE SQL fragment InsertBeingSQLFragment`},
    80  		deleteTestCase{clause: dc, err: `goqu: unsupported DELETE SQL fragment InsertBeingSQLFragment`, isPrepared: true},
    81  	)
    82  }
    83  
    84  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_noFrom() {
    85  	dc := exp.NewDeleteClauses()
    86  	dsgs.assertCases(
    87  		sqlgen.NewDeleteSQLGenerator("test", sqlgen.DefaultDialectOptions()),
    88  		deleteTestCase{clause: dc, err: sqlgen.ErrNoSourceForDelete.Error()},
    89  		deleteTestCase{clause: dc, err: sqlgen.ErrNoSourceForDelete.Error(), isPrepared: true},
    90  	)
    91  }
    92  
    93  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_withErroredBuilder() {
    94  	opts := sqlgen.DefaultDialectOptions()
    95  	d := sqlgen.NewDeleteSQLGenerator("test", opts)
    96  
    97  	dc := exp.NewDeleteClauses().SetFrom(exp.NewIdentifierExpression("", "test", ""))
    98  	b := sb.NewSQLBuilder(false).SetError(errors.New("expected error"))
    99  	d.Generate(b, dc)
   100  	dsgs.assertErrorSQL(b, "goqu: expected error")
   101  
   102  	b = sb.NewSQLBuilder(true).SetError(errors.New("expected error"))
   103  	d.Generate(b, dc)
   104  	dsgs.assertErrorSQL(b, "goqu: expected error")
   105  }
   106  
   107  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_withCommonTables() {
   108  	opts := sqlgen.DefaultDialectOptions()
   109  	opts.WithFragment = []byte("with ")
   110  	opts.RecursiveFragment = []byte("recursive ")
   111  
   112  	tse := newTestAppendableExpression("select * from foo", emptyArgs, nil, nil)
   113  
   114  	dc := exp.NewDeleteClauses().SetFrom(exp.NewIdentifierExpression("", "test_cte", ""))
   115  	dcCte1 := dc.CommonTablesAppend(exp.NewCommonTableExpression(false, "test_cte", tse))
   116  	dcCte2 := dc.CommonTablesAppend(exp.NewCommonTableExpression(true, "test_cte", tse))
   117  
   118  	dsgs.assertCases(
   119  		sqlgen.NewDeleteSQLGenerator("test", opts),
   120  		deleteTestCase{clause: dcCte1, sql: `with test_cte AS (select * from foo) DELETE FROM "test_cte"`},
   121  		deleteTestCase{clause: dcCte1, sql: `with test_cte AS (select * from foo) DELETE FROM "test_cte"`, isPrepared: true},
   122  
   123  		deleteTestCase{clause: dcCte2, sql: `with recursive test_cte AS (select * from foo) DELETE FROM "test_cte"`},
   124  		deleteTestCase{clause: dcCte2, sql: `with recursive test_cte AS (select * from foo) DELETE FROM "test_cte"`, isPrepared: true},
   125  	)
   126  
   127  	opts.SupportsWithCTE = false
   128  	expectedErr := sqlgen.ErrCTENotSupported("test")
   129  	dsgs.assertCases(
   130  		sqlgen.NewDeleteSQLGenerator("test", opts),
   131  		deleteTestCase{clause: dcCte1, err: expectedErr.Error()},
   132  		deleteTestCase{clause: dcCte1, err: expectedErr.Error(), isPrepared: true},
   133  
   134  		deleteTestCase{clause: dcCte2, err: expectedErr.Error()},
   135  		deleteTestCase{clause: dcCte2, err: expectedErr.Error(), isPrepared: true},
   136  	)
   137  
   138  	opts.SupportsWithCTE = true
   139  	opts.SupportsWithCTERecursive = false
   140  	expectedErr = sqlgen.ErrRecursiveCTENotSupported("test")
   141  	dsgs.assertCases(
   142  		sqlgen.NewDeleteSQLGenerator("test", opts),
   143  		deleteTestCase{clause: dcCte1, sql: `with test_cte AS (select * from foo) DELETE FROM "test_cte"`},
   144  		deleteTestCase{clause: dcCte1, sql: `with test_cte AS (select * from foo) DELETE FROM "test_cte"`, isPrepared: true},
   145  
   146  		deleteTestCase{clause: dcCte2, err: expectedErr.Error()},
   147  		deleteTestCase{clause: dcCte2, err: expectedErr.Error(), isPrepared: true},
   148  	)
   149  }
   150  
   151  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_withWhere() {
   152  	dc := exp.NewDeleteClauses().
   153  		SetFrom(exp.NewIdentifierExpression("", "test", "")).
   154  		WhereAppend(exp.NewLiteralExpression(`"a"=?`, 1))
   155  	dsgs.assertCases(
   156  		sqlgen.NewDeleteSQLGenerator("test", sqlgen.DefaultDialectOptions()),
   157  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" WHERE "a"=1`},
   158  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" WHERE "a"=?`, isPrepared: true, args: []interface{}{
   159  			int64(1),
   160  		}},
   161  	)
   162  }
   163  
   164  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_withOrder() {
   165  	opts := sqlgen.DefaultDialectOptions()
   166  	opts.SupportsOrderByOnDelete = true
   167  
   168  	dc := exp.NewDeleteClauses().
   169  		SetFrom(exp.NewIdentifierExpression("", "test", "")).
   170  		SetOrder(exp.NewIdentifierExpression("", "", "c").Desc())
   171  
   172  	dsgs.assertCases(
   173  		sqlgen.NewDeleteSQLGenerator("test", opts),
   174  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" ORDER BY "c" DESC`},
   175  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" ORDER BY "c" DESC`, isPrepared: true},
   176  	)
   177  
   178  	opts.SupportsOrderByOnDelete = false
   179  	dsgs.assertCases(
   180  		sqlgen.NewDeleteSQLGenerator("test", opts),
   181  		deleteTestCase{clause: dc, sql: `DELETE FROM "test"`},
   182  		deleteTestCase{clause: dc, sql: `DELETE FROM "test"`, isPrepared: true},
   183  	)
   184  }
   185  
   186  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_withLimit() {
   187  	opts := sqlgen.DefaultDialectOptions()
   188  	opts.SupportsLimitOnDelete = true
   189  
   190  	dc := exp.NewDeleteClauses().
   191  		SetFrom(exp.NewIdentifierExpression("", "test", "")).
   192  		SetLimit(1)
   193  
   194  	dsgs.assertCases(
   195  		sqlgen.NewDeleteSQLGenerator("test", opts),
   196  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" LIMIT 1`},
   197  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" LIMIT ?`, isPrepared: true, args: []interface{}{int64(1)}},
   198  	)
   199  
   200  	opts.SupportsLimitOnDelete = false
   201  	dsgs.assertCases(
   202  		sqlgen.NewDeleteSQLGenerator("test", opts),
   203  		deleteTestCase{clause: dc, sql: `DELETE FROM "test"`},
   204  		deleteTestCase{clause: dc, sql: `DELETE FROM "test"`, isPrepared: true},
   205  	)
   206  }
   207  
   208  func (dsgs *deleteSQLGeneratorSuite) TestGenerate_withReturning() {
   209  	opts := sqlgen.DefaultDialectOptions()
   210  	opts.SupportsReturn = true
   211  
   212  	dc := exp.NewDeleteClauses().
   213  		SetFrom(exp.NewIdentifierExpression("", "test", "")).
   214  		SetReturning(exp.NewColumnListExpression("a", "b"))
   215  
   216  	dsgs.assertCases(
   217  		sqlgen.NewDeleteSQLGenerator("test", opts),
   218  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" RETURNING "a", "b"`},
   219  		deleteTestCase{clause: dc, sql: `DELETE FROM "test" RETURNING "a", "b"`, isPrepared: true},
   220  	)
   221  
   222  	opts.SupportsReturn = false
   223  	expectedErr := `goqu: dialect does not support RETURNING clause [dialect=test]`
   224  	dsgs.assertCases(
   225  		sqlgen.NewDeleteSQLGenerator("test", opts),
   226  		deleteTestCase{clause: dc, err: expectedErr},
   227  		deleteTestCase{clause: dc, err: expectedErr, isPrepared: true},
   228  	)
   229  }
   230  
   231  func TestDeleteSQLGenerator(t *testing.T) {
   232  	suite.Run(t, new(deleteSQLGeneratorSuite))
   233  }
   234  

View as plain text