12/08/2018, 13:27
Sử dụng Wicked PDF để generate file pdf
Giới thiệu Wicked PDF sử dụng các tiện ích wkhtmltopdf để tạo file PDF cho người dùng từ HTML. Nói cách khác, bạn chỉ cần viết một 1 page HTML như bạn sẽ bình thường, sau đó để cho Wicked PDF sẽ sử dụng đó để tạo ra pdf cho bạn. Wicked PDF làm việc trên các version Ruby từ 1.8.7 -> 2.1, ...
- Giới thiệu
- Wicked PDF sử dụng các tiện ích wkhtmltopdf để tạo file PDF cho người dùng từ HTML. Nói cách khác, bạn chỉ cần viết một 1 page HTML như bạn sẽ bình thường, sau đó để cho Wicked PDF sẽ sử dụng đó để tạo ra pdf cho bạn.
- Wicked PDF làm việc trên các version Ruby từ 1.8.7 -> 2.1, Rails từ 2 -> 4.1
- Cách cài đặt
- Add wicked_pdf vào Gemfile và chạy bundle install :
gem "wicked_pdf"
- Sau đó tạo `initializer`
$ rails generate wicked_pdf
- Cũng có thể cần thêm
Mime::Type.register "application/pdf", :pdf
vào `config/initializers/mime_types.rb` với những versions cũ của Rails. - Ta cũng phải cài đặt `wkhtmltopdf`, bởi vì `wicked_pdf` là wrapper cho `wkhtmltopdf` - Cách đơn giản nhất để cài đặt tất cả các tập tin nhị phân (Linux, OSX, Windows) là thông qua `gem wkhtmltopdf-binary`. Để cài đặt đó, ta thêm `wkhtmltopdf-binary` vào trong Gemfile.
gem "wkhtmltopdf-binary"
- Nếu thực thi `wkhtmltopdf` của bạn không phải là trên `webserver` của bạn, bạn có thể cấu hình nó trong initializer:
WickedPdf.config = { exe_path: "usr/local/bin/wkhtmltopdf" }
- Cách sử dụng cơ bản
class OrdersController < ApplicationController def show respond_to do |format| format.html format.pdf do render pdf: "show" end end end end
- Điều kiện sử dụng
- Các nhị phân wkhtmltopdf đang chạy bên ngoài của ứng dụng Rails của bạn, do đó khi sử dụng layout thông thường sẽ không thể hoạt động. Nếu bạn muốn sử dụng CSS, Javascript hay hiển thị hình ảnh thì bạn phải thay đổi các tham chiếu tuyệt đối đến các tập tin. Cách tốt nhất để Rails không sử dụng asset pipeline là sử dụng wicked_pdf_stylesheet_link_tag, wicked_pdf_javascript_include_tag và wicked_pdf_image_tag hoặc trỏ thẳng đến một CDN cho các thư việc của jquery
html head = wicked_pdf_stylesheet_link_tag "pdf" = wicked_pdf_javascript_include_tag "pdf" title = full_title(yield(:title)) body = wicked_pdf_image_tag "logo.png" = yield
- CDN reference
html head = javascript_include_tag "http://code.jquery.com/jquery-1.10.0.min.js" = javascript_include_tag "http://code.jquery.com/ui/1.10.3/jquery-ui.min.js"
- Sử dụng `Asset pipeline` Cách xử lý này cho `asset pipeline` trên Heroku là bao gồm các tập tin trong danh sách `asset precompile` của bạn, như sau:
config.assets.precompile += ["pdf.css", "pdf.js", ...etc...]
- Cách sử dụng nâng cao với tất cả các tùy chọn có sẵn
def show respond_to do |format| format.html format.pdf do render pdf: "file_name", disposition: "attachment", template: "things/show.pdf.erb", file: "#{Rails.root}/files/foo.erb" layout: "pdf.html", wkhtmltopdf: "/usr/local/bin/wkhtmltopdf", show_as_html: params.key?("debug"), orientation: "Landscape", page_size: "A4, Letter, ...", page_height: NUMBER, page_awidth: NUMBER, save_to_file: Rails.root.join("pdfs", "#{filename}.pdf"), save_only: false, proxy: "TEXT", basic_auth: false username: "TEXT", password: "TEXT", title: "Alternate Title", cover: "URL, Pathname, or raw HTML string", dpi: "dpi", encoding: "TEXT", user_style_sheet: "URL", cookie: ["_session_id SESSION_ID"], post: ["query QUERY_PARAM"], redirect_delay: NUMBER, javascript_delay: NUMBER, window_status: "TEXT", image_quality: NUMBER, no_pdf_compression: true, zoom: FLOAT, page_offset: NUMBER, book: true, default_header: true, disable_javascript: false, grayscale: true, lowquality: true, enable_plugins: true, disable_internal_links: true, disable_external_links: true, print_media_type: true, disable_smart_shrinking: true, use_xserver: true, background: false, no_background: true, viewport_size: "TEXT", extra: "", outline: { outline: true, outline_depth: LEVEL }, margin: { top: SIZE, bottom: SIZE, left: SIZE, right: SIZE }, header: { html: { template: "users/header.pdf.erb", layout: "pdf_plain.html", url: "www.example.com", locals: { foo: @bar }}, center: "TEXT", font_name: "NAME", font_size: SIZE, left: "TEXT", right: "TEXT", spacing: REAL, line: true, content: "HTML CONTENT ALREADY RENDERED"}, footer: { html: { template:"shared/footer.pdf.erb", layout: "pdf_plain.html", url: "www.example.com", locals: { foo: @bar }}, center: "TEXT", font_name: "NAME", font_size: SIZE, left: "TEXT", right: "TEXT", spacing: REAL, line: true, content: "HTML CONTENT ALREADY RENDERED"}, toc: { font_name: "NAME", depth: LEVEL, header_text: "TEXT", header_fs: SIZE, text_size_shrink: 0.8, l1_font_size: SIZE, l2_font_size: SIZE, l3_font_size: SIZE, l4_font_size: SIZE, l5_font_size: SIZE, l6_font_size: SIZE, l7_font_size: SIZE, level_indentation: NUM, l1_indentation: NUM, l2_indentation: NUM, l3_indentation: NUM, l4_indentation: NUM, l5_indentation: NUM, l6_indentation: NUM, l7_indentation: NUM, no_dots: true, disable_dotted_lines: true, disable_links: true, disable_toc_links: true, disable_back_links:true, xsl_style_sheet: "file.xsl"} end end end
- Cách sử dụng nâng cao
- Nếu bạn cần phải chỉ cần tạo ra một pdf và không hiển thị nó:
- Tạo pdf từ string
- Nếu bạn cần phải chỉ cần tạo ra một pdf và không hiển thị nó:
pdf = WickedPdf.new.pdf_from_string("ceate a pdf from a string")
+ Tạo ra một tập tin PDF từ một file html mà không cần chuyển đổi nó thành string. + Đường dẫn là đường dẫ n tuyệt đối
pdf = WickedPdf.new.pdf_from_html_file("your_path")
+ Tạo file PDF từ đường dẫn có sẵn
pdf = WickedPdf.new.pdf_from_url("url)
+ Tạo file PDF từ string sử dụng `template`, `layouts` và nội dung tùy chọn (`header`, `footer`)
string = ApplicationController.new.render_to_string( template: "pc/orders/details.pdf.slim", layout: "pc/layouts/pdf.slim", locals: {:@order => order} ) pdf = WickedPdf.new.pdf_from_string string, encoding: "UTF-8"
+ Lưu file pdf
File.open(save_path, "wb") do file| file << pdf end