Skip to content

Instantly share code, notes, and snippets.

@maxneuvians
Last active February 3, 2016 15:56
Show Gist options
  • Save maxneuvians/1bb797683a19cb8870f3 to your computer and use it in GitHub Desktop.
Save maxneuvians/1bb797683a19cb8870f3 to your computer and use it in GitHub Desktop.
Elixir Plug for PDF generation with WKHTMLTOPDF
defmodule Sample.PdfPlug do
import Plug.Conn
import Plug.Upload
@wkhtmltopdf_path System.find_executable("wkhtmltopdf")
def init(opts) do
opts
end
def call(conn, opts) do
case Regex.match?(~r/.*(pdf)$/, conn.request_path) do
true -> generate_pdf(conn, opts)
false ->
conn
end
end
defp generate_pdf(conn, opts) do
url = "#{conn.scheme}://#{conn.host}:#{conn.port}#{conn.request_path}"
{:ok, file} = random_file("test")
conn = fetch_cookies(conn)
args = ["-q"] ++ join_cookies(conn.req_cookies) ++ join_options(opts) ++ [String.replace(url, ".pdf", ""), file]
System.cmd(@wkhtmltopdf_path, args)
conn
|> send_file(200, file)
|> halt
end
defp join_cookies(cookies) when cookies == %{}, do: []
defp join_cookies(cookies) do
cookies
|> Enum.map(fn{k,v} -> ["--cookie", "#{k}", "#{URI.encode(v)}"] end)
|> List.flatten
end
defp join_options(options) do
options
|> Enum.map(fn{k,v} -> ["--#{k}", "#{v}"] end)
|> List.flatten
end
end
pipeline :browser do
plug :accepts, ["html"]
plug :fetch_session
plug :fetch_flash
plug :protect_from_forgery
plug :put_secure_browser_headers
plug Sample.PdfPlug, orientation: 'landscape'
end
# Explicitly include the .pdf endpoint ex. report.pdf in paths
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment