// Fragments - connection.rs
// Copyright (C) 2022-2023  Felix Häcker <haeckerfelix@gnome.org>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program.  If not, see <https://www.gnu.org/licenses/>.

use std::cell::{Cell, OnceCell};

use gio::prelude::*;
use glib::Properties;
use gtk::subclass::prelude::*;
use gtk::{gio, glib};
use uuid::Uuid;

use crate::i18n::i18n;

static FRAGMENTS_UUID: &str = "00000000-0000-0000-0000-000000000000";

mod imp {
    use super::*;

    #[derive(Debug, Default, Properties)]
    #[properties(wrapper_type = super::FrgConnection)]
    pub struct FrgConnection {
        #[property(get, set, construct_only)]
        title: OnceCell<String>,
        #[property(get, set, construct_only)]
        address: OnceCell<String>,
        #[property(get, set, construct_only)]
        uuid: OnceCell<String>,
        #[property(get = Self::is_fragments, set)]
        is_fragments: Cell<bool>,
    }

    impl FrgConnection {
        pub fn is_fragments(&self) -> bool {
            self.obj().uuid() == FRAGMENTS_UUID
        }
    }

    #[glib::object_subclass]
    impl ObjectSubclass for FrgConnection {
        const NAME: &'static str = "FrgConnection";
        type Type = super::FrgConnection;
    }

    #[glib::derived_properties]
    impl ObjectImpl for FrgConnection {
        fn constructed(&self) {
            self.parent_constructed();

            let obj = self.obj();
            let is_fragments = obj.uuid() == FRAGMENTS_UUID;
            self.is_fragments.set(is_fragments);
        }
    }
}

glib::wrapper! {
    pub struct FrgConnection(ObjectSubclass<imp::FrgConnection>);
}

impl FrgConnection {
    pub fn new(title: &str, address: &str) -> Self {
        let uuid = Uuid::new_v4().to_string();
        glib::Object::builder()
            .property("title", title)
            .property("address", address)
            .property("uuid", uuid)
            .build()
    }

    pub fn new_with_uuid(title: &str, address: &str, uuid: &str) -> Self {
        glib::Object::builder()
            .property("title", title)
            .property("address", address)
            .property("uuid", uuid)
            .build()
    }
}

impl Default for FrgConnection {
    fn default() -> Self {
        Self::new_with_uuid(
            &i18n("Local Fragments session"),
            "http://127.0.0.1:9091/transmission/rpc",
            FRAGMENTS_UUID,
        )
    }
}
