eml_to_pdf 0.2.0 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: e81efeb010801805fe22e63ff844e4a3f400955c
4
- data.tar.gz: 1a02a94a289f960e79827c5f63d927d6d37a2888
2
+ SHA256:
3
+ metadata.gz: 4ca4521f1d3dd67c4bec67daa9470390d9fb4f2ea6567e2623241699f812a9c2
4
+ data.tar.gz: beaaf4003bd695c8621e6a81e4afa66c0bb829a0d0d5fa582ca18815e5e93697
5
5
  SHA512:
6
- metadata.gz: b613139c02acf27408c43fad2114e34db2321ea9fa2b3709923f4dbc610d15f62751bce105a06e046b7d7246487b6e46d59a785fbe0afc84efe47decb1b70e8c
7
- data.tar.gz: 43e6e8b27008a6482229fa8077af78bcc245b0987d905c3fb7636b3de4f387308a9a459aa6413f05bd3df2df000580fa26583622a195808dc7f74a558bdc76cc
6
+ metadata.gz: 404e1d85c233b1fb6a8b753a755210b76f8e3cfa571e0fe3ee8b205d83c0d4bf1f5879f31b30f340133ef94057aa4e67af548c10f67e2a1a7a8627c20a3f3505
7
+ data.tar.gz: 0c8a0d071dad60ce8bfaf43c5b0d33c1250902aa0e032de0f107d8cf7d7996b34c942bd7682b127b4576ecb85b34afc9eccdcd72babdf05facc1748c09cf4bd8
@@ -0,0 +1,5 @@
1
+ languages:
2
+ Ruby: true
3
+ exclude_paths:
4
+ - "lib/eml_to_pdf/extraction_step.rb"
5
+ - "test/"
data/.gitignore CHANGED
@@ -6,4 +6,5 @@
6
6
  /doc/
7
7
  /pkg/
8
8
  /spec/reports/
9
- /tmp/
9
+ /tmp/*
10
+ !/tmp/.gitkeep
@@ -1 +1 @@
1
- 2.2.2
1
+ 2.7.1
@@ -1,4 +1,11 @@
1
1
  language: ruby
2
+ cache: bundler
2
3
  rvm:
3
- - 2.2.2
4
- before_install: gem install bundler -v 1.10.6
4
+ - 2.6
5
+ - 2.7
6
+
7
+ before_install:
8
+ - gem install bundler
9
+ - sudo apt-get install xfonts-75dpi xfonts-base
10
+ - wget https://github.com/wkhtmltopdf/wkhtmltopdf/releases/download/0.12.5/wkhtmltox_0.12.5-1.xenial_amd64.deb
11
+ - sudo apt install ./wkhtmltox_0.12.5-1.xenial_amd64.deb
data/README.md CHANGED
@@ -4,7 +4,8 @@ Welcome to EmlToPdf.
4
4
  A small converter to convert an eml file to a pdf.
5
5
  This gem uses `wkhtmltopdf`. You can get the installer from [here](http://wkhtmltopdf.org/downloads.html)
6
6
 
7
- [![Build Status](https://travis-ci.org/Elektron1c97/eml_to_pdf.svg?branch=master)](https://travis-ci.org/Elektron1c97/eml_to_pdf)
7
+ [![Build Status](https://travis-ci.org/siegy22/eml_to_pdf.svg?branch=master)](https://travis-ci.org/siegy22/eml_to_pdf)
8
+ [![Code Climate](https://codeclimate.com/github/siegy22/eml_to_pdf/badges/gpa.svg)](https://codeclimate.com/github/siegy22/eml_to_pdf)
8
9
 
9
10
  ## Installation
10
11
 
@@ -30,11 +31,14 @@ Use the `configure` method to configure your labels
30
31
 
31
32
  ```ruby
32
33
  EmlToPdf.configure do |config|
34
+ config.timeout = 60 # Seconds, defaults to 0
33
35
  config.from_label = "From =>"
34
36
  config.to_label = "To =>"
35
37
  config.cc_label = "Cc =>"
36
38
  config.date_label = "Date =>"
37
- config.date_format = "%d.%m.%Y" # see Date#strftime
39
+ config.date_format do |date|
40
+ date.strftime("%Y")
41
+ end
38
42
  end
39
43
  ```
40
44
 
@@ -56,7 +60,7 @@ To install this gem onto your local machine, run `bundle exec rake install`. To
56
60
 
57
61
  ## Contributing
58
62
 
59
- Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/eml_to_pdf. This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the [Contributor Covenant](contributor-covenant.org) code of conduct.
63
+ Bug reports and pull requests are welcome on GitHub at https://github.com/siegy22/eml_to_pdf. This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the [Contributor Covenant](contributor-covenant.org) code of conduct.
60
64
 
61
65
 
62
66
  ## License
data/Rakefile CHANGED
@@ -3,6 +3,7 @@ require 'rake/testtask'
3
3
 
4
4
  Rake::TestTask.new do |t|
5
5
  t.libs << 'test'
6
+ t.test_files = FileList['test/*_test.rb']
6
7
  end
7
8
 
8
9
  desc "Run tests"
@@ -19,11 +19,13 @@ Gem::Specification.new do |spec|
19
19
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
20
20
  spec.require_paths = ["lib"]
21
21
 
22
- spec.add_development_dependency "bundler", "~> 1.10"
23
- spec.add_development_dependency "rake", "~> 10.0"
22
+ spec.required_ruby_version = ">= 2.2.0"
23
+
24
+ spec.add_development_dependency "bundler", ">= 1.10"
25
+ spec.add_development_dependency "rake", "~> 12.0"
24
26
  spec.add_development_dependency 'minitest', '~> 5.9'
25
27
 
26
28
  spec.add_runtime_dependency 'filesize', '~> 0.1.1'
27
29
  spec.add_runtime_dependency 'mail', '~> 2.5', '>= 2.5.4'
28
- spec.add_runtime_dependency 'nokogiri', '~> 1.6', '>= 1.6.7.2'
30
+ spec.add_runtime_dependency 'nokogiri', '~> 1.7'
29
31
  end
@@ -1,13 +1,4 @@
1
1
  #!/usr/bin/env ruby
2
- # TODO: use this to convert whole folders
3
- # Dir["test/fixtures/emails/*.eml"].each do |test_file|
4
- # puts "> converting #{test_file}"
5
- # begin
6
- # EmlToPdf.convert(test_file, "#{test_file[0..-5]}_output.pdf")
7
- # rescue NoMethodError => e
8
- # puts e.message
9
- # end
10
- # end
11
2
 
12
3
  if ARGV[0] && ARGV[1]
13
4
  require "bundler/setup"
@@ -5,6 +5,8 @@ require "eml_to_pdf/converter"
5
5
  require "eml_to_pdf/email"
6
6
  require "eml_to_pdf/wkhtmltopdf"
7
7
  require "eml_to_pdf/metadata_context"
8
+ require "eml_to_pdf/extraction_step"
9
+ require "eml_to_pdf/extraction_step_list"
8
10
 
9
11
  module EmlToPdf
10
12
  def self.convert(input, output)
@@ -1,22 +1,27 @@
1
1
  module EmlToPdf
2
2
  class Configuration
3
- attr_accessor :from_label, :to_label, :cc_label, :date_label
4
- attr_reader :date_format
3
+ attr_accessor :from_label, :to_label, :cc_label, :date_label, :wkhtmltopdf, :timeout
5
4
 
6
5
  def initialize
7
6
  @from_label = "From"
8
7
  @to_label = "To"
9
8
  @cc_label = "Cc"
10
9
  @date_label = "Date"
11
- @date_format = "%Y-%m-%d %H:%M:%S %z"
10
+ @date_format = lambda { |date| date.strftime("%Y-%m-%d %H:%M:%S %z") }
11
+ @wkhtmltopdf = 'wkhtmltopdf'
12
+ @timeout = 0
12
13
  end
13
14
 
14
- def date_format=(value)
15
- if value.is_a?(String)
16
- @date_format = value
15
+ def date_format(&block)
16
+ if block_given?
17
+ @date_format = block
17
18
  else
18
- raise ArgumentError, "You can only use a String to format the date. (See Date#strftime)"
19
+ @date_format
19
20
  end
20
21
  end
22
+
23
+ def format_date(date)
24
+ @date_format.call(date)
25
+ end
21
26
  end
22
27
  end
@@ -5,12 +5,6 @@ require "erb"
5
5
 
6
6
  module EmlToPdf
7
7
  class Email
8
- MIME_TYPES = {
9
- plain_text: "text/plain",
10
- html: "text/html",
11
- multipart_alternative: "multipart/alternative"
12
- }
13
-
14
8
  TEMPLATES_PATH = Pathname.new(File.expand_path(__dir__)) + "templates"
15
9
 
16
10
  def initialize(input_path)
@@ -19,26 +13,15 @@ module EmlToPdf
19
13
  end
20
14
 
21
15
  def to_html
22
- html = text_parts(@mail).join
23
- html = resolve_cids_from_attachments(html, @mail.attachments)
16
+ extraction = ExtractionStep.new(@mail)
17
+ extraction = extraction.next until extraction.finished?
18
+ html = extraction.to_html
19
+ html = resolve_cids_from_attachments(html, @mail.all_parts)
24
20
  html = add_mail_metadata_to_html(@mail, html)
25
21
  html
26
22
  end
27
23
 
28
24
  private
29
- def text_parts(mail_or_part)
30
- if mail_or_part.multipart? && multipart_alternative?(mail_or_part)
31
- best_part = extract_best_part(mail_or_part.parts)
32
- text_parts(best_part)
33
- elsif mail_or_part.multipart?
34
- mail_or_part.parts.map do |part|
35
- text_parts(part)
36
- end
37
- else
38
- [text_body(mail_or_part)]
39
- end.flatten
40
- end
41
-
42
25
  def visible_attachments(mail)
43
26
  mail.attachments.select do |attachment|
44
27
  !attachment.inline?
@@ -64,42 +47,6 @@ module EmlToPdf
64
47
  end
65
48
  end
66
49
 
67
- def extract_best_part(parts)
68
- if multipart_part = parts.detect(&:multipart?)
69
- multipart_part
70
- elsif html_part = find_body_with_type(parts, :html)
71
- html_part
72
- elsif text_part = find_body_with_type(parts, :plain_text)
73
- text_part
74
- else
75
- "can't find useable part"
76
- end
77
- end
78
-
79
- def find_body_with_type(parts, type)
80
- parts.detect do |part|
81
- part.mime_type == MIME_TYPES[type]
82
- end
83
- end
84
-
85
- def multipart_alternative?(part)
86
- part.mime_type == MIME_TYPES[:multipart_alternative]
87
- end
88
-
89
- def text_body(mail_or_part)
90
- if mail_or_part.mime_type == MIME_TYPES[:html] && !mail_or_part.attachment?
91
- mail_or_part.decoded
92
- elsif mail_or_part.mime_type == MIME_TYPES[:plain_text] && !mail_or_part.attachment?
93
- wrap_text_in_pre_tag(mail_or_part.decoded)
94
- else
95
- ""
96
- end
97
- end
98
-
99
- def wrap_text_in_pre_tag(text)
100
- "<pre>#{text}</pre>"
101
- end
102
-
103
50
  def add_mail_metadata_to_html(mail, html)
104
51
  context = MetadataContext.new(from: save_extract_header(mail, :from),
105
52
  to: save_extract_header(mail, :to),
@@ -123,11 +70,7 @@ module EmlToPdf
123
70
  end
124
71
 
125
72
  def save_extract_header(mail, header)
126
- if header = mail.header[header]
127
- header.decoded
128
- else
129
- ""
130
- end
73
+ (mail.header[header] && mail.header[header].decoded) || ""
131
74
  end
132
75
  end
133
76
  end
@@ -1,54 +1,63 @@
1
- module EmlToPdf
1
+ require 'eml_to_pdf/extraction_step_list'
2
+ require 'eml_to_pdf/empty_part'
2
3
 
3
- # TODO: in email#to_html remove recursive function with this class
4
- # for a better control and to be able to make more unit tests.
4
+ module EmlToPdf
5
5
  class ExtractionStep
6
+ MIME_TYPES = {
7
+ plain_text: "text/plain",
8
+ html: "text/html",
9
+ multipart_alternative: "multipart/alternative"
10
+ }
11
+
6
12
  def initialize(mail_or_part)
7
13
  @mail_or_part = mail_or_part
8
14
  end
9
15
 
10
- # extraction = ExtractionStep.new(@mail)
11
- # extraction = extraction.next until extraction.finished?
12
-
13
16
  def next
14
17
  if multipart_alternative?(@mail_or_part)
15
18
  best_part = extract_best_part(@mail_or_part.parts)
16
19
  ExtractionStep.new(best_part)
17
20
  elsif @mail_or_part.multipart?
18
-
21
+ ExtractionStepList.new(@mail_or_part.parts.map { |part| ExtractionStep.new(part) })
19
22
  else
20
-
23
+ self
21
24
  end
22
25
  end
23
26
 
24
27
  def finished?
25
- @mail_or_part.parts.none?(&:multipart?)
28
+ !@mail_or_part.multipart?
26
29
  end
27
30
 
28
31
  def to_html
29
- if html_part = @mail_or_part.html_part
30
- html_part
31
- elsif text_part = @mail_or_part.text_part
32
- wrap_text_in_pre_tag(text_part)
32
+ text_body(@mail_or_part)
33
+ end
34
+
35
+ private
36
+ def multipart_alternative?(part)
37
+ part.mime_type == MIME_TYPES[:multipart_alternative]
38
+ end
39
+
40
+ def text_body(mail_or_part)
41
+ if mail_or_part.mime_type == MIME_TYPES[:html] && !mail_or_part.attachment?
42
+ mail_or_part.decoded
43
+ elsif mail_or_part.mime_type == MIME_TYPES[:plain_text] && !mail_or_part.attachment?
44
+ wrap_text_in_pre_tag(mail_or_part.decoded)
33
45
  else
34
46
  ""
35
47
  end
36
48
  end
37
49
 
38
50
  def extract_best_part(parts)
39
- if multipart_part = parts.detect(&:multipart?)
40
- multipart_part
41
- elsif html_part = find_body_with_type(parts, :html)
42
- html_part
43
- elsif text_part = find_body_with_type(parts, :plain_text)
44
- text_part
45
- else
46
- "can't find useable part"
47
- end
51
+ parts.detect(&:multipart?) ||
52
+ find_body_with_type(parts, :html) ||
53
+ find_body_with_type(parts, :plain_text) ||
54
+ EmlToPdf::EmptyPart.new
48
55
  end
49
56
 
50
- def multipart_alternative?(part)
51
- part.mime_type == MIME_TYPES[:multipart_alternative]
57
+ def find_body_with_type(parts, type)
58
+ parts.detect do |part|
59
+ part.mime_type == MIME_TYPES[type]
60
+ end
52
61
  end
53
62
 
54
63
  def wrap_text_in_pre_tag(text)
@@ -0,0 +1,24 @@
1
+ module EmlToPdf
2
+ class ExtractionStepList
3
+ def initialize(steps)
4
+ @steps = steps
5
+ end
6
+
7
+ def next
8
+ self.class.new(@steps.map(&:next))
9
+ end
10
+
11
+ def finished?
12
+ @steps.all?(&:finished?)
13
+ end
14
+
15
+ def to_html
16
+ @steps.flatten.map(&:to_html).join
17
+ end
18
+
19
+ private
20
+ def multipart_alternative?(part)
21
+ part.mime_type == MIME_TYPES[:multipart_alternative]
22
+ end
23
+ end
24
+ end
@@ -1,14 +1,9 @@
1
1
  require "filesize"
2
2
  require "cgi"
3
+ require "ostruct"
3
4
 
4
5
  module EmlToPdf
5
- class MetadataContext
6
- def initialize(metadata)
7
- metadata.each do |k, v|
8
- eval("@#{k}=v")
9
- end
10
- end
11
-
6
+ class MetadataContext < OpenStruct
12
7
  def config
13
8
  EmlToPdf.configuration
14
9
  end
@@ -18,7 +13,7 @@ module EmlToPdf
18
13
  end
19
14
 
20
15
  def format_date(date)
21
- date.strftime(config.date_format)
16
+ config.format_date(date)
22
17
  end
23
18
 
24
19
  def html_escape(str)
@@ -3,25 +3,25 @@
3
3
  <table>
4
4
  <tr>
5
5
  <td><strong><%= config.from_label %></strong></td>
6
- <td><%= html_escape(@from) %></td>
6
+ <td><%= html_escape(from) %></td>
7
7
  </tr>
8
8
  <tr>
9
9
  <td><strong><%= config.to_label %></strong></td>
10
- <td><%= html_escape(@to) %></td>
10
+ <td><%= html_escape(to) %></td>
11
11
  </tr>
12
12
  <tr>
13
13
  <td><strong><%= config.cc_label %></strong></td>
14
- <td><%= html_escape(@cc) %></td>
14
+ <td><%= html_escape(cc) %></td>
15
15
  </tr>
16
16
  <tr>
17
17
  <td><strong><%= config.date_label %></strong></td>
18
- <td><%= format_date(@date) if @date %></td>
18
+ <td><%= format_date(date) if date %></td>
19
19
  </tr>
20
20
  </table>
21
- <h3><%= @subject %></h3>
21
+ <h3><%= subject %></h3>
22
22
  <hr>
23
23
  <ul class="email-attachments">
24
- <% @attachments.each do |att| %>
24
+ <% attachments.each do |att| %>
25
25
  <li class="attachement">
26
26
  <span class="filename"><%= att.filename %></span>
27
27
  <span class="file-size"><%= format_attachment_size(att) %></span>
@@ -1,3 +1,3 @@
1
1
  module EmlToPdf
2
- VERSION = "0.2.0"
2
+ VERSION = "0.5.0"
3
3
  end
@@ -1,10 +1,25 @@
1
+ require 'timeout'
2
+
1
3
  module EmlToPdf
2
4
  class Wkhtmltopdf
5
+ class ConversionError < StandardError; end
6
+ class ConversionTimeoutError < StandardError
7
+ def message
8
+ "Failed to convert within the configured timeout. Use EmlToPdf.configure to increase the timeout if needed."
9
+ end
10
+ end
11
+
3
12
  def self.convert(input, output_path)
4
- IO.popen("wkhtmltopdf --encoding utf-8 --footer-center [page] --footer-spacing 2.5 - #{output_path} 2>&1", "r+") do |pipe|
5
- pipe.puts(input)
6
- pipe.close_write
7
- pipe.readlines # TODO save output
13
+ Timeout.timeout(EmlToPdf.configuration.timeout, ConversionTimeoutError) do
14
+ IO.popen("#{EmlToPdf.configuration.wkhtmltopdf} --encoding utf-8 --footer-center [page] --footer-spacing 2.5 --quiet - #{output_path} 2>&1", "r+") do |pipe|
15
+ pipe.puts(input)
16
+ pipe.close_write
17
+ output = pipe.readlines.join
18
+ pipe.close
19
+ unless $?.success?
20
+ raise ConversionError, output
21
+ end
22
+ end
8
23
  end
9
24
  end
10
25
  end
File without changes
metadata CHANGED
@@ -1,27 +1,27 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: eml_to_pdf
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Yves Siegrist
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2016-06-09 00:00:00.000000000 Z
11
+ date: 2020-06-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
15
15
  requirement: !ruby/object:Gem::Requirement
16
16
  requirements:
17
- - - "~>"
17
+ - - ">="
18
18
  - !ruby/object:Gem::Version
19
19
  version: '1.10'
20
20
  type: :development
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
- - - "~>"
24
+ - - ">="
25
25
  - !ruby/object:Gem::Version
26
26
  version: '1.10'
27
27
  - !ruby/object:Gem::Dependency
@@ -30,14 +30,14 @@ dependencies:
30
30
  requirements:
31
31
  - - "~>"
32
32
  - !ruby/object:Gem::Version
33
- version: '10.0'
33
+ version: '12.0'
34
34
  type: :development
35
35
  prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
38
  - - "~>"
39
39
  - !ruby/object:Gem::Version
40
- version: '10.0'
40
+ version: '12.0'
41
41
  - !ruby/object:Gem::Dependency
42
42
  name: minitest
43
43
  requirement: !ruby/object:Gem::Requirement
@@ -92,20 +92,14 @@ dependencies:
92
92
  requirements:
93
93
  - - "~>"
94
94
  - !ruby/object:Gem::Version
95
- version: '1.6'
96
- - - ">="
97
- - !ruby/object:Gem::Version
98
- version: 1.6.7.2
95
+ version: '1.7'
99
96
  type: :runtime
100
97
  prerelease: false
101
98
  version_requirements: !ruby/object:Gem::Requirement
102
99
  requirements:
103
100
  - - "~>"
104
101
  - !ruby/object:Gem::Version
105
- version: '1.6'
106
- - - ">="
107
- - !ruby/object:Gem::Version
108
- version: 1.6.7.2
102
+ version: '1.7'
109
103
  description: This gem uses wkhtmltopdf to convert an eml to a pdf. (eml -> html ->
110
104
  pdf)
111
105
  email:
@@ -115,6 +109,7 @@ executables:
115
109
  extensions: []
116
110
  extra_rdoc_files: []
117
111
  files:
112
+ - ".codeclimate.yml"
118
113
  - ".gitignore"
119
114
  - ".ruby-version"
120
115
  - ".travis.yml"
@@ -133,11 +128,13 @@ files:
133
128
  - lib/eml_to_pdf/email.rb
134
129
  - lib/eml_to_pdf/empty_part.rb
135
130
  - lib/eml_to_pdf/extraction_step.rb
131
+ - lib/eml_to_pdf/extraction_step_list.rb
136
132
  - lib/eml_to_pdf/metadata_context.rb
137
133
  - lib/eml_to_pdf/templates/heading.html.erb
138
134
  - lib/eml_to_pdf/templates/style.html
139
135
  - lib/eml_to_pdf/version.rb
140
136
  - lib/eml_to_pdf/wkhtmltopdf.rb
137
+ - tmp/.gitkeep
141
138
  homepage: https://github.com/Elektron1c97/eml_to_pdf
142
139
  licenses:
143
140
  - MIT
@@ -150,15 +147,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
150
147
  requirements:
151
148
  - - ">="
152
149
  - !ruby/object:Gem::Version
153
- version: '0'
150
+ version: 2.2.0
154
151
  required_rubygems_version: !ruby/object:Gem::Requirement
155
152
  requirements:
156
153
  - - ">="
157
154
  - !ruby/object:Gem::Version
158
155
  version: '0'
159
156
  requirements: []
160
- rubyforge_project:
161
- rubygems_version: 2.4.5
157
+ rubygems_version: 3.1.2
162
158
  signing_key:
163
159
  specification_version: 4
164
160
  summary: This gem allows you to convert an eml (email) into a pdf.