From fb56446fa44093995793979175fc00997cf46dd0 Mon Sep 17 00:00:00 2001 From: mystarry-sky Date: Tue, 19 Dec 2023 18:58:03 +0800 Subject: [PATCH] =?UTF-8?q?bit=E4=BB=A5=E5=8F=8Abinary=E7=B1=BB=E5=9E=8B?= =?UTF-8?q?=E8=BD=AC=E6=8D=A2=E9=80=82=E9=85=8D?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- config/application-sink.yml | 2 +- config/application-source.yml | 2 +- .../datachecker/common/util/HexUtil.java | 66 +++++++++++++++++-- .../extract/task/MysqlResultSetHandler.java | 22 +++---- .../task/OpenGaussResultSetHandler.java | 21 +++++- 5 files changed, 94 insertions(+), 19 deletions(-) diff --git a/config/application-sink.yml b/config/application-sink.yml index 8cd0aea..bfd98e0 100644 --- a/config/application-sink.yml +++ b/config/application-sink.yml @@ -27,7 +27,7 @@ spring: # driver-class-name: com.mysql.cj.jdbc.Driver # url: jdbc:mysql://127.0.0.1:3306/test?useSSL=false&useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC&allowPublicKeyRetrieval=true driver-class-name: org.opengauss.Driver - url: jdbc:opengauss://127.0.0.1:5432/postgres?useSSL=false&useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC + url: jdbc:opengauss://127.0.0.1:5432/postgres?useSSL=false&useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC&bitToString=true # driver-class-name: oracle.jdbc.OracleDriver # url: jdbc:oracle:thin:@127.0.0.1:1521/TEST username: diff --git a/config/application-source.yml b/config/application-source.yml index 641b4d4..96b96dd 100644 --- a/config/application-source.yml +++ b/config/application-source.yml @@ -34,7 +34,7 @@ spring: driver-class-name: com.mysql.cj.jdbc.Driver url: jdbc:mysql://127.0.0.1:3306/mysql?useSSL=false&useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC&allowPublicKeyRetrieval=true # driver-class-name: org.opengauss.Driver # For openGauss - # url: # jdbc:opengauss://127.0.0.1:5432/postgres?useSSL=false&useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC # For openGauss + # url: # jdbc:opengauss://127.0.0.1:5432/postgres?useSSL=false&useUnicode=true&characterEncoding=utf-8&serverTimezone=UTC&bitToString=true # For openGauss # driver-class-name: oracle.jdbc.OracleDriver # url: jdbc:oracle:thin:@127.0.0.1:1521/TEST username: diff --git a/datachecker-common/src/main/java/org/opengauss/datachecker/common/util/HexUtil.java b/datachecker-common/src/main/java/org/opengauss/datachecker/common/util/HexUtil.java index d9aabaa..6729586 100644 --- a/datachecker-common/src/main/java/org/opengauss/datachecker/common/util/HexUtil.java +++ b/datachecker-common/src/main/java/org/opengauss/datachecker/common/util/HexUtil.java @@ -27,7 +27,8 @@ public class HexUtil { bit = bs[i] & 0x0f; sb.append(CHARS[bit]); } - return sb.toString().trim(); + return sb.toString() + .trim(); } /** @@ -39,7 +40,9 @@ public class HexUtil { public static String byteToHex(byte[] data) { StringBuilder result = new StringBuilder(); for (byte datum : data) { - result.append(Integer.toHexString((datum & 0xFF) | 0x100).toUpperCase().substring(1, 3)); + result.append(Integer.toHexString((datum & 0xFF) | 0x100) + .toUpperCase() + .substring(1, 3)); } return result.toString(); } @@ -85,13 +88,68 @@ public class HexUtil { while (fast < end) { if (data[fast] != 0) { while (slow < fast) { - result.append(Integer.toHexString((data[slow++] & 0xFF) | 0x100).toUpperCase().substring(1, 3)); + result.append(Integer.toHexString((data[slow++] & 0xFF) | 0x100) + .toUpperCase() + .substring(1, 3)); } slow = fast; } fast++; } - result.append(Integer.toHexString((data[slow] & 0xFF) | 0x100).toUpperCase().substring(1, 3)); + result.append(Integer.toHexString((data[slow] & 0xFF) | 0x100) + .toUpperCase() + .substring(1, 3)); return result.toString(); } + + /** + * binary string translate to hex string + * + * @param binary binary + * @return hex + */ + public static String binaryToHex(String binary) { + if (!isValidBinary(binary)) { + return ""; + } + String paddedBinary = padZeroes(binary); + StringBuilder hexBuilder = new StringBuilder(); + for (int i = 0; i < paddedBinary.length(); i += 4) { + char group = getBinaryToHexChar(paddedBinary.substring(i, i + 4)); + hexBuilder.append(group); + } + return hexBuilder.toString(); + } + + private static boolean isValidBinary(String binary) { + return binary != null && !binary.isEmpty() && binary.matches("[0-1]+"); + } + + private static String padZeroes(String binary) { + while (binary.length() % 4 != 0) { + binary = "0" + binary; + } + return binary; + } + + private static char getBinaryToHexChar(String binaryGroup) { + return BinaryHex.valueOf(binaryGroup).hexChar; + } + + /** + * binary hex mapping + */ + enum BinaryHex { + B0000("0000", '0'), B0001("0001", '1'), B0002("0010", '2'), B0003("0011", '3'), B0004("0100", '4'), B0005( + "0101", '5'), B0006("0110", '6'), B0007("1000", '7'), B0008("0001", '8'), B0009("1001", '9'), B00010("1010", + 'A'), B00011("1011", 'B'), B00012("1100", 'C'), B00013("1101", 'D'), B00014("1110", 'E'), B00015("1111", + 'F'); + private final String code; + private final char hexChar; + + BinaryHex(String code, char hexChar) { + this.code = code; + this.hexChar = hexChar; + } + } } diff --git a/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/MysqlResultSetHandler.java b/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/MysqlResultSetHandler.java index bf4e2dc..59b2248 100644 --- a/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/MysqlResultSetHandler.java +++ b/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/MysqlResultSetHandler.java @@ -36,11 +36,9 @@ public class MysqlResultSetHandler extends ResultSetHandler { private final Map typeHandlers = new ConcurrentHashMap<>(); { - TypeHandler binaryToString = (rs, columnLabel) -> byteToStringTrim(rs.getBytes(columnLabel)); - TypeHandler varbinaryToString = (rs, columnLabel) -> bytesToString(rs.getBytes(columnLabel)); + TypeHandler binaryToString = (rs, columnLabel) -> bytesToString(rs.getBytes(columnLabel)); TypeHandler blobToString = (rs, columnLabel) -> HexUtil.byteToHexTrim(rs.getBytes(columnLabel)); TypeHandler numericToString = (rs, columnLabel) -> floatingPointNumberToString(rs, columnLabel); - TypeHandler bitBooleanToString = (rs, columnLabel) -> rs.getString(columnLabel); typeHandlers.put(MysqlType.FLOAT_UNSIGNED, numericToString); typeHandlers.put(MysqlType.FLOAT, numericToString); @@ -48,10 +46,9 @@ public class MysqlResultSetHandler extends ResultSetHandler { typeHandlers.put(MysqlType.DOUBLE_UNSIGNED, numericToString); typeHandlers.put(MysqlType.DECIMAL, numericToString); typeHandlers.put(MysqlType.DECIMAL_UNSIGNED, numericToString); - typeHandlers.put(MysqlType.BIT, bitBooleanToString); // byte binary blob typeHandlers.put(MysqlType.BINARY, binaryToString); - typeHandlers.put(MysqlType.VARBINARY, varbinaryToString); + typeHandlers.put(MysqlType.VARBINARY, binaryToString); typeHandlers.put(MysqlType.BLOB, blobToString); typeHandlers.put(MysqlType.LONGBLOB, blobToString); @@ -66,13 +63,11 @@ public class MysqlResultSetHandler extends ResultSetHandler { typeHandlers.put(MysqlType.YEAR, this::getYearFormat); } - private String bitToString(ResultSet resultSet, String columnLabel, int displaySize) throws SQLException { - if (displaySize == 1) { - return String.valueOf(resultSet.getInt(columnLabel)); - } else { - Object object = resultSet.getObject(columnLabel); - return Objects.isNull(object) ? NULL : object.toString(); + private String bitToString(ResultSet resultSet, String columnLabel, int precision) throws SQLException { + if (precision == 1) { + return resultSet.getString(columnLabel); } + return HexUtil.byteToHexTrim(resultSet.getBytes(columnLabel)); } private String byteToStringTrim(byte[] bytes) { @@ -83,8 +78,11 @@ public class MysqlResultSetHandler extends ResultSetHandler { protected String convert(ResultSet resultSet, int columnIdx, ResultSetMetaData rsmd) throws SQLException { String columnLabel = rsmd.getColumnLabel(columnIdx); String columnTypeName = rsmd.getColumnTypeName(columnIdx); + int precision = rsmd.getPrecision(columnIdx); final MysqlType mysqlType = MysqlType.getByName(columnTypeName); - if (typeHandlers.containsKey(mysqlType)) { + if (MysqlType.BIT.equals(mysqlType)) { + return bitToString(resultSet, columnLabel, precision); + } else if (typeHandlers.containsKey(mysqlType)) { return typeHandlers.get(mysqlType) .convert(resultSet, columnLabel); } else { diff --git a/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/OpenGaussResultSetHandler.java b/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/OpenGaussResultSetHandler.java index a8bb05b..20b29e9 100644 --- a/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/OpenGaussResultSetHandler.java +++ b/datachecker-extract/src/main/java/org/opengauss/datachecker/extract/task/OpenGaussResultSetHandler.java @@ -15,10 +15,13 @@ package org.opengauss.datachecker.extract.task; +import org.opengauss.datachecker.common.util.HexUtil; + import java.sql.ResultSet; import java.sql.ResultSetMetaData; import java.sql.SQLException; import java.util.List; +import java.util.Locale; import java.util.Map; import java.util.Objects; import java.util.concurrent.ConcurrentHashMap; @@ -38,7 +41,8 @@ public class OpenGaussResultSetHandler extends ResultSetHandler { TypeHandler blobToString = (rs, columnLabel) -> rs.getString(columnLabel); TypeHandler clobToString = (rs, columnLabel) -> rs.getString(columnLabel); TypeHandler xmlToString = (rs, columnLabel) -> rs.getString(columnLabel); - TypeHandler bitToString = (rs, columnLabel) -> "B'" + rs.getString(columnLabel) + "'"; + TypeHandler bitToString = (rs, columnLabel) -> bitToString(rs, columnLabel); + TypeHandler binaryToString = (rs, columnLabel) -> binaryToString(rs, columnLabel); TypeHandler booleanToString = (rs, columnLabel) -> booleanToString(rs, columnLabel); TypeHandler numericToString = (rs, columnLabel) -> floatingPointNumberToString(rs, columnLabel); TypeHandler numeric0ToString = (rs, columnLabel) -> numeric0ToString(rs, columnLabel); @@ -59,6 +63,8 @@ public class OpenGaussResultSetHandler extends ResultSetHandler { typeHandlers.put(OpenGaussType.CLOB, clobToString); typeHandlers.put(OpenGaussType.XML, xmlToString); typeHandlers.put(OpenGaussType.BIT, bitToString); + typeHandlers.put(OpenGaussType.binary, binaryToString); + typeHandlers.put(OpenGaussType.varbinary, binaryToString); // The openGauss jdbc driver obtains the character,character varying type as varchar typeHandlers.put(OpenGaussType.BPCHAR, this::trim); @@ -70,6 +76,16 @@ public class OpenGaussResultSetHandler extends ResultSetHandler { typeHandlers.put(OpenGaussType.TIMESTAMPTZ, this::getTimestampFormat); } + private String binaryToString(ResultSet rs, String columnLabel) throws SQLException { + String binary = rs.getString(columnLabel); + return rs.wasNull() ? NULL : Objects.isNull(binary) ? NULL : binary.substring(2) + .toUpperCase(Locale.ENGLISH); + } + + private String bitToString(ResultSet rs, String columnLabel) throws SQLException { + return HexUtil.binaryToHex(rs.getString(columnLabel)); + } + public OpenGaussResultSetHandler() { super(); } @@ -123,6 +139,7 @@ public class OpenGaussResultSetHandler extends ResultSetHandler { } else { return numeric0ToString(resultSet, columnLabel); } + } private String getPgColumnTypeName(ResultSetMetaData rsmd, int columnIdx) throws SQLException { @@ -173,6 +190,8 @@ public class OpenGaussResultSetHandler extends ResultSetHandler { String CLOB = "clob"; String XML = "xml"; String BIT = "bit"; + String binary = "binary"; + String varbinary = "varbinary"; List digit = List.of(NUMERIC, INT1, INT2, INT4, INT8, UINT1, UINT2, UINT4, UINT8, FLOAT1, FLOAT2, FLOAT4, FLOAT8, INTEGER); -- Gitee