@@ -47,8 +47,10 @@ type UpdateBuilder struct {
4747 whereClauseProxy * whereClauseProxy
4848 whereClauseExpr string
4949
50- cteBuilder string
51- table string
50+ cteBuilderVar string
51+ cteBuilder * CTEBuilder
52+
53+ tables []string
5254 assignments []string
5355 orderByCols []string
5456 order string
@@ -63,24 +65,46 @@ type UpdateBuilder struct {
6365var _ Builder = new (UpdateBuilder )
6466
6567// Update sets table name in UPDATE.
66- func Update (table string ) * UpdateBuilder {
67- return DefaultFlavor .NewUpdateBuilder ().Update (table )
68+ func Update (table ... string ) * UpdateBuilder {
69+ return DefaultFlavor .NewUpdateBuilder ().Update (table ... )
6870}
6971
7072// With sets WITH clause (the Common Table Expression) before UPDATE.
7173func (ub * UpdateBuilder ) With (builder * CTEBuilder ) * UpdateBuilder {
7274 ub .marker = updateMarkerAfterWith
73- ub .cteBuilder = ub .Var (builder )
75+ ub .cteBuilderVar = ub .Var (builder )
76+ ub .cteBuilder = builder
7477 return ub
7578}
7679
7780// Update sets table name in UPDATE.
78- func (ub * UpdateBuilder ) Update (table string ) * UpdateBuilder {
79- ub .table = Escape ( table )
81+ func (ub * UpdateBuilder ) Update (table ... string ) * UpdateBuilder {
82+ ub .tables = table
8083 ub .marker = updateMarkerAfterUpdate
8184 return ub
8285}
8386
87+ // TableNames returns all table names in this UPDATE statement.
88+ func (ub * UpdateBuilder ) TableNames () (tableNames []string ) {
89+ var additionalTableNames []string
90+
91+ if ub .cteBuilder != nil {
92+ additionalTableNames = ub .cteBuilder .tableNamesForFrom ()
93+ }
94+
95+ if len (ub .tables ) > 0 && len (additionalTableNames ) > 0 {
96+ tableNames = make ([]string , len (ub .tables )+ len (additionalTableNames ))
97+ copy (tableNames , ub .tables )
98+ copy (tableNames [len (ub .tables ):], additionalTableNames )
99+ } else if len (ub .tables ) > 0 {
100+ tableNames = ub .tables
101+ } else if len (additionalTableNames ) > 0 {
102+ tableNames = additionalTableNames
103+ }
104+
105+ return tableNames
106+ }
107+
84108// Set sets the assignments in SET.
85109func (ub * UpdateBuilder ) Set (assignment ... string ) * UpdateBuilder {
86110 ub .assignments = assignment
@@ -212,14 +236,36 @@ func (ub *UpdateBuilder) BuildWithFlavor(flavor Flavor, initialArg ...interface{
212236 buf := newStringBuilder ()
213237 ub .injection .WriteTo (buf , updateMarkerInit )
214238
215- if ub .cteBuilder != "" {
216- buf .WriteLeadingString (ub .cteBuilder )
239+ if ub .cteBuilder != nil {
240+ buf .WriteLeadingString (ub .cteBuilderVar )
217241 ub .injection .WriteTo (buf , updateMarkerAfterWith )
218242 }
219243
220- if len (ub .table ) > 0 {
221- buf .WriteLeadingString ("UPDATE " )
222- buf .WriteString (ub .table )
244+ switch flavor {
245+ case MySQL :
246+ // CTE table names should be written after UPDATE keyword in MySQL.
247+ tableNames := ub .TableNames ()
248+
249+ if len (tableNames ) > 0 {
250+ buf .WriteLeadingString ("UPDATE " )
251+ buf .WriteStrings (tableNames , ", " )
252+ }
253+
254+ default :
255+ if len (ub .tables ) > 0 {
256+ buf .WriteLeadingString ("UPDATE " )
257+ buf .WriteStrings (ub .tables , ", " )
258+
259+ // For ISO SQL, CTE table names should be written after FROM keyword.
260+ if ub .cteBuilder != nil {
261+ cteTableNames := ub .cteBuilder .tableNamesForFrom ()
262+
263+ if len (cteTableNames ) > 0 {
264+ buf .WriteLeadingString ("FROM " )
265+ buf .WriteStrings (cteTableNames , ", " )
266+ }
267+ }
268+ }
223269 }
224270
225271 ub .injection .WriteTo (buf , updateMarkerAfterUpdate )
0 commit comments