// Exact Rust translation of LibreMetaverse.Tests/EstateToolsTests.cs.
// Source SHA-256: 2f1867304e21e72d20fbeed98e7705528797947eb3115f84f80aa6adc2f3f88e

use libremetaverse::GridClient;
use libremetaverse_compat_tests::{LiveTestRuntime, login_live_grid, logout_live_grid};
use libremetaverse_types::UUID;
use std::sync::mpsc;
use std::time::Duration;

struct LiveEstate {
    client: GridClient,
    runtime: LiveTestRuntime,
}

impl LiveEstate {
    fn login() -> Self {
        let runtime = LiveTestRuntime::new();
        let mut client = GridClient::new().expect("GridClient constructor");
        let network = login_live_grid(
            &runtime,
            &mut client,
            "Unit Test Framework",
            "admin@radegast.life",
        );
        let current = network.current_sim().expect("CurrentSim after login");
        assert!(
            !current.name.is_empty(),
            "OpenSim region handshake returned an empty simulator name"
        );
        Self { client, runtime }
    }
}

impl Drop for LiveEstate {
    fn drop(&mut self) {
        logout_live_grid(&self.runtime, &mut self.client);
    }
}

// parity-case: LibreMetaverse.Tests/EstateToolsTests.cs::EstateToolsTests.RequestConvenant::test d8d752dd6e53477e4c66bcb5d0e3ec1021a9b3ceda1f689f59b5e606e1713729 ignored-live
#[test]
#[cfg_attr(
    not(live_grid_credentials),
    ignore = "requires GRID_USER, GRID_PASSWORD, and GRID_LOGIN_URL in the environment or workspace .env; performs only a reversible read-only covenant request"
)]
fn request_covenant() {
    let live = LiveEstate::login();
    let estate = live.client.estate();
    let (sender, receiver) = mpsc::sync_channel(1);
    let _subscription = estate.subscribe_estate_covenant_reply(std::sync::Arc::new(move |reply| {
        let _ = sender.send((reply.estate_name(), reply.covenant_id()));
    }));
    estate
        .request_covenant()
        .expect("EstateTools RequestCovenant");
    let (name, covenant) = receiver
        .recv_timeout(Duration::from_secs(10))
        .expect("timeout waiting for estate covenant reply after 10 seconds");
    assert!(!name.is_empty());
    assert_ne!(covenant, UUID::zero());
}
