1 // This Source Code Form is subject to the terms of the Mozilla Public
2 // License, v. 2.0. If a copy of the MPL was not distributed with this
3 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
5 //! Rust interface for the Gecko remote agent.
10 use nserror::NS_ERROR_ILLEGAL_VALUE;
11 use nsstring::{nsAString, nsString};
12 use xpcom::interfaces::nsIRemoteAgent;
15 use crate::error::RemoteAgentError::{self, *};
17 pub const DEFAULT_HOST: &'static str = "localhost";
18 pub const DEFAULT_PORT: u16 = 9222;
20 pub type RemoteAgentResult<T> = Result<T, RemoteAgentError>;
22 pub struct RemoteAgent {
23 inner: RefPtr<nsIRemoteAgent>,
27 pub fn get() -> RemoteAgentResult<RemoteAgent> {
28 let inner = xpcom::services::get_RemoteAgent().ok_or(Unavailable)?;
29 Ok(RemoteAgent { inner })
32 pub fn listen(&self, spec: &str) -> RemoteAgentResult<()> {
33 let addr = http::uri::Authority::from_str(spec)?;
34 let host = if addr.host().is_empty() {
40 let port = addr.port_u16().unwrap_or(DEFAULT_PORT);
42 let url = nsString::from(&format!("http://{}:{}/", host, port));
43 unsafe { self.inner.Listen(&*url as &nsAString) }
46 // TODO(ato): https://bugzil.la/1600139
48 NS_ERROR_ILLEGAL_VALUE => RemoteAgentError::LoopbackRestricted,
49 nsresult => RemoteAgentError::from(nsresult),
56 pub fn listening(&self) -> RemoteAgentResult<bool> {
57 let mut listening = false;
58 unsafe { self.inner.GetListening(&mut listening) }.to_result()?;
62 pub fn close(&self) -> RemoteAgentResult<()> {
63 unsafe { self.inner.Close() }.to_result()?;
68 impl Drop for RemoteAgent {
70 // it should always be safe to call nsIRemoteAgent.close()
71 if let Err(e) = self.close() {
72 error!("unable to close remote agent listener: {}", e);