feat(wallet): persist history and surface pending sends

Add an encrypted SQLite transaction history cache with cached tip metadata and
per-address shielded scan progress so startup and full refreshes avoid
re-scanning every z-address while still invalidating on wallet/address/rescan
changes.

Improve wallet history loading by paging transparent transactions, preserving
cached shielded and sent rows, keeping recent/unconfirmed activity visible, and
classifying mining-address receives. Show z_sendmany opid sends immediately in
History and Overview, pin pending rows through refreshes, and apply optimistic
address/balance debits until opids resolve.

Add timestamped RPC console tracing by source/method without logging params or
results, reduce redundant refresh/RPC calls, and cache Explorer recent block
summaries in SQLite.

Expand focused tests for transaction cache encryption, scan-progress
persistence/invalidation, history preservation, operation-status parsing,
pending send visibility, and Explorer/RPC refresh behavior.
This commit is contained in:
2026-05-05 03:22:14 -05:00
parent 948ef419ac
commit 975743f754
43 changed files with 3732 additions and 702 deletions

View File

@@ -110,6 +110,32 @@ FetchContent_Declare(
)
FetchContent_MakeAvailable(tomlplusplus)
# SQLite amalgamation - local Explorer block-summary cache
FetchContent_Declare(
sqlite3
URL https://www.sqlite.org/2024/sqlite-amalgamation-3450300.zip
URL_HASH SHA256=ea170e73e447703e8359308ca2e4366a3ae0c4304a8665896f068c736781c651
)
FetchContent_GetProperties(sqlite3)
if(NOT sqlite3_POPULATED)
FetchContent_Populate(sqlite3)
endif()
file(GLOB SQLITE3_AMALGAMATION_C CONFIGURE_DEPENDS
${sqlite3_SOURCE_DIR}/sqlite3.c
${sqlite3_SOURCE_DIR}/*/sqlite3.c
)
if(NOT SQLITE3_AMALGAMATION_C)
message(FATAL_ERROR "SQLite amalgamation source not found")
endif()
list(GET SQLITE3_AMALGAMATION_C 0 SQLITE3_SOURCE_FILE)
get_filename_component(SQLITE3_INCLUDE_DIR ${SQLITE3_SOURCE_FILE} DIRECTORY)
add_library(sqlite3_amalgamation STATIC ${SQLITE3_SOURCE_FILE})
target_include_directories(sqlite3_amalgamation PUBLIC ${SQLITE3_INCLUDE_DIR})
target_compile_definitions(sqlite3_amalgamation PRIVATE
SQLITE_THREADSAFE=1
SQLITE_OMIT_LOAD_EXTENSION
)
# libcurl for HTTPS RPC connections (more reliable than cpp-httplib with OpenSSL 3.x)
if(WIN32)
# For Windows cross-compilation, fetch and build libcurl statically
@@ -255,8 +281,10 @@ set(APP_SOURCES
src/services/wallet_security_workflow.cpp
src/services/wallet_security_workflow_executor.cpp
src/data/wallet_state.cpp
src/data/transaction_history_cache.cpp
src/ui/theme.cpp
src/ui/theme_loader.cpp
src/ui/explorer/explorer_block_cache.cpp
src/ui/material/color_theme.cpp
src/ui/material/typography.cpp
src/ui/notifications.cpp
@@ -354,8 +382,10 @@ set(APP_HEADERS
src/services/wallet_security_workflow_executor.h
src/config/version.h
src/data/wallet_state.h
src/data/transaction_history_cache.h
src/ui/theme.h
src/ui/theme_loader.h
src/ui/explorer/explorer_block_cache.h
src/ui/notifications.h
src/ui/windows/main_window.h
src/ui/windows/balance_tab.h
@@ -507,6 +537,7 @@ target_link_libraries(ObsidianDragon PRIVATE
SDL3::SDL3
nlohmann_json::nlohmann_json
tomlplusplus::tomlplusplus
sqlite3_amalgamation
${CURL_LIBRARIES}
${SODIUM_LIBRARY}
)
@@ -712,6 +743,7 @@ if(BUILD_TESTING)
src/services/wallet_security_controller.cpp
src/services/wallet_security_workflow.cpp
src/services/wallet_security_workflow_executor.cpp
src/ui/explorer/explorer_block_cache.cpp
src/ui/windows/balance_address_list.cpp
src/ui/windows/balance_recent_tx.cpp
src/ui/windows/console_input_model.cpp
@@ -723,6 +755,7 @@ if(BUILD_TESTING)
src/util/payment_uri.cpp
src/util/amount_format.cpp
src/data/wallet_state.cpp
src/data/transaction_history_cache.cpp
src/daemon/lifecycle_adapters.cpp
src/rpc/connection.cpp
src/resources/embedded_resources.cpp
@@ -742,6 +775,7 @@ if(BUILD_TESTING)
target_link_libraries(ObsidianDragonTests PRIVATE
nlohmann_json::nlohmann_json
sqlite3_amalgamation
${SODIUM_LIBRARY}
)