-
Notifications
You must be signed in to change notification settings - Fork 7
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
SK-1736: Added encoding for column values in get interface (#145)
* SK-1736: Added encoding for column values in get interface
- Loading branch information
1 parent
a27f123
commit 69630e5
Showing
5 changed files
with
147 additions
and
6 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -2,13 +2,15 @@ | |
from unittest.mock import patch, Mock | ||
import os | ||
import json | ||
from unittest.mock import MagicMock | ||
from urllib.parse import quote | ||
from requests import PreparedRequest | ||
from requests.models import HTTPError | ||
from skyflow.error import SkyflowError | ||
from skyflow.utils import get_credentials, SkyflowMessages, get_vault_url, construct_invoke_connection_request, \ | ||
parse_insert_response, parse_update_record_response, parse_delete_response, parse_get_response, \ | ||
parse_detokenize_response, parse_tokenize_response, parse_query_response, parse_invoke_connection_response, \ | ||
handle_exception, validate_api_key | ||
handle_exception, validate_api_key, encode_column_values | ||
from skyflow.utils._utils import parse_path_params, to_lowercase_keys, get_metrics | ||
from skyflow.utils.enums import EnvUrls, Env, ContentType | ||
from skyflow.vault.connection import InvokeConnectionResponse | ||
|
@@ -384,3 +386,17 @@ def test_validate_api_key_invalid_length(self): | |
def test_validate_api_key_invalid_pattern(self): | ||
invalid_key = "sky-ABCDE-1234567890GHIJKL7890abcdef" | ||
self.assertFalse(validate_api_key(invalid_key)) | ||
|
||
def test_encode_column_values(self): | ||
get_request = MagicMock() | ||
get_request.column_values = ["Hello World!", "foo/bar", "key=value", "[email protected]"] | ||
|
||
expected_encoded_values = [ | ||
quote("Hello World!"), | ||
quote("foo/bar"), | ||
quote("key=value"), | ||
quote("[email protected]"), | ||
] | ||
|
||
result = encode_column_values(get_request) | ||
self.assertEqual(result, expected_encoded_values) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,5 @@ | ||
import unittest | ||
from unittest.mock import Mock, patch | ||
|
||
from skyflow.generated.rest import RecordServiceBatchOperationBody, V1BatchRecord, RecordServiceInsertRecordBody, \ | ||
V1FieldRecords, RecordServiceUpdateRecordBody, RecordServiceBulkDeleteRecordBody, QueryServiceExecuteQueryBody, \ | ||
V1DetokenizeRecordRequest, V1DetokenizePayload, V1TokenizePayload, V1TokenizeRecordRequest, RedactionEnumREDACTION | ||
|
@@ -138,6 +137,58 @@ def test_insert_with_continue_on_error_false(self, mock_parse_response, mock_val | |
self.assertEqual(result.inserted_fields, expected_inserted_fields) | ||
self.assertEqual(result.errors, []) # No errors expected | ||
|
||
@patch("skyflow.vault.controller._vault.validate_insert_request") | ||
@patch("skyflow.vault.controller._vault.parse_insert_response") | ||
def test_insert_with_continue_on_error_false_when_tokens_are_not_none(self, mock_parse_response, mock_validate): | ||
"""Test insert functionality when continue_on_error is False, ensuring a single bulk insert.""" | ||
|
||
# Mock request with continue_on_error set to False | ||
request = InsertRequest( | ||
table_name=TABLE_NAME, | ||
values=[{"field": "value"}], | ||
tokens=[{"token_field": "token_val1"}], | ||
return_tokens=True, | ||
upsert=None, | ||
homogeneous=True, | ||
continue_on_error=False | ||
) | ||
|
||
# Expected API request body based on InsertRequest parameters | ||
expected_body = RecordServiceInsertRecordBody( | ||
records=[ | ||
V1FieldRecords(fields={"field": "value"}, tokens={"token_field": "token_val1"}) | ||
], | ||
tokenization=True, | ||
upsert=None, | ||
homogeneous=True | ||
) | ||
|
||
# Mock API response for a successful insert | ||
mock_api_response = Mock() | ||
mock_api_response.records = [{"skyflow_id": "id1", "tokens": {"token_field": "token_val1"}}] | ||
|
||
# Expected parsed response | ||
expected_inserted_fields = [{'skyflow_id': 'id1', 'token_field': 'token_val1'}] | ||
expected_response = InsertResponse(inserted_fields=expected_inserted_fields) | ||
|
||
# Set the return value for the parse response | ||
mock_parse_response.return_value = expected_response | ||
records_api = self.vault_client.get_records_api.return_value | ||
records_api.record_service_insert_record.return_value = mock_api_response | ||
|
||
# Call the insert function | ||
result = self.vault.insert(request) | ||
|
||
# Assertions | ||
mock_validate.assert_called_once_with(self.vault_client.get_logger(), request) | ||
records_api.record_service_insert_record.assert_called_once_with(VAULT_ID, TABLE_NAME, | ||
expected_body) | ||
mock_parse_response.assert_called_once_with(mock_api_response, False) | ||
|
||
# Assert that the result matches the expected InsertResponse | ||
self.assertEqual(result.inserted_fields, expected_inserted_fields) | ||
self.assertEqual(result.errors, []) # No errors expected | ||
|
||
@patch("skyflow.vault.controller._vault.validate_update_request") | ||
@patch("skyflow.vault.controller._vault.parse_update_record_response") | ||
def test_update_successful(self, mock_parse_response, mock_validate): | ||
|
@@ -250,7 +301,8 @@ def test_get_successful(self, mock_parse_response, mock_validate): | |
fields=["field1", "field2"], | ||
offset="0", | ||
limit="10", | ||
download_url=True | ||
download_url=True, | ||
column_values=None | ||
) | ||
|
||
# Expected payload | ||
|
@@ -301,6 +353,58 @@ def test_get_successful(self, mock_parse_response, mock_validate): | |
self.assertEqual(result.data, expected_data) | ||
self.assertEqual(result.errors, []) # No errors expected | ||
|
||
@patch("skyflow.vault.controller._vault.validate_get_request") | ||
@patch("skyflow.vault.controller._vault.parse_get_response") | ||
def test_get_successful_with_column_values(self, mock_parse_response, mock_validate): | ||
"""Test get functionality for a successful get request.""" | ||
|
||
# Mock request | ||
request = GetRequest( | ||
table=TABLE_NAME, | ||
redaction_type=RedactionType.PLAIN_TEXT, | ||
column_values=['[email protected]'], | ||
column_name='email' | ||
) | ||
|
||
# Expected payload | ||
expected_payload = { | ||
"object_name": request.table, | ||
"tokenization": request.return_tokens, | ||
"column_name": request.column_name, | ||
"column_values": request.column_values | ||
} | ||
|
||
# Mock API response | ||
mock_api_response = Mock() | ||
mock_api_response.records = [ | ||
Mock(fields={"field1": "value1", "field2": "value2"}), | ||
Mock(fields={"field1": "value3", "field2": "value4"}) | ||
] | ||
|
||
# Expected parsed response | ||
expected_data = [ | ||
{"field1": "value1", "field2": "value2"}, | ||
{"field1": "value3", "field2": "value4"} | ||
] | ||
expected_response = GetResponse(data=expected_data, errors=[]) | ||
|
||
# Set the return value for parse_get_response | ||
mock_parse_response.return_value = expected_response | ||
records_api = self.vault_client.get_records_api.return_value | ||
records_api.record_service_bulk_get_record.return_value = mock_api_response | ||
|
||
# Call the get function | ||
result = self.vault.get(request) | ||
|
||
# Assertions | ||
mock_validate.assert_called_once_with(self.vault_client.get_logger(), request) | ||
records_api.record_service_bulk_get_record.assert_called_once() | ||
mock_parse_response.assert_called_once_with(mock_api_response) | ||
|
||
# Check that the result matches the expected GetResponse | ||
self.assertEqual(result.data, expected_data) | ||
self.assertEqual(result.errors, []) # No errors expected | ||
|
||
@patch("skyflow.vault.controller._vault.validate_query_request") | ||
@patch("skyflow.vault.controller._vault.parse_query_response") | ||
def test_query_successful(self, mock_parse_response, mock_validate): | ||
|