risingwave_expr_impl/scalar/concat_op.rs
1// Copyright 2025 RisingWave Labs
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15use std::fmt::Write;
16
17use risingwave_expr::function;
18
19#[function("concat_op(varchar, varchar) -> varchar")]
20pub fn concat_op(left: &str, right: &str, writer: &mut impl Write) {
21 writer.write_str(left).unwrap();
22 writer.write_str(right).unwrap();
23}
24
25/// Concatenates the two binary strings.
26///
27/// # Example
28///
29/// ```slt
30/// query I
31/// select '\x123456'::bytea || '\x789a00bcde'::bytea;
32/// ----
33/// \x123456789a00bcde
34///
35/// query I
36/// select '\x123456'::bytea || '\x789a00bcde';
37/// ----
38/// \x123456789a00bcde
39///
40/// query I
41/// select '\x123456'::bytea || ''::bytea;
42/// ----
43/// \x123456
44/// ```
45#[function("bytea_concat_op(bytea, bytea) -> bytea")]
46pub fn bytea_concat_op(left: &[u8], right: &[u8]) -> Box<[u8]> {
47 let mut result = Vec::with_capacity(left.len() + right.len());
48 result.extend_from_slice(left);
49 result.extend_from_slice(right);
50 result.into_boxed_slice()
51}
52
53#[cfg(test)]
54mod tests {
55 use super::*;
56
57 #[test]
58 fn test_concat_op() {
59 let mut s = String::new();
60 concat_op("114", "514", &mut s);
61 assert_eq!(s, "114514")
62 }
63
64 #[test]
65 fn test_bytea_concat_op() {
66 let left = b"\x01\x02\x03";
67 let right = b"\x04\x05";
68 let result = bytea_concat_op(left, right);
69 assert_eq!(&*result, b"\x01\x02\x03\x04\x05");
70 }
71}