返回首页

gbase数据、南大通用产品文档:GBase8sSQLERRD 数组

更新日期:2024年09月11日


GBase 8s SQL 指南:教程
南大通用数据技术股份有限公司 - 204 -

在 SQLCODE 中可报告的某些错误代码反映一般的问题。数据库服务器可在 SQLERRD
的第二个字段中设置更详细的代码,显示数据库服务器 I/O 例程或操作系统遇到的错误。
将 SQLERRD 数组中的整数设置为跟在不同语句之后的不同值。在 GBase 8s ESQL/C 中,
仅使用数组的第一个和第四个元素。下表展示如何使用这些字段。
表 1. SQLERRD 的字段
字段
解释
第一个
对于 SELECT、UPDATE、INSERT 或 DELETE 语句,在成功的 PREPARE 语句之
后,或在打开 Select 游标之后,此字段包含估计的受影响的行数。
第二个
当 SQLCODE 包含一个错误代码时,此字段包含零或附加的错误代码,称
为 ISAM 错误代码,
说明主要错误的原因。
在对单个行的成功的插入操作之
后,
此字段包含任何 SERIAL、
BIGSERIAL 或 SERIAL8 值为那行生成的值。
(然
而,当通过表上的触发器,或通过视图上的 INSTEAD
OF 触发器,将一序列列
作为触发器的活动直接插入时,不更新此字段。)
第三个
在成功的多行插入、更新或删除操作之后,此字段包含处理了的行数。在以错
误结束的多行插入、
更新或删除操作之后,
此字段包含在检测到该错误之前成
功地处理了的行数。
第四个
在对于 SELECT、UPDATE、INSERT 或 DELETE 语句的成功的 PREPARE 语句之
后,
或在已打开了选择游标之后,
此字段包含磁盘访问的与处理的全部行的估
计加权总和。
第五个
在 PREPARE、EXECUTE
IMMEDIATE、DECLARE 或静态的 SQL 语句中的语法错误
之后,此字段包含检测到该错误的位置的语句文本的偏移量。
第六个
在对选择了的行的成功的访存之后,或成功的插入、更新或删除操作之后,此
字段包含处理了的最后一行的 rowid(物理地址)。此 rowid 值是否对应于
数据库服务器返回给用户的行,
依赖于数据库服务器处理查询的方式,
特别是
对于 SELECT 语句。
第七个
保留。
这些附加的详细信息可是有用的。例如,您可使用第三个字段中的值来报告删除了或更新
了多少行。当您的程序准备一个用户输入的 SQL 语句并发现错误时,第五个字段中的值
使得您能够向用户显示错误的精确点。(当您在错误之后请求修改语句时,DB-Access 使
用此特性来定位游标。)


GBase 8s SQL 指南:教程
南大通用数据技术股份有限公司 - 205 -

ldchar() 函数将定长的字符串复制至以空终止的字符串内,并移除任何结尾的空格。

语法
void ldchar(from, count, to)
char *from;
mint count;
char *to;
from
指向定长的源字符串的指针。
count
定长的源字符串中的字节数。
to
指向以空为终止的目标字符串的第一个字节的指针。
to 参数可指向与 from 参数相同
的位置,或指向覆盖 from 参数的位置。如果如此,则 ldchar() 不保留 from 指向的值。

示例
demo 目录中 ldchar.ec 的文件中为此样例程序。
/*
* ldchar.ec *

The following program loads characters to specific locations in an array that is initialized
to z's. It displays the result of each ldchar() operation.
*/

#include

main()

GBase 8s ESQL/C 编程指南
南大通用数据技术股份有限公司
- 848 -

{
static char src1[] = "abcd ";
static char src2[] = "abcd g ";
static char dest[40];

printf("LDCHAR Sample ESQL Program running.\n\n");

ldchar(src1, stleng(src1), dest);
printf("\tSource: [%s]\n\tDestination: [%s]\n\n", src1, dest);

ldchar(src2, stleng(src2), dest);
printf("\tSource: [%s]\n\tDestfination: [%s]\n", src2, dest);

printf("\nLDCHAR Sample Program over.\n\n");
}
输出
LDCHAR Sample ESQL Program running.

Source: [abcd ]
Destination: [abcd]

Source: [abcd g ]
Destination: [abcd g]
LDCHAR Sample Program over.

日志管理
GBase 8c JDBC 驱动程序支持使用日志记录,
来帮助解决在应用程序中使用JDBC 驱动
程序时的问题。GBase 8c 的JDBC 支持如下三种日志管理方式:

对接应用程序使用的SLF4J 日志框架。

GBase 8c V5 开发者手册
南大通用数据技术股份有限公司
84

对接应用程序使用的JdkLogger 日志框架。

SLF4J 和JdkLogger 是业界Java 应用程序日志管理的主流框架,
描述应用程序如何使用
这些框架超出了本文范围,用户请参考对应的官方文档(SLF4J :http://
www.slf4j.org/manual.html

JdkLogger

https://docs.oracle.com/javase/8/
docs/technotes/guides/logging/overview.html)。
方式一:对接应用程序的SLF4J 日志框架。
在建立连接时,url 配置logger=Slf4JLogger。
可采用Log4j 或Log4j2 来实现SLF4J。
当采用Log4j 实现SLF4J,
需要添加如下jar 包:
log4j-*.jar、slf4j-api-*.jar、slf4j-log4*-*.jar,(*区分版本),和配置文件:
log4j.properties。若采用Log4j2 实现SLF4J,需要添加如下jar 包:log4j-api-*.jar、
log4j-core-*.jar、log4j-slf4j18-impl-*.jar、slf4j-api-*-alpha1.jar(*区分版本),和配置文件:
log4j2.xml。
此方式支持日志管控。
SLF4J 可通过文件中的相关配置实现强大的日志管控功能,
建议
使用此方式进行日志管理。
此方式依赖slf4j 的通用API 接口,如org.slf4j.LoggerFactory.getLogger(String name)、
org.slf4j.Logger.debug(String
var1)

org.slf4j.Logger.info(String
var1)

org.slf4j.Logger.warn(String warn)、org.slf4j.Logger.warn(String warn)等,若以上接口发生变
更,日志将无法打印。
示例:
public static Connection GetConnection(String username, String passwd){
String sourceURL = "jdbc:postgresql://10.10.0.13:15432/postgres?logger=Slf4JLogger";
Connection conn = null;
try{
//创建连接
conn = DriverManager.getConnection(sourceURL,username,passwd);
System.out.println("Connection succeed!");
}catch (Exception e){ e.printStackTrace(); return null;
}
return conn;
}

GBase 8c V5 开发者手册
南大通用数据技术股份有限公司
85
log4j.properties 示例:
log4j.logger.org.postgresql=ALL, log_gsjdbc
# 默认文件输出配置log4j.appender.log_gsjdbc=org.apache.log4j.RollingFileAppender
log4j.appender.log_gsjdbc.Append=true log4j.appender.log_gsjdbc.File=gsjdbc.log
log4j.appender.log_gsjdbc.Threshold=TRACE log4j.appender.log_gsjdbc.MaxFileSize=10MB
log4j.appender.log_gsjdbc.MaxBackupIndex=5
log4j.appender.log_gsjdbc.layout=org.apache.log4j.PatternLayout
log4j.appender.log_gsjdbc.layout.ConversionPattern=%d %p %t %c - %m%n
log4j.appender.log_gsjdbc.File.Encoding = UTF-8
log4j2.xml 示例:










filePattern="%d{yyyy-MM-dd}-%i.log">


















GBase 8c V5 开发者手册
南大通用数据技术股份有限公司
86
方式二:对接应用程序使用的JdkLogger 日志框架。
默认的Java 日志记录框架将其配置存储在名为logging.properties 的文件中。Java 会在
Java 安装目录的文件夹中安装全局配置文件。logging.properties 文件也可以创建并与单个项
目一起存储。
logging.properties 配置示例:
# 指定处理程序为文件。
handlers= java.util.logging.FileHandler
# 指定默认全局日志级别
.level= ALL
# 指定日志输出管控标准java.util.logging.FileHandler.level=ALL
java.util.logging.FileHandler.pattern = gsjdbc.log java.util.logging.FileHandler.limit = 500000
java.util.logging.FileHandler.count = 30 java.util.logging.FileHandler.formatter =
java.util.logging.SimpleFormatter java.util.logging.FileHandler.append=false
代码中使用示例:
System.setProperty("java.util.logging.FileHandler.pattern","jdbc.log");
FileHandler fileHandler = new
FileHandler(System.getProperty("java.util.logging.FileHandler.pattern")); Formatter formatter
= new SimpleFormatter();
fileHandler.setFormatter(formatter);
Logger logger = Logger.getLogger("org.postgresql"); logger.addHandler(fileHandler);
logger.setLevel(Level.ALL); logger.setUseParentHandlers(false);
链路跟踪功能
JDBC 驱动程序提供了应用到数据库的链路跟踪功能,用于将数据库端离散的SQL 和
应用程序的请求关联起来。该功能需要应用开发者实现org.postgresql.log.Tracer 接口类,并
在url 中指定接口实现类的全限定名。
url 示例:
String URL = "jdbc:postgresql://127.0.0.1:15432/postgres?
traceInterfaceClass=xxx.xxx.xxx.OpenGaussTraceImpl";
org.postgresql.log.Tracer 接口类定义如下:
public interface Tracer {
// Retrieves the value of traceId. String getTraceId();
}
org.postgresql.log.Tracer 接口实现类示例:

GBase 8c V5 开发者手册
南大通用数据技术股份有限公司
87
import org.postgresql.log.Tracer;
public class OpenGaussTraceImpl implements Tracer {
private static MDC mdc = new MDC(); private final String TRACE_ID_KEY = "traceId";
public void set(String traceId) { mdc.put(TRACE_ID_KEY, traceId);
}
public void reset() { mdc.clear();
}
@Override
public String getTraceId() {
return mdc.get(TRACE_ID_KEY);
}
}
上下文映射示例,用于存放不同请求的生成的traceId。
import java.util.HashMap;
public class MDC {
static final private ThreadLocal> threadLocal = new
ThreadLocal<>();
public void put(String key, String val) { if (key == null || val == null) {
throw new IllegalArgumentException("key or val cannot be null");
} else {
if (threadLocal.get() == null) { threadLocal.set(new HashMap<>());
}
threadLocal.get().put(key, val);
}
}
public String get(String key) { if (key == null) {
throw new IllegalArgumentException("key cannot be null");
} else if (threadLocal.get() == null) { return null;
} else {
return threadLocal.get().get(key);
}
}
public void clear() {
if (threadLocal.get() == null) { return;
} else {
threadLocal.get().clear();
}
}
}
业务使用traceId 示例。

GBase 8c V5 开发者手册
南大通用数据技术股份有限公司
88
String traceId = UUID.randomUUID().toString().replaceAll("-", "");
openGaussTrace.set(traceId);
pstm = con.prepareStatement("select * from test_trace_id where id = ?"); pstm.setInt(1, 1);
pstm.execute();
pstm = con.prepareStatement("insert into test_trace_id values(?,?)"); pstm.setInt(1, 2);
pstm.setString(2, "test"); pstm.execute(); openGaussTrace.reset();