// This file was generated by gir (https://github.com/gtk-rs/gir)
// from
// from gir-files (https://github.com/gtk-rs/gir-files.git)
// DO NOT EDIT
#![allow(deprecated)]

#[cfg(any(feature = "v3_1", feature = "dox"))]
#[cfg_attr(feature = "dox", doc(cfg(feature = "v3_1")))]
use crate::Resource;
use crate::{
    Batch, NamespaceManager, Notifier, SparqlConnectionFlags, SparqlCursor, SparqlStatement,
};
use glib::{prelude::*, translate::*};
use std::{boxed::Box as Box_, fmt, pin::Pin, ptr};

glib::wrapper! {
    #[doc(alias = "TrackerSparqlConnection")]
    pub struct SparqlConnection(Object<ffi::TrackerSparqlConnection, ffi::TrackerSparqlConnectionClass>);

    match fn {
        type_ => || ffi::tracker_sparql_connection_get_type(),
    }
}

impl SparqlConnection {
    #[doc(alias = "tracker_sparql_connection_bus_new")]
    pub fn bus_new(
        service_name: &str,
        object_path: Option<&str>,
        dbus_connection: Option<&gio::DBusConnection>,
    ) -> Result<SparqlConnection, glib::Error> {
        assert_initialized_main_thread!();
        unsafe {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_bus_new(
                service_name.to_glib_none().0,
                object_path.to_glib_none().0,
                dbus_connection.to_glib_none().0,
                &mut error,
            );
            if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    #[doc(alias = "tracker_sparql_connection_new")]
    pub fn new(
        flags: SparqlConnectionFlags,
        store: Option<&impl IsA<gio::File>>,
        ontology: Option<&impl IsA<gio::File>>,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
    ) -> Result<SparqlConnection, glib::Error> {
        assert_initialized_main_thread!();
        unsafe {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_new(
                flags.into_glib(),
                store.map(|p| p.as_ref()).to_glib_none().0,
                ontology.map(|p| p.as_ref()).to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                &mut error,
            );
            if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    #[doc(alias = "tracker_sparql_connection_remote_new")]
    pub fn remote_new(uri_base: &str) -> SparqlConnection {
        assert_initialized_main_thread!();
        unsafe {
            from_glib_full(ffi::tracker_sparql_connection_remote_new(
                uri_base.to_glib_none().0,
            ))
        }
    }

    #[doc(alias = "tracker_sparql_connection_close")]
    pub fn close(&self) {
        unsafe {
            ffi::tracker_sparql_connection_close(self.to_glib_none().0);
        }
    }

    #[doc(alias = "tracker_sparql_connection_close_async")]
    pub fn close_async<P: FnOnce(Result<(), glib::Error>) + 'static>(
        &self,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
        callback: P,
    ) {
        let main_context = glib::MainContext::ref_thread_default();
        let is_main_context_owner = main_context.is_owner();
        let has_acquired_main_context = (!is_main_context_owner)
            .then(|| main_context.acquire().ok())
            .flatten();
        assert!(
            is_main_context_owner || has_acquired_main_context.is_some(),
            "Async operations only allowed if the thread is owning the MainContext"
        );

        let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
            Box_::new(glib::thread_guard::ThreadGuard::new(callback));
        unsafe extern "C" fn close_async_trampoline<
            P: FnOnce(Result<(), glib::Error>) + 'static,
        >(
            _source_object: *mut glib::gobject_ffi::GObject,
            res: *mut gio::ffi::GAsyncResult,
            user_data: glib::ffi::gpointer,
        ) {
            let mut error = ptr::null_mut();
            let _ = ffi::tracker_sparql_connection_close_finish(
                _source_object as *mut _,
                res,
                &mut error,
            );
            let result = if error.is_null() {
                Ok(())
            } else {
                Err(from_glib_full(error))
            };
            let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
                Box_::from_raw(user_data as *mut _);
            let callback: P = callback.into_inner();
            callback(result);
        }
        let callback = close_async_trampoline::<P>;
        unsafe {
            ffi::tracker_sparql_connection_close_async(
                self.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                Some(callback),
                Box_::into_raw(user_data) as *mut _,
            );
        }
    }

    pub fn close_future(
        &self,
    ) -> Pin<Box_<dyn std::future::Future<Output = Result<(), glib::Error>> + 'static>> {
        Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
            obj.close_async(Some(cancellable), move |res| {
                send.resolve(res);
            });
        }))
    }

    #[doc(alias = "tracker_sparql_connection_create_batch")]
    pub fn create_batch(&self) -> Option<Batch> {
        unsafe {
            from_glib_full(ffi::tracker_sparql_connection_create_batch(
                self.to_glib_none().0,
            ))
        }
    }

    #[doc(alias = "tracker_sparql_connection_create_notifier")]
    pub fn create_notifier(&self) -> Option<Notifier> {
        unsafe {
            from_glib_full(ffi::tracker_sparql_connection_create_notifier(
                self.to_glib_none().0,
            ))
        }
    }

    //#[cfg(any(feature = "v3_4", feature = "dox"))]
    //#[cfg_attr(feature = "dox", doc(cfg(feature = "v3_4")))]
    //#[doc(alias = "tracker_sparql_connection_deserialize_async")]
    //pub fn deserialize_async<P: FnOnce(Result<(), glib::Error>) + 'static>(&self, flags: /*Ignored*/DeserializeFlags, format: /*Ignored*/RdfFormat, default_graph: &str, stream: &impl IsA<gio::InputStream>, cancellable: Option<&impl IsA<gio::Cancellable>>, callback: P) {
    //    unsafe { TODO: call ffi:tracker_sparql_connection_deserialize_async() }
    //}

    //
    //#[cfg(any(feature = "v3_4", feature = "dox"))]
    //#[cfg_attr(feature = "dox", doc(cfg(feature = "v3_4")))]
    //pub fn deserialize_future(&self, flags: /*Ignored*/DeserializeFlags, format: /*Ignored*/RdfFormat, default_graph: &str, stream: &(impl IsA<gio::InputStream> + Clone + 'static)) -> Pin<Box_<dyn std::future::Future<Output = Result<(), glib::Error>> + 'static>> {

    //let default_graph = String::from(default_graph);
    //let stream = stream.clone();
    //Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
    //    obj.deserialize_async(
    //        flags,
    //        format,
    //        &default_graph,
    //        &stream,
    //        Some(cancellable),
    //        move |res| {
    //            send.resolve(res);
    //        },
    //    );
    //}))
    //}

    #[doc(alias = "tracker_sparql_connection_get_namespace_manager")]
    #[doc(alias = "get_namespace_manager")]
    pub fn namespace_manager(&self) -> Option<NamespaceManager> {
        unsafe {
            from_glib_none(ffi::tracker_sparql_connection_get_namespace_manager(
                self.to_glib_none().0,
            ))
        }
    }

    #[cfg(any(feature = "v3_3", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_3")))]
    #[doc(alias = "tracker_sparql_connection_load_statement_from_gresource")]
    pub fn load_statement_from_gresource(
        &self,
        resource_path: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
    ) -> Result<Option<SparqlStatement>, glib::Error> {
        unsafe {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_load_statement_from_gresource(
                self.to_glib_none().0,
                resource_path.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                &mut error,
            );
            if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    #[cfg(any(feature = "v3_3", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_3")))]
    #[doc(alias = "tracker_sparql_connection_map_connection")]
    pub fn map_connection(&self, handle_name: &str, service_connection: &SparqlConnection) {
        unsafe {
            ffi::tracker_sparql_connection_map_connection(
                self.to_glib_none().0,
                handle_name.to_glib_none().0,
                service_connection.to_glib_none().0,
            );
        }
    }

    #[doc(alias = "tracker_sparql_connection_query")]
    pub fn query(
        &self,
        sparql: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
    ) -> Result<SparqlCursor, glib::Error> {
        unsafe {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_query(
                self.to_glib_none().0,
                sparql.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                &mut error,
            );
            if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    #[doc(alias = "tracker_sparql_connection_query_async")]
    pub fn query_async<P: FnOnce(Result<SparqlCursor, glib::Error>) + 'static>(
        &self,
        sparql: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
        callback: P,
    ) {
        let main_context = glib::MainContext::ref_thread_default();
        let is_main_context_owner = main_context.is_owner();
        let has_acquired_main_context = (!is_main_context_owner)
            .then(|| main_context.acquire().ok())
            .flatten();
        assert!(
            is_main_context_owner || has_acquired_main_context.is_some(),
            "Async operations only allowed if the thread is owning the MainContext"
        );

        let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
            Box_::new(glib::thread_guard::ThreadGuard::new(callback));
        unsafe extern "C" fn query_async_trampoline<
            P: FnOnce(Result<SparqlCursor, glib::Error>) + 'static,
        >(
            _source_object: *mut glib::gobject_ffi::GObject,
            res: *mut gio::ffi::GAsyncResult,
            user_data: glib::ffi::gpointer,
        ) {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_query_finish(
                _source_object as *mut _,
                res,
                &mut error,
            );
            let result = if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            };
            let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
                Box_::from_raw(user_data as *mut _);
            let callback: P = callback.into_inner();
            callback(result);
        }
        let callback = query_async_trampoline::<P>;
        unsafe {
            ffi::tracker_sparql_connection_query_async(
                self.to_glib_none().0,
                sparql.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                Some(callback),
                Box_::into_raw(user_data) as *mut _,
            );
        }
    }

    pub fn query_future(
        &self,
        sparql: &str,
    ) -> Pin<Box_<dyn std::future::Future<Output = Result<SparqlCursor, glib::Error>> + 'static>>
    {
        let sparql = String::from(sparql);
        Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
            obj.query_async(&sparql, Some(cancellable), move |res| {
                send.resolve(res);
            });
        }))
    }

    #[doc(alias = "tracker_sparql_connection_query_statement")]
    pub fn query_statement(
        &self,
        sparql: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
    ) -> Result<Option<SparqlStatement>, glib::Error> {
        unsafe {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_query_statement(
                self.to_glib_none().0,
                sparql.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                &mut error,
            );
            if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    //#[cfg(any(feature = "v3_3", feature = "dox"))]
    //#[cfg_attr(feature = "dox", doc(cfg(feature = "v3_3")))]
    //#[doc(alias = "tracker_sparql_connection_serialize_async")]
    //pub fn serialize_async<P: FnOnce(Result<gio::InputStream, glib::Error>) + 'static>(&self, flags: /*Ignored*/SerializeFlags, format: /*Ignored*/RdfFormat, query: &str, cancellable: Option<&impl IsA<gio::Cancellable>>, callback: P) {
    //    unsafe { TODO: call ffi:tracker_sparql_connection_serialize_async() }
    //}

    //
    //#[cfg(any(feature = "v3_3", feature = "dox"))]
    //#[cfg_attr(feature = "dox", doc(cfg(feature = "v3_3")))]
    //pub fn serialize_future(&self, flags: /*Ignored*/SerializeFlags, format: /*Ignored*/RdfFormat, query: &str) -> Pin<Box_<dyn std::future::Future<Output = Result<gio::InputStream, glib::Error>> + 'static>> {

    //let query = String::from(query);
    //Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
    //    obj.serialize_async(
    //        flags,
    //        format,
    //        &query,
    //        Some(cancellable),
    //        move |res| {
    //            send.resolve(res);
    //        },
    //    );
    //}))
    //}

    #[doc(alias = "tracker_sparql_connection_update_async")]
    pub fn update_async<P: FnOnce(Result<(), glib::Error>) + 'static>(
        &self,
        sparql: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
        callback: P,
    ) {
        let main_context = glib::MainContext::ref_thread_default();
        let is_main_context_owner = main_context.is_owner();
        let has_acquired_main_context = (!is_main_context_owner)
            .then(|| main_context.acquire().ok())
            .flatten();
        assert!(
            is_main_context_owner || has_acquired_main_context.is_some(),
            "Async operations only allowed if the thread is owning the MainContext"
        );

        let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
            Box_::new(glib::thread_guard::ThreadGuard::new(callback));
        unsafe extern "C" fn update_async_trampoline<
            P: FnOnce(Result<(), glib::Error>) + 'static,
        >(
            _source_object: *mut glib::gobject_ffi::GObject,
            res: *mut gio::ffi::GAsyncResult,
            user_data: glib::ffi::gpointer,
        ) {
            let mut error = ptr::null_mut();
            let _ = ffi::tracker_sparql_connection_update_finish(
                _source_object as *mut _,
                res,
                &mut error,
            );
            let result = if error.is_null() {
                Ok(())
            } else {
                Err(from_glib_full(error))
            };
            let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
                Box_::from_raw(user_data as *mut _);
            let callback: P = callback.into_inner();
            callback(result);
        }
        let callback = update_async_trampoline::<P>;
        unsafe {
            ffi::tracker_sparql_connection_update_async(
                self.to_glib_none().0,
                sparql.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                Some(callback),
                Box_::into_raw(user_data) as *mut _,
            );
        }
    }

    pub fn update_future(
        &self,
        sparql: &str,
    ) -> Pin<Box_<dyn std::future::Future<Output = Result<(), glib::Error>> + 'static>> {
        let sparql = String::from(sparql);
        Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
            obj.update_async(&sparql, Some(cancellable), move |res| {
                send.resolve(res);
            });
        }))
    }

    #[cfg_attr(feature = "v3_5", deprecated = "Since 3.5")]
    #[allow(deprecated)]
    #[doc(alias = "tracker_sparql_connection_update_blank")]
    pub fn update_blank(
        &self,
        sparql: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
    ) -> Result<glib::Variant, glib::Error> {
        unsafe {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_update_blank(
                self.to_glib_none().0,
                sparql.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                &mut error,
            );
            if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    #[cfg_attr(feature = "v3_5", deprecated = "Since 3.5")]
    #[allow(deprecated)]
    #[doc(alias = "tracker_sparql_connection_update_blank_async")]
    pub fn update_blank_async<P: FnOnce(Result<glib::Variant, glib::Error>) + 'static>(
        &self,
        sparql: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
        callback: P,
    ) {
        let main_context = glib::MainContext::ref_thread_default();
        let is_main_context_owner = main_context.is_owner();
        let has_acquired_main_context = (!is_main_context_owner)
            .then(|| main_context.acquire().ok())
            .flatten();
        assert!(
            is_main_context_owner || has_acquired_main_context.is_some(),
            "Async operations only allowed if the thread is owning the MainContext"
        );

        let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
            Box_::new(glib::thread_guard::ThreadGuard::new(callback));
        unsafe extern "C" fn update_blank_async_trampoline<
            P: FnOnce(Result<glib::Variant, glib::Error>) + 'static,
        >(
            _source_object: *mut glib::gobject_ffi::GObject,
            res: *mut gio::ffi::GAsyncResult,
            user_data: glib::ffi::gpointer,
        ) {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_update_blank_finish(
                _source_object as *mut _,
                res,
                &mut error,
            );
            let result = if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            };
            let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
                Box_::from_raw(user_data as *mut _);
            let callback: P = callback.into_inner();
            callback(result);
        }
        let callback = update_blank_async_trampoline::<P>;
        unsafe {
            ffi::tracker_sparql_connection_update_blank_async(
                self.to_glib_none().0,
                sparql.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                Some(callback),
                Box_::into_raw(user_data) as *mut _,
            );
        }
    }

    #[cfg_attr(feature = "v3_5", deprecated = "Since 3.5")]

    pub fn update_blank_future(
        &self,
        sparql: &str,
    ) -> Pin<Box_<dyn std::future::Future<Output = Result<glib::Variant, glib::Error>> + 'static>>
    {
        let sparql = String::from(sparql);
        Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
            obj.update_blank_async(&sparql, Some(cancellable), move |res| {
                send.resolve(res);
            });
        }))
    }

    #[cfg(any(feature = "v3_1", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_1")))]
    #[doc(alias = "tracker_sparql_connection_update_resource")]
    pub fn update_resource(
        &self,
        graph: Option<&str>,
        resource: &Resource,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
    ) -> Result<(), glib::Error> {
        unsafe {
            let mut error = ptr::null_mut();
            let is_ok = ffi::tracker_sparql_connection_update_resource(
                self.to_glib_none().0,
                graph.to_glib_none().0,
                resource.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                &mut error,
            );
            debug_assert_eq!(is_ok == glib::ffi::GFALSE, !error.is_null());
            if error.is_null() {
                Ok(())
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    #[cfg(any(feature = "v3_1", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_1")))]
    #[doc(alias = "tracker_sparql_connection_update_resource_async")]
    pub fn update_resource_async<P: FnOnce(Result<(), glib::Error>) + 'static>(
        &self,
        graph: Option<&str>,
        resource: &Resource,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
        callback: P,
    ) {
        let main_context = glib::MainContext::ref_thread_default();
        let is_main_context_owner = main_context.is_owner();
        let has_acquired_main_context = (!is_main_context_owner)
            .then(|| main_context.acquire().ok())
            .flatten();
        assert!(
            is_main_context_owner || has_acquired_main_context.is_some(),
            "Async operations only allowed if the thread is owning the MainContext"
        );

        let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
            Box_::new(glib::thread_guard::ThreadGuard::new(callback));
        unsafe extern "C" fn update_resource_async_trampoline<
            P: FnOnce(Result<(), glib::Error>) + 'static,
        >(
            _source_object: *mut glib::gobject_ffi::GObject,
            res: *mut gio::ffi::GAsyncResult,
            user_data: glib::ffi::gpointer,
        ) {
            let mut error = ptr::null_mut();
            let _ = ffi::tracker_sparql_connection_update_resource_finish(
                _source_object as *mut _,
                res,
                &mut error,
            );
            let result = if error.is_null() {
                Ok(())
            } else {
                Err(from_glib_full(error))
            };
            let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
                Box_::from_raw(user_data as *mut _);
            let callback: P = callback.into_inner();
            callback(result);
        }
        let callback = update_resource_async_trampoline::<P>;
        unsafe {
            ffi::tracker_sparql_connection_update_resource_async(
                self.to_glib_none().0,
                graph.to_glib_none().0,
                resource.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                Some(callback),
                Box_::into_raw(user_data) as *mut _,
            );
        }
    }

    #[cfg(any(feature = "v3_1", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_1")))]
    pub fn update_resource_future(
        &self,
        graph: Option<&str>,
        resource: &Resource,
    ) -> Pin<Box_<dyn std::future::Future<Output = Result<(), glib::Error>> + 'static>> {
        let graph = graph.map(ToOwned::to_owned);
        let resource = resource.clone();
        Box_::pin(gio::GioFuture::new(self, move |obj, cancellable, send| {
            obj.update_resource_async(
                graph.as_ref().map(::std::borrow::Borrow::borrow),
                &resource,
                Some(cancellable),
                move |res| {
                    send.resolve(res);
                },
            );
        }))
    }

    #[cfg(any(feature = "v3_5", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_5")))]
    #[doc(alias = "tracker_sparql_connection_update_statement")]
    pub fn update_statement(
        &self,
        sparql: &str,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
    ) -> Result<Option<SparqlStatement>, glib::Error> {
        unsafe {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_update_statement(
                self.to_glib_none().0,
                sparql.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                &mut error,
            );
            if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            }
        }
    }

    #[cfg(any(feature = "v3_1", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_1")))]
    #[doc(alias = "tracker_sparql_connection_bus_new_async")]
    pub fn bus_new_async<P: FnOnce(Result<SparqlConnection, glib::Error>) + 'static>(
        service_name: &str,
        object_path: Option<&str>,
        dbus_connection: Option<&gio::DBusConnection>,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
        callback: P,
    ) {
        assert_initialized_main_thread!();

        let main_context = glib::MainContext::ref_thread_default();
        let is_main_context_owner = main_context.is_owner();
        let has_acquired_main_context = (!is_main_context_owner)
            .then(|| main_context.acquire().ok())
            .flatten();
        assert!(
            is_main_context_owner || has_acquired_main_context.is_some(),
            "Async operations only allowed if the thread is owning the MainContext"
        );

        let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
            Box_::new(glib::thread_guard::ThreadGuard::new(callback));
        unsafe extern "C" fn bus_new_async_trampoline<
            P: FnOnce(Result<SparqlConnection, glib::Error>) + 'static,
        >(
            _source_object: *mut glib::gobject_ffi::GObject,
            res: *mut gio::ffi::GAsyncResult,
            user_data: glib::ffi::gpointer,
        ) {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_bus_new_finish(res, &mut error);
            let result = if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            };
            let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
                Box_::from_raw(user_data as *mut _);
            let callback: P = callback.into_inner();
            callback(result);
        }
        let callback = bus_new_async_trampoline::<P>;
        unsafe {
            ffi::tracker_sparql_connection_bus_new_async(
                service_name.to_glib_none().0,
                object_path.to_glib_none().0,
                dbus_connection.to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                Some(callback),
                Box_::into_raw(user_data) as *mut _,
            );
        }
    }

    #[cfg(any(feature = "v3_1", feature = "dox"))]
    #[cfg_attr(feature = "dox", doc(cfg(feature = "v3_1")))]
    pub fn bus_new_future(
        service_name: &str,
        object_path: Option<&str>,
        dbus_connection: Option<&gio::DBusConnection>,
    ) -> Pin<Box_<dyn std::future::Future<Output = Result<SparqlConnection, glib::Error>> + 'static>>
    {
        skip_assert_initialized!();
        let service_name = String::from(service_name);
        let object_path = object_path.map(ToOwned::to_owned);
        let dbus_connection = dbus_connection.map(ToOwned::to_owned);
        Box_::pin(gio::GioFuture::new(&(), move |_obj, cancellable, send| {
            Self::bus_new_async(
                &service_name,
                object_path.as_ref().map(::std::borrow::Borrow::borrow),
                dbus_connection.as_ref().map(::std::borrow::Borrow::borrow),
                Some(cancellable),
                move |res| {
                    send.resolve(res);
                },
            );
        }))
    }

    #[doc(alias = "tracker_sparql_connection_new_async")]
    pub fn new_async<P: FnOnce(Result<SparqlConnection, glib::Error>) + 'static>(
        flags: SparqlConnectionFlags,
        store: Option<&impl IsA<gio::File>>,
        ontology: Option<&impl IsA<gio::File>>,
        cancellable: Option<&impl IsA<gio::Cancellable>>,
        callback: P,
    ) {
        assert_initialized_main_thread!();

        let main_context = glib::MainContext::ref_thread_default();
        let is_main_context_owner = main_context.is_owner();
        let has_acquired_main_context = (!is_main_context_owner)
            .then(|| main_context.acquire().ok())
            .flatten();
        assert!(
            is_main_context_owner || has_acquired_main_context.is_some(),
            "Async operations only allowed if the thread is owning the MainContext"
        );

        let user_data: Box_<glib::thread_guard::ThreadGuard<P>> =
            Box_::new(glib::thread_guard::ThreadGuard::new(callback));
        unsafe extern "C" fn new_async_trampoline<
            P: FnOnce(Result<SparqlConnection, glib::Error>) + 'static,
        >(
            _source_object: *mut glib::gobject_ffi::GObject,
            res: *mut gio::ffi::GAsyncResult,
            user_data: glib::ffi::gpointer,
        ) {
            let mut error = ptr::null_mut();
            let ret = ffi::tracker_sparql_connection_new_finish(res, &mut error);
            let result = if error.is_null() {
                Ok(from_glib_full(ret))
            } else {
                Err(from_glib_full(error))
            };
            let callback: Box_<glib::thread_guard::ThreadGuard<P>> =
                Box_::from_raw(user_data as *mut _);
            let callback: P = callback.into_inner();
            callback(result);
        }
        let callback = new_async_trampoline::<P>;
        unsafe {
            ffi::tracker_sparql_connection_new_async(
                flags.into_glib(),
                store.map(|p| p.as_ref()).to_glib_none().0,
                ontology.map(|p| p.as_ref()).to_glib_none().0,
                cancellable.map(|p| p.as_ref()).to_glib_none().0,
                Some(callback),
                Box_::into_raw(user_data) as *mut _,
            );
        }
    }

    pub fn new_future(
        flags: SparqlConnectionFlags,
        store: Option<&(impl IsA<gio::File> + Clone + 'static)>,
        ontology: Option<&(impl IsA<gio::File> + Clone + 'static)>,
    ) -> Pin<Box_<dyn std::future::Future<Output = Result<SparqlConnection, glib::Error>> + 'static>>
    {
        skip_assert_initialized!();
        let store = store.map(ToOwned::to_owned);
        let ontology = ontology.map(ToOwned::to_owned);
        Box_::pin(gio::GioFuture::new(&(), move |_obj, cancellable, send| {
            Self::new_async(
                flags,
                store.as_ref().map(::std::borrow::Borrow::borrow),
                ontology.as_ref().map(::std::borrow::Borrow::borrow),
                Some(cancellable),
                move |res| {
                    send.resolve(res);
                },
            );
        }))
    }
}

impl fmt::Display for SparqlConnection {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        f.write_str("SparqlConnection")
    }
}
