Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
51 changes: 45 additions & 6 deletions packages/rs-sdk-ffi/src/sdk.rs
Original file line number Diff line number Diff line change
Expand Up @@ -334,10 +334,47 @@ pub unsafe extern "C" fn dash_sdk_create_trusted(config: *const DashSDKConfig) -
"dash_sdk_create_trusted: creating trusted context provider"
);

// Create trusted context provider
// For regtest, use the quorum sidecar at localhost:22444 (dashmate Docker default)
let is_local = matches!(network, Network::Regtest);
let trusted_provider = if is_local {
// Create trusted context provider. Resolution order for the quorum
// lookup base URL:
// 1. Caller-provided `config.quorum_url` (highest priority — required
// for devnet, also usable for non-default mainnet/testnet shards).
// 2. Regtest fallback to the local quorum sidecar `127.0.0.1:22444`
// (the dashmate Docker default).
// 3. Network-derived default (mainnet/testnet only).
let explicit_quorum_url: Option<String> = if config.quorum_url.is_null() {
None
} else {
match unsafe { CStr::from_ptr(config.quorum_url) }.to_str() {
Ok(s) if !s.is_empty() => Some(s.to_string()),
Ok(_) => None,
Err(e) => {
return DashSDKResult::error(DashSDKError::new(
DashSDKErrorCode::InvalidParameter,
format!("Invalid quorum URL string: {}", e),
))
}
}
};
let trusted_provider = if let Some(quorum_url) = explicit_quorum_url {
info!(
quorum_url = %quorum_url,
"dash_sdk_create_trusted: using caller-provided quorum URL"
);
match rs_sdk_trusted_context_provider::TrustedHttpContextProvider::new_with_url(
network,
quorum_url,
std::num::NonZeroUsize::new(100).unwrap(),
) {
Ok(provider) => Arc::new(provider),
Err(e) => {
error!(error = %e, "dash_sdk_create_trusted: failed to create context provider from override URL");
return DashSDKResult::error(DashSDKError::new(
DashSDKErrorCode::InternalError,
format!("Failed to create context provider: {}", e),
));
}
}
} else if matches!(network, Network::Regtest) {
info!("dash_sdk_create_trusted: using local quorum sidecar for regtest");
match rs_sdk_trusted_context_provider::TrustedHttpContextProvider::new_with_url(
network,
Expand Down Expand Up @@ -376,10 +413,11 @@ pub unsafe extern "C" fn dash_sdk_create_trusted(config: *const DashSDKConfig) -
}
};

// Parse DAPI addresses - for trusted setup, we always need real addresses
// Parse DAPI addresses - for trusted setup, we always need real addresses.
// Devnet/regtest have no built-in defaults; callers must supply
// `dapi_addresses` (and typically `quorum_url`) for those networks.
let builder = if config.dapi_addresses.is_null() {
info!("dash_sdk_create_trusted: no DAPI addresses provided, using defaults for network");
// Use default addresses for the network
match network {
Network::Testnet => SdkBuilder::new_testnet(),
Network::Mainnet => SdkBuilder::new_mainnet(),
Expand Down Expand Up @@ -600,6 +638,7 @@ pub unsafe extern "C" fn dash_sdk_create_with_callbacks(
skip_asset_lock_proof_verification: config_ref.skip_asset_lock_proof_verification,
request_retry_count: config_ref.request_retry_count,
request_timeout_ms: config_ref.request_timeout_ms,
quorum_url: config_ref.quorum_url,
platform_version: config_ref.platform_version,
},
Comment thread
shumkov marked this conversation as resolved.
context_provider: context_provider_handle,
Expand Down
1 change: 1 addition & 0 deletions packages/rs-sdk-ffi/src/token/claim.rs
Original file line number Diff line number Diff line change
Expand Up @@ -203,6 +203,7 @@ mod tests {
skip_asset_lock_proof_verification: false,
request_retry_count: 3,
request_timeout_ms: 5000,
quorum_url: ptr::null(),
platform_version: 0,
};

Expand Down
1 change: 1 addition & 0 deletions packages/rs-sdk-ffi/src/token/emergency_action.rs
Original file line number Diff line number Diff line change
Expand Up @@ -210,6 +210,7 @@ mod tests {
skip_asset_lock_proof_verification: false,
request_retry_count: 3,
request_timeout_ms: 5000,
quorum_url: ptr::null(),
platform_version: 0,
};

Expand Down
1 change: 1 addition & 0 deletions packages/rs-sdk-ffi/src/token/freeze.rs
Original file line number Diff line number Diff line change
Expand Up @@ -212,6 +212,7 @@ mod tests {
skip_asset_lock_proof_verification: false,
request_retry_count: 3,
request_timeout_ms: 5000,
quorum_url: ptr::null(),
platform_version: 0,
};

Expand Down
16 changes: 16 additions & 0 deletions packages/rs-sdk-ffi/src/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,22 @@ pub struct DashSDKConfig {
pub request_retry_count: u32,
/// Timeout for requests in milliseconds
pub request_timeout_ms: u64,
/// Optional override for the trusted-context-provider quorum lookup base URL
/// (e.g., `"https://quorums.devnet.example.networks.dash.org"` or
/// `"http://127.0.0.1:22444"`). When null/empty, the provider uses the
/// default endpoint derived from `network` (mainnet/testnet only — devnet
/// needs an explicit URL, regtest defaults to the local sidecar).
///
/// **Only honored on the `dash_sdk_create_trusted` path** — that's the
/// path that builds a `TrustedHttpContextProvider`, which is the
/// component that actually performs quorum lookups. The callback-based
/// path (`dash_sdk_create_with_callbacks`) uses `CallbackContextProvider`
/// and ignores this field entirely; non-null values there are silently
/// dropped.
///
/// Same lifetime contract as `dapi_addresses`: borrowed, copied
/// immediately, caller may free after the FFI call returns.
pub quorum_url: *const c_char,
/// Pin to a specific Dash Platform protocol version.
/// `0` keeps the SDK default (auto-detect / latest); any non-zero value
/// is forwarded to `SdkBuilder::with_version` and rejected if unknown.
Expand Down
1 change: 1 addition & 0 deletions packages/rs-sdk-ffi/tests/context_provider_test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,7 @@ mod tests {
skip_asset_lock_proof_verification: false,
request_retry_count: 3,
request_timeout_ms: 30000,
quorum_url: ptr::null(),
platform_version: 0,
};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,12 @@ public enum LoggingPreferences {
public enum SDKLogger {
public static func log(_ message: String, minimumLevel level: LoggingPreset = .medium) {
guard LoggingPreferences.allows(level) else { return }
// Mirror to NSLog (unified logging) in addition to stdout so
// `xcrun simctl spawn booted log stream` and Console.app see
// the message even when no Xcode debugger is attached. The
// `print` path is preserved because the dev loop still wants
// stdout for in-Xcode use; NSLog goes to os_log.
NSLog("%@", message)
Swift.print(message)
}

Expand Down
Loading
Loading