github.com/Ali-iotechsys/sqlboiler/v4@v4.0.0-20221208124957-6aec9a5f1f71/templates/main/12_relationship_to_many_setops.go.tpl (about) 1 {{- if or .Table.IsJoinTable .Table.IsView -}} 2 {{- else -}} 3 {{- $table := .Table -}} 4 {{- range $rel := .Table.ToManyRelationships -}} 5 {{- $ltable := $.Aliases.Table $rel.Table -}} 6 {{- $ftable := $.Aliases.Table $rel.ForeignTable -}} 7 {{- $relAlias := $.Aliases.ManyRelationship $rel.ForeignTable $rel.Name $rel.JoinTable $rel.JoinLocalFKeyName -}} 8 {{- $col := $ltable.Column $rel.Column -}} 9 {{- $fcol := $ftable.Column $rel.ForeignColumn -}} 10 {{- $usesPrimitives := usesPrimitives $.Tables $rel.Table $rel.Column $rel.ForeignTable $rel.ForeignColumn -}} 11 {{- $schemaForeignTable := $rel.ForeignTable | $.SchemaTable }} 12 {{- $foreignPKeyCols := (getTable $.Tables $rel.ForeignTable).PKey.Columns }} 13 {{if $.AddGlobal -}} 14 // Add{{$relAlias.Local}}G adds the given related objects to the existing relationships 15 // of the {{$table.Name | singular}}, optionally inserting them as new records. 16 // Appends related to o.R.{{$relAlias.Local}}. 17 {{- if not $.NoBackReferencing}} 18 // Sets related.R.{{$relAlias.Foreign}} appropriately. 19 {{- end}} 20 // Uses the global database handle. 21 func (o *{{$ltable.UpSingular}}) Add{{$relAlias.Local}}G({{if not $.NoContext}}ctx context.Context, {{end -}} insert bool, related ...*{{$ftable.UpSingular}}) error { 22 return o.Add{{$relAlias.Local}}({{if $.NoContext}}boil.GetDB(){{else}}ctx, boil.GetContextDB(){{end}}, insert, related...) 23 } 24 25 {{end -}} 26 27 {{if $.AddPanic -}} 28 // Add{{$relAlias.Local}}P adds the given related objects to the existing relationships 29 // of the {{$table.Name | singular}}, optionally inserting them as new records. 30 // Appends related to o.R.{{$relAlias.Local}}. 31 {{- if not $.NoBackReferencing}} 32 // Sets related.R.{{$relAlias.Foreign}} appropriately. 33 {{- end}} 34 // Panics on error. 35 func (o *{{$ltable.UpSingular}}) Add{{$relAlias.Local}}P({{if $.NoContext}}exec boil.Executor{{else}}ctx context.Context, exec boil.ContextExecutor{{end}}, insert bool, related ...*{{$ftable.UpSingular}}) { 36 if err := o.Add{{$relAlias.Local}}({{if not $.NoContext}}ctx, {{end -}} exec, insert, related...); err != nil { 37 panic(boil.WrapErr(err)) 38 } 39 } 40 41 {{end -}} 42 43 {{if and $.AddGlobal $.AddPanic -}} 44 // Add{{$relAlias.Local}}GP adds the given related objects to the existing relationships 45 // of the {{$table.Name | singular}}, optionally inserting them as new records. 46 // Appends related to o.R.{{$relAlias.Local}}. 47 {{- if not $.NoBackReferencing}} 48 // Sets related.R.{{$relAlias.Foreign}} appropriately. 49 {{- end}} 50 // Uses the global database handle and panics on error. 51 func (o *{{$ltable.UpSingular}}) Add{{$relAlias.Local}}GP({{if not $.NoContext}}ctx context.Context, {{end -}} insert bool, related ...*{{$ftable.UpSingular}}) { 52 if err := o.Add{{$relAlias.Local}}({{if $.NoContext}}boil.GetDB(){{else}}ctx, boil.GetContextDB(){{end}}, insert, related...); err != nil { 53 panic(boil.WrapErr(err)) 54 } 55 } 56 57 {{end -}} 58 59 // Add{{$relAlias.Local}} adds the given related objects to the existing relationships 60 // of the {{$table.Name | singular}}, optionally inserting them as new records. 61 // Appends related to o.R.{{$relAlias.Local}}. 62 {{- if not $.NoBackReferencing}} 63 // Sets related.R.{{$relAlias.Foreign}} appropriately. 64 {{- end}} 65 func (o *{{$ltable.UpSingular}}) Add{{$relAlias.Local}}({{if $.NoContext}}exec boil.Executor{{else}}ctx context.Context, exec boil.ContextExecutor{{end}}, insert bool, related ...*{{$ftable.UpSingular}}) error { 66 var err error 67 for _, rel := range related { 68 if insert { 69 {{if not .ToJoinTable -}} 70 {{if $usesPrimitives -}} 71 rel.{{$fcol}} = o.{{$col}} 72 {{else -}} 73 queries.Assign(&rel.{{$fcol}}, o.{{$col}}) 74 {{end -}} 75 {{end -}} 76 77 if err = rel.Insert({{if not $.NoContext}}ctx, {{end -}} exec, boil.Infer()); err != nil { 78 return errors.Wrap(err, "failed to insert into foreign table") 79 } 80 }{{if not .ToJoinTable}} else { 81 updateQuery := fmt.Sprintf( 82 "UPDATE {{$schemaForeignTable}} SET %s WHERE %s", 83 strmangle.SetParamNames("{{$.LQ}}", "{{$.RQ}}", {{if $.Dialect.UseIndexPlaceholders}}1{{else}}0{{end}}, []string{{"{"}}"{{.ForeignColumn}}"{{"}"}}), 84 strmangle.WhereClause("{{$.LQ}}", "{{$.RQ}}", {{if $.Dialect.UseIndexPlaceholders}}2{{else}}0{{end}}, {{$ftable.DownSingular}}PrimaryKeyColumns), 85 ) 86 values := []interface{}{o.{{$col}}, rel.{{$foreignPKeyCols | stringMap (aliasCols $ftable) | join ", rel."}}{{"}"}} 87 88 {{if $.NoContext -}} 89 if boil.DebugMode { 90 fmt.Fprintln(boil.DebugWriter, updateQuery) 91 fmt.Fprintln(boil.DebugWriter, values) 92 } 93 {{else -}} 94 if boil.IsDebug(ctx) { 95 writer := boil.DebugWriterFrom(ctx) 96 fmt.Fprintln(writer, updateQuery) 97 fmt.Fprintln(writer, values) 98 } 99 {{end -}} 100 101 {{if $.NoContext -}} 102 if _, err = exec.Exec(updateQuery, values...); err != nil { 103 {{else -}} 104 if _, err = exec.ExecContext(ctx, updateQuery, values...); err != nil { 105 {{end -}} 106 return errors.Wrap(err, "failed to update foreign table") 107 } 108 109 {{if $usesPrimitives -}} 110 rel.{{$fcol}} = o.{{$col}} 111 {{else -}} 112 queries.Assign(&rel.{{$fcol}}, o.{{$col}}) 113 {{end -}} 114 }{{end -}} 115 } 116 117 {{if .ToJoinTable -}} 118 for _, rel := range related { 119 query := "insert into {{.JoinTable | $.SchemaTable}} ({{.JoinLocalColumn | $.Quotes}}, {{.JoinForeignColumn | $.Quotes}}) values {{if $.Dialect.UseIndexPlaceholders}}($1, $2){{else}}(?, ?){{end}}" 120 values := []interface{}{{"{"}}o.{{$col}}, rel.{{$fcol}}} 121 122 {{if $.NoContext -}} 123 if boil.DebugMode { 124 fmt.Fprintln(boil.DebugWriter, query) 125 fmt.Fprintln(boil.DebugWriter, values) 126 } 127 {{else -}} 128 if boil.IsDebug(ctx) { 129 writer := boil.DebugWriterFrom(ctx) 130 fmt.Fprintln(writer, query) 131 fmt.Fprintln(writer, values) 132 } 133 {{end -}} 134 135 {{if $.NoContext -}} 136 _, err = exec.Exec(query, values...) 137 {{else -}} 138 _, err = exec.ExecContext(ctx, query, values...) 139 {{end -}} 140 if err != nil { 141 return errors.Wrap(err, "failed to insert into join table") 142 } 143 } 144 {{end -}} 145 146 if o.R == nil { 147 o.R = &{{$ltable.DownSingular}}R{ 148 {{$relAlias.Local}}: related, 149 } 150 } else { 151 o.R.{{$relAlias.Local}} = append(o.R.{{$relAlias.Local}}, related...) 152 } 153 154 {{if not $.NoBackReferencing -}} 155 {{if .ToJoinTable -}} 156 for _, rel := range related { 157 if rel.R == nil { 158 rel.R = &{{$ftable.DownSingular}}R{ 159 {{$relAlias.Foreign}}: {{$ltable.UpSingular}}Slice{{"{"}}o{{"}"}}, 160 } 161 } else { 162 rel.R.{{$relAlias.Foreign}} = append(rel.R.{{$relAlias.Foreign}}, o) 163 } 164 } 165 {{else -}} 166 for _, rel := range related { 167 if rel.R == nil { 168 rel.R = &{{$ftable.DownSingular}}R{ 169 {{$relAlias.Foreign}}: o, 170 } 171 } else { 172 rel.R.{{$relAlias.Foreign}} = o 173 } 174 } 175 {{end -}} 176 {{end -}} 177 178 return nil 179 } 180 181 {{- if (or .ForeignColumnNullable .ToJoinTable)}} 182 {{if $.AddGlobal -}} 183 // Set{{$relAlias.Local}}G removes all previously related items of the 184 // {{$table.Name | singular}} replacing them completely with the passed 185 // in related items, optionally inserting them as new records. 186 // Sets o.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 187 // Replaces o.R.{{$relAlias.Local}} with related. 188 {{- if not $.NoBackReferencing}} 189 // Sets related.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 190 {{- end}} 191 // Uses the global database handle. 192 func (o *{{$ltable.UpSingular}}) Set{{$relAlias.Local}}G({{if not $.NoContext}}ctx context.Context, {{end -}} insert bool, related ...*{{$ftable.UpSingular}}) error { 193 return o.Set{{$relAlias.Local}}({{if $.NoContext}}boil.GetDB(){{else}}ctx, boil.GetContextDB(){{end}}, insert, related...) 194 } 195 196 {{end -}} 197 198 {{if $.AddPanic -}} 199 // Set{{$relAlias.Local}}P removes all previously related items of the 200 // {{$table.Name | singular}} replacing them completely with the passed 201 // in related items, optionally inserting them as new records. 202 // Sets o.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 203 // Replaces o.R.{{$relAlias.Local}} with related. 204 {{- if not $.NoBackReferencing}} 205 // Sets related.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 206 {{- end}} 207 // Panics on error. 208 func (o *{{$ltable.UpSingular}}) Set{{$relAlias.Local}}P({{if $.NoContext}}exec boil.Executor{{else}}ctx context.Context, exec boil.ContextExecutor{{end}}, insert bool, related ...*{{$ftable.UpSingular}}) { 209 if err := o.Set{{$relAlias.Local}}({{if not $.NoContext}}ctx, {{end -}} exec, insert, related...); err != nil { 210 panic(boil.WrapErr(err)) 211 } 212 } 213 214 {{end -}} 215 216 {{if and $.AddGlobal $.AddPanic -}} 217 // Set{{$relAlias.Local}}GP removes all previously related items of the 218 // {{$table.Name | singular}} replacing them completely with the passed 219 // in related items, optionally inserting them as new records. 220 // Sets o.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 221 // Replaces o.R.{{$relAlias.Local}} with related. 222 {{- if not $.NoBackReferencing}} 223 // Sets related.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 224 {{- end}} 225 // Uses the global database handle and panics on error. 226 func (o *{{$ltable.UpSingular}}) Set{{$relAlias.Local}}GP({{if not $.NoContext}}ctx context.Context, {{end -}} insert bool, related ...*{{$ftable.UpSingular}}) { 227 if err := o.Set{{$relAlias.Local}}({{if $.NoContext}}boil.GetDB(){{else}}ctx, boil.GetContextDB(){{end}}, insert, related...); err != nil { 228 panic(boil.WrapErr(err)) 229 } 230 } 231 232 {{end -}} 233 234 // Set{{$relAlias.Local}} removes all previously related items of the 235 // {{$table.Name | singular}} replacing them completely with the passed 236 // in related items, optionally inserting them as new records. 237 // Sets o.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 238 // Replaces o.R.{{$relAlias.Local}} with related. 239 {{- if not $.NoBackReferencing}} 240 // Sets related.R.{{$relAlias.Foreign}}'s {{$relAlias.Local}} accordingly. 241 {{- end}} 242 func (o *{{$ltable.UpSingular}}) Set{{$relAlias.Local}}({{if $.NoContext}}exec boil.Executor{{else}}ctx context.Context, exec boil.ContextExecutor{{end}}, insert bool, related ...*{{$ftable.UpSingular}}) error { 243 {{if .ToJoinTable -}} 244 query := "delete from {{.JoinTable | $.SchemaTable}} where {{.JoinLocalColumn | $.Quotes}} = {{if $.Dialect.UseIndexPlaceholders}}$1{{else}}?{{end}}" 245 values := []interface{}{{"{"}}o.{{$col}}} 246 {{else -}} 247 query := "update {{.ForeignTable | $.SchemaTable}} set {{.ForeignColumn | $.Quotes}} = null where {{.ForeignColumn | $.Quotes}} = {{if $.Dialect.UseIndexPlaceholders}}$1{{else}}?{{end}}" 248 values := []interface{}{{"{"}}o.{{$col}}} 249 {{end -}} 250 {{if $.NoContext -}} 251 if boil.DebugMode { 252 fmt.Fprintln(boil.DebugWriter, query) 253 fmt.Fprintln(boil.DebugWriter, values) 254 } 255 {{else -}} 256 if boil.IsDebug(ctx) { 257 writer := boil.DebugWriterFrom(ctx) 258 fmt.Fprintln(writer, query) 259 fmt.Fprintln(writer, values) 260 } 261 {{end -}} 262 263 {{if $.NoContext -}} 264 _, err := exec.Exec(query, values...) 265 {{else -}} 266 _, err := exec.ExecContext(ctx, query, values...) 267 {{end -}} 268 if err != nil { 269 return errors.Wrap(err, "failed to remove relationships before set") 270 } 271 272 {{if and .ToJoinTable (not $.NoBackReferencing) -}} 273 remove{{$relAlias.Local}}From{{$relAlias.Foreign}}Slice(o, related) 274 if o.R != nil { 275 o.R.{{$relAlias.Local}} = nil 276 } 277 {{else -}} 278 if o.R != nil { 279 {{if not $.NoBackReferencing -}} 280 for _, rel := range o.R.{{$relAlias.Local}} { 281 queries.SetScanner(&rel.{{$fcol}}, nil) 282 if rel.R == nil { 283 continue 284 } 285 286 rel.R.{{$relAlias.Foreign}} = nil 287 } 288 {{end -}} 289 290 o.R.{{$relAlias.Local}} = nil 291 } 292 {{- end}} 293 294 return o.Add{{$relAlias.Local}}({{if not $.NoContext}}ctx, {{end -}} exec, insert, related...) 295 } 296 297 {{if $.AddGlobal -}} 298 // Remove{{$relAlias.Local}}G relationships from objects passed in. 299 // Removes related items from R.{{$relAlias.Local}} (uses pointer comparison, removal does not keep order) 300 {{- if not $.NoBackReferencing}} 301 // Sets related.R.{{$relAlias.Foreign}}. 302 {{- end}} 303 // Uses the global database handle. 304 func (o *{{$ltable.UpSingular}}) Remove{{$relAlias.Local}}G({{if not $.NoContext}}ctx context.Context, {{end -}} related ...*{{$ftable.UpSingular}}) error { 305 return o.Remove{{$relAlias.Local}}({{if $.NoContext}}boil.GetDB(){{else}}ctx, boil.GetContextDB(){{end}}, related...) 306 } 307 308 {{end -}} 309 310 {{if $.AddPanic -}} 311 // Remove{{$relAlias.Local}}P relationships from objects passed in. 312 // Removes related items from R.{{$relAlias.Local}} (uses pointer comparison, removal does not keep order) 313 {{- if not $.NoBackReferencing}} 314 // Sets related.R.{{$relAlias.Foreign}}. 315 {{- end}} 316 // Panics on error. 317 func (o *{{$ltable.UpSingular}}) Remove{{$relAlias.Local}}P({{if $.NoContext}}exec boil.Executor{{else}}ctx context.Context, exec boil.ContextExecutor{{end}}, related ...*{{$ftable.UpSingular}}) { 318 if err := o.Remove{{$relAlias.Local}}({{if not $.NoContext}}ctx, {{end -}} exec, related...); err != nil { 319 panic(boil.WrapErr(err)) 320 } 321 } 322 323 {{end -}} 324 325 {{if and $.AddGlobal $.AddPanic -}} 326 // Remove{{$relAlias.Local}}GP relationships from objects passed in. 327 // Removes related items from R.{{$relAlias.Local}} (uses pointer comparison, removal does not keep order) 328 {{- if not $.NoBackReferencing}} 329 // Sets related.R.{{$relAlias.Foreign}}. 330 {{- end}} 331 // Uses the global database handle and panics on error. 332 func (o *{{$ltable.UpSingular}}) Remove{{$relAlias.Local}}GP({{if not $.NoContext}}ctx context.Context, {{end -}} related ...*{{$ftable.UpSingular}}) { 333 if err := o.Remove{{$relAlias.Local}}({{if $.NoContext}}boil.GetDB(){{else}}ctx, boil.GetContextDB(){{end}}, related...); err != nil { 334 panic(boil.WrapErr(err)) 335 } 336 } 337 338 {{end -}} 339 340 // Remove{{$relAlias.Local}} relationships from objects passed in. 341 // Removes related items from R.{{$relAlias.Local}} (uses pointer comparison, removal does not keep order) 342 {{- if not $.NoBackReferencing}} 343 // Sets related.R.{{$relAlias.Foreign}}. 344 {{- end}} 345 func (o *{{$ltable.UpSingular}}) Remove{{$relAlias.Local}}({{if $.NoContext}}exec boil.Executor{{else}}ctx context.Context, exec boil.ContextExecutor{{end}}, related ...*{{$ftable.UpSingular}}) error { 346 if len(related) == 0 { 347 return nil 348 } 349 350 var err error 351 {{if .ToJoinTable -}} 352 query := fmt.Sprintf( 353 "delete from {{.JoinTable | $.SchemaTable}} where {{.JoinLocalColumn | $.Quotes}} = {{if $.Dialect.UseIndexPlaceholders}}$1{{else}}?{{end}} and {{.JoinForeignColumn | $.Quotes}} in (%s)", 354 strmangle.Placeholders(dialect.UseIndexPlaceholders, len(related), 2, 1), 355 ) 356 values := []interface{}{{"{"}}o.{{$col}}} 357 for _, rel := range related { 358 values = append(values, rel.{{$fcol}}) 359 } 360 361 {{if $.NoContext -}} 362 if boil.DebugMode { 363 fmt.Fprintln(boil.DebugWriter, query) 364 fmt.Fprintln(boil.DebugWriter, values) 365 } 366 {{else -}} 367 if boil.IsDebug(ctx) { 368 writer := boil.DebugWriterFrom(ctx) 369 fmt.Fprintln(writer, query) 370 fmt.Fprintln(writer, values) 371 } 372 {{end -}} 373 374 {{if $.NoContext -}} 375 _, err = exec.Exec(query, values...) 376 {{else -}} 377 _, err = exec.ExecContext(ctx, query, values...) 378 {{end -}} 379 if err != nil { 380 return errors.Wrap(err, "failed to remove relationships before set") 381 } 382 {{else -}} 383 for _, rel := range related { 384 queries.SetScanner(&rel.{{$fcol}}, nil) 385 {{if and (not .ToJoinTable) (not $.NoBackReferencing) -}} 386 if rel.R != nil { 387 rel.R.{{$relAlias.Foreign}} = nil 388 } 389 {{end -}} 390 if {{if not $.NoRowsAffected}}_, {{end -}} err = rel.Update({{if not $.NoContext}}ctx, {{end -}} exec, boil.Whitelist("{{.ForeignColumn}}")); err != nil { 391 return err 392 } 393 } 394 {{end -}} 395 396 {{if and .ToJoinTable (not $.NoBackReferencing) -}} 397 remove{{$relAlias.Local}}From{{$relAlias.Foreign}}Slice(o, related) 398 {{end -}} 399 if o.R == nil { 400 return nil 401 } 402 403 for _, rel := range related { 404 for i, ri := range o.R.{{$relAlias.Local}} { 405 if rel != ri { 406 continue 407 } 408 409 ln := len(o.R.{{$relAlias.Local}}) 410 if ln > 1 && i < ln-1 { 411 o.R.{{$relAlias.Local}}[i] = o.R.{{$relAlias.Local}}[ln-1] 412 } 413 o.R.{{$relAlias.Local}} = o.R.{{$relAlias.Local}}[:ln-1] 414 break 415 } 416 } 417 418 return nil 419 } 420 421 {{if and .ToJoinTable (not $.NoBackReferencing) -}} 422 func remove{{$relAlias.Local}}From{{$relAlias.Foreign}}Slice(o *{{$ltable.UpSingular}}, related []*{{$ftable.UpSingular}}) { 423 for _, rel := range related { 424 if rel.R == nil { 425 continue 426 } 427 for i, ri := range rel.R.{{$relAlias.Foreign}} { 428 {{if $usesPrimitives -}} 429 if o.{{$col}} != ri.{{$col}} { 430 {{else -}} 431 if !queries.Equal(o.{{$col}}, ri.{{$col}}) { 432 {{end -}} 433 continue 434 } 435 436 ln := len(rel.R.{{$relAlias.Foreign}}) 437 if ln > 1 && i < ln-1 { 438 rel.R.{{$relAlias.Foreign}}[i] = rel.R.{{$relAlias.Foreign}}[ln-1] 439 } 440 rel.R.{{$relAlias.Foreign}} = rel.R.{{$relAlias.Foreign}}[:ln-1] 441 break 442 } 443 } 444 } 445 {{end -}}{{- /* if ToJoinTable */ -}} 446 {{- end -}}{{- /* if nullable foreign key */ -}} 447 {{- end -}}{{- /* range relationships */ -}} 448 {{- end -}}{{- /* if IsJoinTable */ -}}