diff --git a/CHANGELOG.md b/CHANGELOG.md index 6bcaac83f..e587f4eed 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,4 +3,4 @@ - Add the number of hits in search result (#541) - Add support for aligned crop in search result (#543) - Sanitize the content displayed in the web interface (#539) - - Add support of nested null and boolean values (#571 and #568) + - Add support of nested null, boolean and seq values (#571 and #568, #574) diff --git a/meilisearch-core/src/serde/convert_to_string.rs b/meilisearch-core/src/serde/convert_to_string.rs index ca5c59a78..cd072c904 100644 --- a/meilisearch-core/src/serde/convert_to_string.rs +++ b/meilisearch-core/src/serde/convert_to_string.rs @@ -8,7 +8,7 @@ pub struct ConvertToString; impl ser::Serializer for ConvertToString { type Ok = String; type Error = SerializerError; - type SerializeSeq = ser::Impossible; + type SerializeSeq = SeqConvertToString; type SerializeTuple = ser::Impossible; type SerializeTupleStruct = ser::Impossible; type SerializeTupleVariant = ser::Impossible; @@ -135,8 +135,8 @@ impl ser::Serializer for ConvertToString { } fn serialize_seq(self, _len: Option) -> Result { - Err(SerializerError::UnserializableType { - type_name: "sequence", + Ok(SeqConvertToString { + text: String::new(), }) } @@ -254,3 +254,26 @@ impl ser::SerializeStruct for StructConvertToString { Ok(self.text) } } + +pub struct SeqConvertToString { + text: String, +} + +impl ser::SerializeSeq for SeqConvertToString { + type Ok = String; + type Error = SerializerError; + + fn serialize_element(&mut self, key: &T) -> Result<(), Self::Error> + where + T: ser::Serialize, + { + let text = key.serialize(ConvertToString)?; + self.text.push_str(&text); + self.text.push_str(" "); + Ok(()) + } + + fn end(self) -> Result { + Ok(self.text) + } +} diff --git a/meilisearch-http/tests/documents_add.rs b/meilisearch-http/tests/documents_add.rs index 847179c7d..a223c4757 100644 --- a/meilisearch-http/tests/documents_add.rs +++ b/meilisearch-http/tests/documents_add.rs @@ -30,7 +30,7 @@ fn check_add_documents_with_primary_key_param() { let update_id = response["updateId"].as_u64().unwrap(); server.wait_update_id(update_id); - // 3 - Check update sucess + // 3 - Check update success let (response, status_code) = server.get_update_status(update_id); assert_eq!(status_code, 200); @@ -70,7 +70,7 @@ fn check_add_documents_with_nested_boolean() { let update_id = response["updateId"].as_u64().unwrap(); server.wait_update_id(update_id); - // 3 - Check update sucess + // 3 - Check update success let (response, status_code) = server.get_update_status(update_id); assert_eq!(status_code, 200); @@ -105,9 +105,73 @@ fn check_add_documents_with_nested_null() { let update_id = response["updateId"].as_u64().unwrap(); server.wait_update_id(update_id); - // 3 - Check update sucess + // 3 - Check update success let (response, status_code) = server.get_update_status(update_id); assert_eq!(status_code, 200); assert_eq!(response["status"], "processed"); } + +// Test issue https://github.com/meilisearch/MeiliSearch/issues/574 +#[test] +fn check_add_documents_with_nested_sequence() { + let mut server = common::Server::with_uid("tasks"); + + // 1 - Create the index with no primary_key + + let body = json!({ "uid": "tasks" }); + let (response, status_code) = server.create_index(body); + assert_eq!(status_code, 201); + assert_eq!(response["primaryKey"], json!(null)); + + // 2 - Add a document that contains a seq in a nested object + + let body = json!([{ + "id": 0, + "foo": { + "bar": [123,456], + "fez": [{ + "id": 255, + "baz": "leesz", + "fuzz": { + "fax": [234] + }, + "sas": [] + }], + "foz": [{ + "id": 255, + "baz": "leesz", + "fuzz": { + "fax": [234] + }, + "sas": [] + }, + { + "id": 256, + "baz": "loss", + "fuzz": { + "fax": [235] + }, + "sas": [321, 321] + }] + } + }]); + + let url = "/indexes/tasks/documents"; + let (response, status_code) = server.post_request(&url, body.clone()); + eprintln!("{:#?}", response); + assert_eq!(status_code, 202); + let update_id = response["updateId"].as_u64().unwrap(); + server.wait_update_id(update_id); + + // 3 - Check update success + + let (response, status_code) = server.get_update_status(update_id); + assert_eq!(status_code, 200); + assert_eq!(response["status"], "processed"); + + let url = "/indexes/tasks/search?q=leesz"; + let (response, status_code) = server.get_request(&url); + assert_eq!(status_code, 200); + assert_eq!(response["hits"], body); +}