From bb26ed5b60aba8a922faab4a83b6101334b0a7c1 Mon Sep 17 00:00:00 2001 From: Awais Malik Date: Tue, 11 May 2021 15:18:39 -0700 Subject: [PATCH] fix: deprecates the usage of gcp-inspec and replaces integration tests with gcloud --- kitchen.yml | 3 +- modules/postgresql/README.md | 6 +- modules/postgresql/variables.tf | 6 +- test/integration/mssql-ha/controls/mssql.rb | 144 ++++++--- test/integration/mssql-ha/inspec.yml | 3 - .../mssql-public/controls/mssql.rb | 98 ++++-- test/integration/mssql-public/inspec.yml | 3 - test/integration/mysql-ha/controls/mysql.rb | 300 +++++++++++++----- test/integration/mysql-ha/inspec.yml | 3 - .../mysql-private/controls/mysql.rb | 112 ++++--- .../mysql-private/controls/peering.rb | 20 +- test/integration/mysql-private/inspec.yml | 3 - .../mysql-public/controls/mysql.rb | 104 ++++-- test/integration/mysql-public/inspec.yml | 3 - test/integration/postgresql-ha/controls/pg.rb | 290 ++++++++++++----- test/integration/postgresql-ha/inspec.yml | 3 - .../postgresql-public/controls/pg.rb | 102 ++++-- test/integration/postgresql-public/inspec.yml | 3 - 18 files changed, 857 insertions(+), 349 deletions(-) diff --git a/kitchen.yml b/kitchen.yml index 2a2f6c95..b557a839 100644 --- a/kitchen.yml +++ b/kitchen.yml @@ -27,8 +27,7 @@ verifier: name: terraform systems: - name: system - backend: gcp - shell: true + backend: local suites: - name: mysql-public diff --git a/modules/postgresql/README.md b/modules/postgresql/README.md index 525dde5d..87a64a09 100644 --- a/modules/postgresql/README.md +++ b/modules/postgresql/README.md @@ -12,13 +12,13 @@ Note: CloudSQL provides [disk autoresize](https://cloud.google.com/sql/docs/mysq | additional\_users | A list of users to be created in your cluster |
list(object({
name = string
password = string
}))
| `[]` | no | | availability\_type | The availability type for the master instance.This is only used to set up high availability for the PostgreSQL instance. Can be either `ZONAL` or `REGIONAL`. | `string` | `"ZONAL"` | no | | backup\_configuration | The backup\_configuration settings subblock for the database setings |
object({
enabled = bool
start_time = string
location = string
point_in_time_recovery_enabled = bool
})
|
{
"enabled": false,
"location": null,
"point_in_time_recovery_enabled": false,
"start_time": null
}
| no | -| create\_timeout | The optional timout that is applied to limit long database creates. | `string` | `"10m"` | no | +| create\_timeout | The optional timout that is applied to limit long database creates. | `string` | `"15m"` | no | | database\_flags | The database flags for the master instance. See [more details](https://cloud.google.com/sql/docs/postgres/flags) |
list(object({
name = string
value = string
}))
| `[]` | no | | database\_version | The database version to use | `string` | n/a | yes | | db\_charset | The charset for the default database | `string` | `""` | no | | db\_collation | The collation for the default database. Example: 'en\_US.UTF8' | `string` | `""` | no | | db\_name | The name of the default database to create | `string` | `"default"` | no | -| delete\_timeout | The optional timout that is applied to limit long database deletes. | `string` | `"10m"` | no | +| delete\_timeout | The optional timout that is applied to limit long database deletes. | `string` | `"15m"` | no | | deletion\_protection | Used to block Terraform from deleting a SQL Instance. | `bool` | `true` | no | | disk\_autoresize | Configuration to increase storage size. | `bool` | `true` | no | | disk\_size | The disk size for the master instance. | `number` | `10` | no | @@ -41,7 +41,7 @@ Note: CloudSQL provides [disk autoresize](https://cloud.google.com/sql/docs/mysq | read\_replicas | List of read replicas to create |
list(object({
name = string
tier = string
zone = string
disk_type = string
disk_autoresize = bool
disk_size = string
user_labels = map(string)
database_flags = list(object({
name = string
value = string
}))
ip_configuration = object({
authorized_networks = list(map(string))
ipv4_enabled = bool
private_network = string
require_ssl = bool
})
}))
| `[]` | no | | region | The region of the Cloud SQL resources | `string` | `"us-central1"` | no | | tier | The tier for the master instance. | `string` | `"db-f1-micro"` | no | -| update\_timeout | The optional timout that is applied to limit long database updates. | `string` | `"10m"` | no | +| update\_timeout | The optional timout that is applied to limit long database updates. | `string` | `"15m"` | no | | user\_labels | The key/value labels for the master instances. | `map(string)` | `{}` | no | | user\_name | The name of the default user | `string` | `"default"` | no | | user\_password | The password for the default user. If not set, a random one will be generated and available in the generated\_user\_password output variable. | `string` | `""` | no | diff --git a/modules/postgresql/variables.tf b/modules/postgresql/variables.tf index 423235cf..8957db7d 100644 --- a/modules/postgresql/variables.tf +++ b/modules/postgresql/variables.tf @@ -247,19 +247,19 @@ variable "additional_users" { variable "create_timeout" { description = "The optional timout that is applied to limit long database creates." type = string - default = "10m" + default = "15m" } variable "update_timeout" { description = "The optional timout that is applied to limit long database updates." type = string - default = "10m" + default = "15m" } variable "delete_timeout" { description = "The optional timout that is applied to limit long database deletes." type = string - default = "10m" + default = "15m" } variable "encryption_key_name" { diff --git a/test/integration/mssql-ha/controls/mssql.rb b/test/integration/mssql-ha/controls/mssql.rb index 26d13d65..4a4cd0d8 100644 --- a/test/integration/mssql-ha/controls/mssql.rb +++ b/test/integration/mssql-ha/controls/mssql.rb @@ -12,46 +12,118 @@ # See the License for the specific language governing permissions and # limitations under the License. +require 'json' + project_id = attribute('project_id') basename = attribute('name') authorized_network = attribute('authorized_network') +region = "us-central1" + +activation_policy = "ALWAYS" +availability_type = "REGIONAL" +data_disk_size_gb = 10 +data_disk_type = "PD_SSD" +kind = "sql#settings" +pricing_plan = "PER_USE" +replication_type = "SYNCHRONOUS" +storage_auto_resize = true +storage_auto_resize_limit = 0 +tier = "db-custom-2-13312" + +describe command("gcloud --project='#{project_id}' sql instances describe #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mssql_ha_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['availabilityType']).to eq "#{availability_type}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq 'SQLSERVER_2017_STANDARD' + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end -describe google_sql_database_instance(project: project_id, database: basename) do - let(:expected_settings) { - { - activation_policy: "ALWAYS", - availability_type: "REGIONAL", - data_disk_size_gb: 10, - data_disk_type: "PD_SSD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: "db-custom-2-13312", - } - } - let(:settings) { subject.settings.item } - let(:backup_configuration) { settings[:backup_configuration] } - let(:ip_configuration) { settings[:ip_configuration] } - let(:location_preference) { settings[:location_preference] } - let(:maintenance_window) { settings[:maintenance_window] } - let(:user_labels) { settings[:user_labels] } - - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq 'SQLSERVER_2017_STANDARD' } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq 'us-central1' } - its(:gce_zone) { should eq 'us-central1-a' } - - it { expect(settings).to include(expected_settings) } - it { expect(ip_configuration).to include(authorized_networks: [{kind: 'sql#aclEntry', name: "#{project_id}-cidr", value: authorized_network}], ipv4_enabled: true, require_ssl: true) } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "us-central1-a") } - it { expect(maintenance_window).to include(kind: "sql#maintenanceWindow", day: 7, hour: 12, update_track: "stable") } - it { expect(user_labels).to include(foo: "bar") } + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-a" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-a") + end + + it "maintenance window is valid" do + expect(data['settings']['maintenanceWindow']).to include( + "kind" => "sql#maintenanceWindow", + "day" => 7, + "hour" => 12, + "updateTrack" => "stable") + end + + it "ip configuration and authorized networks are valid" do + expect(data['settings']['ipConfiguration']).to include( + ["authorizedNetworks"][0] => [{ + "kind" => "sql#aclEntry", + "name" => "#{project_id}-cidr", + "value" => authorized_network + }], + "ipv4Enabled" => true, + "requireSsl" => true, + ) + end + + it "user labels are set" do + expect(data['settings']['userLabels']).to include( + "foo" => "bar") + end + end end -describe google_sql_users(project: project_id, database: basename).where(user_name: /\Atftest/) do - its(:count) { should be 3 } - it { should exist } +describe command("gcloud --project='#{project_id}' sql users list --instance #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mssql_ha_database" do + it "has 3 users" do + expect(data.select {|k,v| k['name'].start_with?("tftest")}.size).to eq 3 + end + end end diff --git a/test/integration/mssql-ha/inspec.yml b/test/integration/mssql-ha/inspec.yml index e03832b3..5230eafb 100644 --- a/test/integration/mssql-ha/inspec.yml +++ b/test/integration/mssql-ha/inspec.yml @@ -15,9 +15,6 @@ name: cloud-sql title: Google Cloud SQL version: 0.1.0 -depends: - - name: inspec-gcp - url: https://github.com/inspec/inspec-gcp/archive/v0.21.4.tar.gz attributes: - name: project_id type: string diff --git a/test/integration/mssql-public/controls/mssql.rb b/test/integration/mssql-public/controls/mssql.rb index b3695e95..005410d1 100644 --- a/test/integration/mssql-public/controls/mssql.rb +++ b/test/integration/mssql-public/controls/mssql.rb @@ -12,33 +12,79 @@ # See the License for the specific language governing permissions and # limitations under the License. +require 'json' + project_id = attribute('project_id') basename = attribute('name') +region = "us-central1" + +activation_policy = "ALWAYS" +data_disk_size_gb = 10 +data_disk_type = "PD_SSD" +kind = "sql#settings" +pricing_plan = "PER_USE" +replication_type = "SYNCHRONOUS" +storage_auto_resize = true +storage_auto_resize_limit = 0 +tier = "db-custom-2-3840" + +describe command("gcloud --project='#{project_id}' sql instances describe #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mssql_public_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq 'SQLSERVER_2017_STANDARD' + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-a" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-a") + end -describe google_sql_database_instance(project: project_id, database: basename) do - let(:expected_settings) { - { - activation_policy: "ALWAYS", - data_disk_size_gb: 10, - data_disk_type: "PD_SSD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: "db-custom-2-3840", - } - } - let(:settings) { subject.settings.item } - let(:location_preference) { settings[:location_preference] } - let(:maintenance_window) { settings[:maintenance_window] } - - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq 'SQLSERVER_2017_STANDARD' } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq 'us-central1' } - its(:gce_zone) { should eq 'us-central1-a' } - it { expect(settings).to include(expected_settings) } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "us-central1-a") } - it { expect(maintenance_window).to include(kind: "sql#maintenanceWindow", day: 1, hour: 23, update_track: "canary") } + it "maintenance window is valid" do + expect(data['settings']['maintenanceWindow']).to include( + "kind" => "sql#maintenanceWindow", + "day" => 1, + "hour" => 23, + "updateTrack" => "canary") + end + end end diff --git a/test/integration/mssql-public/inspec.yml b/test/integration/mssql-public/inspec.yml index 8411be46..1dbd1e9a 100644 --- a/test/integration/mssql-public/inspec.yml +++ b/test/integration/mssql-public/inspec.yml @@ -15,9 +15,6 @@ name: cloud-sql title: Google Cloud SQL version: 0.1.0 -depends: - - name: inspec-gcp - url: https://github.com/inspec/inspec-gcp/archive/v0.21.4.tar.gz attributes: - name: project_id type: string diff --git a/test/integration/mysql-ha/controls/mysql.rb b/test/integration/mysql-ha/controls/mysql.rb index 1e4a7667..d1d7e02a 100644 --- a/test/integration/mysql-ha/controls/mysql.rb +++ b/test/integration/mysql-ha/controls/mysql.rb @@ -12,99 +12,239 @@ # See the License for the specific language governing permissions and # limitations under the License. +require 'json' + project_id = attribute('project_id') basename = attribute('name') authorized_network = attribute('authorized_network') replicas = attribute('replicas') instances = attribute('instances') +mysql_version = "MYSQL_5_7" +region = "us-central1" + +activation_policy = "ALWAYS" +availability_type = "REGIONAL" +availability_type_replica = "ZONAL" +data_disk_size_gb = 10 +data_disk_type = "PD_SSD" +data_disk_type_replica = "PD_HDD" +kind = "sql#settings" +pricing_plan = "PER_USE" +replication_type = "SYNCHRONOUS" +storage_auto_resize = true +storage_auto_resize_limit = 0 +tier = "db-n1-standard-1" -describe google_sql_database_instances(project: project_id).where(instance_name: /#{basename}/) do - its(:count) { should eq 4 } - its(:count) { should eq 1 + replicas.length } - its(:count) { should eq instances.length } +describe command("gcloud --project='#{project_id}' sql instances list --filter='name ~ ^#{basename}' --format=json") do + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_ha_database" do + it "has 1 primary instance and 3 replicas" do + expect(data.size).to eq 4 + end + end end -describe google_sql_database_instance(project: project_id, database: basename) do - let(:expected_settings) { - { - activation_policy: "ALWAYS", - availability_type: "REGIONAL", - data_disk_size_gb: 10, - data_disk_type: "PD_SSD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: "db-n1-standard-1", - } - } - let(:settings) { subject.settings.item } - let(:backup_configuration) { settings[:backup_configuration] } - let(:ip_configuration) { settings[:ip_configuration] } - let(:database_flags) { settings[:database_flags] } - let(:location_preference) { settings[:location_preference] } - let(:maintenance_window) { settings[:maintenance_window] } - let(:user_labels) { settings[:user_labels] } - - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq 'MYSQL_5_7' } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq 'us-central1' } - its(:gce_zone) { should eq 'us-central1-c' } - - it { expect(settings).to include(expected_settings) } - it { expect(backup_configuration).to include(binary_log_enabled: true, enabled: true, kind: "sql#backupConfiguration", start_time: "20:55") } - it { expect(ip_configuration).to include(authorized_networks: [{kind: 'sql#aclEntry', name: "#{project_id}-cidr", value: authorized_network}], ipv4_enabled: true, require_ssl: true) } - it { expect(database_flags).to include(name: "long_query_time", value: "1") } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "us-central1-c") } - it { expect(maintenance_window).to include(kind: "sql#maintenanceWindow", day: 7, hour: 12, update_track: "stable") } - it { expect(user_labels).to include(foo: "bar") } +describe command("gcloud --project='#{project_id}' sql instances describe #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_ha_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['availabilityType']).to eq "#{availability_type}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq mysql_version + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-c" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-c") + end + + it "maintenance window is valid" do + expect(data['settings']['maintenanceWindow']).to include( + "kind" => "sql#maintenanceWindow", + "day" => 7, + "hour" => 12, + "updateTrack" => "stable") + end + + it "ip configuration and authorized networks are valid" do + expect(data['settings']['ipConfiguration']).to include( + ["authorizedNetworks"][0] => [{ + "kind" => "sql#aclEntry", + "name" => "#{project_id}-cidr", + "value" => authorized_network + }], + "ipv4Enabled" => true, + "requireSsl" => true, + ) + end + + it "user labels are set" do + expect(data['settings']['userLabels']).to include( + "foo" => "bar") + end + + it "database flags are set" do + expect(data['settings']['databaseFlags']).to include({ + "name" => "long_query_time", + "value" => "1"}) + end + + it "backup configuration is enabled" do + expect(data['settings']['backupConfiguration']).to include( + "binaryLogEnabled" => true, + "enabled" => true, + "kind" => "sql#backupConfiguration", + "startTime" => "20:55") + end + + end end %i[a b c].each_with_index do |zone, index| - name = "#{basename}-replica-test#{index}" - describe google_sql_database_instance(project: project_id, database: name) do - its(:name) { should eq replicas[index]['name'] } - - let(:expected_settings) { - { - activation_policy: "ALWAYS", - data_disk_size_gb: 10, - data_disk_type: "PD_HDD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: "db-n1-standard-1", - } - } - let(:settings) { subject.settings.item } - let(:ip_configuration) { settings[:ip_configuration] } - let(:database_flags) { settings[:database_flags] } - let(:location_preference) { settings[:location_preference] } - let(:user_labels) { settings[:user_labels] } - - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq 'MYSQL_5_7' } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq 'us-central1' } - its(:gce_zone) { should eq "us-central1-#{zone}" } - - it { expect(settings).to include(expected_settings) } - it { expect(ip_configuration).to include(authorized_networks: [{kind: 'sql#aclEntry', name: "#{project_id}-cidr", value: authorized_network}], ipv4_enabled: true, require_ssl: false) } - it { expect(database_flags).to include(name: "long_query_time", value: "1") } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "us-central1-#{zone}") } - it { expect(user_labels).to include(bar: "baz") } + replica_name = "#{basename}-replica-test#{index}" + + describe command("gcloud --project='#{project_id}' sql instances describe #{replica_name} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_ha_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['availabilityType']).to eq "#{availability_type_replica}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type_replica}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq mysql_version + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-#{zone}" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-#{zone}") + end + + it "ip configuration and authorized networks are valid" do + expect(data['settings']['ipConfiguration']).to include( + ["authorizedNetworks"][0] => [{ + "kind" => "sql#aclEntry", + "name" => "#{project_id}-cidr", + "value" => authorized_network + }], + "ipv4Enabled" => true, + "requireSsl" => false, + ) + end + + it "user labels are set" do + expect(data['settings']['userLabels']).to include( + "bar" => "baz") + end + + it "database flags are set" do + expect(data['settings']['databaseFlags']).to include({ + "name" => "long_query_time", + "value" => "1"}) + end + end end end -describe google_sql_users(project: project_id, database: basename).where(user_name: /\Atftest/) do - its(:count) { should be 3 } - it { should exist } -end +describe command("gcloud --project='#{project_id}' sql users list --instance #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } -describe google_sql_users(project: project_id, database: basename).where(user_host: 'localhost') do - it { should exist } + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_ha_database" do + it "has 3 users" do + expect(data.select {|k,v| k['name'].start_with?("tftest")}.size).to eq 3 + end + + it "is setup for localhost" do + expect(data.select {|k,v| k['host'] == "localhost"}.size).to be >= 1 + end + end end diff --git a/test/integration/mysql-ha/inspec.yml b/test/integration/mysql-ha/inspec.yml index d2947aa9..b5b8fd5f 100644 --- a/test/integration/mysql-ha/inspec.yml +++ b/test/integration/mysql-ha/inspec.yml @@ -15,9 +15,6 @@ name: cloud-sql title: Google Cloud SQL version: 0.1.0 -depends: - - name: inspec-gcp - url: https://github.com/inspec/inspec-gcp/archive/v0.21.4.tar.gz attributes: - name: project_id type: string diff --git a/test/integration/mysql-private/controls/mysql.rb b/test/integration/mysql-private/controls/mysql.rb index 19c78b62..3fd60765 100644 --- a/test/integration/mysql-private/controls/mysql.rb +++ b/test/integration/mysql-private/controls/mysql.rb @@ -12,6 +12,8 @@ # See the License for the specific language governing permissions and # limitations under the License. +require 'json' + project_id = attribute('project_id') basename = attribute('name') public_ip_address = attribute('public_ip_address') @@ -20,56 +22,94 @@ region = "us-central1" tier = "db-n1-standard-1" +activation_policy = "ALWAYS" +data_disk_size_gb = 10 +data_disk_type = "PD_SSD" +kind = "sql#settings" +pricing_plan = "PER_USE" +replication_type = "SYNCHRONOUS" +storage_auto_resize = true +storage_auto_resize_limit = 0 + +describe command("gcloud --project='#{project_id}' sql instances describe #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_private_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq mysql_version + end -describe google_sql_database_instance(project: project_id, database: basename) do - let(:expected_settings) { - { - activation_policy: "ALWAYS", - data_disk_size_gb: 10, - data_disk_type: "PD_SSD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: tier, - } - } - - let(:settings) { subject.settings.item } - let(:instance_ip_addresses) { subject.ip_addresses } - let(:location_preference) { settings[:location_preference] } - let(:maintenance_window) { settings[:maintenance_window] } - - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq mysql_version } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq region } - its(:gce_zone) { should eq "#{region}-c" } - - it { expect(settings).to include(expected_settings) } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "#{region}-c") } - it { expect(maintenance_window).to include(kind: "sql#maintenanceWindow", day: 1, hour: 23, update_track: "stable") } + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-c" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-c") + end + + it "maintenance window is valid" do + expect(data['settings']['maintenanceWindow']).to include( + "kind" => "sql#maintenanceWindow", + "day" => 1, + "hour" => 23, + "updateTrack" => "stable") + end + end describe "MySQL private instance" do it "has two assigned IP addresses" do - expect(instance_ip_addresses.count).to eq(2) + expect(data["ipAddresses"].count).to eq(2) end it "has expected external IP address" do - expect(instance_ip_addresses[0].item).to eq( + expect(data["ipAddresses"][0]).to eq( { - type: "PRIMARY", - ip_address: "#{public_ip_address}" + "type" => "PRIMARY", + "ipAddress" => "#{public_ip_address}" } ) end it "has expected internal IP address" do - expect(instance_ip_addresses[1].item).to eq( + expect(data["ipAddresses"][1]).to eq( { - type: "PRIVATE", - ip_address: "#{private_ip_address}" + "type" => "PRIVATE", + "ipAddress" => "#{private_ip_address}" } ) end diff --git a/test/integration/mysql-private/controls/peering.rb b/test/integration/mysql-private/controls/peering.rb index c6e56b77..94043edd 100644 --- a/test/integration/mysql-private/controls/peering.rb +++ b/test/integration/mysql-private/controls/peering.rb @@ -15,7 +15,21 @@ project_id = attribute('project_id') range = attribute('reserved_range_name') -describe google_compute_global_address(project: project_id, name: range) do - it { should exist } - # Verify that address_type eq INTERNAL, once inspec supports it. +describe command("gcloud --project='#{project_id}' compute addresses list --global --filter='#{range}' --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_private_database" do + it "has peering setup" do + expect(data.size).to eq(1) + end end +end diff --git a/test/integration/mysql-private/inspec.yml b/test/integration/mysql-private/inspec.yml index bbd9552b..df8af61a 100644 --- a/test/integration/mysql-private/inspec.yml +++ b/test/integration/mysql-private/inspec.yml @@ -15,9 +15,6 @@ name: cloud-sql title: Google Cloud SQL version: 0.1.0 -depends: - - name: inspec-gcp - url: https://github.com/inspec/inspec-gcp/archive/v0.21.4.tar.gz attributes: - name: project_id type: string diff --git a/test/integration/mysql-public/controls/mysql.rb b/test/integration/mysql-public/controls/mysql.rb index d1005acd..db52a1b7 100644 --- a/test/integration/mysql-public/controls/mysql.rb +++ b/test/integration/mysql-public/controls/mysql.rb @@ -12,6 +12,8 @@ # See the License for the specific language governing permissions and # limitations under the License. +require 'json' + project_id = attribute('project_id') basename = attribute('name') public_ip_address = attribute('public_ip_address') @@ -20,45 +22,85 @@ region = "us-central1" tier = "db-n1-standard-1" -describe google_sql_database_instance(project: project_id, database: basename) do - let(:expected_settings) { - { - activation_policy: "ALWAYS", - data_disk_size_gb: 10, - data_disk_type: "PD_SSD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: tier, - } - } - let(:settings) { subject.settings.item } - let(:location_preference) { settings[:location_preference] } - let(:maintenance_window) { settings[:maintenance_window] } - let(:instance_ip_addresses) { subject.ip_addresses } +activation_policy = "ALWAYS" +data_disk_size_gb = 10 +data_disk_type = "PD_SSD" +kind = "sql#settings" +pricing_plan = "PER_USE" +replication_type = "SYNCHRONOUS" +storage_auto_resize = true +storage_auto_resize_limit = 0 + +describe command("gcloud --project='#{project_id}' sql instances describe #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq mysql_version + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq mysql_version } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq region } - its(:gce_zone) { should eq "#{region}-c" } + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-c" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-c") + end - it { expect(settings).to include(expected_settings) } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "#{region}-c") } - it { expect(maintenance_window).to include(kind: "sql#maintenanceWindow", day: 1, hour: 23, update_track: "canary") } + it "maintenance window is valid" do + expect(data['settings']['maintenanceWindow']).to include( + "kind" => "sql#maintenanceWindow", + "day" => 1, + "hour" => 23, + "updateTrack" => "canary") + end + end -describe "MySQL pubic instance" do + describe "MySQL public instance" do it "has just one assigned IP address" do - expect(instance_ip_addresses.count).to eq(1) + expect(data["ipAddresses"].count).to eq(1) end it "has expected external IP address" do - expect(instance_ip_addresses[0].item).to eq( + expect(data["ipAddresses"][0]).to eq( { - type: "PRIMARY", - ip_address: "#{public_ip_address}" + "type" => "PRIMARY", + "ipAddress" => "#{public_ip_address}" } ) end diff --git a/test/integration/mysql-public/inspec.yml b/test/integration/mysql-public/inspec.yml index 57d541ec..0aa32592 100644 --- a/test/integration/mysql-public/inspec.yml +++ b/test/integration/mysql-public/inspec.yml @@ -15,9 +15,6 @@ name: cloud-sql title: Google Cloud SQL version: 0.1.0 -depends: - - name: inspec-gcp - url: https://github.com/inspec/inspec-gcp/archive/v0.21.4.tar.gz attributes: - name: project_id type: string diff --git a/test/integration/postgresql-ha/controls/pg.rb b/test/integration/postgresql-ha/controls/pg.rb index 8e318ac9..e04b5dec 100644 --- a/test/integration/postgresql-ha/controls/pg.rb +++ b/test/integration/postgresql-ha/controls/pg.rb @@ -12,95 +12,231 @@ # See the License for the specific language governing permissions and # limitations under the License. +require 'json' + project_id = attribute('project_id') basename = attribute('name') authorized_network = attribute('authorized_network') replicas = attribute('replicas') instances = attribute('instances') +db_version = "POSTGRES_9_6" +region = "us-central1" + +activation_policy = "ALWAYS" +availability_type = "REGIONAL" +data_disk_size_gb = 10 +data_disk_type = "PD_SSD" +data_disk_type_replica = "PD_HDD" +kind = "sql#settings" +pricing_plan = "PER_USE" +replication_type = "SYNCHRONOUS" +storage_auto_resize = true +storage_auto_resize_limit = 0 +tier = "db-custom-2-13312" -describe google_sql_database_instances(project: project_id).where(instance_name: /#{basename}/) do - its(:count) { should eq 4 } - its(:count) { should eq 1 + replicas.length } - its(:count) { should eq instances.length } +describe command("gcloud --project='#{project_id}' sql instances list --filter='name ~ ^#{basename}' --format=json") do + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "postgresql_ha_database" do + it "has 1 primary instance and 3 replicas" do + expect(data.size).to eq 4 + end + end end -describe google_sql_database_instance(project: project_id, database: basename) do - let(:expected_settings) { - { - activation_policy: "ALWAYS", - availability_type: "REGIONAL", - data_disk_size_gb: 10, - data_disk_type: "PD_SSD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: "db-custom-2-13312", - } - } - let(:settings) { subject.settings.item } - let(:backup_configuration) { settings[:backup_configuration] } - let(:ip_configuration) { settings[:ip_configuration] } - let(:database_flags) { settings[:database_flags] } - let(:location_preference) { settings[:location_preference] } - let(:maintenance_window) { settings[:maintenance_window] } - let(:user_labels) { settings[:user_labels] } - - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq 'POSTGRES_9_6' } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq 'us-central1' } - its(:gce_zone) { should eq 'us-central1-c' } - - it { expect(settings).to include(expected_settings) } - it { expect(backup_configuration).to include(enabled: true, kind: "sql#backupConfiguration", start_time: "20:55") } - it { expect(ip_configuration).to include(authorized_networks: [{kind: 'sql#aclEntry', name: "#{project_id}-cidr", value: authorized_network}], ipv4_enabled: true, require_ssl: true) } - it { expect(database_flags).to include(name: "autovacuum", value: "off") } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "us-central1-c") } - it { expect(maintenance_window).to include(kind: "sql#maintenanceWindow", day: 7, hour: 12, update_track: "stable") } - it { expect(user_labels).to include(foo: "bar") } +describe command("gcloud --project='#{project_id}' sql instances describe #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "postgresql_ha_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['availabilityType']).to eq "#{availability_type}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq db_version + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-c" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-c") + end + + it "maintenance window is valid" do + expect(data['settings']['maintenanceWindow']).to include( + "kind" => "sql#maintenanceWindow", + "day" => 7, + "hour" => 12, + "updateTrack" => "stable") + end + + it "ip configuration and authorized networks are valid" do + expect(data['settings']['ipConfiguration']).to include( + ["authorizedNetworks"][0] => [{ + "kind" => "sql#aclEntry", + "name" => "#{project_id}-cidr", + "value" => authorized_network + }], + "ipv4Enabled" => true, + "requireSsl" => true, + ) + end + + it "user labels are set" do + expect(data['settings']['userLabels']).to include( + "foo" => "bar") + end + + it "database flags are set" do + expect(data['settings']['databaseFlags']).to include({ + "name" => "autovacuum", + "value" => "off"}) + end + + it "backup configuration is enabled" do + expect(data['settings']['backupConfiguration']).to include( + "enabled" => true, + "kind" => "sql#backupConfiguration", + "startTime" => "20:55") + end + end end %i[a b c].each_with_index do |zone, index| - name = "#{basename}-replica-test#{index}" - describe google_sql_database_instance(project: project_id, database: name) do - its(:name) { should eq replicas[index]['name'] } - - let(:expected_settings) { - { - activation_policy: "ALWAYS", - data_disk_size_gb: 10, - data_disk_type: "PD_HDD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: "db-custom-2-13312", - } - } - let(:settings) { subject.settings.item } - let(:ip_configuration) { settings[:ip_configuration] } - let(:database_flags) { settings[:database_flags] } - let(:location_preference) { settings[:location_preference] } - let(:user_labels) { settings[:user_labels] } - - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq 'POSTGRES_9_6' } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq 'us-central1' } - its(:gce_zone) { should eq "us-central1-#{zone}" } - - it { expect(settings).to include(expected_settings) } - it { expect(ip_configuration).to include(authorized_networks: [{kind: 'sql#aclEntry', name: "#{project_id}-cidr", value: authorized_network}], ipv4_enabled: true, require_ssl: false) } - it { expect(database_flags).to include(name: "autovacuum", value: "off") } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "us-central1-#{zone}") } - it { expect(user_labels).to include(bar: "baz") } + replica_name = "#{basename}-replica-test#{index}" + + describe command("gcloud --project='#{project_id}' sql instances describe #{replica_name} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "postgresql_ha_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type_replica}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq db_version + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-#{zone}" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-#{zone}") + end + + it "ip configuration and authorized networks are valid" do + expect(data['settings']['ipConfiguration']).to include( + ["authorizedNetworks"][0] => [{ + "kind" => "sql#aclEntry", + "name" => "#{project_id}-cidr", + "value" => authorized_network + }], + "ipv4Enabled" => true, + "requireSsl" => false, + ) + end + + it "user labels are set" do + expect(data['settings']['userLabels']).to include( + "bar" => "baz") + end + + it "database flags are set" do + expect(data['settings']['databaseFlags']).to include({ + "name" => "autovacuum", + "value" => "off"}) + end + end end end -describe google_sql_users(project: project_id, database: basename).where(user_name: /\Atftest/) do - its(:count) { should be 3 } - it { should exist } +describe command("gcloud --project='#{project_id}' sql users list --instance #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "mysql_ha_database" do + it "has 3 users" do + expect(data.select {|k,v| k['name'].start_with?("tftest")}.size).to eq 3 + end + end end diff --git a/test/integration/postgresql-ha/inspec.yml b/test/integration/postgresql-ha/inspec.yml index d2947aa9..b5b8fd5f 100644 --- a/test/integration/postgresql-ha/inspec.yml +++ b/test/integration/postgresql-ha/inspec.yml @@ -15,9 +15,6 @@ name: cloud-sql title: Google Cloud SQL version: 0.1.0 -depends: - - name: inspec-gcp - url: https://github.com/inspec/inspec-gcp/archive/v0.21.4.tar.gz attributes: - name: project_id type: string diff --git a/test/integration/postgresql-public/controls/pg.rb b/test/integration/postgresql-public/controls/pg.rb index afccc671..d336bc18 100644 --- a/test/integration/postgresql-public/controls/pg.rb +++ b/test/integration/postgresql-public/controls/pg.rb @@ -19,47 +19,87 @@ tier = "db-f1-micro" public_ip_address = attribute('public_ip_address') -describe google_sql_database_instance(project: project_id, database: basename) do - let(:expected_settings) { - { - activation_policy: "ALWAYS", - data_disk_size_gb: 10, - data_disk_type: "PD_SSD", - kind: "sql#settings", - pricing_plan: "PER_USE", - replication_type: "SYNCHRONOUS", - storage_auto_resize: true, - storage_auto_resize_limit: 0, - tier: tier, - } - } - let(:settings) { subject.settings.item } - let(:location_preference) { settings[:location_preference] } - let(:maintenance_window) { settings[:maintenance_window] } - let(:instance_ip_addresses) { subject.ip_addresses } +activation_policy = "ALWAYS" +data_disk_size_gb = 10 +data_disk_type = "PD_SSD" +kind = "sql#settings" +pricing_plan = "PER_USE" +replication_type = "SYNCHRONOUS" +storage_auto_resize = true +storage_auto_resize_limit = 0 - its(:backend_type) { should eq 'SECOND_GEN' } - its(:database_version) { should eq db_version } - its(:state) { should eq 'RUNNABLE' } - its(:region) { should eq region } - its(:gce_zone) { should eq "#{region}-c" } - it { expect(settings).to include(expected_settings) } - it { expect(location_preference).to include(kind: "sql#locationPreference", zone: "#{region}-c") } - it { expect(maintenance_window).to include(kind: "sql#maintenanceWindow", day: 1, hour: 23, update_track: "canary") } +describe command("gcloud --project='#{project_id}' sql instances describe #{basename} --format=json") do + its(:exit_status) { should eq 0 } + its(:stderr) { should eq '' } + + let!(:data) do + if subject.exit_status == 0 + JSON.parse(subject.stdout) + else + {} + end + end + + describe "postgresql_public_database" do + it "global settings are valid" do + expect(data['settings']['activationPolicy']).to eq "#{activation_policy}" + expect(data['settings']['dataDiskSizeGb']).to eq "#{data_disk_size_gb}" + expect(data['settings']['dataDiskType']).to eq "#{data_disk_type}" + expect(data['settings']['kind']).to eq "#{kind}" + expect(data['settings']['pricingPlan']).to eq "#{pricing_plan}" + expect(data['settings']['replicationType']).to eq "#{replication_type}" + expect(data['settings']['storageAutoResize']).to eq storage_auto_resize + expect(data['settings']['storageAutoResizeLimit']).to eq "#{storage_auto_resize_limit}" + expect(data['settings']['tier']).to eq "#{tier}" + end + + it "backend type is valid" do + expect(data['backendType']).to eq 'SECOND_GEN' + end + + it "database versions is valid" do + expect(data['databaseVersion']).to eq db_version + end + + it "state is valid" do + expect(data['state']).to eq 'RUNNABLE' + end + + it "region is valid" do + expect(data['region']).to eq region + end + + it "gce zone is valid" do + expect(data['gceZone']).to eq "#{region}-c" + end + + it "location preference is valid" do + expect(data['settings']['locationPreference']).to include( + "kind" => "sql#locationPreference", + "zone" => "#{region}-c") + end + + it "maintenance window is valid" do + expect(data['settings']['maintenanceWindow']).to include( + "kind" => "sql#maintenanceWindow", + "day" => 1, + "hour" => 23, + "updateTrack" => "canary") + end + end describe "Postgres SQL pubic instance" do it "has just one assigned IP address" do - expect(instance_ip_addresses.count).to eq(1) + expect(data["ipAddresses"].count).to eq(1) end it "has expected external IP address" do - expect(instance_ip_addresses[0].item).to eq( + expect(data["ipAddresses"][0]).to eq( { - type: "PRIMARY", - ip_address: "#{public_ip_address}" + "type" => "PRIMARY", + "ipAddress" => "#{public_ip_address}" } ) end end - end diff --git a/test/integration/postgresql-public/inspec.yml b/test/integration/postgresql-public/inspec.yml index 16224674..cc3ca618 100644 --- a/test/integration/postgresql-public/inspec.yml +++ b/test/integration/postgresql-public/inspec.yml @@ -15,9 +15,6 @@ name: cloud-sql title: Google Cloud SQL version: 0.1.0 -depends: - - name: inspec-gcp - url: https://github.com/inspec/inspec-gcp/archive/v0.21.4.tar.gz attributes: - name: project_id type: string