Handle text values with potential memory mapping for large strings
(
&self,
text_data: &str,
pg_type_oid: i32,
binary_format: bool,
)
| 121 | |
| 122 | /// Handle text values with potential memory mapping for large strings |
| 123 | fn handle_text_value( |
| 124 | &self, |
| 125 | text_data: &str, |
| 126 | pg_type_oid: i32, |
| 127 | binary_format: bool, |
| 128 | ) -> io::Result<Option<MappedValue>> { |
| 129 | if text_data.is_empty() { |
| 130 | return Ok(Some(MappedValue::Memory(Vec::new()))); |
| 131 | } |
| 132 | |
| 133 | let pg_type = PgType::from_oid(pg_type_oid); |
| 134 | |
| 135 | // Handle boolean values specially - convert "t"/"f" strings to proper boolean format |
| 136 | if pg_type_oid == PgType::Bool.to_oid() { |
| 137 | let bool_value = match text_data { |
| 138 | "t" | "true" | "TRUE" | "1" => true, |
| 139 | "f" | "false" | "FALSE" | "0" => false, |
| 140 | _ => return Err(io::Error::new(io::ErrorKind::InvalidData, |
| 141 | format!("Invalid boolean value: {}", text_data))), |
| 142 | }; |
| 143 | |
| 144 | if binary_format { |
| 145 | // Use binary boolean encoding |
| 146 | let pg_data = crate::protocol::BinaryEncoder::encode_bool(bool_value); |
| 147 | return Ok(Some(MappedValue::Memory(pg_data))); |
| 148 | } else { |
| 149 | // Use text format |
| 150 | let pg_data = if bool_value { b"t".to_vec() } else { b"f".to_vec() }; |
| 151 | return Ok(Some(MappedValue::Memory(pg_data))); |
| 152 | } |
| 153 | } |
| 154 | |
| 155 | // If the target is a numeric type, try to parse and re-serialize |
| 156 | if !binary_format && pg_type.is_some() && pg_type.unwrap().is_numeric() { |
| 157 | if let Ok(val) = text_data.parse::<i64>() { |
| 158 | return self.handle_integer_value(val, pg_type_oid, binary_format); |
| 159 | } else if let Ok(val) = text_data.parse::<f64>() { |
| 160 | return self.handle_real_value(val, pg_type_oid, binary_format); |
| 161 | } |
| 162 | } |
| 163 | |
| 164 | // Check if this is an array type and needs JSON to array conversion |
| 165 | let pg_data = if pg_type.is_some() && pg_type.unwrap().is_array() { |
| 166 | // Convert JSON array to PostgreSQL array format for text protocol |
| 167 | if !binary_format { |
| 168 | self.convert_json_to_pg_array(text_data)? |
| 169 | } else { |
| 170 | // Binary format will be handled in a future update |
| 171 | text_data.as_bytes().to_vec() |
| 172 | } |
| 173 | } else { |
| 174 | text_data.as_bytes().to_vec() |
| 175 | }; |
| 176 | |
| 177 | // Check if this should use memory mapping |
| 178 | if self.config.enable_mmap && pg_data.len() >= self.config.large_value_threshold { |
| 179 | debug!("Using memory mapping for large text value: {} bytes", pg_data.len()); |
| 180 | Ok(Some(self.mmap_factory.create_from_blob(&pg_data)?)) |
no test coverage detected