From 639b3956f96f53d916d346f8e5f8f0e67f6c03c7 Mon Sep 17 00:00:00 2001 From: GrantBirki Date: Tue, 15 Jul 2025 13:32:40 -0700 Subject: [PATCH] improved testing around yaml expirations --- .../data/groups/calculated/yaml_spec.rb | 107 +++++++++++++++++- .../expiration-all-individual-expired.yaml | 10 ++ .../ldap-config/yaml/expiration-groups.yaml | 10 ++ .../yaml/expiration-ignore-test.yaml | 9 ++ .../yaml/expiration-individual-usernames.yaml | 10 ++ .../yaml/expiration-invalid-date.yaml | 7 ++ .../yaml/expiration-mixed-nested.yaml | 16 +++ 7 files changed, 168 insertions(+), 1 deletion(-) create mode 100644 spec/unit/fixtures/ldap-config/yaml/expiration-all-individual-expired.yaml create mode 100644 spec/unit/fixtures/ldap-config/yaml/expiration-groups.yaml create mode 100644 spec/unit/fixtures/ldap-config/yaml/expiration-ignore-test.yaml create mode 100644 spec/unit/fixtures/ldap-config/yaml/expiration-individual-usernames.yaml create mode 100644 spec/unit/fixtures/ldap-config/yaml/expiration-invalid-date.yaml create mode 100644 spec/unit/fixtures/ldap-config/yaml/expiration-mixed-nested.yaml diff --git a/spec/unit/entitlements/data/groups/calculated/yaml_spec.rb b/spec/unit/entitlements/data/groups/calculated/yaml_spec.rb index a39bc79..8a176ae 100644 --- a/spec/unit/entitlements/data/groups/calculated/yaml_spec.rb +++ b/spec/unit/entitlements/data/groups/calculated/yaml_spec.rb @@ -1,6 +1,8 @@ # frozen_string_literal: true require_relative "../../../../spec_helper" +# NOTE: The test suite mocks all dates with allow(Time).to receive(:now).and_return(Time.utc(2018, 4, 1, 12, 0, 0)) + describe Entitlements::Data::Groups::Calculated::YAML do let(:people_obj) { Entitlements::Data::People::YAML.new(filename: fixture("people.yaml")) } let(:cache) { { people_obj: people_obj } } @@ -283,7 +285,12 @@ context "complex structure" do let(:filename) { fixture("ldap-config/yaml/expiration-complex.yaml") } - it "constructs the correct rule set" do + it "constructs the correct rule set with complex nested expiration" do + # Expected results based on expiration-complex.yaml: + # - username: peterbald (no expiration) -> kept + # - and: group foo/bar (Sept 2018, not expired) and foo/baz (March 2018, expired) -> only foo/bar kept + # - or: all usernames expired (March 2018) -> empty array + # - or: cheetoh (March 2018, expired) and nebelung (Sept 2018, not expired) -> only nebelung kept answer = { "or"=>[ {"username"=>"peterbald"}, @@ -296,6 +303,104 @@ expect(result).to eq(answer) end end + + context "individual username expiration" do + let(:filename) { fixture("ldap-config/yaml/expiration-individual-usernames.yaml") } + + it "filters out expired usernames while keeping non-expired ones" do + answer = { + "or" => [ + { "username" => "alice" }, + { "username" => "charlie" }, + { "username" => "diana" } + ] + } + result = subject.send(:rules) + expect(result).to eq(answer) + end + end + + context "group expiration" do + let(:filename) { fixture("ldap-config/yaml/expiration-groups.yaml") } + + it "filters out expired groups while keeping non-expired ones" do + answer = { + "or" => [ + { "group" => "team/active" }, + { "group" => "team/future" }, + { "username" => "standalone" } + ] + } + result = subject.send(:rules) + expect(result).to eq(answer) + end + end + + context "mixed expiration with nested structures" do + let(:filename) { fixture("ldap-config/yaml/expiration-mixed-nested.yaml") } + + it "correctly handles expiration in nested and/or structures" do + answer = { + "or" => [ + { "username" => "always-active" }, + { "and" => [ + { "group" => "team/core" } + ] + }, + { "or" => [ + { "username" => "still-active" } + ] + } + ] + } + result = subject.send(:rules) + expect(result).to eq(answer) + end + end + + context "all individual entries expired" do + let(:filename) { fixture("ldap-config/yaml/expiration-all-individual-expired.yaml") } + + it "returns empty arrays for containers with all expired entries" do + answer = { + "or" => [] + } + result = subject.send(:rules) + expect(result).to eq(answer) + end + end + + context "expired entries but expirations are disabled" do + let(:filename) { fixture("ldap-config/yaml/expiration-ignore-test.yaml") } + + it "ignores all expiration dates when ignore_expirations is true" do + begin + Entitlements.config["ignore_expirations"] = true + + answer = { + "or" => [ + { "username" => "active-user" }, + { "username" => "expired-user" }, + { "group" => "expired-group" } + ] + } + result = subject.send(:rules) + expect(result).to eq(answer) + ensure + Entitlements.config.delete("ignore_expirations") + end + end + end + + context "invalid expiration date" do + let(:filename) { fixture("ldap-config/yaml/expiration-invalid-date.yaml") } + + it "raises an error for invalid expiration date format" do + expect do + subject.send(:rules) + end.to raise_error(ArgumentError, /Invalid expiration date "not-a-date"/) + end + end end end end diff --git a/spec/unit/fixtures/ldap-config/yaml/expiration-all-individual-expired.yaml b/spec/unit/fixtures/ldap-config/yaml/expiration-all-individual-expired.yaml new file mode 100644 index 0000000..400c1fc --- /dev/null +++ b/spec/unit/fixtures/ldap-config/yaml/expiration-all-individual-expired.yaml @@ -0,0 +1,10 @@ +--- +description: All individual entries expired +rules: + or: + - username: expired1 + expiration: "2018-02-01" + - username: expired2 + expiration: "2018-02-01" + - group: team/expired + expiration: "2018-02-01" diff --git a/spec/unit/fixtures/ldap-config/yaml/expiration-groups.yaml b/spec/unit/fixtures/ldap-config/yaml/expiration-groups.yaml new file mode 100644 index 0000000..ac2a6af --- /dev/null +++ b/spec/unit/fixtures/ldap-config/yaml/expiration-groups.yaml @@ -0,0 +1,10 @@ +--- +description: Group expiration test +rules: + or: + - group: team/active + - group: team/expired + expiration: "2018-02-01" + - group: team/future + expiration: "2018-06-01" + - username: standalone diff --git a/spec/unit/fixtures/ldap-config/yaml/expiration-ignore-test.yaml b/spec/unit/fixtures/ldap-config/yaml/expiration-ignore-test.yaml new file mode 100644 index 0000000..46fbb52 --- /dev/null +++ b/spec/unit/fixtures/ldap-config/yaml/expiration-ignore-test.yaml @@ -0,0 +1,9 @@ +--- +description: Test with expired entries but ignoring expiration +rules: + or: + - username: active-user + - username: expired-user + expiration: "2018-02-01" + - group: expired-group + expiration: "2018-02-01" diff --git a/spec/unit/fixtures/ldap-config/yaml/expiration-individual-usernames.yaml b/spec/unit/fixtures/ldap-config/yaml/expiration-individual-usernames.yaml new file mode 100644 index 0000000..eb7d397 --- /dev/null +++ b/spec/unit/fixtures/ldap-config/yaml/expiration-individual-usernames.yaml @@ -0,0 +1,10 @@ +--- +description: Individual username expiration test +rules: + or: + - username: alice + - username: bob + expiration: "2018-02-01" + - username: charlie + expiration: "2018-06-01" + - username: diana diff --git a/spec/unit/fixtures/ldap-config/yaml/expiration-invalid-date.yaml b/spec/unit/fixtures/ldap-config/yaml/expiration-invalid-date.yaml new file mode 100644 index 0000000..81ce3be --- /dev/null +++ b/spec/unit/fixtures/ldap-config/yaml/expiration-invalid-date.yaml @@ -0,0 +1,7 @@ +--- +description: Test with invalid expiration date +rules: + or: + - username: valid-user + - username: invalid-expiry + expiration: "not-a-date" diff --git a/spec/unit/fixtures/ldap-config/yaml/expiration-mixed-nested.yaml b/spec/unit/fixtures/ldap-config/yaml/expiration-mixed-nested.yaml new file mode 100644 index 0000000..d52b976 --- /dev/null +++ b/spec/unit/fixtures/ldap-config/yaml/expiration-mixed-nested.yaml @@ -0,0 +1,16 @@ +--- +description: Mixed expiration test with nested structures +rules: + or: + - username: always-active + - and: + - group: team/core + - username: temp-user + expiration: "2018-02-01" + - or: + - username: expired1 + expiration: "2018-02-01" + - username: expired2 + expiration: "2018-02-01" + - username: still-active + expiration: "2018-06-01"