Hey guys -
I wrote this post as a question… but as I was writing I just got it to work so this is more a code snippet in case anyone is interested.
I want a user to access a route with some parameters, and depending on the parameters, adjust ffmpeg filters and allow the user to download the file as it’s being processed by ffmpeg.
I also didn’t want to create any temp files.
I’m setting the headers and sending a chunked/streamed response with this code:
conn =
conn
|> put_resp_header("content-type", "video/mp4")
|> put_resp_header("content-disposition", "attachment; filename=video.mp4")
|> send_chunked(200)
porc = Porcelain.spawn_shell("ffmpeg -i input.avi -f mp4 -movflags frag_keyframe+empty_moov pipe:", out: :stream)
Enum.reduce_while(porc.out, conn, fn (chunk, conn) ->
case Plug.Conn.chunk(conn, chunk) do
{:ok, conn} ->
{:cont, conn}
{:error, :closed} ->
{:halt, conn}
end
end)
end
No error handling yet but in the happy case it works.