Skip to content

Commit 2a50604

Browse files
committed
test: integration test for Resource Service and Controller Runtime
1 parent 113202d commit 2a50604

File tree

6 files changed

+168
-35
lines changed

6 files changed

+168
-35
lines changed

test/integration/consul-container/go.mod

Lines changed: 18 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -7,12 +7,14 @@ require (
77
github.com/avast/retry-go v3.0.0+incompatible
88
github.com/docker/docker v23.0.6+incompatible
99
github.com/docker/go-connections v0.4.0
10+
github.com/hashicorp/consul v0.0.0-00010101000000-000000000000
1011
github.com/hashicorp/consul/api v1.20.0
1112
github.com/hashicorp/consul/envoyextensions v0.1.2
13+
github.com/hashicorp/consul/proto-public v0.2.1
1214
github.com/hashicorp/consul/sdk v0.13.1
1315
github.com/hashicorp/go-cleanhttp v0.5.2
1416
github.com/hashicorp/go-multierror v1.1.1
15-
github.com/hashicorp/go-uuid v1.0.2
17+
github.com/hashicorp/go-uuid v1.0.3
1618
github.com/hashicorp/go-version v1.2.1
1719
github.com/hashicorp/serf v0.10.1
1820
github.com/itchyny/gojq v0.12.9
@@ -24,6 +26,7 @@ require (
2426
github.com/testcontainers/testcontainers-go v0.20.1
2527
golang.org/x/mod v0.10.0
2628
google.golang.org/grpc v1.55.0
29+
google.golang.org/protobuf v1.30.0
2730
)
2831

2932
require (
@@ -49,7 +52,7 @@ require (
4952
github.com/google/btree v1.0.0 // indirect
5053
github.com/google/uuid v1.3.0 // indirect
5154
github.com/hashicorp/errwrap v1.1.0 // indirect
52-
github.com/hashicorp/go-hclog v1.2.1 // indirect
55+
github.com/hashicorp/go-hclog v1.5.0 // indirect
5356
github.com/hashicorp/go-immutable-radix v1.3.1 // indirect
5457
github.com/hashicorp/go-msgpack v1.1.5 // indirect
5558
github.com/hashicorp/go-rootcerts v1.0.2 // indirect
@@ -64,7 +67,7 @@ require (
6467
github.com/mattn/go-isatty v0.0.17 // indirect
6568
github.com/miekg/dns v1.1.41 // indirect
6669
github.com/mitchellh/go-homedir v1.1.0 // indirect
67-
github.com/mitchellh/mapstructure v1.4.3 // indirect
70+
github.com/mitchellh/mapstructure v1.5.0 // indirect
6871
github.com/mitchellh/reflectwalk v1.0.2 // indirect
6972
github.com/moby/patternmatcher v0.5.0 // indirect
7073
github.com/moby/sys/sequential v0.5.0 // indirect
@@ -77,20 +80,19 @@ require (
7780
github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529 // indirect
7881
github.com/sirupsen/logrus v1.9.0 // indirect
7982
golang.org/x/exp v0.0.0-20230321023759-10a507213a29 // indirect
80-
golang.org/x/net v0.10.0 // indirect
81-
golang.org/x/sys v0.8.0 // indirect
82-
golang.org/x/text v0.9.0 // indirect
83-
golang.org/x/tools v0.9.1 // indirect
84-
google.golang.org/genproto v0.0.0-20230410155749-daa745c078e1 // indirect
85-
google.golang.org/protobuf v1.30.0 // indirect
83+
golang.org/x/net v0.8.0 // indirect
84+
golang.org/x/sys v0.7.0 // indirect
85+
golang.org/x/text v0.8.0 // indirect
86+
golang.org/x/tools v0.7.0 // indirect
87+
google.golang.org/genproto v0.0.0-20230306155012-7f2fa6fef1f4 // indirect
8688
gopkg.in/yaml.v3 v3.0.1 // indirect
8789
gotest.tools/v3 v3.4.0 // indirect
8890
)
8991

90-
replace github.com/hashicorp/consul/api => ../../../api
91-
92-
replace github.com/hashicorp/consul/sdk => ../../../sdk
93-
94-
replace github.com/hashicorp/consul => ../../..
95-
96-
replace github.com/hashicorp/consul/envoyextensions => ../../../envoyextensions
92+
replace (
93+
github.com/hashicorp/consul => ../../..
94+
github.com/hashicorp/consul/api => ../../../api
95+
github.com/hashicorp/consul/envoyextensions => ../../../envoyextensions
96+
github.com/hashicorp/consul/proto-public => ../../../proto-public
97+
github.com/hashicorp/consul/sdk => ../../../sdk
98+
)

test/integration/consul-container/go.sum

Lines changed: 18 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -104,8 +104,8 @@ github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brv
104104
github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
105105
github.com/hashicorp/go-cleanhttp v0.5.2 h1:035FKYIWjmULyFRBKPs8TBQoi0x6d9G4xc9neXJWAZQ=
106106
github.com/hashicorp/go-cleanhttp v0.5.2/go.mod h1:kO/YDlP8L1346E6Sodw+PrpBSV4/SoxCXGY6BqNFT48=
107-
github.com/hashicorp/go-hclog v1.2.1 h1:YQsLlGDJgwhXFpucSPyVbCBviQtjlHv3jLTlp8YmtEw=
108-
github.com/hashicorp/go-hclog v1.2.1/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
107+
github.com/hashicorp/go-hclog v1.5.0 h1:bI2ocEMgcVlz55Oj1xZNBsVi900c7II+fWDyV9o+13c=
108+
github.com/hashicorp/go-hclog v1.5.0/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
109109
github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60=
110110
github.com/hashicorp/go-immutable-radix v1.3.1 h1:DKHmCUm2hRBK510BaiZlwvpD40f8bJFeZnpfm2KLowc=
111111
github.com/hashicorp/go-immutable-radix v1.3.1/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60=
@@ -125,8 +125,8 @@ github.com/hashicorp/go-sockaddr v1.0.2/go.mod h1:rB4wwRAUzs07qva3c5SdrY/NEtAUjG
125125
github.com/hashicorp/go-syslog v1.0.0/go.mod h1:qPfqrKkXGihmCqbJM2mZgkZGvKG1dFdvsLplgctolz4=
126126
github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
127127
github.com/hashicorp/go-uuid v1.0.1/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
128-
github.com/hashicorp/go-uuid v1.0.2 h1:cfejS+Tpcp13yd5nYHWDI6qVCny6wyX2Mt5SGur2IGE=
129-
github.com/hashicorp/go-uuid v1.0.2/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
128+
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
129+
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
130130
github.com/hashicorp/go-version v1.2.1 h1:zEfKbn2+PDgroKdiOzqiE8rsmLqU2uwi5PB5pBJ3TkI=
131131
github.com/hashicorp/go-version v1.2.1/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA=
132132
github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
@@ -187,8 +187,8 @@ github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG
187187
github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
188188
github.com/mitchellh/go-wordwrap v1.0.0/go.mod h1:ZXFpozHsX6DPmq2I0TCekCxypsnAUbP2oI0UX1GXzOo=
189189
github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
190-
github.com/mitchellh/mapstructure v1.4.3 h1:OVowDSCllw/YjdLkam3/sm7wEtOy59d8ndGgCcyj8cs=
191-
github.com/mitchellh/mapstructure v1.4.3/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo=
190+
github.com/mitchellh/mapstructure v1.5.0 h1:jeMsZIYE/09sWLaz43PL7Gy6RuMjD2eJVyuac5Z2hdY=
191+
github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo=
192192
github.com/mitchellh/reflectwalk v1.0.2 h1:G2LzWKi524PWgd3mLHV8Y5k7s6XUvT0Gef6zxSIeXaQ=
193193
github.com/mitchellh/reflectwalk v1.0.2/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw=
194194
github.com/moby/patternmatcher v0.5.0 h1:YCZgJOeULcxLw1Q+sVR636pmS7sPEn1Qo2iAN6M7DBo=
@@ -295,8 +295,8 @@ golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLL
295295
golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
296296
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
297297
golang.org/x/net v0.0.0-20210410081132-afb366fc7cd1/go.mod h1:9tjilg8BloeKEkVJvy7fQ90B1CfIiPueXVOjqfkSzI8=
298-
golang.org/x/net v0.10.0 h1:X2//UzNDwYmtCLn7To6G58Wr6f5ahEAQgKNzv9Y951M=
299-
golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
298+
golang.org/x/net v0.8.0 h1:Zrh2ngAOFYneWTAIAPethzeaQLuHwhuBkuV6ZiRnUaQ=
299+
golang.org/x/net v0.8.0/go.mod h1:QVkue5JL9kW//ek3r6jTKnTFis1tRmNAW2P1shuFdJc=
300300
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
301301
golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
302302
golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
@@ -305,7 +305,7 @@ golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJ
305305
golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
306306
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
307307
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
308-
golang.org/x/sync v0.2.0 h1:PUR+T4wwASmuSTYdKjYHI5TD22Wy5ogLU5qZCOLxBrI=
308+
golang.org/x/sync v0.1.0 h1:wsuoTGHzEhffawBOhz5CYhcrV4IdKZbEyZjBMuTp12o=
309309
golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
310310
golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
311311
golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
@@ -332,16 +332,16 @@ golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBc
332332
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
333333
golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
334334
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
335-
golang.org/x/sys v0.8.0 h1:EBmGv8NaZBZTWvrbjNoL6HVt+IVy3QDQpJs7VRIw3tU=
336-
golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
335+
golang.org/x/sys v0.7.0 h1:3jlCCIQZPdOYu1h8BkNvLz8Kgwtae2cagcG/VamtZRU=
336+
golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
337337
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
338338
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
339339
golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
340340
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
341341
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
342-
golang.org/x/text v0.9.0 h1:2sjJmO8cDvYveuX97RDLsxlyUxLl+GHoLxBiRdHllBE=
343-
golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
344-
golang.org/x/time v0.0.0-20220210224613-90d013bbcef8 h1:vVKdlvoWBphwdxWKrFZEuM0kGgGLxUOYcY4U/2Vjg44=
342+
golang.org/x/text v0.8.0 h1:57P1ETyNKtuIjB4SRd15iJxuhj8Gc416Y78H3qgMh68=
343+
golang.org/x/text v0.8.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
344+
golang.org/x/time v0.3.0 h1:rg5rLMjNzMS1RkNLzCG38eapWhnYLFYXDXj2gOlr8j4=
345345
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
346346
golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
347347
golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY=
@@ -353,8 +353,8 @@ golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtn
353353
golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE=
354354
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
355355
golang.org/x/tools v0.1.0/go.mod h1:xkSsbof2nBLbhDlRMhhhyNLN/zl3eTqcnHD5viDpcZ0=
356-
golang.org/x/tools v0.9.1 h1:8WMNJAz3zrtPmnYC7ISf5dEn3MT0gY7jBJfw27yrrLo=
357-
golang.org/x/tools v0.9.1/go.mod h1:owI94Op576fPu3cIGQeHs3joujW/2Oc6MtlxbF5dfNc=
356+
golang.org/x/tools v0.7.0 h1:W4OVu8VVOaIO0yzWMNdepAulS7YfoS3Zabrm8DOXXU4=
357+
golang.org/x/tools v0.7.0/go.mod h1:4pg6aUX35JBAogB10C9AtvVL+qowtN4pT3CGSQex14s=
358358
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
359359
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
360360
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
@@ -363,8 +363,8 @@ google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9Ywl
363363
google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
364364
google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
365365
google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc=
366-
google.golang.org/genproto v0.0.0-20230410155749-daa745c078e1 h1:KpwkzHKEF7B9Zxg18WzOa7djJ+Ha5DzthMyZYQfEn2A=
367-
google.golang.org/genproto v0.0.0-20230410155749-daa745c078e1/go.mod h1:nKE/iIaLqn2bQwXBg8f1g2Ylh6r5MN5CmZvuzZCgsCU=
366+
google.golang.org/genproto v0.0.0-20230306155012-7f2fa6fef1f4 h1:DdoeryqhaXp1LtT/emMP1BRJPHHKFi5akj/nbx/zNTA=
367+
google.golang.org/genproto v0.0.0-20230306155012-7f2fa6fef1f4/go.mod h1:NWraEVixdDnqcqQ30jipen1STv2r/n24Wb7twVTGR4s=
368368
google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
369369
google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg=
370370
google.golang.org/grpc v1.25.1/go.mod h1:c3i+UQWmh7LiEpx4sFZnkU36qjEYZ0imhYfXVyQciAY=

test/integration/consul-container/libs/cluster/agent.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import (
77
"context"
88

99
"github.com/testcontainers/testcontainers-go"
10+
"google.golang.org/grpc"
1011

1112
"github.com/hashicorp/consul/api"
1213

@@ -34,6 +35,7 @@ type Agent interface {
3435
Upgrade(ctx context.Context, config Config) error
3536
Exec(ctx context.Context, cmd []string) (string, error)
3637
DataDir() string
38+
GetGRPCConn() *grpc.ClientConn
3739
}
3840

3941
// Config is a set of configurations required to create a Agent

test/integration/consul-container/libs/cluster/container.go

Lines changed: 43 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,18 +8,22 @@ import (
88
"encoding/json"
99
"fmt"
1010
"io"
11+
"net/url"
1112
"os"
1213
"path/filepath"
1314
"strconv"
1415
"time"
1516

1617
goretry "github.com/avast/retry-go"
1718
dockercontainer "github.com/docker/docker/api/types/container"
19+
"github.com/docker/go-connections/nat"
1820
"github.com/hashicorp/go-multierror"
1921
"github.com/otiai10/copy"
2022
"github.com/pkg/errors"
2123
"github.com/testcontainers/testcontainers-go"
2224
"github.com/testcontainers/testcontainers-go/wait"
25+
"google.golang.org/grpc"
26+
"google.golang.org/grpc/credentials/insecure"
2327

2428
"github.com/hashicorp/consul/api"
2529

@@ -58,6 +62,8 @@ type consulContainerNode struct {
5862
clientCACertFile string
5963
ip string
6064

65+
grpcConn *grpc.ClientConn
66+
6167
nextAdminPortOffset int
6268
nextConnectPortOffset int
6369

@@ -168,7 +174,8 @@ func NewConsulContainer(ctx context.Context, config Config, cluster *Cluster, po
168174
clientAddr string
169175
clientCACertFile string
170176

171-
info AgentInfo
177+
info AgentInfo
178+
grpcConn *grpc.ClientConn
172179
)
173180
debugURI := ""
174181
if utils.Debug {
@@ -232,6 +239,28 @@ func NewConsulContainer(ctx context.Context, config Config, cluster *Cluster, po
232239
info.CACertFile = clientCACertFile
233240
}
234241

242+
// TODO: Support gRPC+TLS port.
243+
if pc.Ports.GRPC > 0 {
244+
port, err := nat.NewPort("tcp", strconv.Itoa(pc.Ports.GRPC))
245+
if err != nil {
246+
return nil, fmt.Errorf("failed to parse gRPC TLS port: %w", err)
247+
}
248+
endpoint, err := podContainer.PortEndpoint(ctx, port, "tcp")
249+
if err != nil {
250+
return nil, fmt.Errorf("failed to get gRPC TLS endpoint: %w", err)
251+
}
252+
url, err := url.Parse(endpoint)
253+
if err != nil {
254+
return nil, fmt.Errorf("failed to parse gRPC endpoint URL: %w", err)
255+
}
256+
conn, err := grpc.Dial(url.Host, grpc.WithTransportCredentials(insecure.NewCredentials()))
257+
if err != nil {
258+
return nil, fmt.Errorf("failed to dial gRPC connection: %w", err)
259+
}
260+
deferClean.Add(func() { _ = conn.Close() })
261+
grpcConn = conn
262+
}
263+
235264
ip, err := podContainer.ContainerIP(ctx)
236265
if err != nil {
237266
return nil, err
@@ -278,6 +307,7 @@ func NewConsulContainer(ctx context.Context, config Config, cluster *Cluster, po
278307
name: name,
279308
ip: ip,
280309
info: info,
310+
grpcConn: grpcConn,
281311
}
282312

283313
if httpPort > 0 || httpsPort > 0 {
@@ -372,6 +402,10 @@ func (c *consulContainerNode) GetClient() *api.Client {
372402
return c.client
373403
}
374404

405+
func (c *consulContainerNode) GetGRPCConn() *grpc.ClientConn {
406+
return c.grpcConn
407+
}
408+
375409
// NewClient returns an API client by making a new one based on the provided token
376410
// - updateDefault: if true update the default client
377411
func (c *consulContainerNode) NewClient(token string, updateDefault bool) (*api.Client, error) {
@@ -522,6 +556,13 @@ func (c *consulContainerNode) terminate(retainPod bool, skipFuncs bool) error {
522556
c.pod = nil
523557
}
524558

559+
if c.grpcConn != nil {
560+
if err := c.grpcConn.Close(); err != nil {
561+
merr = multierror.Append(merr, err)
562+
}
563+
c.grpcConn = nil
564+
}
565+
525566
return merr
526567
}
527568

@@ -561,6 +602,7 @@ func newContainerRequest(config Config, opts containerOpts, ports ...int) (podRe
561602
ExposedPorts: []string{
562603
"8500/tcp", // Consul HTTP API
563604
"8501/tcp", // Consul HTTPs API
605+
"8502/tcp", // Consul gRPC API
564606

565607
"8443/tcp", // Envoy Gateway Listener
566608

test/integration/consul-container/libs/cluster/network.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ func createNetwork(t TestingT, name string) (testcontainers.Network, error) {
2020
Name: name,
2121
Attachable: true,
2222
CheckDuplicate: true,
23+
SkipReaper: isRYUKDisabled(),
2324
},
2425
}
2526
first := true
Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
package resources
2+
3+
import (
4+
"testing"
5+
6+
"github.com/stretchr/testify/require"
7+
"google.golang.org/protobuf/types/known/anypb"
8+
9+
"github.com/hashicorp/consul/sdk/testutil"
10+
"github.com/hashicorp/consul/sdk/testutil/retry"
11+
libcluster "github.com/hashicorp/consul/test/integration/consul-container/libs/cluster"
12+
libtopology "github.com/hashicorp/consul/test/integration/consul-container/libs/topology"
13+
14+
pbresource "github.com/hashicorp/consul/proto-public/pbresource"
15+
pbdemov2 "github.com/hashicorp/consul/proto/private/pbdemo/v2"
16+
)
17+
18+
// TestResources exercises the full Resource Service and Controller stack.
19+
func TestResources(t *testing.T) {
20+
t.Parallel()
21+
22+
cluster, _, _ := libtopology.NewCluster(t, &libtopology.ClusterConfig{
23+
NumServers: 2,
24+
Cmd: `-hcl=enable_dev_resources = true`,
25+
BuildOpts: &libcluster.BuildOptions{Datacenter: "dc1"},
26+
})
27+
28+
// Write an artist resource to a follower to exercise leader forwarding.
29+
followers, err := cluster.Followers()
30+
require.NoError(t, err)
31+
32+
conn := followers[0].GetGRPCConn()
33+
client := pbresource.NewResourceServiceClient(conn)
34+
ctx := testutil.TestContext(t)
35+
36+
artist, err := anypb.New(&pbdemov2.Artist{
37+
Name: "Five Iron Frenzy",
38+
Genre: pbdemov2.Genre_GENRE_SKA,
39+
})
40+
require.NoError(t, err)
41+
42+
writeRsp, err := client.Write(ctx, &pbresource.WriteRequest{
43+
Resource: &pbresource.Resource{
44+
Id: &pbresource.ID{
45+
Type: &pbresource.Type{
46+
Group: "demo",
47+
GroupVersion: "v2",
48+
Kind: "artist",
49+
},
50+
Tenancy: &pbresource.Tenancy{
51+
Partition: "default",
52+
PeerName: "local",
53+
Namespace: "default",
54+
},
55+
Name: "five-iron-frenzy",
56+
},
57+
Data: artist,
58+
},
59+
})
60+
require.NoError(t, err)
61+
62+
// Wait for controller to run and update the artist's status. Also checks
63+
// leader to follower replication is working.
64+
retry.Run(t, func(r *retry.R) {
65+
readRsp, err := client.Read(ctx, &pbresource.ReadRequest{Id: writeRsp.Resource.Id})
66+
require.NoError(r, err)
67+
require.NotNil(r, readRsp.Resource.Status)
68+
require.Contains(r, readRsp.Resource.Status, "consul.io/artist-controller")
69+
})
70+
71+
// Controller will create albums for the artist.
72+
listRsp, err := client.List(ctx, &pbresource.ListRequest{
73+
Type: &pbresource.Type{
74+
Group: "demo",
75+
GroupVersion: "v2",
76+
Kind: "album",
77+
},
78+
Tenancy: &pbresource.Tenancy{
79+
Partition: "default",
80+
PeerName: "local",
81+
Namespace: "default",
82+
},
83+
})
84+
require.NoError(t, err)
85+
require.Len(t, listRsp.Resources, 3)
86+
}

0 commit comments

Comments
 (0)