добавил toString для классов Body
This commit is contained in:
AidarKC 2025-12-29 15:31:20 +03:00
parent 08d90b6e8e
commit b6b50557a7
4 changed files with 106 additions and 16 deletions

View File

@ -5,6 +5,7 @@ import blockchain.body.BodyRecordParser;
import java.nio.ByteBuffer; import java.nio.ByteBuffer;
import java.nio.ByteOrder; import java.nio.ByteOrder;
import java.time.Instant;
import java.util.Arrays; import java.util.Arrays;
import java.util.Objects; import java.util.Objects;
@ -175,4 +176,59 @@ public final class BchBlockEntry {
public byte[] toBytes() { public byte[] toBytes() {
return Arrays.copyOf(fullBytes, fullBytes.length); return Arrays.copyOf(fullBytes, fullBytes.length);
} }
@Override
public String toString() {
String timeIso;
try {
timeIso = Instant.ofEpochSecond(timestamp).toString();
} catch (Exception e) {
timeIso = "некорректныйTimestamp";
}
return "BchBlockEntry{"
+ "RAW{"
+ "recordSize=" + recordSize
+ ", recordNumber=" + recordNumber
+ ", timestamp=" + timestamp + " (" + timeIso + ")"
+ ", lineIndex=" + lineIndex
+ ", lineNumber=" + lineNumber
+ ", bodyLen=" + (bodyBytes == null ? -1 : bodyBytes.length)
+ ", bodyType=" + (body == null ? "?" : (body.type() & 0xFFFF))
+ ", bodyVer=" + (body == null ? "?" : (body.version() & 0xFFFF))
+ "}"
+ ", TAIL{"
+ "signature64(hex)=" + toHex(signature64)
+ ", hash32(hex)=" + toHex(hash32)
+ "}"
+ ", FULL{"
+ "fullLen=" + (fullBytes == null ? -1 : fullBytes.length)
+ ", rawLen=" + recordSize
+ "}"
+ ", body=" + (body == null ? "null" : body.toString())
+ ", bodyBytesPreview(hex32)=" + toHexPreview(bodyBytes, 32)
+ "}";
}
private static String toHex(byte[] bytes) {
if (bytes == null) return "null";
char[] HEX = "0123456789abcdef".toCharArray();
char[] out = new char[bytes.length * 2];
for (int i = 0; i < bytes.length; i++) {
int v = bytes[i] & 0xFF;
out[i * 2] = HEX[v >>> 4];
out[i * 2 + 1] = HEX[v & 0x0F];
}
return new String(out);
}
private static String toHexPreview(byte[] bytes, int maxBytes) {
if (bytes == null) return "null";
if (maxBytes <= 0) return "";
int n = Math.min(bytes.length, maxBytes);
byte[] cut = Arrays.copyOf(bytes, n);
String hex = toHex(cut);
if (bytes.length > n) hex += "…(+" + (bytes.length - n) + " байт)";
return hex;
}
} }

View File

@ -100,4 +100,16 @@ public final class HeaderBody implements BodyRecord {
return bb.array(); return bb.array();
} }
@Override
public String toString() {
return """
HeaderBody {
тип записи : HEADER (type=0, ver=1)
ожидаемая линия : 0 (genesis)
тег формата : "%s"
login владельца : "%s"
}
""".formatted(tag, login);
}
} }

View File

@ -34,7 +34,6 @@ public final class ReactionBody implements BodyRecord {
public final int toBlockGlobalNumber; public final int toBlockGlobalNumber;
public final byte[] toBlockHash32; public final byte[] toBlockHash32;
/** Десериализация из полного bodyBytes (включая type/version). */
public ReactionBody(byte[] bodyBytes) { public ReactionBody(byte[] bodyBytes) {
Objects.requireNonNull(bodyBytes, "bodyBytes == null"); Objects.requireNonNull(bodyBytes, "bodyBytes == null");
if (bodyBytes.length < 4 + 4 + 1 + 1 + 4 + 32) { if (bodyBytes.length < 4 + 4 + 1 + 1 + 4 + 32) {
@ -88,16 +87,10 @@ public final class ReactionBody implements BodyRecord {
public ReactionBody check() { public ReactionBody check() {
if (toBlockchainName == null || toBlockchainName.isBlank()) if (toBlockchainName == null || toBlockchainName.isBlank())
throw new IllegalArgumentException("toBlockchainName is blank"); throw new IllegalArgumentException("toBlockchainName is blank");
byte[] nameBytes = toBlockchainName.getBytes(StandardCharsets.UTF_8);
if (nameBytes.length == 0 || nameBytes.length > 255)
throw new IllegalArgumentException("toBlockchainName utf8 len must be 1..255");
if (toBlockGlobalNumber < 0) if (toBlockGlobalNumber < 0)
throw new IllegalArgumentException("toBlockGlobalNumber < 0"); throw new IllegalArgumentException("toBlockGlobalNumber < 0");
if (toBlockHash32 == null || toBlockHash32.length != 32) if (toBlockHash32 == null || toBlockHash32.length != 32)
throw new IllegalArgumentException("toBlockHash32 invalid"); throw new IllegalArgumentException("toBlockHash32 invalid");
return this; return this;
} }
@ -121,16 +114,30 @@ public final class ReactionBody implements BodyRecord {
return bb.array(); return bb.array();
} }
/** Для записи в БД (toBlockHashe TEXT) удобно хранить hex. */ @Override
public String toBlockHashHex() { public String toString() {
return toHex(toBlockHash32); return """
ReactionBody {
тип записи : REACTION (type=2, ver=1)
ожидаемая линия : 2
код реакции : %d
целевой блокчейн : "%s"
globalNumber цели : %d
hash цели (hex) : %s
}
""".formatted(
reactionCode,
toBlockchainName,
toBlockGlobalNumber,
toBlockHashHex()
);
} }
private static String toHex(byte[] bytes) { public String toBlockHashHex() {
char[] HEX = "0123456789abcdef".toCharArray(); char[] HEX = "0123456789abcdef".toCharArray();
char[] out = new char[bytes.length * 2]; char[] out = new char[64];
for (int i = 0; i < bytes.length; i++) { for (int i = 0; i < 32; i++) {
int v = bytes[i] & 0xFF; int v = toBlockHash32[i] & 0xFF;
out[i * 2] = HEX[v >>> 4]; out[i * 2] = HEX[v >>> 4];
out[i * 2 + 1] = HEX[v & 0x0F]; out[i * 2 + 1] = HEX[v & 0x0F];
} }

View File

@ -88,4 +88,19 @@ public final class TextBody implements BodyRecord {
bb.put(msg); bb.put(msg);
return bb.array(); return bb.array();
} }
@Override
public String toString() {
return """
TextBody {
тип записи : TEXT (type=1, ver=1)
ожидаемая линия : 1
длина сообщения : %d байт
текст сообщения : "%s"
}
""".formatted(
message.getBytes(StandardCharsets.UTF_8).length,
message
);
}
} }