Skip to content
No description, website, or topics provided.
Elixir
Branch: master
Clone or download
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Permalink
Type Name Latest commit message Commit time
Failed to load latest commit information.
.circleci
lib
test
.formatter.exs
.gitignore
LICENSE.md
README.md
mix.exs
mix.lock

README.md

Membrane Multimedia Framework: UDP Element

Hex.pm API Docs CircleCI

This package provides elements that can be used to read from and write to UDP sockets.

Installation

Add the following line to your deps in mix.exs. Run mix deps.get.

{:membrane_element_udp, "~> 0.2"}

Usage example

The example below shows 2 pipelines. UDPDemo.Send downloads an example file over HTTP and sends it over UDP socket via localhost:

defmodule UDPDemo.Send do
  use Membrane.Pipeline

  alias Membrane.Element.{Hackney, UDP}
  alias Membrane.Pipeline.Spec

  def handle_init(_) do
    children = [
      source: %Hackney.Source{
        location: "https://membraneframework.github.io/static/video-samples/test-video.h264"
      },
      udp: %UDP.Sink{
        destination_address: {127, 0, 0, 1},
        destination_port_no: 5001,
        local_address: {127, 0, 0, 1}
      }
    ]

    links = %{
      {:source, :output} => {:udp, :input}
    }

    spec = %Spec{children: children, links: links}
    {{:ok, spec: spec}, %{}}
  end
end

The UDPDemo.Receive retrieves packets from UDP socket and saves the data to the /tmp/udp-recv.h264 file.

Bear in mind that for other files/sending pipelines you may need do adjust recv_buffer_size option in Membrane.Element.UDP.Source that determines the maximum size of received packets.

defmodule UDPDemo.Receive do
  use Membrane.Pipeline

  alias Membrane.Element.{File, UDP}
  alias Membrane.Pipeline.Spec

  def handle_init(_) do
    children = [
      udp: %UDP.Source{
        local_address: {127, 0, 0, 1},
        local_port_no: 5001
      },
      sink: %File.Sink{
        location: "/tmp/udp-recv.h264"
      }
    ]

    links = %{
      {:udp, :output} => {:sink, :input}
    }

    spec = %Spec{children: children, links: links}
    {{:ok, spec: spec}, %{}}
  end
end

The snippet below presents how to run these pipelines. For convenience, it uses Membrane.Testing.Pipeline that wraps the pipeline modules above and allows to assert on state changes and end of stream events from the elements. Thanks to that, we can make sure the data is sent only when the receiving end is ready and the pipelines are stopped after everything has been sent.

alias Membrane.Testing.Pipeline
import Membrane.Testing.Assertions

{:ok, sender} = Pipeline.start_link(%Pipeline.Options{module: UDPDemo.Send})
{:ok, receiver} = Pipeline.start_link(%Pipeline.Options{module: UDPDemo.Receive})

:ok = Pipeline.play(receiver)

assert_pipeline_playback_changed(receiver, :prepared, :playing)

:ok = Pipeline.play(sender)

assert_end_of_stream(sender, :udp, :input, 5000)

:ok = Pipeline.stop(sender)
assert_pipeline_playback_changed(sender, :prepared, :stopped)

:ok = Pipeline.stop(receiver)
assert_pipeline_playback_changed(receiver, :prepared, :stopped)

The deps required to run the example:

defp deps do
  [
    {:membrane_core, "~> 0.4.1"},
    {:membrane_element_udp, "~> 0.2"},
    {:membrane_element_hackney, "~> 0.2"},
    {:membrane_element_file, "~> 0.2"}
  ]
end

Copyright and License

Copyright 2019, Software Mansion

Software Mansion

Licensed under the Apache License, Version 2.0

You can’t perform that action at this time.