Skip to content

Commit

Permalink
feat: add user details secure endpoint
Browse files Browse the repository at this point in the history
Add a secure endpoint for user detail that exposes more information about an individual than the standard users endpoint.
  • Loading branch information
gregmundy committed Nov 9, 2020
1 parent 2bedcbe commit dceb78f
Show file tree
Hide file tree
Showing 3 changed files with 60 additions and 20 deletions.
2 changes: 1 addition & 1 deletion mci/api/user.py
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ def delete(self):
class SecureUserDetailResource(UserResource):
""" A specific user. """

# @token_required(Config.get_oauth2_provider(), scopes=['mci.secure-user-detail:get'])
@token_required(Config.get_oauth2_provider(), scopes=['mci.secure-user-detail:get'])
def get(self, mci_id: str):
return self.get_request_handler(request.headers).create_secure_user_blob(mci_id)

Expand Down
77 changes: 59 additions & 18 deletions tests/test_user_endpoints.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@

from .utils import post_new_individual


class TestMCIAPI(object):
@mock.patch('brighthive_authlib.providers.AuthZeroProvider.validate_token', return_value=True)
def test_users_endpoint_empty(self, mocker, database, test_client):
Expand All @@ -21,7 +22,7 @@ def test_users_endpoint_empty(self, mocker, database, test_client):

assert response.status_code == 200
assert response.json['users'] == []

@mock.patch('brighthive_authlib.providers.AuthZeroProvider.validate_token', return_value=True)
def test_users_endpoint_populated(self, mocker, database, individual_data, test_client, json_headers):
'''
Expand All @@ -45,31 +46,35 @@ def test_get_user_invalid(self, mocker, database, test_client):
assert response.status_code == 410
assert response.json['message']
assert response.json['message'] == 'An individual with that ID does not exist in the MCI.'

@mock.patch('brighthive_authlib.providers.AuthZeroProvider.validate_token', return_value=True)
def test_get_user_valid(self, mocker, database, individual_data, test_client, json_headers):
'''
Tests that GETing a valid user returns the JSON and 200 status code.
'''
new_individual = post_new_individual(individual_data, test_client, json_headers)
new_individual = post_new_individual(
individual_data, test_client, json_headers)

response = test_client.get('/users/{}'.format(new_individual['mci_id']))
response = test_client.get(
'/users/{}'.format(new_individual['mci_id']))

assert response.status_code == 200
assert response.json

@mock.patch('brighthive_authlib.providers.AuthZeroProvider.validate_token', return_value=True)
def test_post_users_existing(self, mocker, database, individual_data, test_client, json_headers):
'''
Tests that POSTing an existing user returns a 200 with correct user information.
'''
new_individual = post_new_individual(individual_data, test_client, json_headers)
'''
new_individual = post_new_individual(
individual_data, test_client, json_headers)

with requests_mock.Mocker() as m:
m.post("http://mcimatchingservice_mci_1:8000/compute-match",
json={"mci_id": new_individual['mci_id'], "score": 10.0}, status_code=201)
json={"mci_id": new_individual['mci_id'], "score": 10.0}, status_code=201)

response = test_client.post('/users', data=json.dumps(individual_data), headers=json_headers)
response = test_client.post(
'/users', data=json.dumps(individual_data), headers=json_headers)

assert response.status_code == 200
assert response.json['first_name'] == individual_data['first_name']
Expand All @@ -81,21 +86,23 @@ def test_post_users_existing(self, mocker, database, individual_data, test_clien
def test_post_users_bad_json(self, mocker, test_client, json_headers):
with requests_mock.Mocker() as m:
m.post("http://mcimatchingservice_mci_1:8000/compute-match",
json={"mci_id": "", "score": ""}, status_code=201)
json={"mci_id": "", "score": ""}, status_code=201)

bad_json = {
'first_name': "Single",
'middle_name': "Quote",
'last_name': "Mistake",
}

response = test_client.post('/users', data=bad_json, headers=json_headers)
response = test_client.post(
'/users', data=bad_json, headers=json_headers)
assert response.status_code == 400
assert response.json['error'] == 'Malformed or empty JSON object found in request body.'

@mock.patch('brighthive_authlib.providers.AuthZeroProvider.validate_token', return_value=True)
def test_post_users_matching_down(self, mocker, individual_data, test_client, json_headers):
response = test_client.post('/users', data=json.dumps(individual_data), headers=json_headers)
response = test_client.post(
'/users', data=json.dumps(individual_data), headers=json_headers)

assert response.status_code == 400
assert response.json['error'] == 'The matching service did not return a response.'
Expand All @@ -104,15 +111,17 @@ def test_post_users_matching_down(self, mocker, individual_data, test_client, js
def test_remove_pii_invalid_id(self, mocker, database, test_client, json_headers):
response = test_client.post(
'/users/remove-pii', data=json.dumps({"mci_id": "123fakeid"}), headers=json_headers)

assert response.status_code == 410
assert response.json['message'] == 'An individual with that ID does not exist in the MCI.'

@mock.patch('brighthive_authlib.providers.AuthZeroProvider.validate_token', return_value=True)
def test_remove_pii_valid_id(self, mocker, app_context, database, individual_data, test_client, json_headers):
new_individual = post_new_individual(individual_data, test_client, json_headers)

assert database.session.query(Individual).filter_by(first_name=individual_data['first_name']).first()
new_individual = post_new_individual(
individual_data, test_client, json_headers)

assert database.session.query(Individual).filter_by(
first_name=individual_data['first_name']).first()

response = test_client.post(
'/users/remove-pii',
Expand All @@ -121,11 +130,43 @@ def test_remove_pii_valid_id(self, mocker, app_context, database, individual_dat

assert response.status_code == 201

updated_individual = database.session.query(Individual).filter_by(mci_id=new_individual['mci_id']).first()
updated_individual = database.session.query(
Individual).filter_by(mci_id=new_individual['mci_id']).first()
assert updated_individual.first_name == None
assert updated_individual.last_name == None
assert updated_individual.middle_name == None
assert updated_individual.date_of_birth == None
assert updated_individual.email_address == None
assert updated_individual.telephone == None
assert updated_individual.ssn == None

@mock.patch('brighthive_authlib.providers.AuthZeroProvider.validate_token', return_value=True)
def test_user_detail_endpoint(self, mocker, test_client, json_headers):
new_user = {
"vendor_id": "abc-123",
"ssn": "9999",
"first_name": "Jacob",
"last_name": "Test",
"middle_name": "James",
"suffix": "Jr.",
"mailing_address": {
"address": "2000 Somewhere Street",
"city": "Arlington",
"state": "VA",
"postal_code": "25531",
"county": "Prince George",
"country": "US"
},
"date_of_birth": "2020-11-09",
"email_address": "[email protected]",
"telephone": "string"
}

new_individual = post_new_individual(
new_user, test_client, json_headers)
mci_id = new_individual['mci_id']
response = test_client.get(f'/user-details/{mci_id}',
headers=json_headers)
assert response.status_code == 200
assert 'ssn' in response.json.keys()
assert 'county' in response.json['mailing_address'].keys()
1 change: 0 additions & 1 deletion tests/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ def post_new_individual(individual_data, test_client, headers):
json={"mci_id": "", "score": ""}, status_code=201)

response = test_client.post('/users', data=json.dumps(individual_data), headers=headers)

assert response.status_code == 201
assert response.json['first_name'] == individual_data['first_name']
assert response.json['last_name'] == individual_data['last_name']
Expand Down

0 comments on commit dceb78f

Please sign in to comment.