From 16c730783be16fdb66388373f837be6823cc5aed Mon Sep 17 00:00:00 2001 From: Zac Cicala Date: Mon, 5 Oct 2020 21:44:12 -0700 Subject: [PATCH 01/10] * Create locale specific org level gsuite groups * Add some basic unit tests --- Gemfile | 1 + lib/terraorg/model/org.rb | 27 +++++++++++++++++------ test/terraorg/model/org_test.rb | 38 +++++++++++++++++++++++++++++++++ 3 files changed, 60 insertions(+), 6 deletions(-) create mode 100644 test/terraorg/model/org_test.rb diff --git a/Gemfile b/Gemfile index 1cee56e..3a65ec3 100644 --- a/Gemfile +++ b/Gemfile @@ -15,3 +15,4 @@ source 'https://rubygems.org' gemspec +gem "minitest" \ No newline at end of file diff --git a/lib/terraorg/model/org.rb b/lib/terraorg/model/org.rb index 7eea787..79a6488 100644 --- a/lib/terraorg/model/org.rb +++ b/lib/terraorg/model/org.rb @@ -202,13 +202,14 @@ def get_squads_md md_lines.join("\n") end - def generate_tf - tf = @member_platoons.map { |p| p.generate_tf(@id) }.join("\n") - File.write('auto.platoons.tf', tf) + # def generate_tf_platoons + # @member_platoons.map { |p| p.generate_tf(@id) }.join("\n") - tf = @member_exception_squads.map { |s| s.generate_tf(@id) }.join("\n") - File.write('auto.exception_squads.tf', tf) + # def generate_tf_sqauds + # @member_exception_squads.map { |s| s.generate_tf(@id) }.join("\n") + def generate_tf_org + tf = '' # Roll all platoons and exception squads into the org. roll_up_to_org = \ @member_exception_squads.map { |s| s.unique_name(@id, nil) } + \ @@ -248,14 +249,18 @@ def generate_tf all_locations[@manager_location] = all_locations.fetch(@manager_location, Set.new).add(@manager) all_locations.each do |l, m| + description = "#{@name} organization members based in #{l} (terraorg)" name = "#{unique_name}-#{l.downcase}" tf += <<-EOF resource "okta_group" "#{name}" { name = "#{name}" - description = "#{@name} organization members based in #{l} (terraorg)" + description = "#{description}" users = #{Util.persons_tf(m)} } + +#{Util.gsuite_group_tf(name, @gsuite_domain, m, description)} EOF + end # Generate a special GSuite group for all managers (org, platoon, squad @@ -264,7 +269,17 @@ def generate_tf all_managers = Set.new([@manager] + @platoons.all.map(&:manager) + @squads.all.map(&:manager).select { |m| m }) manager_dl = "#{@id}-managers" tf += Util.gsuite_group_tf(manager_dl, @gsuite_domain, all_managers, "All managers of the #{@name} organization (terraorg)") + tf + end + + def generate_tf + tf = generate_tf_platoons + File.write('auto.platoons.tf', tf) + + tf = generate_tf_sqauds + File.write('auto.exception_squads.tf', tf) + tf = generate_tf_org File.write('auto.org.tf', tf) end diff --git a/test/terraorg/model/org_test.rb b/test/terraorg/model/org_test.rb new file mode 100644 index 0000000..0f1fa79 --- /dev/null +++ b/test/terraorg/model/org_test.rb @@ -0,0 +1,38 @@ +require 'minitest/autorun' +require './lib/terraorg/model/org' +require './lib/terraorg/model/people' +require './lib/terraorg/model/squads' +require './lib/terraorg/model/platoons' + +class OrgTest < Minitest::Test + def setup + gsuite_domain = "gsuite" + slack_domain = "slack" + people = People.new + squads_data = File.read('./examples/squads.json') + squads = Squads.new(JSON.parse(squads_data), people, gsuite_domain, slack_domain) + platoons_data = File.read('./examples/platoons.json') + platoons = Platoons.new(JSON.parse(platoons_data), squads, people, gsuite_domain) + org_data = File.read('./examples/org.json') + @org = Org.new(JSON.parse(org_data), platoons, squads, people, gsuite_domain) + + end + + def test_org_exists + assert @org != nil + end + + def test_org_tg_generation + tf = @org.generate_tf_org + + puts tf + + assert tf != nil + + # Assert tf contains locale specific okta group + assert tf.include?('resource "okta_group" "contoso-all-gb" {') + + # Assert tf contains locale specific gsuite group + assert tf.include?('resource "gsuite_group" "contoso-all-gb" {') + end +end From 7ba8b21c86eb84280a8473cb06d9641cbf16e205 Mon Sep 17 00:00:00 2001 From: Zac Cicala Date: Mon, 5 Oct 2020 21:50:07 -0700 Subject: [PATCH 02/10] Remove print --- test/terraorg/model/org_test.rb | 2 -- 1 file changed, 2 deletions(-) diff --git a/test/terraorg/model/org_test.rb b/test/terraorg/model/org_test.rb index 0f1fa79..7b122c7 100644 --- a/test/terraorg/model/org_test.rb +++ b/test/terraorg/model/org_test.rb @@ -25,8 +25,6 @@ def test_org_exists def test_org_tg_generation tf = @org.generate_tf_org - puts tf - assert tf != nil # Assert tf contains locale specific okta group From e51b8bd64c1d4dcd9ed9961ef4e3d05f4a888e9f Mon Sep 17 00:00:00 2001 From: Zac Cicala Date: Tue, 6 Oct 2020 16:27:49 -0700 Subject: [PATCH 03/10] Add better tests, update docs, fix typos --- README.md | 4 ++++ lib/terraorg/model/org.rb | 12 ++++++----- lib/terraorg/version.rb | 4 ++-- test/terraorg/model/org_test.rb | 35 ++++++++++++++++++++++++++++++--- 4 files changed, 45 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 8740cc7..f3f8b4e 100644 --- a/README.md +++ b/README.md @@ -126,6 +126,10 @@ information on how to configure the providers. [articulate/terraform-provider-okta]: https://github.com/articulate/terraform-provider-okta [DeviaVir/terraform-provider-gsuite]: https://github.com/DeviaVir/terraform-provider-gsuite +## Running tests +There are a limited number of tests that can be invoked with +`ruby -I lib test/terraorg/model/org_test.rb ` + ## Suggested process At [LiveRamp], a pull request based workflow leveraging [Atlantis] is used to diff --git a/lib/terraorg/model/org.rb b/lib/terraorg/model/org.rb index 79a6488..221f2cf 100644 --- a/lib/terraorg/model/org.rb +++ b/lib/terraorg/model/org.rb @@ -202,11 +202,13 @@ def get_squads_md md_lines.join("\n") end - # def generate_tf_platoons - # @member_platoons.map { |p| p.generate_tf(@id) }.join("\n") + def generate_tf_platoons + @member_platoons.map { |p| p.generate_tf(@id) }.join("\n") + end - # def generate_tf_sqauds - # @member_exception_squads.map { |s| s.generate_tf(@id) }.join("\n") + def generate_tf_squads + @member_exception_squads.map { |s| s.generate_tf(@id) }.join("\n") + end def generate_tf_org tf = '' @@ -276,7 +278,7 @@ def generate_tf tf = generate_tf_platoons File.write('auto.platoons.tf', tf) - tf = generate_tf_sqauds + tf = generate_tf_squads File.write('auto.exception_squads.tf', tf) tf = generate_tf_org diff --git a/lib/terraorg/version.rb b/lib/terraorg/version.rb index ad537fe..7cbef22 100644 --- a/lib/terraorg/version.rb +++ b/lib/terraorg/version.rb @@ -1,4 +1,4 @@ -# Copyright 2019-2020 LiveRamp Holdings, Inc. +5.0# Copyright 2019-2020 LiveRamp Holdings, Inc. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. @@ -13,5 +13,5 @@ # limitations under the License. module Terraorg - VERSION = '0.4.0' + VERSION = '0.5.0' end diff --git a/test/terraorg/model/org_test.rb b/test/terraorg/model/org_test.rb index 7b122c7..3019fea 100644 --- a/test/terraorg/model/org_test.rb +++ b/test/terraorg/model/org_test.rb @@ -18,13 +18,26 @@ def setup end - def test_org_exists - assert @org != nil + + def test_platoons_tf_generation + tf = @org.generate_tf_platoons + + #Make sure not null + assert tf != nil + + #Make sure we're producing global squads Okta and Gsuite tf + assert tf.include?('resource "okta_group" "contoso-squad-sales"') + assert tf.include?('resource "gsuite_group_members" "contoso-squad-sales"') + + #Make sure we're producing locale squads Okta and Gsuite tf + assert tf.include?('resource "gsuite_group" "contoso-squad-sales-gb"') + assert tf.include?('resource "gsuite_group_members" "contoso-squad-sales-gb"') end - def test_org_tg_generation + def test_org_tf_generation tf = @org.generate_tf_org + #Make sure not null assert tf != nil # Assert tf contains locale specific okta group @@ -33,4 +46,20 @@ def test_org_tg_generation # Assert tf contains locale specific gsuite group assert tf.include?('resource "gsuite_group" "contoso-all-gb" {') end + + def test_files_written + @org.generate_tf + + #Make sure we're generating the files we expect to generate + assert File.exist?('auto.platoons.tf') + assert File.exist?('auto.exception_squads.tf') + assert File.exist?('auto.org.tf') + end + + def teardown + FileUtils.rm_f('auto.platoons.tf') if File.exist?('auto.platoons.tf') + FileUtils.rm_f('auto.exception_squads.tf') if File.exist?('auto.exception_squads.tf') + FileUtils.rm_f('auto.org.tf') if File.exist?('auto.org.tf') + end + end From a169b5e52cc68a65f0f4b3de106cfbc75a0952a1 Mon Sep 17 00:00:00 2001 From: Zac Cicala Date: Tue, 6 Oct 2020 17:14:03 -0700 Subject: [PATCH 04/10] I think this is how you add test/dev dependencies --- Gemfile | 6 +++++- test/terraorg/model/org_test.rb | 5 +++++ 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/Gemfile b/Gemfile index 3a65ec3..1bbc167 100644 --- a/Gemfile +++ b/Gemfile @@ -15,4 +15,8 @@ source 'https://rubygems.org' gemspec -gem "minitest" \ No newline at end of file + +group :test do + gem "minitest" +end + diff --git a/test/terraorg/model/org_test.rb b/test/terraorg/model/org_test.rb index 3019fea..d0d1570 100644 --- a/test/terraorg/model/org_test.rb +++ b/test/terraorg/model/org_test.rb @@ -1,3 +1,8 @@ + +require 'rubygems' +require 'bundler/setup' + +Bundler.setup(:default, :test) require 'minitest/autorun' require './lib/terraorg/model/org' require './lib/terraorg/model/people' From eff55db1c47d2eed75b4502b5242fcde9f71597d Mon Sep 17 00:00:00 2001 From: Zac Cicala Date: Wed, 7 Oct 2020 10:59:27 -0700 Subject: [PATCH 05/10] Move minitest dependency to gemspec file --- Gemfile | 5 ----- lib/terraorg/version.rb | 2 +- terraorg.gemspec | 2 ++ 3 files changed, 3 insertions(+), 6 deletions(-) diff --git a/Gemfile b/Gemfile index 1bbc167..1cee56e 100644 --- a/Gemfile +++ b/Gemfile @@ -15,8 +15,3 @@ source 'https://rubygems.org' gemspec - -group :test do - gem "minitest" -end - diff --git a/lib/terraorg/version.rb b/lib/terraorg/version.rb index 7cbef22..0439a41 100644 --- a/lib/terraorg/version.rb +++ b/lib/terraorg/version.rb @@ -1,4 +1,4 @@ -5.0# Copyright 2019-2020 LiveRamp Holdings, Inc. +# Copyright 2019-2020 LiveRamp Holdings, Inc. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. diff --git a/terraorg.gemspec b/terraorg.gemspec index ae6d4d5..79d1554 100644 --- a/terraorg.gemspec +++ b/terraorg.gemspec @@ -34,6 +34,8 @@ Gem::Specification.new do |gem| gem.add_dependency 'faraday', '~> 1' gem.add_dependency 'neatjson', '~> 0.9' gem.add_dependency 'oktakit', '~> 0.2' + + gem.add_development_dependency 'minitest', '~> 5.14' # ensure the gem is built out of versioned files gem.files = Dir['{bin,lib}/**/*', 'README*', 'LICENSE*'] From 212c0eb6ac70e2367b14b3b27e62e4df9df60ad2 Mon Sep 17 00:00:00 2001 From: Zac Cicala Date: Tue, 13 Oct 2020 16:46:15 -0700 Subject: [PATCH 06/10] Fix associate validation bug, add tests, make associate check optional --- bin/terraorg | 4 +- lib/terraorg/model/org.rb | 12 +- test/terraorg/model/org_test.rb | 286 ++++++++++++++++++++++++++++++-- 3 files changed, 284 insertions(+), 18 deletions(-) diff --git a/bin/terraorg b/bin/terraorg index 6a0e61d..7328d05 100755 --- a/bin/terraorg +++ b/bin/terraorg @@ -32,6 +32,7 @@ ACTIONS = [ ].freeze STRICT_VALIDATION = ENV.fetch('TERRAORG_STRICT_VALIDATION', 'true') +ALLOW_ORPHANED_ASSOCIATES = ENV.fetch('ALLOW_ORPHANED_ASSOCIATES', 'false') SQUADS_FILE = ENV.fetch('TERRAORG_SQUADS', 'squads.json') PLATOONS_FILE = ENV.fetch('TERRAORG_PLATOONS', 'platoons.json') ORG_FILE = ENV.fetch('TERRAORG_ROOT', 'org.json') @@ -97,7 +98,8 @@ org_data = File.read(ORG_FILE) org = Org.new(JSON.parse(org_data), platoons, squads, people, GSUITE_DOMAIN) strict = (STRICT_VALIDATION == 'true') -org.validate!(strict: strict) +allow_orphaned_associates = (ALLOW_ORPHANED_ASSOCIATES == 'true') +org.validate!(strict: strict, allow_orphaned_associates) case action when 'generate-squads-md' diff --git a/lib/terraorg/model/org.rb b/lib/terraorg/model/org.rb index 6a5ba52..f27d904 100644 --- a/lib/terraorg/model/org.rb +++ b/lib/terraorg/model/org.rb @@ -50,7 +50,7 @@ def initialize(parsed_data, platoons, squads, people, gsuite_domain) @squads = squads end - def validate!(strict: true) + def validate!(strict: true, allow_orhpaned_associates: false) failure = false # Do not allow the JSON files to contain any people who have left. @@ -134,10 +134,12 @@ def validate!(strict: true) end # Validate that any associate is a member of some squad - associates_but_not_members = Set.new(all_associates.map(&:id)) - Set.new(all_members.map(&:id)) - exceptions - if !associates_but_not_members.empty? - $stderr.puts "ERROR: #{associates_but_not_members} are associates of squads but not members of any squad" - failure = true + if !allow_orhpaned_associates + associates_but_not_members = Set.new(all_associates.map(&:id)) - Set.new(all_members.map(&:id)) - exceptions + if !associates_but_not_members.empty? + $stderr.puts "ERROR: #{associates_but_not_members.to_a().join()} are associates of squads but not members of any squad" + failure = true + end end raise "CRITICAL: Validation failed due to at least one error above" if failure && strict diff --git a/test/terraorg/model/org_test.rb b/test/terraorg/model/org_test.rb index d0d1570..f9b12ea 100644 --- a/test/terraorg/model/org_test.rb +++ b/test/terraorg/model/org_test.rb @@ -11,21 +11,14 @@ class OrgTest < Minitest::Test def setup - gsuite_domain = "gsuite" - slack_domain = "slack" - people = People.new - squads_data = File.read('./examples/squads.json') - squads = Squads.new(JSON.parse(squads_data), people, gsuite_domain, slack_domain) - platoons_data = File.read('./examples/platoons.json') - platoons = Platoons.new(JSON.parse(platoons_data), squads, people, gsuite_domain) - org_data = File.read('./examples/org.json') - @org = Org.new(JSON.parse(org_data), platoons, squads, people, gsuite_domain) + end def test_platoons_tf_generation - tf = @org.generate_tf_platoons + org = generate_org($WORKING_ORG, $WORKING_PLATOONS, $WORKING_SQUADS) + tf = org.generate_tf_platoons #Make sure not null assert tf != nil @@ -40,7 +33,8 @@ def test_platoons_tf_generation end def test_org_tf_generation - tf = @org.generate_tf_org + org = generate_org($WORKING_ORG, $WORKING_PLATOONS, $WORKING_SQUADS) + tf = org.generate_tf_org #Make sure not null assert tf != nil @@ -53,7 +47,8 @@ def test_org_tf_generation end def test_files_written - @org.generate_tf + org = generate_org($WORKING_ORG, $WORKING_PLATOONS, $WORKING_SQUADS) + tf = org.generate_tf #Make sure we're generating the files we expect to generate assert File.exist?('auto.platoons.tf') @@ -61,10 +56,277 @@ def test_files_written assert File.exist?('auto.org.tf') end + def test_associate_without_squad + org = generate_org($WORKING_ORG, $WORKING_PLATOONS, $ORPHANED_ASSOCIATE_SQUADS) + assert_output('', "ERROR: associate1 are associates of squads but not members of any squad\n") { + org.validate!(strict: false) + } + + assert_output('', "") { + org.validate!(strict: false, allow_orhpaned_associates: true) + } + + end + def teardown FileUtils.rm_f('auto.platoons.tf') if File.exist?('auto.platoons.tf') FileUtils.rm_f('auto.exception_squads.tf') if File.exist?('auto.exception_squads.tf') FileUtils.rm_f('auto.org.tf') if File.exist?('auto.org.tf') end + def generate_org(org_data, platoons_data, squads_data) + gsuite_domain = "gsuite" + slack_domain = "slack" + people = People.new + squads = Squads.new(JSON.parse(squads_data), people, gsuite_domain, slack_domain) + platoons = Platoons.new(JSON.parse(platoons_data), squads, people, gsuite_domain) + return Org.new(JSON.parse(org_data), platoons, squads, people, gsuite_domain) + end + + $WORKING_ORG = <<-JSON + { + "exception_people": [ + { + "location": "US", + "members": [ + "exception1" + ] + } + ], + "exception_squads": [], + "id": "contoso", + "manager": "rchen", + "manager_location": "US", + "metadata": {}, + "name": "Contoso", + "platoons": [ + "sprockets", + "widgets" + ], + "version": "v1" + } + JSON + + $WORKING_PLATOONS = <<-JSON + { + "platoons": [ + { + "id": "sprockets", + "manager": "manager2", + "name": "Sprockets", + "squads": [ + "legal", + "logistics" + ] + }, + { + "id": "widgets", + "manager": "manager1", + "name": "Widgets", + "squads": [ + "marketing", + "sales" + ] + } + ], + "version": "v1" + } + + JSON + + $WORKING_SQUADS = <<-JSON + { + "squads": [ + { + "id": "legal", + "metadata": { + "epo": "epo4", + "manager": "manager5", + "pm": [ + "pm1" + ], + "slack": "#legal", + "sme": "sme8" + }, + "name": "Legal", + "team": [ + { + "location": "US", + "members": [ + "member1", + "member2" + ] + } + ] + }, + { + "id": "logistics", + "metadata": { + "epo": "epo9", + "manager": "manager11", + "pm": [ + "pm9" + ], + "slack": "#logistics", + "sme": "sme9" + }, + "name": "Logistics", + "team": [ + { + "location": "CN", + "members": [ + "member55", + "member56" + ] + } + ] + }, + { + "id": "marketing", + "metadata": { + "manager": "manager2", + "pm": [ + "pm2" + ], + "slack": "#marketing", + "sme": "sme2" + }, + "name": "Marketing", + "team": [ + { + "location": "FR", + "members": [ + "member3", + "member4" + ] + } + ] + }, + { + "id": "sales", + "metadata": { + "epo": "epo1", + "manager": "epo2", + "pm": [ + "pm1" + ], + "slack": "#sales", + "sme": "sme1" + }, + "name": "Sales", + "team": [ + { + "location": "GB", + "members": [ + "member8", + "member9" + ] + } + ] + } + ], + "version": "v1" +} + + JSON + + $ORPHANED_ASSOCIATE_SQUADS = <<-JSON + { + "squads": [ + { + "id": "legal", + "metadata": { + "epo": "epo4", + "manager": "manager5", + "pm": [ + "pm1" + ], + "slack": "#legal", + "sme": "sme8" + }, + "name": "Legal", + "team": [ + { + "location": "US", + "members": [ + "member1", + "member2" + ] + } + ] + }, + { + "id": "logistics", + "metadata": { + "epo": "epo9", + "manager": "manager11", + "pm": [ + "pm9" + ], + "slack": "#logistics", + "sme": "sme9" + }, + "name": "Logistics", + "team": [ + { + "location": "CN", + "members": [ + "member55", + "member56" + ] + } + ] + }, + { + "id": "marketing", + "metadata": { + "manager": "manager2", + "pm": [ + "pm2" + ], + "slack": "#marketing", + "sme": "sme2" + }, + "name": "Marketing", + "team": [ + { + "location": "FR", + "associates":[ + "associate1" + ], + "members": [ + "member3", + "member4" + ] + } + ] + }, + { + "id": "sales", + "metadata": { + "epo": "epo1", + "manager": "epo2", + "pm": [ + "pm1" + ], + "slack": "#sales", + "sme": "sme1" + }, + "name": "Sales", + "team": [ + { + "location": "GB", + "members": [ + "member8", + "member9" + ] + } + ] + } + ], + "version": "v1" +} + + JSON + end From 3dc3ade63c2c9fac3bf92ecdfd2d27b85b4f2633 Mon Sep 17 00:00:00 2001 From: Zac Cicala Date: Tue, 13 Oct 2020 19:24:23 -0700 Subject: [PATCH 07/10] Bump version --- lib/terraorg/version.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/terraorg/version.rb b/lib/terraorg/version.rb index 0439a41..561a7cf 100644 --- a/lib/terraorg/version.rb +++ b/lib/terraorg/version.rb @@ -13,5 +13,5 @@ # limitations under the License. module Terraorg - VERSION = '0.5.0' + VERSION = '0.5.1' end From 3b781ffa3b60765869faac180fa36cdea44f1648 Mon Sep 17 00:00:00 2001 From: zcicala Date: Wed, 14 Oct 2020 09:18:09 -0700 Subject: [PATCH 08/10] Update lib/terraorg/model/org.rb Co-authored-by: Joshua Kwan --- lib/terraorg/model/org.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/terraorg/model/org.rb b/lib/terraorg/model/org.rb index f27d904..f2a36ed 100644 --- a/lib/terraorg/model/org.rb +++ b/lib/terraorg/model/org.rb @@ -50,7 +50,7 @@ def initialize(parsed_data, platoons, squads, people, gsuite_domain) @squads = squads end - def validate!(strict: true, allow_orhpaned_associates: false) + def validate!(strict: true, allow_orphaned_associates: false) failure = false # Do not allow the JSON files to contain any people who have left. From ce0ba06cf96d353172549b58177d4128fc7f2e88 Mon Sep 17 00:00:00 2001 From: zcicala Date: Wed, 14 Oct 2020 10:52:41 -0700 Subject: [PATCH 09/10] Update lib/terraorg/model/org.rb Co-authored-by: Joshua Kwan --- lib/terraorg/model/org.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/terraorg/model/org.rb b/lib/terraorg/model/org.rb index f2a36ed..8cd5ce8 100644 --- a/lib/terraorg/model/org.rb +++ b/lib/terraorg/model/org.rb @@ -134,7 +134,7 @@ def validate!(strict: true, allow_orphaned_associates: false) end # Validate that any associate is a member of some squad - if !allow_orhpaned_associates + if !allow_orphaned_associates associates_but_not_members = Set.new(all_associates.map(&:id)) - Set.new(all_members.map(&:id)) - exceptions if !associates_but_not_members.empty? $stderr.puts "ERROR: #{associates_but_not_members.to_a().join()} are associates of squads but not members of any squad" From 7a4c0ba0381b404f3cb5e70cb440432796f7ee93 Mon Sep 17 00:00:00 2001 From: zcicala Date: Wed, 14 Oct 2020 10:53:43 -0700 Subject: [PATCH 10/10] Update lib/terraorg/model/org.rb Co-authored-by: Joshua Kwan --- lib/terraorg/model/org.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/terraorg/model/org.rb b/lib/terraorg/model/org.rb index 8cd5ce8..768a8bf 100644 --- a/lib/terraorg/model/org.rb +++ b/lib/terraorg/model/org.rb @@ -137,7 +137,7 @@ def validate!(strict: true, allow_orphaned_associates: false) if !allow_orphaned_associates associates_but_not_members = Set.new(all_associates.map(&:id)) - Set.new(all_members.map(&:id)) - exceptions if !associates_but_not_members.empty? - $stderr.puts "ERROR: #{associates_but_not_members.to_a().join()} are associates of squads but not members of any squad" + $stderr.puts "ERROR: #{associates_but_not_members.to_a} are associates of squads but not members of any squad" failure = true end end