Kumquat

 Kumquat

0426d158b1df6dcbcfdc0823db883eae?s=128

Fred Benenson

August 17, 2015
Tweet

Transcript

  1. fred@kickstarter.com / @fredbenenson Kumquat Rendering RMarkdown in Rails https://github.com/kickstarter/kumquat

  2. This is actually a story about an email

  3. A single, very important, email

  4. None
  5. The data you report to yourself is the story you

    tell yourself about your business.
  6. There are a couple of ways to look at data*

    • Interactive Tools • Dashboards • Recurring Reports • One-off reports
  7. Current Options for Offline Reports & Graphs • Google Charts

    API • rChart • ???
  8. None
  9. None
  10. None
  11. None
  12. None
  13. None
  14. None
  15. None
  16. None
  17. None
  18. knitr & RMarkdown • Like Markdown, but for R •

    Can evaluate R code chunks into HTML & PNG output (or PDF) • Helpful for generating reproducible reports A Test Report for Kumquat ======================================================== This is some code for Knitr, including [a link](https://www.kickstarter.com). A list: * One * Another thing * Last thing! ### More stuff. Lorem Ipsum. ```{r, fig.width=10, fig.height=8, echo=FALSE, message=FALSE} library(ggplot2) qplot(data = data.frame( x = runif(100), y = runif(100) ), x = x, y = y) ``` ### Another ```{r, fig.width=10, fig.height=8, echo=FALSE, message=FALSE} library(ggplot2) qplot(data = data.frame( x = runif(100), y = runif(100) ), x = x, y = y) ``` ### A Table ```{r, results='asis', echo=FALSE} library(hwriter) cat(hwrite(data.frame( x = runif(10), y = runif(10) ))) ```
  19. A Test Report for Kumquat ======================================================== This is some code

    for Knitr, including [a link](https://www.kickstarter.com). A list: * One * Another thing * Last thing! ### More stuff. Lorem Ipsum. ```{r, fig.width=10, fig.height=8, echo=FALSE, message=FALSE} Normal Markdown } library(ggplot2) qplot(data = data.frame( x = runif(100), y = runif(100) ), x = x, y = y) ``` knitr call } R code }
  20. None
  21. R + ggplot2 + knitr + Redshift + Rails +

    Email = New Email Reporting Framework
  22. Kumquat • Shells out to `Rscript`, runs knitr, returns HTML

    & base64 encoded images • Includes a Ruby Template Handler for rendering .Rmd Files • Includes a Mail Interceptor for attaching inline images • Includes a Chef recipe for installing R & libraries in production
  23. Rails Template Handlers • Extremely flexible system for adding support

    for new file types to your system • .haml, .ruby, etc. • So why not .Rmd?
  24. Running RScript in Production $ Rscript -e "library(knitr); library(redshift); setwd('/var/folders/sy/

    gsrl8ysx5jvdmjc61b__qyhw0000gn/T/kumquat_20150313-85241-10r0rg6'); source('redshift_credentials.r'); knit2html('/Users/fcb/Desktop/Kickstarter/kickstarter/app/ reports/admin_mailer/_live_project_graphs.Rmd', options=c('use_xhtml','smartypants','mathjax','highlight_code', 'base64_images'))" 2>&1
  25. Template Handler for .Rmd class RmdTemplateHandler class_attribute :default_format self.default_format =

    Mime::HTML def call(template) k = Knit2HTML.new(Rails.root.join(template.inspect)) k.knit.inspect + '.html_safe' end end
  26. Mail Interceptor pt. 1 def extract_images cleaned = @content.dup ts

    = Time.now.to_f @content.scan(/img src="(.+?)"/).flatten.each.with_index do |img_data, index| (type, b64) = img_data.split(',', 2) name = "image_#{index}" cid = "#{ts}_#{name}@kumquat.magic" @images[name] = { mime_type: type[%r|\w+/\w+|], content: Base64.decode64(b64), cid: cid, content_id: "<#{cid}>" } cleaned.gsub!(img_data, "cid:#{URI.escape(cid)}") end cleaned end
  27. Mail Interceptor pt. 2 def process mail['X-KUMQUAT'] = nil mail.html_part.body

    = extract_images mail['X-SIG'] = 'bypass' m = mail # Need a local variable so that we don't fight with the mail object mixed_part = Mail::Part.new do content_type 'multipart/alternative' m.parts.delete_if { |p| add_part p } end mail.add_part mixed_part # Set the message content-type to be 'multipart/mixed' mail.content_type 'multipart/related' mail.header['content-type'].parameters[:boundary] = mail.body.boundary @images.each do |key, image| mail.attachments.inline[key] = image end mail end
  28. None
  29. _test_report.Rmd A Test Report for Kumquat ======================================================== This is some

    code for Knitr, including [a link](https://www.kickstarter.com). A list: * One * Another thing * Last thing! ### More stuff. Lorem Ipsum. ```{r, fig.width=10, fig.height=8, echo=FALSE, message=FALSE} library(ggplot2) qplot(data = data.frame( x = runif(100), y = runif(100) ), x = x, y = y) ```
  30. None
  31. fred@kickstarter.com / @fredbenenson Kumquat Rendering RMarkdown in Rails https://github.com/kickstarter/kumquat