collaborative_sessions/
lib.rs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
use hdk::prelude::*;

#[hdk_extern]
pub fn init(_: ()) -> ExternResult<InitCallbackResult> {
    let mut fns = BTreeSet::new();
    fns.insert((zome_info()?.name, "recv_remote_signal".into()));
    let functions = GrantedFunctions::Listed(fns);
    create_cap_grant(CapGrantEntry {
        tag: "".into(),
        access: CapAccess::Unrestricted,
        functions,
    })?;

    Ok(InitCallbackResult::Pass)
}

#[derive(Serialize, Deserialize, Debug)]
pub struct SendPresenceSignalInput {
    pub session_id: String,
    pub peers: Vec<AgentPubKey>,
}

#[hdk_extern]
pub fn send_presence_signal(input: SendPresenceSignalInput) -> ExternResult<()> {
    debug!(
        "Sending presence signal for session_id '{}' to {:?}",
        input.session_id, input.peers
    );
    send_remote_signal(
        RemoteSignal::Presence {
            session_id: input.session_id,
        },
        input.peers,
    )?;
    Ok(())
}

#[derive(Serialize, Deserialize, Debug)]
pub struct SessionMessage {
    pub session_id: String,
    pub message: SerializedBytes,
}

#[derive(Serialize, Deserialize, Debug)]
pub struct SendSessionMessageInput {
    pub session_message: SessionMessage,
    pub peers: Vec<AgentPubKey>,
}

#[hdk_extern]
pub fn send_session_message(input: SendSessionMessageInput) -> ExternResult<()> {
    debug!(
        "Sending session message for session_id '{}' to {:?}",
        input.session_message.session_id, input.peers
    );
    send_remote_signal(
        RemoteSignal::SessionMessage {
            session_id: input.session_message.session_id,
            message: input.session_message.message,
        },
        input.peers,
    )?;
    Ok(())
}

#[derive(Serialize, Deserialize, Debug)]
pub struct SendLeaveSessionSignalInput {
    pub session_id: String,
    pub peers: Vec<AgentPubKey>,
}

#[hdk_extern]
pub fn send_leave_session_signal(input: SendLeaveSessionSignalInput) -> ExternResult<()> {
    debug!(
        "Sending leave session signal for session_id '{}' to {:?}",
        input.session_id, input.peers
    );
    send_remote_signal(
        RemoteSignal::LeaveSession {
            session_id: input.session_id,
        },
        input.peers,
    )?;
    Ok(())
}

#[derive(Serialize, Deserialize, Debug)]
#[serde(tag = "type")]
pub enum RemoteSignal {
    Presence {
        session_id: String,
    },
    SessionMessage {
        session_id: String,
        message: SerializedBytes,
    },
    LeaveSession {
        session_id: String,
    },
}

impl RemoteSignal {
    fn session_id(&self) -> String {
        match self {
            Self::Presence { session_id } => session_id.clone(),
            Self::SessionMessage { session_id, .. } => session_id.clone(),
            Self::LeaveSession { session_id } => session_id.clone(),
        }
    }
}

#[derive(Serialize, Deserialize, Debug)]
pub struct Signal {
    pub provenance: AgentPubKey,
    pub remote_signal: RemoteSignal,
}

#[hdk_extern]
pub fn recv_remote_signal(remote_signal: RemoteSignal) -> ExternResult<()> {
    let call_info = call_info()?;
    debug!(
        "Received session signal for session_id '{}'",
        remote_signal.session_id()
    );

    emit_signal(Signal {
        provenance: call_info.provenance,
        remote_signal,
    })
}