@@ -25,6 +25,7 @@ import (
2525 "context"
2626 "fmt"
2727 "log"
28+ "time"
2829
2930 "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource"
3031 "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
@@ -61,7 +62,6 @@ func resourceTencentCloudPostgresqlReadonlyGroup() *schema.Resource {
6162 },
6263 "vpc_id" : {
6364 Type : schema .TypeString ,
64- ForceNew : true ,
6565 Required : true ,
6666 Description : "VPC ID." ,
6767 },
@@ -119,13 +119,13 @@ func resourceTencentCloudPostgresqlReadOnlyGroupCreate(d *schema.ResourceData, m
119119 logId := getLogId (contextNil )
120120
121121 var (
122- request = postgresql .NewCreateReadOnlyGroupRequest ()
123- response * postgresql.CreateReadOnlyGroupResponse
124- dbInstanceId string
122+ request = postgresql .NewCreateReadOnlyGroupRequest ()
123+ response * postgresql.CreateReadOnlyGroupResponse
124+ msaterDbInstanceId string
125125 )
126126 if v , ok := d .GetOk ("master_db_instance_id" ); ok {
127127 request .MasterDBInstanceId = helper .String (v .(string ))
128- dbInstanceId = v .(string )
128+ msaterDbInstanceId = v .(string )
129129 }
130130 if v , ok := d .GetOk ("name" ); ok {
131131 request .Name = helper .String (v .(string ))
@@ -189,7 +189,7 @@ func resourceTencentCloudPostgresqlReadOnlyGroupCreate(d *schema.ResourceData, m
189189 postgresqlService := PostgresqlService {client : meta .(* TencentCloudClient ).apiV3Conn }
190190
191191 err = resource .Retry (writeRetryTimeout , func () * resource.RetryError {
192- groups , e := postgresqlService .DescribePostgresqlReadOnlyGroupById (ctx , dbInstanceId )
192+ groups , e := postgresqlService .DescribePostgresqlReadOnlyGroupById (ctx , msaterDbInstanceId )
193193 if e != nil {
194194 return retryError (e )
195195 }
@@ -238,29 +238,134 @@ func resourceTencentCloudPostgresqlReadOnlyGroupUpdate(d *schema.ResourceData, m
238238 defer logElapsed ("resource.tencentcloud_postgresql_readonly_group.update" )()
239239
240240 logId := getLogId (contextNil )
241+ ctx := context .WithValue (context .TODO (), logIdKey , logId )
241242 request := postgresql .NewModifyReadOnlyGroupConfigRequest ()
242243
243244 request .ReadOnlyGroupId = helper .String (d .Id ())
244245
245- if d .HasChange ("name" ) {
246- request .ReadOnlyGroupName = helper .String (d .Get ("name" ).(string ))
247- }
248- if d .HasChange ("replay_lag_eliminate" ) {
249- request .ReplayLagEliminate = helper .IntUint64 (d .Get ("replay_lag_eliminate" ).(int ))
250- }
251- if d .HasChange ("replay_latency_eliminate" ) {
252- request .ReplayLatencyEliminate = helper .IntUint64 (d .Get ("replay_latency_eliminate" ).(int ))
253- }
254- if d .HasChange ("max_replay_lag" ) {
255- request .MaxReplayLag = helper .IntUint64 (d .Get ("max_replay_lag" ).(int ))
256- }
257- if d .HasChange ("max_replay_latency" ) {
258- request .MaxReplayLatency = helper .IntUint64 (d .Get ("max_replay_latency" ).(int ))
259- }
260- if d .HasChange ("min_delay_eliminate_reserve" ) {
261- request .MinDelayEliminateReserve = helper .IntUint64 (d .Get ("min_delay_eliminate_reserve" ).(int ))
246+ // update vpc and subnet
247+ if d .HasChange ("vpc_id" ) || d .HasChange ("subnet_id" ) {
248+ var (
249+ vpcOld string
250+ vpcNew string
251+ subnetOld string
252+ subnetNew string
253+ vipOld string
254+ vipNew string
255+ msaterDbInstanceId string
256+ )
257+
258+ if v , ok := d .GetOk ("master_db_instance_id" ); ok {
259+ msaterDbInstanceId = v .(string )
260+ }
261+
262+ old , new := d .GetChange ("vpc_id" )
263+ if old != nil {
264+ vpcOld = old .(string )
265+ }
266+ if new != nil {
267+ vpcNew = new .(string )
268+ }
269+
270+ old , new = d .GetChange ("subnet_id" )
271+ if old != nil {
272+ subnetOld = old .(string )
273+ }
274+ if new != nil {
275+ subnetNew = new .(string )
276+ }
277+
278+ service := PostgresqlService {client : meta .(* TencentCloudClient ).apiV3Conn }
279+ // get the old ip before creating
280+ netInfos , err := service .DescribePostgresqlReadonlyGroupNetInfosById (ctx , msaterDbInstanceId , d .Id ())
281+ if err != nil {
282+ return err
283+ }
284+
285+ var oldNetInfo * postgresql.DBInstanceNetInfo
286+ for _ , info := range netInfos {
287+ if * info .NetType == "private" {
288+ if * info .VpcId == vpcOld && * info .SubnetId == subnetOld {
289+ oldNetInfo = info
290+ break
291+ }
292+ }
293+ }
294+
295+ if oldNetInfo != nil {
296+ vipOld = * oldNetInfo .Ip
297+ }
298+
299+ // Create new network first, then delete the old one
300+ request := postgresql .NewCreateReadOnlyGroupNetworkAccessRequest ()
301+ request .ReadOnlyGroupId = helper .String (d .Id ())
302+ request .VpcId = helper .String (vpcNew )
303+ request .SubnetId = helper .String (subnetNew )
304+ // ip assigned by system
305+ request .IsAssignVip = helper .Bool (false )
306+
307+ err = resource .Retry (writeRetryTimeout , func () * resource.RetryError {
308+ result , e := meta .(* TencentCloudClient ).apiV3Conn .UsePostgresqlClient ().CreateReadOnlyGroupNetworkAccess (request )
309+ if e != nil {
310+ return retryError (e )
311+ } else {
312+ log .Printf ("[DEBUG]%s api[%s] success, request body [%s], response body [%s]\n " , logId , request .GetAction (), request .ToJsonString (), result .ToJsonString ())
313+ }
314+ return nil
315+ })
316+ if err != nil {
317+ log .Printf ("[CRITAL]%s create postgresql ReadOnlyGroup NetworkAccess failed, reason:%+v" , logId , err )
318+ return err
319+ }
320+
321+ // wait for new network enabled
322+ conf := BuildStateChangeConf ([]string {}, []string {"opened" }, 3 * readRetryTimeout , time .Second , service .PostgresqlReadonlyGroupNetworkAccessStateRefreshFunc (msaterDbInstanceId , d .Id (), vpcNew , subnetNew , vipOld , "" , []string {}))
323+
324+ if object , e := conf .WaitForState (); e != nil {
325+ return e
326+ } else {
327+ // find the vip assiged by system
328+ ret := object .(* postgresql.DBInstanceNetInfo )
329+ vipNew = * ret .Ip
330+ }
331+
332+ log .Printf ("[DEBUG]%s resourceTencentCloudPostgresqlReadOnlyGroupUpdate, msaterDbInstanceId:[%s], roGroupId:[%s], vpcOld:[%s], vpcNew:[%s], subnetOld:[%s], subnetNew:[%s], vipOld:[%s], vipNew:[%s]\n " ,
333+ logId , msaterDbInstanceId , d .Id (), vpcOld , vpcNew , subnetOld , subnetNew , vipOld , vipNew )
334+
335+ // wait unit network changing operation of ro group done
336+ conf = BuildStateChangeConf ([]string {}, []string {"ok" }, 3 * readRetryTimeout , time .Second , service .PostgresqlReadonlyGroupStateRefreshFunc (msaterDbInstanceId , d .Id (), []string {}))
337+ if _ , e := conf .WaitForState (); e != nil {
338+ return e
339+ }
340+
341+ // delete the old one
342+ if err := service .DeletePostgresqlReadonlyGroupNetworkAccessById (ctx , d .Id (), vpcOld , subnetOld , vipOld ); err != nil {
343+ return err
344+ }
345+
346+ // wait for old network removed
347+ conf = BuildStateChangeConf ([]string {}, []string {"closed" }, 3 * readRetryTimeout , time .Second , service .PostgresqlReadonlyGroupNetworkAccessStateRefreshFunc (msaterDbInstanceId , d .Id (), vpcOld , subnetOld , vipNew , vipOld , []string {}))
348+ if _ , e := conf .WaitForState (); e != nil {
349+ return e
350+ }
351+
352+ // wait unit network changing operation of ro group done
353+ conf = BuildStateChangeConf ([]string {}, []string {"ok" }, 3 * readRetryTimeout , time .Second , service .PostgresqlReadonlyGroupStateRefreshFunc (msaterDbInstanceId , d .Id (), []string {}))
354+ if _ , e := conf .WaitForState (); e != nil {
355+ return e
356+ }
357+
358+ // refresh the private ip with new one
262359 }
263360
361+ // required attributes
362+ request .ReadOnlyGroupName = helper .String (d .Get ("name" ).(string ))
363+ request .ReplayLagEliminate = helper .IntUint64 (d .Get ("replay_lag_eliminate" ).(int ))
364+ request .ReplayLatencyEliminate = helper .IntUint64 (d .Get ("replay_latency_eliminate" ).(int ))
365+ request .MaxReplayLag = helper .IntUint64 (d .Get ("max_replay_lag" ).(int ))
366+ request .MaxReplayLatency = helper .IntUint64 (d .Get ("max_replay_latency" ).(int ))
367+ request .MinDelayEliminateReserve = helper .IntUint64 (d .Get ("min_delay_eliminate_reserve" ).(int ))
368+
264369 err := resource .Retry (writeRetryTimeout , func () * resource.RetryError {
265370 result , e := meta .(* TencentCloudClient ).apiV3Conn .UsePostgresqlClient ().ModifyReadOnlyGroupConfig (request )
266371 if e != nil {
0 commit comments