def test_size_is_invalid(self, mock_url_for): """The order parameter on the request is invalid.""" request_data = MultiDict({ "advanced": True, "terms-0-operator": "AND", "terms-0-field": "title", "terms-0-term": "foo", "size": 51, # Invalid "order": "", # Valid }) with self.assertRaises(BadRequest): advanced.search(request_data)
def test_size_is_invalid(self, mock_url_for): """The order parameter on the request is invalid.""" request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'title', 'terms-0-term': 'foo', 'size': 51, # Invalid 'order': '' # Valid }) with self.assertRaises(BadRequest): advanced.search(request_data)
def test_index_raises_query_error(self, mock_index): """Index service raises a QueryError.""" # We need to explicit assign the exception to the mock, otherwise the # exception raised in the side-effect will just be a mock object (not # inheriting from BaseException). mock_index.QueryError = QueryError mock_index.IndexConnectionError = IndexConnectionError def _raiseQueryError(*args, **kwargs): raise QueryError('What now') mock_index.search.side_effect = _raiseQueryError request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'title', 'terms-0-term': 'foo' }) with self.assertRaises(InternalServerError): try: response_data, code, headers = advanced.search(request_data) except QueryError as e: self.fail("QueryError should be handled (caught %s)" % e) self.assertEqual(mock_index.search.call_count, 1, "A search should be attempted")
def test_index_raises_connection_exception(self, mock_index): """Index service raises a IndexConnectionError.""" # We need to explicit assign the exception to the mock, otherwise the # exception raised in the side-effect will just be a mock object (not # inheriting from BaseException). mock_index.IndexConnectionError = IndexConnectionError def _raiseIndexConnectionError(*args, **kwargs): raise IndexConnectionError('What now') mock_index.search.side_effect = _raiseIndexConnectionError request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'title', 'terms-0-term': 'foo' }) with self.assertRaises(InternalServerError): response_data, code, headers = advanced.search(request_data) self.assertEqual(mock_index.search.call_count, 1, "A search should be attempted") call_args, call_kwargs = mock_index.search.call_args self.assertIsInstance( call_args[0], AdvancedQuery, "An AdvancedQuery is passed to the search index")
def advanced_search() -> Union[str, Response]: """Advanced search interface.""" response, code, headers = advanced.search(request.args) return render_template( # type: ignore "search/advanced_search.html", pagetitle="Advanced Search", **response)
def test_no_form_data(self, mock_index): """No form data has been submitted.""" request_data = MultiDict() response_data, code, headers = advanced.search(request_data) self.assertEqual(code, HTTPStatus.OK, "Response should be OK.") self.assertIn("form", response_data, "Response should include form.") self.assertEqual(mock_index.search.call_count, 0, "No search should be attempted")
def advanced_search() -> _Response: """Advanced search interface.""" data, code, hdrs = advanced.search(request.args) content = render_template("search/advanced_search.html", pagetitle="Advanced Search", **data) response: Response = make_response(content) response.status_code = code for key, value in hdrs.items(): response.headers[key] = value return response
def test_invalid_data(self, mock_index): """Form data are invalid.""" request_data = MultiDict({ "advanced": True, "date-past_12": True, "date-specific_year": True, "date-year": "2012", }) response_data, code, headers = advanced.search(request_data) self.assertEqual(code, HTTPStatus.OK, "Response should be OK.") self.assertIn("form", response_data, "Response should include form.") self.assertEqual(mock_index.search.call_count, 0, "No search should be attempted")
def test_invalid_data(self, mock_index): """Form data are invalid.""" request_data = MultiDict({ 'advanced': True, 'date-past_12': True, 'date-specific_year': True, 'date-year': '2012' }) response_data, code, headers = advanced.search(request_data) self.assertEqual(code, status.HTTP_200_OK, "Response should be OK.") self.assertIn('form', response_data, "Response should include form.") self.assertEqual(mock_index.search.call_count, 0, "No search should be attempted")
def test_title_search_contains_classic_syntax(self, mock_index): """User has entered a `surname_f` query in a title search.""" request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'title', 'terms-0-term': 'franklin_r', 'size': 50, 'order': '' }) mock_index.search.return_value = DocumentSet(metadata={}, results=[]) data, code, headers = advanced.search(request_data) self.assertEqual(data['query'].terms[0].term, "franklin_r", "The query should not be rewritten.") self.assertFalse(data['has_classic_format'], "Flag should not be set, as no rewrite has occurred.")
def test_single_field_term(self, mock_index): """Form data and ``advanced`` param are present.""" mock_index.search.return_value = DocumentSet(metadata={}, results=[]) request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'title', 'terms-0-term': 'foo' }) response_data, code, headers = advanced.search(request_data) self.assertEqual(mock_index.search.call_count, 1, "A search should be attempted") call_args, call_kwargs = mock_index.search.call_args self.assertIsInstance(call_args[0], AdvancedQuery, "An AdvancedQuery is passed to the search index") self.assertEqual(code, status.HTTP_200_OK, "Response should be OK.")
def test_author_search_contains_classic_syntax(self, mock_index): """User has entered a `surname_f` query in an author search.""" request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'author', 'terms-0-term': 'franklin_r', 'size': 50, 'order': '' }) mock_index.search.return_value = DocumentSet(metadata={}, results=[]) data, code, headers = advanced.search(request_data) self.assertEqual(data['query'].terms[0].term, "franklin, r", "The query should be rewritten.") self.assertTrue(data['has_classic_format'], "A flag denoting the syntax interception should be set" " in the response context, so that a message may be" " rendered in the template.")
def test_single_field_term(self, mock_index): """Form data and ``advanced`` param are present.""" mock_index.search.return_value = {"metadata": {}, "results": []} request_data = MultiDict({ "advanced": True, "terms-0-operator": "AND", "terms-0-field": "title", "terms-0-term": "foo", }) response_data, code, headers = advanced.search(request_data) self.assertEqual(mock_index.search.call_count, 1, "A search should be attempted") call_args, call_kwargs = mock_index.search.call_args self.assertIsInstance( call_args[0], AdvancedQuery, "An AdvancedQuery is passed to the search index", ) self.assertEqual(code, HTTPStatus.OK, "Response should be OK.")
def test_all_fields_search_multiple_classic_syntax(self, mock_index): """User has entered a classic query with multiple authors.""" request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'all', 'terms-0-term': 'j franklin_r hawking_s', 'size': 50, 'order': '' }) mock_index.search.return_value = dict(metadata={}, results=[]) data, code, headers = advanced.search(request_data) self.assertEqual(data['query'].terms[0].term, "j franklin, r; hawking, s", "The query should be rewritten.") self.assertTrue( data['has_classic_format'], "A flag denoting the syntax interception should be set" " in the response context, so that a message may be" " rendered in the template.")
def test_index_raises_query_error(self, mock_index): """Index service raises a QueryError.""" def _raiseQueryError(*args, **kwargs): raise QueryError("What now") mock_index.search.side_effect = _raiseQueryError request_data = MultiDict({ "advanced": True, "terms-0-operator": "AND", "terms-0-field": "title", "terms-0-term": "foo", }) with self.assertRaises(InternalServerError): try: response_data, code, headers = advanced.search(request_data) except QueryError as ex: self.fail("QueryError should be handled (caught %s)" % ex) self.assertEqual(mock_index.search.call_count, 1, "A search should be attempted")
def test_index_raises_connection_exception(self, mock_index): """Index service raises a IndexConnectionError.""" def _raiseIndexConnectionError(*args, **kwargs): raise IndexConnectionError('What now') mock_index.search.side_effect = _raiseIndexConnectionError request_data = MultiDict({ 'advanced': True, 'terms-0-operator': 'AND', 'terms-0-field': 'title', 'terms-0-term': 'foo' }) with self.assertRaises(InternalServerError): response_data, code, headers = advanced.search(request_data) self.assertEqual(mock_index.search.call_count, 1, "A search should be attempted") call_args, call_kwargs = mock_index.search.call_args self.assertIsInstance( call_args[0], AdvancedQuery, "An AdvancedQuery is passed to the search index")
def test_title_search_contains_classic_syntax(self, mock_index): """User has entered a `surname_f` query in a title search.""" request_data = MultiDict({ "advanced": True, "terms-0-operator": "AND", "terms-0-field": "title", "terms-0-term": "franklin_r", "size": 50, "order": "", }) mock_index.search.return_value = {"metadata": {}, "results": []} data, code, headers = advanced.search(request_data) self.assertEqual( data["query"].terms[0].term, "franklin_r", "The query should not be rewritten.", ) self.assertFalse( data["has_classic_format"], "Flag should not be set, as no rewrite has occurred.", )
def test_all_fields_search_contains_classic_syntax(self, mock_index): """User has entered a `surname_f` query in an all-fields term.""" request_data = MultiDict({ "advanced": True, "terms-0-operator": "AND", "terms-0-field": "all", "terms-0-term": "franklin_r", "size": 50, "order": "", }) mock_index.search.return_value = {"metadata": {}, "results": []} data, code, headers = advanced.search(request_data) self.assertEqual( data["query"].terms[0].term, "franklin, r", "The query should be rewritten.", ) self.assertTrue( data["has_classic_format"], "A flag denoting the syntax interception should be set" " in the response context, so that a message may be" " rendered in the template.", )