SHA256
Закомитил промежуточную почти работающую версию ...
This commit is contained in:
+21
-2
@@ -6,6 +6,7 @@ import blockchain.MsgSubType;
|
||||
import blockchain.body.BodyHasLine;
|
||||
import blockchain.body.BodyHasTarget;
|
||||
import blockchain.body.CreateChannelBody;
|
||||
import blockchain.body.UserParamBody;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import server.logic.ws_protocol.Base64Ws;
|
||||
@@ -21,8 +22,10 @@ import server.logic.ws_protocol.JSON.handlers.blockchain.entyties.Net_AddBlock_R
|
||||
import server.logic.ws_protocol.WireCodes;
|
||||
import shine.db.dao.BlockchainStateDAO;
|
||||
import shine.db.dao.BlocksDAO;
|
||||
import shine.db.dao.UserParamsDAO;
|
||||
import shine.db.entities.BlockchainStateEntry;
|
||||
import shine.db.entities.BlockEntry;
|
||||
import shine.db.entities.UserParamEntry;
|
||||
import utils.blockchain.BlockchainNameUtil;
|
||||
|
||||
import java.util.Arrays;
|
||||
@@ -45,8 +48,9 @@ public final class Net_AddBlock_Handler implements JsonMessageHandler {
|
||||
|
||||
private final BlocksDAO blocksDAO = BlocksDAO.getInstance();
|
||||
private final BlockchainStateDAO stateDAO = BlockchainStateDAO.getInstance();
|
||||
private final UserParamsDAO userParamsDAO = UserParamsDAO.getInstance();
|
||||
|
||||
private final BlockchainWriter dbWriter = new BlockchainWriter(blocksDAO, stateDAO);
|
||||
private final BlockchainWriter dbWriter = new BlockchainWriter(blocksDAO, stateDAO, userParamsDAO);
|
||||
|
||||
@Override
|
||||
public Net_Response handle(Net_Request baseReq, ConnectionContext ctx) {
|
||||
@@ -370,7 +374,22 @@ public final class Net_AddBlock_Handler implements JsonMessageHandler {
|
||||
be.setEditedByBlockNumber(be.getToBlockNumber());
|
||||
}
|
||||
|
||||
dbWriter.appendBlockAndState(blockchainName, block, st, be);
|
||||
UserParamEntry upsertedParam = null;
|
||||
if (block.body instanceof UserParamBody upBody) {
|
||||
String effectiveLogin = (st.getLogin() != null && !st.getLogin().isBlank())
|
||||
? st.getLogin()
|
||||
: login;
|
||||
upsertedParam = new UserParamEntry(
|
||||
effectiveLogin,
|
||||
upBody.paramKey,
|
||||
block.timestamp * 1000L,
|
||||
upBody.paramValue,
|
||||
null,
|
||||
null
|
||||
);
|
||||
}
|
||||
|
||||
dbWriter.appendBlockAndState(blockchainName, block, st, be, upsertedParam);
|
||||
|
||||
} catch (Exception e) {
|
||||
log.error("AddBlock: внутренняя ошибка при записи блока (login={}, blockchainName={}, blockNumber={})",
|
||||
|
||||
+13
-3
@@ -3,8 +3,10 @@ package server.logic.ws_protocol.JSON.handlers.blockchain.Net_AddBlock_Handler_u
|
||||
import blockchain.BchBlockEntry;
|
||||
import shine.db.dao.BlockchainStateDAO;
|
||||
import shine.db.dao.BlocksDAO;
|
||||
import shine.db.dao.UserParamsDAO;
|
||||
import shine.db.entities.BlockchainStateEntry;
|
||||
import shine.db.entities.BlockEntry;
|
||||
import shine.db.entities.UserParamEntry;
|
||||
import utils.files.FileStoreUtil;
|
||||
|
||||
import java.sql.Connection;
|
||||
@@ -21,17 +23,20 @@ public final class BlockchainWriter {
|
||||
|
||||
private final BlocksDAO blocksDAO;
|
||||
private final BlockchainStateDAO stateDAO;
|
||||
private final UserParamsDAO userParamsDAO;
|
||||
private final FileStoreUtil fs = FileStoreUtil.getInstance();
|
||||
|
||||
public BlockchainWriter(BlocksDAO blocksDAO, BlockchainStateDAO stateDAO) {
|
||||
public BlockchainWriter(BlocksDAO blocksDAO, BlockchainStateDAO stateDAO, UserParamsDAO userParamsDAO) {
|
||||
this.blocksDAO = blocksDAO;
|
||||
this.stateDAO = stateDAO;
|
||||
this.userParamsDAO = userParamsDAO;
|
||||
}
|
||||
|
||||
public void appendBlockAndState(String blockchainName,
|
||||
BchBlockEntry block,
|
||||
BlockchainStateEntry st,
|
||||
BlockEntry be) throws SQLException {
|
||||
BlockEntry be,
|
||||
UserParamEntry userParamEntry) throws SQLException {
|
||||
|
||||
long nowMs = System.currentTimeMillis();
|
||||
|
||||
@@ -49,6 +54,11 @@ public final class BlockchainWriter {
|
||||
|
||||
stateDAO.upsert(c, st);
|
||||
|
||||
// 2.1) Если блок — USER_PARAM, синхронизируем снимок в users_params в той же транзакции.
|
||||
if (userParamEntry != null) {
|
||||
userParamsDAO.upsertIfNewer(c, userParamEntry);
|
||||
}
|
||||
|
||||
c.commit();
|
||||
} catch (Exception e) {
|
||||
try { c.rollback(); } catch (Exception ignored) {}
|
||||
@@ -64,4 +74,4 @@ public final class BlockchainWriter {
|
||||
String fileName = fs.buildBlockchainFileName(blockchainName);
|
||||
fs.addDataToFile(fileName, block.toBytes());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+42
@@ -10,10 +10,13 @@ import server.logic.ws_protocol.JSON.handlers.tempToTest.entyties.Net_GetUser_Re
|
||||
import server.logic.ws_protocol.JSON.handlers.tempToTest.entyties.Net_GetUser_Response;
|
||||
import server.logic.ws_protocol.JSON.utils.NetExceptionResponseFactory;
|
||||
import server.logic.ws_protocol.WireCodes;
|
||||
import shine.db.dao.BlockchainStateDAO;
|
||||
import shine.db.dao.SolanaUsersDAO;
|
||||
import shine.db.entities.BlockchainStateEntry;
|
||||
import shine.db.entities.SolanaUserEntry;
|
||||
|
||||
import java.sql.SQLException;
|
||||
import java.util.Arrays;
|
||||
|
||||
public class Net_GetUser_Handler implements JsonMessageHandler {
|
||||
|
||||
@@ -35,6 +38,7 @@ public class Net_GetUser_Handler implements JsonMessageHandler {
|
||||
}
|
||||
|
||||
SolanaUsersDAO usersDAO = SolanaUsersDAO.getInstance();
|
||||
BlockchainStateDAO stateDAO = BlockchainStateDAO.getInstance();
|
||||
|
||||
try {
|
||||
SolanaUserEntry u = usersDAO.getByLogin(req.getLogin());
|
||||
@@ -60,6 +64,32 @@ public class Net_GetUser_Handler implements JsonMessageHandler {
|
||||
resp.setBlockchainKey(u.getBlockchainKey());
|
||||
resp.setDeviceKey(u.getDeviceKey());
|
||||
|
||||
// Возвращаем актуальный курсор блокчейна и, если запись состояния потеряна,
|
||||
// автоматически восстанавливаем её для существующего пользователя.
|
||||
BlockchainStateEntry st = stateDAO.getByBlockchainName(u.getBlockchainName());
|
||||
if (st == null) {
|
||||
st = new BlockchainStateEntry();
|
||||
st.setBlockchainName(u.getBlockchainName());
|
||||
st.setLogin(u.getLogin());
|
||||
st.setBlockchainKey(u.getBlockchainKey());
|
||||
st.setLastBlockNumber(-1);
|
||||
st.setLastBlockHash(new byte[32]);
|
||||
st.setFileSizeBytes(0);
|
||||
st.setSizeLimit(1_000_000L);
|
||||
st.setUpdatedAtMs(System.currentTimeMillis());
|
||||
stateDAO.upsert(st);
|
||||
log.warn("GetUser: восстановлена запись blockchain_state для login={}, blockchainName={}",
|
||||
u.getLogin(), u.getBlockchainName());
|
||||
}
|
||||
|
||||
int lastNum = st.getLastBlockNumber();
|
||||
byte[] lastHash = st.getLastBlockHash();
|
||||
if (lastHash == null || lastHash.length != 32) {
|
||||
lastHash = new byte[32];
|
||||
}
|
||||
resp.setServerLastGlobalNumber(lastNum);
|
||||
resp.setServerLastGlobalHash(toHex32(lastHash));
|
||||
|
||||
log.info("✅ GetUser: found login={}, blockchainName={}", u.getLogin(), u.getBlockchainName());
|
||||
return resp;
|
||||
|
||||
@@ -81,4 +111,16 @@ public class Net_GetUser_Handler implements JsonMessageHandler {
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
private static String toHex32(byte[] bytes32) {
|
||||
byte[] b = (bytes32 == null) ? new byte[32] : Arrays.copyOf(bytes32, 32);
|
||||
final char[] HEX = "0123456789abcdef".toCharArray();
|
||||
char[] out = new char[64];
|
||||
for (int i = 0; i < 32; i++) {
|
||||
int v = b[i] & 0xFF;
|
||||
out[i * 2] = HEX[v >>> 4];
|
||||
out[i * 2 + 1] = HEX[v & 0x0F];
|
||||
}
|
||||
return new String(out);
|
||||
}
|
||||
}
|
||||
|
||||
+9
-1
@@ -39,6 +39,8 @@ public class Net_GetUser_Response extends Net_Response {
|
||||
private String solanaKey;
|
||||
private String blockchainKey;
|
||||
private String deviceKey;
|
||||
private Integer serverLastGlobalNumber;
|
||||
private String serverLastGlobalHash;
|
||||
|
||||
public Boolean getExists() { return exists; }
|
||||
public void setExists(Boolean exists) { this.exists = exists; }
|
||||
@@ -57,4 +59,10 @@ public class Net_GetUser_Response extends Net_Response {
|
||||
|
||||
public String getDeviceKey() { return deviceKey; }
|
||||
public void setDeviceKey(String deviceKey) { this.deviceKey = deviceKey; }
|
||||
}
|
||||
|
||||
public Integer getServerLastGlobalNumber() { return serverLastGlobalNumber; }
|
||||
public void setServerLastGlobalNumber(Integer serverLastGlobalNumber) { this.serverLastGlobalNumber = serverLastGlobalNumber; }
|
||||
|
||||
public String getServerLastGlobalHash() { return serverLastGlobalHash; }
|
||||
public void setServerLastGlobalHash(String serverLastGlobalHash) { this.serverLastGlobalHash = serverLastGlobalHash; }
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user