Commit 0b5c207fca9aca403d1b3a9be2fd4b1645d41aa1
Committed by
Kyle Werner
1 parent
705f0922
Exists in
master
Fix exception raised when patch endpoint receives invalid request
fixes lessonly/scim_rails#29 The patch endpoint isn't fully scim compliant yet and only allows for specific operations. When we received a specific format of request that wasn't valid, it was raising an exception instead of returning the expected 422 response. Add extra validation to prevent this situation when receiving an unexpected body for a patch request.
Showing
2 changed files
with
64 additions
and
3 deletions
Show diff stats
app/controllers/scim_rails/scim_users_controller.rb
... | ... | @@ -126,9 +126,23 @@ module ScimRails |
126 | 126 | end |
127 | 127 | |
128 | 128 | def patch_active_param |
129 | - active = params.dig("Operations", 0, "value", "active") | |
130 | - raise ScimRails::ExceptionHandler::UnsupportedPatchRequest if active.nil? | |
131 | - active | |
129 | + handle_invalid = lambda do | |
130 | + raise ScimRails::ExceptionHandler::UnsupportedPatchRequest | |
131 | + end | |
132 | + | |
133 | + operations = params["Operations"] || {} | |
134 | + | |
135 | + valid_operation = operations.find(handle_invalid) do |operation| | |
136 | + valid_patch_operation?(operation) | |
137 | + end | |
138 | + | |
139 | + valid_operation.dig("value", "active") | |
140 | + end | |
141 | + | |
142 | + def valid_patch_operation?(operation) | |
143 | + operation["op"] == "replace" && | |
144 | + operation["value"] && | |
145 | + operation["value"]["active"] | |
132 | 146 | end |
133 | 147 | end |
134 | 148 | end | ... | ... |
spec/controllers/scim_rails/scim_users_controller_spec.rb
... | ... | @@ -569,6 +569,53 @@ RSpec.describe ScimRails::ScimUsersController, type: :controller do |
569 | 569 | response_body = JSON.parse(response.body) |
570 | 570 | expect(response_body.dig("schemas", 0)).to eq "urn:ietf:params:scim:api:messages:2.0:Error" |
571 | 571 | end |
572 | + | |
573 | + it "returns 422 when value is " do | |
574 | + patch :patch_update, params: { | |
575 | + id: 1, | |
576 | + Operations: [ | |
577 | + { | |
578 | + op: "replace", | |
579 | + path: "displayName", | |
580 | + value: "Francis" | |
581 | + } | |
582 | + ] | |
583 | + } | |
584 | + | |
585 | + expect(response.status).to eq 422 | |
586 | + response_body = JSON.parse(response.body) | |
587 | + expect(response_body.dig("schemas", 0)).to eq "urn:ietf:params:scim:api:messages:2.0:Error" | |
588 | + end | |
589 | + | |
590 | + it "returns 422 when value is missing" do | |
591 | + patch :patch_update, params: { | |
592 | + id: 1, | |
593 | + Operations: [ | |
594 | + { | |
595 | + op: "replace" | |
596 | + } | |
597 | + ] | |
598 | + } | |
599 | + | |
600 | + expect(response.status).to eq 422 | |
601 | + response_body = JSON.parse(response.body) | |
602 | + expect(response_body.dig("schemas", 0)).to eq "urn:ietf:params:scim:api:messages:2.0:Error" | |
603 | + end | |
604 | + | |
605 | + it "returns 422 operations key is missing" do | |
606 | + patch :patch_update, params: { | |
607 | + id: 1, | |
608 | + Foobars: [ | |
609 | + { | |
610 | + op: "replace" | |
611 | + } | |
612 | + ] | |
613 | + } | |
614 | + | |
615 | + expect(response.status).to eq 422 | |
616 | + response_body = JSON.parse(response.body) | |
617 | + expect(response_body.dig("schemas", 0)).to eq "urn:ietf:params:scim:api:messages:2.0:Error" | |
618 | + end | |
572 | 619 | end |
573 | 620 | end |
574 | 621 | ... | ... |