-
-
Notifications
You must be signed in to change notification settings - Fork 825
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
CRM-21753 add json validation for incoming criteria #11666
Conversation
test this please |
@eileenmcnaughton I have tested and extended UT to include Json type check. Is there anything else that need to addressed before merging this PR? |
Note from my point of view but I wanted to get some confirmation from security team that they agree in principle (@xurizaemon @totten @mlutfy @seamuslee001 ) - longer usage is in the linked PR but this is really covering it |
From a security perspective, the mere act of parsing JSON should be fairly safe. It's more akin to Note:
The main security concerns of passing through JSON are subjective/contextual -- e.g. it would be a mistake for someone to say: /* Line 1 */ $criteria = CRM_Utils_Request::retrieve('criteria', 'Json', $this, FALSE);
/* Line 2 */ civicrm_api3('Contact', 'get', $criteria) The problem there isn't really with JSON parsing in line 1. Getting /* Line 1 */ $criteria = CRM_Utils_Request::retrieve('criteria', 'Json', $this, FALSE);
/* Line 2 */ civicrm_api3('Contact', 'get', array_intersect_key($criteria, ['first_name'=>1, 'last_name'=>1, 'contact_id'=>1])) |
Hmm - what is the issue with 'passing anything' to the api? I guess the main concern would be to block any chaining. Ie. any criteria that alter the get in this context is fine (& permissions are applied later in the dupe calculation). So I feel like this is mergeable but in the larger PR (#11658) I should ensure any chaining fields are culled before calling |
Right. I'd steer towards whitelisting fields/notations rather blacklisting fields/notations because it's hard to anticipate what notations might be supported in future revisions of the API framework. Tangentially, I don't know how much of a system you need for that use-case. The $apiRequest = \Civi\API\Request::create($entity, $action, $params);
$rule = new \Civi\API\WhitelistRule(/* see docblock */);
echo $rule->matches($apiRequest) ? "Good to go" : "No go";
Makes sense. |
Hmm - I specifically don't want to be whitelisting because I think there is a wide array of criteria you might want to use. But I think I can block anything that starts with 'api' & I'd be happy to block anything with a '.' in it - that would block any joins. I could also block any params that pass in arrays where the key is not an accepted sql operator. That covers what I can think of that would involve chaining. Being the contact api you could still get away with doing a search for contacts with contributions I think but if not then we can cross that when the demand arises |
All the changes in All those heuristics in your last comment sound plausible, but I wanted to check... in this case (
To do any of this, one needs to get on the page
I can't really say if interpretation |
#2 is the way it is currrently - ie. AFTER the api call a list of mergeable contacts is generated & ACLs are applied to both sides of this list (ie. contact_a & contact_b). Adding 'check_permissions' to the api call would not add more permissioning but I am inclined to do it because a) it would be clearer to someone reading the code and Regarding preventing chaining - the main risk would be that someone redirected someone to a url that has a chained call in it. I'm inclined to add an api option 'no_chaining' - it seems easier at the calling end to add that parameter & have it interpreted in the api than to code up the heuristics in some helper function that the calling function calls before calling the api. |
185846c
to
3cb1096
Compare
@totten I've updated the filter at the point where the api call is actioned per discussion. Can we merge this now (it won't actually do anything without the larger PR but with this merged I can get the review of the larger PR to focus on the functionality & the code that really relates to that issue) |
Per civicrm#11658 the dedupe code has a mechanism to handle a nuanced array of criteria. This PR is purely to support the passing of that json through the url criteria with a proposed validation rule. The criteria in the url might look like criteria={"contact" : {"first_name" :{"IN" : ["Peter", "Paul", "Mary"]]]} This is passed to the contact api to limit the contacts to look for matches for (before actually finding the matches). In discussion the biggest risk seemed to be the possibility of chaining so I have added a filter on the criteria & set check_permissions (acls are applied in the next step but having it on the api call is clearer & may reduce matches for the next step).
3cb1096
to
8825143
Compare
@monishdeb discussion on security channel has been from @seanmadsen "Hmmm. My initial gut read is that that's probably pretty safe the concerns raised have been about the existing XSS String validation - in this context that is ADDITIONAL security - ie the key security is
I think that we should merge & if @seanmadsen can find time to try to break the rc we can fix it in the rc since this has kicked a lot of cans without an actual objection |
Ok tested it again on my local and also it got UT now. Also we got feedback from @totten I am going to merge this PR. If there is any issue/security concern like already discussed, the PR fix would be submitted against rc. (CiviCRM Review Template WORD-1.1) |
This is an adjunct to #11658 & intended to clarify discussion of the potential security aspect of processing input from the url. I will add the decision to that PR
the dedupe code has a mechanism to handle a nuanced array of criteria.
This PR is purely to discuss the passing of that criteria through the UI, with
a proposed validation rule.
The criteria in the url might look like
criteria={"contact" : {"first_name" :{"IN" : ["Peter", "Paul", "Mary"]]]}
This is passed to the contact api to limit the contacts to look for matches
for, prior to applying permissions (which is done when actually finding the
matches.
My specific concern is that the criteria is passed back to the template and
used in constructed urls - so I am looking to validate it on the way in
for xss in this PR.