///|
/// Converts a MoonBit string into a UTF-8 C string for native FFI calls.
fn to_cstr(value : String) -> Bytes {
let bytes = @utf8.encode(value).to_array()
bytes.push(0)
Bytes::from_array(bytes)
}
///|
/// Maps the public severity enum to the native integer level used by the backends.
fn level_to_native_code(level : NotificationLevel) -> Int {
match level {
Info => 0
Warning => 1
Error => 2
}
}
///|
/// Returns the backend selected by the native build.
extern "C" fn notification_backend_kind_ffi() -> Int = "desktop_notification_backend_kind"
///|
/// Returns whether the current runtime can deliver notifications.
extern "C" fn notification_is_supported_ffi() -> Bool = "desktop_notification_is_supported"
///|
/// Invokes the native backend selected at compile time.
#borrow(title, body)
extern "C" fn show_notification_ffi(
window_handle : Int64,
title : Bytes,
body : Bytes,
level : Int,
) -> Bool = "desktop_notification_show"
///|
/// Returns whether the current build/runtime can attempt to deliver a notification.
fn backend_is_supported() -> Bool {
notification_is_supported_ffi()
}
///|
/// Returns the support error for the active native backend.
fn backend_support_error() -> String {
match notification_backend_kind_ffi() {
1 => "desktop notifications are unavailable on the current Windows runtime"
2 => "desktop notifications on macOS require /usr/bin/osascript"
3 => "desktop notifications on Linux require the notify-send executable"
_ => "desktop notifications are not supported on this platform"
}
}
///|
/// Executes the selected native backend and normalizes native failures.
fn backend_deliver(
window_handle : Int64,
title : String,
body : String,
level : NotificationLevel,
) -> Result[Unit, String] {
if show_notification_ffi(
window_handle,
to_cstr(title),
to_cstr(body),
level_to_native_code(level),
) {
Ok(())
} else {
Err("native notification delivery failed")
}
}