fix期权复盘同步后无变化不重绘,避免进页闪动。

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
dekun
2026-10-13 13:52:35 +08:00
parent 03acecf015
commit b62107fbd5
2 changed files with 85 additions and 10 deletions
+84 -9
View File
@@ -32,11 +32,68 @@
var tradesPages = 1; var tradesPages = 1;
var reviewedPage = 0; var reviewedPage = 0;
var reviewedPages = 1; var reviewedPages = 1;
var tradesListFp = "";
var reviewedListFp = "";
var statsFp = "";
function $(id) { function $(id) {
return document.getElementById(id); return document.getElementById(id);
} }
function listFingerprint(kind, data, rows) {
var parts = [
kind,
activeSource,
String((data && data.total) || 0),
String((data && data.page) || 0),
String((data && data.pages) || 0),
];
(rows || []).forEach(function (t) {
var e = t.entry || {};
parts.push(
[
t.id,
t.realized_pnl_total,
t.profit_rate,
t.initial_premium_usdt,
t.option_fee_usdt,
t.status_raw,
t.reviewed ? 1 : 0,
t.opened_at,
t.closed_at,
t.hold_seconds,
t.reviewed_at,
t.strategy_tag || e.strategy_tag,
t.result_tag || e.result_tag,
t.direction_view || e.direction_view,
t.entry_logic || e.entry_logic,
t.source_label || t.source_type,
t.inst_id,
t.underlying,
t.direction,
t.plan_close_reason,
].join("\u001f")
);
});
return parts.join("\u001e");
}
function statsFingerprint(data) {
try {
return JSON.stringify({
kpi: data.kpi || {},
by_source_type: data.by_source_type || [],
by_underlying: data.by_underlying || [],
by_strategy: data.by_strategy || [],
by_close_reason: data.by_close_reason || [],
by_hold_bucket: data.by_hold_bucket || [],
by_opt_type: data.by_opt_type || [],
});
} catch (_) {
return String(Date.now());
}
}
function escapeHtml(s) { function escapeHtml(s) {
return String(s == null ? "" : s) return String(s == null ? "" : s)
.replace(/&/g, "&amp;") .replace(/&/g, "&amp;")
@@ -203,7 +260,7 @@
setSyncStatus("读取本地记录…"); setSyncStatus("读取本地记录…");
loadTrades({ sync: false }); loadTrades({ sync: false });
loadReviewed({ sync: false }); loadReviewed({ sync: false });
loadStats(); loadStats({ soft: false });
backgroundSync(); backgroundSync();
} }
@@ -221,7 +278,7 @@
setSyncStatus("本地记录已加载"); setSyncStatus("本地记录已加载");
loadTrades({ sync: false, soft: true }); loadTrades({ sync: false, soft: true });
loadReviewed({ sync: false, soft: true }); loadReviewed({ sync: false, soft: true });
loadStats(); loadStats({ soft: true });
}) })
.catch(function () { .catch(function () {
setSyncStatus("同步跳过,已显示本地缓存"); setSyncStatus("同步跳过,已显示本地缓存");
@@ -379,12 +436,8 @@
function beginListLoad(wrapId, soft) { function beginListLoad(wrapId, soft) {
var wrap = $(wrapId); var wrap = $(wrapId);
if (!wrap) return null; if (!wrap) return null;
if (soft) { // soft 刷新不打半透明:无变化时也不应闪;有变化时静默换表
if (!wrap.style.minHeight) { if (!soft) {
wrap.style.minHeight = Math.max(wrap.offsetHeight, 1) + "px";
}
wrap.classList.add("or-list-loading");
} else {
wrap.classList.remove("or-list-loading"); wrap.classList.remove("or-list-loading");
wrap.style.minHeight = ""; wrap.style.minHeight = "";
} }
@@ -405,6 +458,7 @@
if (!tbody) return; if (!tbody) return;
var wrap = beginListLoad("or-trades-wrap", soft); var wrap = beginListLoad("or-trades-wrap", soft);
if (!soft) { if (!soft) {
tradesListFp = "";
tbody.innerHTML = '<tr><td colspan="10" class="muted">加载中…</td></tr>'; tbody.innerHTML = '<tr><td colspan="10" class="muted">加载中…</td></tr>';
} }
var p = baseQs(); var p = baseQs();
@@ -419,6 +473,7 @@
.then(function (data) { .then(function (data) {
if (doSync) setSyncStatus("本地记录已加载"); if (doSync) setSyncStatus("本地记录已加载");
if (!data.ok) { if (!data.ok) {
tradesListFp = "";
tbody.innerHTML = '<tr><td colspan="10" class="muted">加载失败</td></tr>'; tbody.innerHTML = '<tr><td colspan="10" class="muted">加载失败</td></tr>';
endListLoad(wrap); endListLoad(wrap);
return; return;
@@ -428,6 +483,12 @@
return; return;
} }
var rows = data.trades || []; var rows = data.trades || [];
var fp = listFingerprint("trades", data, rows);
if (soft && fp === tradesListFp) {
endListLoad(wrap);
return;
}
tradesListFp = fp;
tradesCache = {}; tradesCache = {};
if (!rows.length) { if (!rows.length) {
tbody.innerHTML = tbody.innerHTML =
@@ -546,6 +607,7 @@
if (!tbody) return; if (!tbody) return;
var wrap = beginListLoad("or-reviewed-wrap", soft); var wrap = beginListLoad("or-reviewed-wrap", soft);
if (!soft) { if (!soft) {
reviewedListFp = "";
tbody.innerHTML = '<tr><td colspan="13" class="muted">加载中…</td></tr>'; tbody.innerHTML = '<tr><td colspan="13" class="muted">加载中…</td></tr>';
} }
var p = baseQs(); var p = baseQs();
@@ -559,6 +621,7 @@
}) })
.then(function (data) { .then(function (data) {
if (!data.ok) { if (!data.ok) {
reviewedListFp = "";
tbody.innerHTML = '<tr><td colspan="13" class="muted">加载失败</td></tr>'; tbody.innerHTML = '<tr><td colspan="13" class="muted">加载失败</td></tr>';
endListLoad(wrap); endListLoad(wrap);
return; return;
@@ -568,6 +631,12 @@
return; return;
} }
var rows = data.trades || []; var rows = data.trades || [];
var fp = listFingerprint("reviewed", data, rows);
if (soft && fp === reviewedListFp) {
endListLoad(wrap);
return;
}
reviewedListFp = fp;
reviewedCache = {}; reviewedCache = {};
if (!rows.length) { if (!rows.length) {
tbody.innerHTML = '<tr><td colspan="13" class="muted">暂无复盘记录</td></tr>'; tbody.innerHTML = '<tr><td colspan="13" class="muted">暂无复盘记录</td></tr>';
@@ -1024,10 +1093,13 @@
); );
} }
function loadStats() { function loadStats(opts) {
opts = opts || {};
var soft = !!opts.soft;
var kpi = $("or-kpi"); var kpi = $("or-kpi");
var groups = $("or-stats-groups"); var groups = $("or-stats-groups");
if (!kpi || !groups) return; if (!kpi || !groups) return;
if (!soft) statsFp = "";
// 与 trades?sync=1 并行时不再二次同步,避免 SQLite database is locked // 与 trades?sync=1 并行时不再二次同步,避免 SQLite database is locked
var qs = baseQs(); var qs = baseQs();
qs.set("sync", "0"); qs.set("sync", "0");
@@ -1037,6 +1109,9 @@
}) })
.then(function (data) { .then(function (data) {
if (!data.ok) return; if (!data.ok) return;
var fp = statsFingerprint(data);
if (soft && fp === statsFp) return;
statsFp = fp;
var k = data.kpi || {}; var k = data.kpi || {};
kpi.innerHTML = [ kpi.innerHTML = [
["笔数", k.total], ["笔数", k.total],
@@ -465,4 +465,4 @@
</section> </section>
</div> </div>
<script src="/static/options_review.js?v=28"></script> <script src="/static/options_review.js?v=29"></script>