架构message
的数据库表fsr_system_log
中有一列fsr_appl
。该表应该存储系统日志消息。列的大小为255,数据类型为varchar2
。用于保存大小超过255个字符的消息的逻辑是:
public void saveSystemLog(SystemLogRequest systemLog){
User user = systemLog.getUser();
String system = systemLog.getSystem();
Log log = systemLog.getSystemLog();
try {
initializeDelegate();
delegate.beginTransaction();
LogEntry[] logEntries = log.getItemArray();
for (LogEntry logEntry : logEntries) {
// Save each entry
ParamVector<Object> params = new ParamVector<Object>();
//Check if message is greater than 255 characters
String message = logEntry.getMsg();
notifier.debug("Log Message is : " + message);
if(message.length()>255){
message = message.substring(0,255);
notifier().debug("Message string greater than 255 characters : " + message);
}
params.add(message, 255, false);
}
但是尽管实现了代码,我还是面临以下错误:
由于SQL错误而无法保存系统日志:ORA-12899:值对于“FSR_APPL”列而言太大。 “FSR_SYSTEM_LOG”。 “MESSAGE”(实际:257, 最大值:255)
正在使用的示例日志是:
<xbe:systemLogRequest xmlns:xbe="http://tdc.dk/fsr/common/xbean">
<user>
<userNumber>a62267</userNumber>
</user>
<system>Client</system>
<systemLog>
<item>
<timestamp>2011-10-27T17:03:08.404+02:00</timestamp>
<type>Info</type>
<msg><![CDATA[<html><center>Din registrering er nu sendt<br><br>Tak for indmeldingen</center></html>]]></msg>
</item>
<item>
<timestamp>2011-10-27T17:03:13.701+02:00</timestamp>
<type>Info</type>
<msg><![CDATA[<html><center>Din registrering er nu sendt<br><br>Tak for indmeldingen</center></html>]]></msg>
</item>
<item>
<timestamp>2011-10-28T12:45:47.801+02:00</timestamp>
<type>Info</type>
<msg><![CDATA[<html><center>Din registrering er nu sendt<br><br>Tak for indmeldingen</center></html>]]></msg>
</item>
<item>
<timestamp>2011-10-28T12:45:57.926+02:00</timestamp>
<type>Info</type>
<msg>Afsluttet uden at gemme fejlregistering</msg>
</item>
</systemLog>
</xbe:systemLogRequest>
请帮忙!
注意:抛出的错误仅适用于某些系统日志消息。当抛出此错误时,实际值始终为常量257。
答案 0 :(得分:1)
显然,您有一些用多个字节表示的字符。
在Java中,您可以获得字符中字符串的长度,而Oracle显然会检查字节限制,因为列的定义方式。
查看表的定义,很可能列是使用默认字符语义定义的 - 这是字节(但取决于您的Oracle安装),因此它默认为VARCHAR2(255 Byte)
如果您将列重新定义为VARCHAR2(255 Char)
,那么一切都应该没问题。
类似的东西:
CREATE TABLE FSR_SYSTEM_LOG
(
...
MESSAGE VARCHAR2(255 Char),
...
);
对我来说,在这样一个(长度)有限列中存储XML似乎很奇怪。您能否确保您的XML 从不超过255个字符?为什么不将邮件存储为CLOB
?
答案 1 :(得分:0)
乍一看,我怀疑编码问题......
Java使用unicode:unicode中的字符可能会花费一个很多字节... 一个java字符串的长度可能是1但是当在存储上编组时,它可能需要2个字节,4个字节......
要检查字节长度,也许你应该尝试:
if(message.getBytes("US-ASCII").length()>255){
Oracle DB的编码是什么?
另一个可能的问题是,写入数据库的类会将一个CR / LF(0D0A)添加到msg参数或其他内容......
答案 2 :(得分:0)
您可以将字段类型更改为CLOB,BLOB或XMLType。查找Oracle数据类型,VARCHAR2似乎也适用于字节。
您可以理解,您可能不想更改字段类型,在这种情况下,请替换
if(message.length()>255){
message = message.substring(0,255);
notifier().debug("Message string greater than 255 characters : " + message);
}
与
pos = 255
while (message.getBytes().size() > 255) {
message = message.substring(0,pos--);
}