every.channel: sanitized baseline
This commit is contained in:
commit
897e556bea
258 changed files with 74298 additions and 0 deletions
95
third_party/iroh-live/iroh-live/examples/publish.rs
vendored
Normal file
95
third_party/iroh-live/iroh-live/examples/publish.rs
vendored
Normal file
|
|
@ -0,0 +1,95 @@
|
|||
use clap::Parser;
|
||||
use iroh::{Endpoint, SecretKey, protocol::Router};
|
||||
use iroh_live::{
|
||||
Live,
|
||||
media::{
|
||||
audio::AudioBackend,
|
||||
av::{AudioPreset, VideoCodec, VideoPreset},
|
||||
capture::CameraCapturer,
|
||||
ffmpeg::{H264Encoder, OpusEncoder},
|
||||
publish::{AudioRenditions, PublishBroadcast, VideoRenditions},
|
||||
},
|
||||
ticket::LiveTicket,
|
||||
};
|
||||
use n0_error::StdResultExt;
|
||||
|
||||
#[tokio::main]
|
||||
async fn main() -> n0_error::Result {
|
||||
tracing_subscriber::fmt::init();
|
||||
let cli = Cli::parse();
|
||||
|
||||
// Setup audio backend.
|
||||
let audio_ctx = AudioBackend::new();
|
||||
|
||||
// Setup iroh and iroh-live.
|
||||
let endpoint = Endpoint::builder()
|
||||
.secret_key(secret_key_from_env()?)
|
||||
.bind()
|
||||
.await?;
|
||||
let live = Live::new(endpoint.clone());
|
||||
let router = Router::builder(endpoint)
|
||||
.accept(iroh_live::ALPN, live.moq.protocol_handler())
|
||||
.spawn();
|
||||
|
||||
// Create a publish broadcast.
|
||||
let mut broadcast = PublishBroadcast::new();
|
||||
|
||||
// Capture audio, and encode with the cli-provided preset.
|
||||
if !cli.no_audio {
|
||||
let mic = audio_ctx.default_input().await?;
|
||||
let audio = AudioRenditions::new::<OpusEncoder>(mic, [cli.audio_preset]);
|
||||
broadcast.set_audio(Some(audio))?;
|
||||
}
|
||||
|
||||
// Capture camera, and encode with the cli-provided presets.
|
||||
if !cli.no_video {
|
||||
let camera = CameraCapturer::new()?;
|
||||
let video = VideoRenditions::new::<H264Encoder>(camera, cli.video_presets);
|
||||
broadcast.set_video(Some(video))?;
|
||||
}
|
||||
|
||||
// Publish under the name "hello".
|
||||
let name = "hello";
|
||||
live.publish(name, broadcast.producer()).await?;
|
||||
|
||||
// Create a ticket string and print
|
||||
let ticket = LiveTicket::new(router.endpoint().id(), name);
|
||||
println!("publishing at {ticket}");
|
||||
let long_ticket = LiveTicket::new(router.endpoint().addr(), name);
|
||||
println!("\nticket with addrs: {long_ticket}");
|
||||
|
||||
// Wait for ctrl-c and then shutdown.
|
||||
tokio::signal::ctrl_c().await?;
|
||||
live.shutdown();
|
||||
router.shutdown().await.std_context("router shutdown")?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[derive(Parser, Debug)]
|
||||
struct Cli {
|
||||
#[arg(long, default_value_t=VideoCodec::H264)]
|
||||
codec: VideoCodec,
|
||||
#[arg(long, value_delimiter=',', default_values_t=[VideoPreset::P180, VideoPreset::P360, VideoPreset::P720, VideoPreset::P1080])]
|
||||
video_presets: Vec<VideoPreset>,
|
||||
#[arg(long, default_value_t=AudioPreset::Hq)]
|
||||
audio_preset: AudioPreset,
|
||||
#[arg(long)]
|
||||
no_video: bool,
|
||||
#[arg(long)]
|
||||
no_audio: bool,
|
||||
}
|
||||
|
||||
fn secret_key_from_env() -> n0_error::Result<SecretKey> {
|
||||
Ok(match std::env::var("IROH_SECRET") {
|
||||
Ok(key) => key.parse()?,
|
||||
Err(_) => {
|
||||
let key = SecretKey::generate(&mut rand::rng());
|
||||
println!(
|
||||
"Created new secret. Reuse with IROH_SECRET={}",
|
||||
data_encoding::HEXLOWER.encode(&key.to_bytes())
|
||||
);
|
||||
key
|
||||
}
|
||||
})
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue