 KBrown revised this gist 4 months ago. Go to revision
                
                KBrown revised this gist 4 months ago. Go to revision
                
                    1 file changed, 45 insertions
PgBinaryProtocol.rs(file created)
| @@ -0,0 +1,45 @@ | |||
| 1 | + | if args.contains(&PostgresTypeAttribute::PgBinaryProtocol) { | |
| 2 | + | // At this time, the `PostgresTypeAttribute` does not impact the way we generate | |
| 3 | + | // the `recv` and `send` functions. | |
| 4 | + | stream.extend(quote! { | |
| 5 | + | #[doc(hidden)] | |
| 6 | + | #[::pgrx::pgrx_macros::pg_extern(immutable, strict, parallel_safe)] | |
| 7 | + | pub fn #funcname_recv #generics( | |
| 8 | + | internal: ::pgrx::datum::Internal, | |
| 9 | + | ) -> #name #generics { | |
| 10 | + | let buf = unsafe { internal.get_mut::<::pgrx::pg_sys::StringInfoData>().unwrap() }; | |
| 11 | + | ||
| 12 | + | let mut serialized = ::pgrx::StringInfo::new(); | |
| 13 | + | ||
| 14 | + | serialized.push_bytes(&[0u8; ::pgrx::pg_sys::VARHDRSZ]); // reserve space for the header | |
| 15 | + | serialized.push_bytes(unsafe { | |
| 16 | + | core::slice::from_raw_parts( | |
| 17 | + | buf.data as *const u8, | |
| 18 | + | buf.len as usize | |
| 19 | + | ) | |
| 20 | + | }); | |
| 21 | + | ||
| 22 | + | let size = serialized.len(); | |
| 23 | + | let varlena = serialized.into_char_ptr(); | |
| 24 | + | ||
| 25 | + | unsafe{ | |
| 26 | + | ::pgrx::set_varsize_4b(varlena as *mut ::pgrx::pg_sys::varlena, size as i32); | |
| 27 | + | buf.cursor = buf.len; | |
| 28 | + | ::pgrx::datum::cbor_decode(varlena as *mut ::pgrx::pg_sys::varlena) | |
| 29 | + | } | |
| 30 | + | } | |
| 31 | + | #[doc(hidden)] | |
| 32 | + | #[::pgrx::pgrx_macros::pg_extern(immutable, strict, parallel_safe)] | |
| 33 | + | pub fn #funcname_send #generics(input: #name #generics) -> Vec<u8> { | |
| 34 | + | use ::pgrx::datum::{FromDatum, IntoDatum}; | |
| 35 | + | let Some(datum): Option<::pgrx::pg_sys::Datum> = input.into_datum() else { | |
| 36 | + | ::pgrx::error!("Datum of type `{}` is unexpectedly NULL.", stringify!(#name)); | |
| 37 | + | }; | |
| 38 | + | unsafe { | |
| 39 | + | let Some(serialized): Option<Vec<u8>> = FromDatum::from_datum(datum, false) else { | |
| 40 | + | ::pgrx::error!("Failed to CBOR-serialize Datum to type `{}`.", stringify!(#name)); | |
| 41 | + | }; | |
| 42 | + | serialized | |
| 43 | + | } | |
| 44 | + | } | |
| 45 | + | }); | |
    
    
                            
                            Newer
    
    
    Older