postgresql - libpqxx C 聚合扩展返回错误数据?
问题描述
我正在学习如何创建 C 聚合扩展并在客户端使用 libpqxx 和 C++ 来处理数据。
我的玩具聚合扩展有一个类型参数,bytea
状态也是类型bytea
。以下是我的问题的最简单示例:
服务器端:
PG_FUNCTION_INFO_V1( simple_func );
Datum simple_func( PG_FUNCTION_ARGS ){
bytea *new_state = (bytea *) palloc( 128 + VARHDRSZ );
memset(new_state, 0, 128 + VARHDRSZ );
SET_VARSIZE( new_state,128 + VARHDRSZ );
PG_RETURN_BYTEA_P( new_state );
}
客户端:
std::basic_string< std::byte > buffer;
pqxx::connection c{"postgresql://user:simplepassword@localhost/contrib_regression"};
pqxx::work w(c);
c.prepare( "simple_func", "SELECT simple_func( $1 ) FROM table" );
pqxx::result r = w.exec_prepared( "simple_func", buffer );
for (auto row: r){
cout << " Result Size: " << row[ "simple_func" ].size() << endl;
cout << "Raw Result Data: ";
for( int jj=0; jj < row[ "simple_func" ].size(); jj++ ) printf( "%02" PRIx8, (uint8_t) row[ "simple_func" ].c_str()[jj] ) ;
cout << endl;
}
客户端的结果打印:
Result Size: 258
Raw Result Data: 5c783030303030303030303030303030...
模式30
重复直到字符串结尾,十六进制打印字符串为 512 字节。
我希望收到一个长度为 128 字节的数组,其中每个字节都设置为零。我究竟做错了什么?
libpqxx 版本是 7.2 和 Ubuntu 20.04 上的 PostgreSQL 12。
附录
安装扩展sql语句;
CREATE OR REPLACE FUNCTION agg_simple_func( state bytea, arg1 bytea)
RETURNS bytea
AS '$libdir/agg_simple_func'
LANGUAGE C IMMUTABLE STRICT;
CREATE OR REPLACE AGGREGATE simple_func( arg1 bytea)
(
sfunc = agg_simple_func,
stype = bytea,
initcond = "\xFFFF"
);
解决方案
答案似乎是,从 7.0 开始,客户端的 bytea 类型数据必须在 libpqxx 库中按如下方式检索(在早期版本中未测试):
row[ "simple_func" ].as<std::basic_string<std::byte>>()
这会检索正确的 bytea 数据,而无需像我看到的那样进行任何转换、字符串特性或意外行为。
推荐阅读
- python - Python,无法将字符串转换为浮点数:'7a'
- javascript - 在 jquery Datatable 中显示数据
- database - 如何更新 mongo 数据库集合中的数组
- flutter - Flutter TTS(文本到语音) - 是否有可能以及如何获取 iOS 语音的语言代码?
- android - 远程调试 AOSP 框架服务
- javascript - 使用 forloop 创建动态 javascript 对象
- javascript - 将 AudioBuffer 发送到扬声器
- r - 在 R 中将键值表透视到整洁的数据框
- c - 如何将带有管道的字符串解析为 exec()?
- erlang - 如何使用函数值在erlang中切换大小写?