annotate libervia/frontends/tools/webrtc_file.py @ 4240:79c8a70e1813

backend, frontend: prepare remote control: This is a series of changes necessary to prepare the implementation of remote control feature: - XEP-0166: add a `priority` attribute to `ApplicationData`: this is needed when several applications are working in a same session, to know which one must be handled first. Will be used to make Remote Control have precedence over Call content. - XEP-0166: `_call_plugins` is now async and is not used with `DeferredList` anymore: the benefit to have methods called in parallels is very low, and it cause a lot of trouble as we can't predict order. Methods are now called sequentially so workflow can be predicted. - XEP-0167: fix `senders` XMPP attribute <=> SDP mapping - XEP-0234: preflight acceptance key is now `pre-accepted` instead of `file-accepted`, so the same key can be used with other jingle applications. - XEP-0167, XEP-0343: move some method to XEP-0167 - XEP-0353: use new `priority` feature to call preflight methods of applications according to it. - frontend (webrtc): refactor the sources/sink handling with a more flexible mechanism based on Pydantic models. It is now possible to have has many Data Channel as necessary, to have them in addition to A/V streams, to specify manually GStreamer sources and sinks, etc. - frontend (webrtc): rework of the pipeline to reduce latency. - frontend: new `portal_desktop` method. Screenshare portal handling has been moved there, and RemoteDesktop portal has been added. - frontend (webrtc): fix `extract_ufrag_pwd` method. rel 436
author Goffi <goffi@goffi.org>
date Sat, 11 May 2024 13:52:41 +0200
parents d01b8d002619
children 0d7bb4df2343
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
4233
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
1 #!/usr/bin/env python3
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
2
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
3 # Libervia WebRTC implementation
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
4 # Copyright (C) 2009-2024 Jérôme Poisson (goffi@goffi.org)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
5
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
6 # This program is free software: you can redistribute it and/or modify
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
7 # it under the terms of the GNU Affero General Public License as published by
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
8 # the Free Software Foundation, either version 3 of the License, or
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
9 # (at your option) any later version.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
10
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
11 # This program is distributed in the hope that it will be useful,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
14 # GNU Affero General Public License for more details.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
15
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
16 # You should have received a copy of the GNU Affero General Public License
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
17 # along with this program. If not, see <http://www.gnu.org/licenses/>.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
18
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
19
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
20 import asyncio
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
21 import atexit
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
22 from functools import partial
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
23 import logging
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
24 from pathlib import Path
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
25 from typing import Any, Callable, IO
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
26
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
27 import gi
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
28
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
29 gi.require_versions({"Gst": "1.0", "GstWebRTC": "1.0"})
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
30 from gi.repository import GLib, GstWebRTC
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
31
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
32 from libervia.backend.core import exceptions
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
33 from libervia.backend.core.i18n import _
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
34 from libervia.backend.tools.common import data_format, utils
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
35 from libervia.frontends.tools import aio, jid, webrtc
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
36 from libervia.frontends.tools.webrtc_models import CallData
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
37
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
38
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
39 log = logging.getLogger(__name__)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
40
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
41 WEBRTC_CHUNK_SIZE = 64 * 1024
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
42
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
43
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
44 class WebRTCFileSender:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
45
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
46 def __init__(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
47 self,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
48 bridge,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
49 profile: str,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
50 on_call_start_cb: Callable[[dict], Any] | None = None,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
51 end_call_cb: Callable[[], Any] | None = None,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
52 ) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
53 """Initializes the File Sender.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
54
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
55 @param bridge: An async Bridge instance.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
56 @param profile: The profile name to be used.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
57 @param on_call_start_cb: A blocking or async callable that accepts a dict as its
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
58 only argument.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
59 @param end_call_cb: A callable to be invoked at the end of a call.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
60 """
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
61
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
62 self.bridge = bridge
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
63 self.profile = profile
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
64 self.on_call_start_cb = on_call_start_cb
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
65 self.end_call_cb = end_call_cb
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
66 self.loop = asyncio.get_event_loop()
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
67
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
68 async def _on_webrtc_call_start(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
69 self,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
70 file_path: Path,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
71 file_name: str | None,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
72 callee: str,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
73 call_data: dict,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
74 profile: str,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
75 ) -> str:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
76 file_data_s = await self.bridge.file_jingle_send(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
77 str(callee),
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
78 "",
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
79 file_name or file_path.name,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
80 "",
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
81 data_format.serialise(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
82 {
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
83 "webrtc": True,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
84 "call_data": call_data,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
85 "size": file_path.stat().st_size,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
86 }
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
87 ),
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
88 self.profile,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
89 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
90 file_data = data_format.deserialise(file_data_s)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
91
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
92 if self.on_call_start_cb is not None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
93 await aio.maybe_async(self.on_call_start_cb(file_data))
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
94 return file_data["session_id"]
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
95
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
96 async def _send_file(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
97 self, file_path: Path, data_channel: GstWebRTC.WebRTCDataChannel
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
98 ) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
99 """Send file to Data Channel by chunks"""
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
100 try:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
101 with file_path.open("rb") as file:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
102 while True:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
103 data = file.read(WEBRTC_CHUNK_SIZE)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
104 if not data:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
105 break
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
106 data_channel.send_data(GLib.Bytes(data))
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
107 # We give control back to the loop to avoid freezing everything.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
108 await asyncio.sleep(0)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
109 finally:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
110 webrtc_call = self.webrtc_call
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
111 # we connect to the "on-close" signal to wait for the data channel to be
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
112 # actually closed before closing the call and quitting the app.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
113 data_channel.connect("on-close", partial(self._on_dc_close, webrtc_call))
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
114 data_channel.close()
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
115
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
116 def _on_dc_close(self, webrtc_call, data_channel: GstWebRTC.WebRTCDataChannel):
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
117 if webrtc_call is not None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
118 aio.run_from_thread(self._end_call_and_quit, webrtc_call, loop=self.loop)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
119
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
120 async def _end_call_and_quit(self, webrtc_call):
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
121 await webrtc_call.webrtc.end_call()
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
122 if self.end_call_cb is not None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
123 await aio.maybe_async(self.end_call_cb())
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
124
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
125 def _on_dc_open(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
126 self, file_path: Path, data_channel: GstWebRTC.WebRTCDataChannel
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
127 ) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
128 """Called when datachannel is open"""
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
129 aio.run_from_thread(self._send_file, file_path, data_channel, loop=self.loop)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
130
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
131 async def send_file_webrtc(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
132 self,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
133 file_path: Path|str,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
134 callee: jid.JID,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
135 file_name: str | None = None,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
136 ) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
137 """Send a file using WebRTC to the given callee JID.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
138
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
139 @param file_path: The local path to the file to send.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
140 @param callee: The JID of the recipient to send the file to.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
141 @param file_name: Name of the file as sent to the peer.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
142 If None or empty string, name will be retrieved from file path.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
143 """
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
144 file_path = Path(file_path)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
145 call_data = CallData(callee=callee)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
146 self.webrtc_call = await webrtc.WebRTCCall.make_webrtc_call(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
147 self.bridge,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
148 self.profile,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
149 call_data,
4240
79c8a70e1813 backend, frontend: prepare remote control:
Goffi <goffi@goffi.org>
parents: 4233
diff changeset
150 sources_data=webrtc.SourcesDataChannel(
79c8a70e1813 backend, frontend: prepare remote control:
Goffi <goffi@goffi.org>
parents: 4233
diff changeset
151 dc_open_cb=partial(self._on_dc_open, file_path)
79c8a70e1813 backend, frontend: prepare remote control:
Goffi <goffi@goffi.org>
parents: 4233
diff changeset
152 ),
4233
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
153 call_start_cb=partial(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
154 self._on_webrtc_call_start,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
155 file_path,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
156 file_name,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
157 ),
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
158 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
159
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
160
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
161 class WebRTCFileReceiver:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
162
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
163 def __init__(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
164 self, bridge, profile: str, on_close_cb: Callable[[], Any] | None = None
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
165 ) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
166 """Initializes the File Receiver.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
167
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
168 @param bridge: An async Bridge instance.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
169 @param profile: The profile name to be used.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
170 @param on_close_cb: Called when the Data Channel is closed.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
171 """
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
172 self.bridge = bridge
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
173 self.profile = profile
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
174 self.on_close_cb = on_close_cb
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
175 self.loop = asyncio.get_event_loop()
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
176 self.file_data: dict | None = None
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
177 self.fd: IO[bytes] | None = None
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
178
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
179 @staticmethod
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
180 def format_confirm_msg(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
181 action_data: dict,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
182 peer_jid: jid.JID,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
183 peer_name: str|None = None
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
184 ) -> str:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
185 """Format a user-friendly confirmation message.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
186
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
187 File data will be retrieve from ``action_data`` and used to format a user-friendly
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
188 file confirmation message.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
189 @param action_data: Data as returned by the "FILE" ``action_new`` signal.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
190 @return: User-friendly confirmation message.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
191 """
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
192 file_data = action_data.get("file_data", {})
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
193
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
194 file_name = file_data.get('name')
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
195 file_size = file_data.get('size')
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
196
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
197 if file_name:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
198 file_name_msg = 'wants to send you the file "{file_name}"'.format(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
199 file_name=file_name
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
200 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
201 else:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
202 file_name_msg = 'wants to send you an unnamed file'
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
203
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
204 if file_size is not None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
205 file_size_msg = "which has a size of {file_size_human}".format(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
206 file_size_human=utils.get_human_size(file_size)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
207 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
208 else:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
209 file_size_msg = "which has an unknown size"
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
210
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
211 file_description = file_data.get('desc')
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
212 if file_description:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
213 description_msg = " Description: {}.".format(file_description)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
214 else:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
215 description_msg = ""
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
216
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
217 file_data = action_data.get("file_data", {})
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
218
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
219 if not peer_name:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
220 peer_name = str(peer_jid)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
221 else:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
222 peer_name = f"{peer_name} ({peer_jid})"
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
223
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
224 return (
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
225 _("{peer_name} {file_name_msg} {file_size_msg}.{description_msg} "
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
226 "Do you accept?").format(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
227 peer_name=peer_name,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
228 file_name_msg=file_name_msg,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
229 file_size_msg=file_size_msg,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
230 description_msg=description_msg
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
231 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
232 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
233
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
234 def _on_dc_message_data(self, fd, data_channel, glib_data) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
235 """A data chunk of the file has been received."""
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
236 fd.write(glib_data.get_data())
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
237
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
238 def _on_dc_close(self, data_channel) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
239 """Data channel is closed
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
240
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
241 The file download should be complete, we close it.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
242 """
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
243 aio.run_from_thread(self._on_close, loop=self.loop)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
244
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
245 async def _on_close(self) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
246 assert self.fd is not None
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
247 self.fd.close()
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
248 if self.on_close_cb is not None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
249 await aio.maybe_async(self.on_close_cb())
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
250
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
251 def _on_data_channel(self, webrtcbin, data_channel) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
252 """The data channel has been opened."""
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
253 data_channel.connect(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
254 "on-message-data", partial(self._on_dc_message_data, self.fd)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
255 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
256 data_channel.connect("on-close", self._on_dc_close)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
257
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
258 def _on_fd_clean(self, fd) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
259 """Closed opened file object if not already.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
260
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
261 If the file object was not closed, an error message is returned.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
262 """
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
263 if fd is None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
264 return
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
265 if not fd.closed:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
266 log.error(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
267 f"The file {fd.name!r} was not closed properly, which might "
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
268 "indicate an incomplete download."
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
269 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
270 fd.close()
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
271
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
272 async def receive_file_webrtc(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
273 self,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
274 from_jid: jid.JID,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
275 session_id: str,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
276 file_path: Path,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
277 file_data: dict,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
278 ) -> None:
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
279 """Receives a file via WebRTC and saves it to the specified path.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
280
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
281 @param from_jid: The JID of the entity sending the file.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
282 @param session_id: The Jingle FT Session ID.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
283 @param file_path: The local path where the received file will be saved.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
284 If a file already exists at this path, it will be overwritten.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
285 @param file_data: Additional data about the file being transferred.
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
286 """
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
287 if file_path.exists() and not file_path.is_file():
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
288 raise exceptions.InternalError(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
289 f"{file_path} is not a valid destination path."
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
290 )
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
291 self.fd = file_path.open("wb")
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
292 atexit.register(self._on_fd_clean, self.fd)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
293 self.file_data = file_data
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
294 call_data = CallData(callee=from_jid, sid=session_id)
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
295 await webrtc.WebRTCCall.make_webrtc_call(
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
296 self.bridge,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
297 self.profile,
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
298 call_data,
4240
79c8a70e1813 backend, frontend: prepare remote control:
Goffi <goffi@goffi.org>
parents: 4233
diff changeset
299 sinks_data=webrtc.SinksDataChannel(
79c8a70e1813 backend, frontend: prepare remote control:
Goffi <goffi@goffi.org>
parents: 4233
diff changeset
300 dc_on_data_channel=self._on_data_channel,
79c8a70e1813 backend, frontend: prepare remote control:
Goffi <goffi@goffi.org>
parents: 4233
diff changeset
301 ),
4233
d01b8d002619 cli (call, file), frontends: implement webRTC data channel transfer:
Goffi <goffi@goffi.org>
parents:
diff changeset
302 )