Skip to content

Commit 5cee249

Browse files
authored
Merge pull request #43 from terraform-providers/networkPeering
Network peering
2 parents e651f1c + a2f4598 commit 5cee249

File tree

4 files changed

+130
-49
lines changed

4 files changed

+130
-49
lines changed

GNUmakefile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ websitefmtcheck:
2929

3030
lint:
3131
@echo "==> Checking source code against linters..."
32-
@GOGC=30 golangci-lint run ./$(PKG_NAME)
32+
@GOGC=30 golangci-lint run ./$(PKG_NAME) --deadline=30m
3333

3434
tools:
3535
GO111MODULE=off go get -u github.com/client9/misspell/cmd/misspell

mongodbatlas/resource_mongodbatlas_network_peering.go

Lines changed: 77 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -136,6 +136,16 @@ func resourceMongoDBAtlasNetworkPeering() *schema.Resource {
136136
Optional: true,
137137
Computed: true,
138138
},
139+
"atlas_gcp_project_id": {
140+
Type: schema.TypeString,
141+
Computed: true,
142+
Optional: true,
143+
},
144+
"atlas_vpc_name": {
145+
Type: schema.TypeString,
146+
Computed: true,
147+
Optional: true,
148+
},
139149
"error_message": {
140150
Type: schema.TypeString,
141151
Computed: true,
@@ -238,15 +248,10 @@ func resourceMongoDBAtlasNetworkPeeringCreate(d *schema.ResourceData, meta inter
238248
return fmt.Errorf(errorPeersCreate, err)
239249
}
240250

241-
d.SetId(encodeStateID(map[string]string{
242-
"project_id": projectID,
243-
"peer_id": peer.ID,
244-
}))
245-
246251
stateConf := &resource.StateChangeConf{
247252
Pending: []string{"INITIATING", "FINALIZING", "ADDING_PEER", "WAITING_FOR_USER"},
248253
Target: []string{"AVAILABLE", "PENDING_ACCEPTANCE"},
249-
Refresh: resourceNetworkPeeringRefreshFunc(peer.ID, projectID, conn),
254+
Refresh: resourceNetworkPeeringRefreshFunc(peer.ID, projectID, peerRequest.ContainerID, conn),
250255
Timeout: 1 * time.Hour,
251256
MinTimeout: 10 * time.Second,
252257
Delay: 30 * time.Second,
@@ -258,6 +263,13 @@ func resourceMongoDBAtlasNetworkPeeringCreate(d *schema.ResourceData, meta inter
258263
return fmt.Errorf(errorPeersCreate, err)
259264
}
260265

266+
// container := cont.(matlas.Container)
267+
d.SetId(encodeStateID(map[string]string{
268+
"project_id": projectID,
269+
"peer_id": peer.ID,
270+
"provider_name": providerName,
271+
}))
272+
261273
return resourceMongoDBAtlasNetworkPeeringRead(d, meta)
262274
}
263275

@@ -267,11 +279,11 @@ func resourceMongoDBAtlasNetworkPeeringRead(d *schema.ResourceData, meta interfa
267279
ids := decodeStateID(d.Id())
268280
projectID := ids["project_id"]
269281
peerID := ids["peer_id"]
282+
providerName := ids["provider_name"]
270283

271284
peer, resp, err := conn.Peers.Get(context.Background(), projectID, peerID)
272285
if err != nil {
273286
if resp != nil && resp.StatusCode == http.StatusNotFound {
274-
275287
return nil
276288
}
277289
return fmt.Errorf(errorPeersRead, peerID, err)
@@ -336,6 +348,23 @@ func resourceMongoDBAtlasNetworkPeeringRead(d *schema.ResourceData, meta interfa
336348
if err := d.Set("peer_id", peer.ID); err != nil {
337349
return fmt.Errorf("error setting `peer_id` for Network Peering Connection (%s): %s", peerID, err)
338350
}
351+
352+
// If provider name is GCP we need to get the parameters to configure the the reciprocal connection
353+
// between Mongo and Google
354+
container := &matlas.Container{}
355+
if strings.ToUpper(providerName) == "GCP" {
356+
container, _, err = conn.Containers.Get(context.Background(), projectID, peer.ContainerID)
357+
if err != nil {
358+
return err
359+
}
360+
}
361+
if err := d.Set("atlas_gcp_project_id", container.GCPProjectID); err != nil {
362+
return fmt.Errorf("error setting `atlas_gcp_project_id` for Network Peering Connection (%s): %s", peerID, err)
363+
}
364+
if err := d.Set("atlas_vpc_name", container.NetworkName); err != nil {
365+
return fmt.Errorf("error setting `atlas_vpc_name` for Network Peering Connection (%s): %s", peerID, err)
366+
}
367+
339368
return nil
340369
}
341370

@@ -404,7 +433,7 @@ func resourceMongoDBAtlasNetworkPeeringUpdate(d *schema.ResourceData, meta inter
404433
stateConf := &resource.StateChangeConf{
405434
Pending: []string{"INITIATING", "FINALIZING", "ADDING_PEER", "WAITING_FOR_USER"},
406435
Target: []string{"AVAILABLE", "PENDING_ACCEPTANCE"},
407-
Refresh: resourceNetworkPeeringRefreshFunc(peerID, projectID, conn),
436+
Refresh: resourceNetworkPeeringRefreshFunc(peerID, projectID, "", conn),
408437
Timeout: d.Timeout(schema.TimeoutCreate),
409438
MinTimeout: 30 * time.Second,
410439
Delay: 1 * time.Minute,
@@ -437,10 +466,10 @@ func resourceMongoDBAtlasNetworkPeeringDelete(d *schema.ResourceData, meta inter
437466
stateConf := &resource.StateChangeConf{
438467
Pending: []string{"AVAILABLE", "INITIATING", "PENDING_ACCEPTANCE", "FINALIZING", "ADDING_PEER", "WAITING_FOR_USER", "TERMINATING", "DELETING"},
439468
Target: []string{"DELETED"},
440-
Refresh: resourceNetworkPeeringRefreshFunc(peerID, projectID, conn),
469+
Refresh: resourceNetworkPeeringRefreshFunc(peerID, projectID, "", conn),
441470
Timeout: 1 * time.Hour,
442471
MinTimeout: 30 * time.Second,
443-
Delay: 1 * time.Minute, // Wait 30 secs before starting
472+
Delay: 10 * time.Second, // Wait 10 secs before starting
444473
}
445474

446475
// Wait, catching any errors
@@ -454,52 +483,55 @@ func resourceMongoDBAtlasNetworkPeeringDelete(d *schema.ResourceData, meta inter
454483
func resourceMongoDBAtlasNetworkPeeringImportState(d *schema.ResourceData, meta interface{}) ([]*schema.ResourceData, error) {
455484
conn := meta.(*matlas.Client)
456485

457-
parts := strings.SplitN(d.Id(), "-", 2)
458-
if len(parts) != 2 {
459-
return nil, errors.New("import format error: to import a peer, use the format {project_id}-{peer_id}")
486+
parts := strings.SplitN(d.Id(), "-", 3)
487+
if len(parts) != 3 {
488+
return nil, errors.New("import format error: to import a peer, use the format {project_id}-{peer_id}-{provider_name}")
460489
}
461490

462491
projectID := parts[0]
463492
peerID := parts[1]
493+
providerName := parts[2]
464494

465495
peer, _, err := conn.Peers.Get(context.Background(), projectID, peerID)
466496
if err != nil {
467497
return nil, fmt.Errorf("couldn't import peer %s in project %s, error: %s", peerID, projectID, err)
468498
}
469499

470-
d.SetId(encodeStateID(map[string]string{
471-
"project_id": projectID,
472-
"peer_id": peer.ID,
473-
}))
474-
475-
if err := d.Set("project_id", projectID); err != nil {
476-
log.Printf("[WARN] Error setting project_id for (%s): %s", peerID, err)
477-
}
478-
479-
if err := d.Set("container_id", peer.ContainerID); err != nil {
480-
log.Printf("[WARN] Error setting container_id for (%s): %s", peerID, err)
481-
}
482-
483500
//Check wich provider is using.
484501
provider := "AWS"
485502
if peer.VNetName != "" {
486503
provider = "AZURE"
487504
} else if peer.NetworkName != "" {
488505
provider = "GCP"
489506
}
507+
if providerName != provider {
508+
providerName = provider
509+
}
490510

491-
if err := d.Set("provider_name", provider); err != nil {
511+
if err := d.Set("project_id", projectID); err != nil {
512+
log.Printf("[WARN] Error setting project_id for (%s): %s", peerID, err)
513+
}
514+
if err := d.Set("container_id", peer.ContainerID); err != nil {
515+
log.Printf("[WARN] Error setting container_id for (%s): %s", peerID, err)
516+
}
517+
if err := d.Set("provider_name", providerName); err != nil {
492518
log.Printf("[WARN] Error setting provider_name for (%s): %s", peerID, err)
493519
}
494520

521+
d.SetId(encodeStateID(map[string]string{
522+
"project_id": projectID,
523+
"peer_id": peer.ID,
524+
"provider_name": providerName,
525+
}))
526+
495527
return []*schema.ResourceData{d}, nil
496528
}
497529

498-
func resourceNetworkPeeringRefreshFunc(peerID, projectID string, client *matlas.Client) resource.StateRefreshFunc {
530+
func resourceNetworkPeeringRefreshFunc(peerID, projectID, containerID string, client *matlas.Client) resource.StateRefreshFunc {
499531
return func() (interface{}, string, error) {
500532
c, resp, err := client.Peers.Get(context.Background(), projectID, peerID)
501533
if err != nil {
502-
if resp.StatusCode == 404 {
534+
if resp != nil && resp.StatusCode == 404 {
503535
return 42, "DELETED", nil
504536
}
505537
log.Printf("error reading MongoDB Network Peering Connection %s: %s", peerID, err)
@@ -511,9 +543,24 @@ func resourceNetworkPeeringRefreshFunc(peerID, projectID string, client *matlas.
511543
if len(c.StatusName) > 0 {
512544
status = c.StatusName
513545
}
514-
515546
log.Printf("[DEBUG] status for MongoDB Network Peering Connection: %s: %s", peerID, status)
516547

548+
/* We need to get the provisioned status from Mongo container that contains the peering connection
549+
* to validate if it has changed to true. This means that the reciprocal connection in Mongo side
550+
* is right, and the Mongo parameters used on the Google side to configure the reciprocal connection
551+
* are now available. */
552+
if status == "WAITING_FOR_USER" {
553+
container, _, err := client.Containers.Get(context.Background(), projectID, containerID)
554+
555+
if err != nil {
556+
return nil, "", fmt.Errorf(errorContainerRead, containerID, err)
557+
}
558+
559+
if *container.Provisioned {
560+
return container, "PENDING_ACCEPTANCE", nil
561+
}
562+
}
563+
517564
return c, status, nil
518565
}
519566
}

mongodbatlas/resource_mongodbatlas_network_peering_test.go

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@ func TestAccResourceMongoDBAtlasNetworkPeering_basicAWS(t *testing.T) {
5353
}
5454

5555
func TestAccResourceMongoDBAtlasNetworkPeering_basicAzure(t *testing.T) {
56+
t.Skip()
5657
var peer matlas.Peer
5758

5859
resourceName := "mongodbatlas_network_peering.test"
@@ -85,7 +86,7 @@ func TestAccResourceMongoDBAtlasNetworkPeering_basicAzure(t *testing.T) {
8586
ImportStateIdFunc: testAccCheckMongoDBAtlasNetworkPeeringImportStateIDFunc(resourceName),
8687
ImportState: true,
8788
ImportStateVerify: true,
88-
ImportStateVerifyIgnore: []string{"region_name", "atlas_cidr_block"},
89+
ImportStateVerifyIgnore: []string{"atlas_cidr_block"},
8990
},
9091
},
9192
})
@@ -113,15 +114,14 @@ func TestAccResourceMongoDBAtlasNetworkPeering_basicGCP(t *testing.T) {
113114
resource.TestCheckResourceAttrSet(resourceName, "project_id"),
114115
resource.TestCheckResourceAttrSet(resourceName, "container_id"),
115116
resource.TestCheckResourceAttr(resourceName, "provider_name", providerName),
116-
resource.TestCheckResourceAttr(resourceName, "azure_directory_id", gcpProjectID),
117+
resource.TestCheckResourceAttr(resourceName, "gcp_project_id", gcpProjectID),
117118
),
118119
},
119120
{
120-
ResourceName: resourceName,
121-
ImportStateIdFunc: testAccCheckMongoDBAtlasNetworkPeeringImportStateIDFunc(resourceName),
122-
ImportState: true,
123-
ImportStateVerify: true,
124-
ImportStateVerifyIgnore: []string{"region_name"},
121+
ResourceName: resourceName,
122+
ImportStateIdFunc: testAccCheckMongoDBAtlasNetworkPeeringImportStateIDFunc(resourceName),
123+
ImportState: true,
124+
ImportStateVerify: true,
125125
},
126126
},
127127
})
@@ -133,7 +133,7 @@ func testAccCheckMongoDBAtlasNetworkPeeringImportStateIDFunc(resourceName string
133133
if !ok {
134134
return "", fmt.Errorf("Not found: %s", resourceName)
135135
}
136-
return fmt.Sprintf("%s-%s", rs.Primary.Attributes["project_id"], rs.Primary.Attributes["peer_id"]), nil
136+
return fmt.Sprintf("%s-%s-%s", rs.Primary.Attributes["project_id"], rs.Primary.Attributes["peer_id"], rs.Primary.Attributes["provider_name"]), nil
137137
}
138138
}
139139

@@ -236,7 +236,7 @@ func testAccMongoDBAtlasNetworkPeeringConfigGCP(projectID, providerName, gcpProj
236236
return fmt.Sprintf(`
237237
resource "mongodbatlas_network_container" "test" {
238238
project_id = "%[1]s"
239-
atlas_cidr_block = "192.168.208.0/21"
239+
atlas_cidr_block = "192.168.192.0/18"
240240
provider_name = "%[2]s"
241241
}
242242
@@ -245,7 +245,7 @@ func testAccMongoDBAtlasNetworkPeeringConfigGCP(projectID, providerName, gcpProj
245245
container_id = mongodbatlas_network_container.test.container_id
246246
provider_name = "%[2]s"
247247
gcp_project_id = "%[3]s"
248-
network_name = "mongodbatlas_network_container.test.network_name"
248+
network_name = "myNetworkName"
249249
}
250250
`, projectID, providerName, gcpProjectID)
251251
}

website/docs/r/network_peering.html.markdown

Lines changed: 42 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,20 @@ description: |-
1818

1919
## Example Usage
2020

21+
### Global configuration for the following examples
22+
```hcl
23+
locals {
24+
project_id = <your-project-id>
25+
google_project_id = <your-google-project-id>
26+
}
27+
```
28+
2129
### Example with AWS.
2230

2331
```hcl
2432
resource "mongodbatlas_network_peering" "test" {
2533
accepter_region_name = "us-east-1"
26-
project_id = "<YOUR-PROJEC-ID>"
34+
project_id = local.project_id
2735
container_id = "507f1f77bcf86cd799439011"
2836
provider_name = "AWS"
2937
route_table_cidr_block = "192.168.0.0/24"
@@ -35,20 +43,44 @@ resource "mongodbatlas_network_peering" "test" {
3543
### Example with GCP
3644

3745
```hcl
46+
47+
resource "mongodbatlas_network_container" "test" {
48+
project_id = local.project_id
49+
atlas_cidr_block = "192.168.192.0/18"
50+
provider_name = "GCP"
51+
}
52+
53+
resource "mongodbatlas_private_ip_mode" "my_private_ip_mode" {
54+
project_id = local.project_id
55+
enabled = true
56+
}
57+
3858
resource "mongodbatlas_network_peering" "test" {
39-
project_id = "<YOUR-PROJEC-ID>"
40-
container_id = "507f1f77bcf86cd799439011"
59+
project_id = local.project_id
60+
container_id = mongodbatlas_network_container.test.container_id
4161
provider_name = "GCP"
42-
gcp_project_id = "my-sample-project-191923"
43-
network_name = "test1"
62+
network_name = "myNetWorkPeering"
63+
gcp_project_id = local.google_project_id
64+
65+
depends_on = [mongodbatlas_private_ip_mode.my_private_ip_mode]
66+
}
67+
68+
resource "google_compute_network" "vpc_network" {
69+
name = "vpcnetwork"
70+
}
71+
72+
resource "google_compute_network_peering" "gcp_main_atlas_peering" {
73+
name = "atlas-gcp-main"
74+
network = google_compute_network.vpc_network.self_link
75+
peer_network = "projects/${mongodbatlas_network_peering.test.atlas_gcp_project_id}/global/networks/${mongodbatlas_network_peering.test.atlas_vpc_name}"
4476
}
4577
```
4678

4779
### Example with Azure
4880

4981
```hcl
5082
resource "mongodbatlas_network_peering" "test" {
51-
project_id = "<YOUR-PROJEC-ID>"
83+
project_id = local.project_id
5284
atlas_cidr_block = "192.168.0.0/21"
5385
container_id = "507f1f77bcf86cd799439011"
5486
provider_name = "AZURE"
@@ -98,16 +130,18 @@ In addition to all arguments above, the following attributes are exported:
98130
* `error_state` - Description of the Atlas error when `status` is `Failed`, Otherwise, Atlas returns `null`.
99131
* `status` - Status of the Atlas network peering connection: `ADDING_PEER`, `AVAILABLE`, `FAILED`, `DELETING`, `WAITING_FOR_USER`.
100132
* `gcp_project_id` - GCP project ID of the owner of the network peer.
133+
* `atlas_gcp_project_id` - The Atlas GCP Project ID for the GCP VPC used by your atlas cluster that it is need to set up the reciprocal connection.
134+
* `atlas_vpc_name` - The Atlas VPC Name is used by your atlas clister that it is need to set up the reciprocal connection.
101135
* `network_name` - Name of the network peer to which Atlas connects.
102136
* `error_message` - When `"status" : "FAILED"`, Atlas provides a description of the error.
103137

104138

105139
## Import
106140

107-
Clusters can be imported using project ID and network peering peering id, in the format `PROJECTID-PEER-ID`, e.g.
141+
Clusters can be imported using project ID and network peering peering id, in the format `PROJECTID-PEERID-PROVIDERNAME`, e.g.
108142

109143
```
110-
$ terraform import mongodbatlas_network_peering.my_peering 1112222b3bf99403840e8934-5cbf563d87d9d67253be590a
144+
$ terraform import mongodbatlas_network_peering.my_peering 1112222b3bf99403840e8934-5cbf563d87d9d67253be590a-AWS
111145
```
112146

113147
See detailed information for arguments and attributes: [MongoDB API Network Peering Connection](https://docs.atlas.mongodb.com/reference/api/vpc-create-peering-connection/)

0 commit comments

Comments
 (0)