pdfgen 0.3.1 → 0.4.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +26 -0
- data/README.md +109 -4
- data/VERSION +1 -1
- data/lib/javascript_bin/make_pdf.js +17 -4
- data/lib/pdfgen.rb +42 -8
- metadata +3 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 45448b8e51eeefad7bc03b038ee898858bac2ac1
|
4
|
+
data.tar.gz: ca91ce8dc5d9935e9826be88d07e606110cce11d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: cce5490b833405690e1ee9f306d54cba65d36b634e262b8a234150d305212b284a745a38537ee337d649295573df3c64fff00fd19ea3ee9b1d2027a4254e400b
|
7
|
+
data.tar.gz: '009f9f2a12c02ae43de9fb28743baf42b7ad653c23c6a0434a9c371d9d0452758434ea9fa5f87c66c38ce937f1057d86f13726dbd9ee90302102f3e62009c0bd'
|
data/CHANGELOG.md
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
## Pdfgen 0.4.0 (May 12, 2018)
|
2
|
+
|
3
|
+
* Can now provide a URL to the initializer.
|
4
|
+
|
5
|
+
Providing a URL to the initializer will now nagivate to the URL and then render the
|
6
|
+
page to a PDF.
|
7
|
+
|
8
|
+
* Adds a debug mode.
|
9
|
+
|
10
|
+
Calling debug_mode and passing in a time in milliseconds to wait with the browser
|
11
|
+
not headless. This may change to be forever in the future but that would cause weird
|
12
|
+
issues since the Ruby code expects the Javascript to return the PDF on stdout and
|
13
|
+
there isn't yet a good way to indicate that you are done debugging and the rendering
|
14
|
+
can continue.
|
15
|
+
|
16
|
+
## Pdfgen 0.3.1 (April 23, 2018)
|
17
|
+
|
18
|
+
* Fixes bug by passing the wait_for_timeout to the Javascript script.
|
19
|
+
|
20
|
+
## Pdfgen 0.3.0 (April 23, 2018)
|
21
|
+
|
22
|
+
* Allows optional period in milliseconds to wait for the page to finish rendering.
|
23
|
+
|
24
|
+
A new optional wait timeout that will occur after the content has been set,
|
25
|
+
the media emulation set, and the viewport has been set to allow for javascript
|
26
|
+
and rendering to run before printing to a pdf
|
data/README.md
CHANGED
@@ -24,15 +24,120 @@ pdf_as_string = Pdfgen.new(html_to_turn_into_pdf).to_pdf
|
|
24
24
|
`to_pdf` returns the pdf as a string. This makes it easy to send to a client from a web server like
|
25
25
|
Rails or to save to a file if that is desired.
|
26
26
|
|
27
|
-
If you need to provide options such as page margins you can pass them as a hash to `to_pdf`. Any
|
27
|
+
If you need to provide options such as page margins you can pass them as a hash to `to_pdf`. Any
|
28
28
|
options that work for [Puppeteer's `pdf` method](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pagepdfoptions)
|
29
29
|
are accepted as they are passed through without modification.
|
30
30
|
```ruby
|
31
31
|
pdf_as_string = Pdfgen.new(html_to_turn_into_pdf).to_pdf(margins: { top: '1in', bottom: '1in' })
|
32
|
-
```
|
32
|
+
```
|
33
|
+
|
34
|
+
# Reference
|
35
|
+
|
36
|
+
All methods other than `to_pdf` are chainable. This allows for setting multiple configuration options before rendering the PDF.
|
37
|
+
It also does not matter the order that they are called in except that `to_pdf` must be last since it returns the PDF.
|
38
|
+
|
39
|
+
Example:
|
40
|
+
```ruby
|
41
|
+
Pdfgen.new(html).set_viewport(width: 1024, height: 768).wait_for_timeout(1000).emulate_media('screen').to_pdf(format: 'Letter')
|
42
|
+
```
|
43
|
+
|
44
|
+
## Initialize
|
45
|
+
|
46
|
+
### new(html_or_url)
|
47
|
+
|
48
|
+
Takes a string of HTML to put into the page or a URL to nagivate to. If it is a URL, extra options for the navigation can be
|
49
|
+
provided with [`url_options`](#url_optionsurl_options). If a string of HTML, the assets must be inlined to work. See [Limitations](#limitations)
|
50
|
+
|
51
|
+
## Chainable configuration methods
|
52
|
+
|
53
|
+
### debug_mode(debug_time)
|
54
|
+
|
55
|
+
Sets a couple of options so the browser window used to print the PDF can be seen and inspected. *debug_time* is
|
56
|
+
the amount of time in milliseconds to leave the browser window open before the PDF will be printed and the browser
|
57
|
+
closed. It also disables headless mode.
|
58
|
+
|
59
|
+
Example: Turns on debug mode and waits for 5 minutes.
|
60
|
+
```ruby
|
61
|
+
Pdfgen.new(html).debug_mode(300_000).to_pdf
|
62
|
+
```
|
63
|
+
|
64
|
+
### emulate_media(media_type)
|
65
|
+
|
66
|
+
Configure the media type for the browser used to render the PDF. Media type can be `'screen'`, `'print'`, or `null`.
|
67
|
+
See [emulateMedia](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pageemulatemediamediatype) for more info.
|
68
|
+
|
69
|
+
Example: Set the media emulation type to print.
|
70
|
+
```ruby
|
71
|
+
Pdfgen.new(html).emulate_media('print').to_pdf
|
72
|
+
```
|
73
|
+
|
74
|
+
### launch_options(launch_options)
|
75
|
+
|
76
|
+
Configure the options used to launch the browser. Can be used to set extra args for the browser such as `--no-sandbox` or to
|
77
|
+
disable headless mode. *launch_options* is a hash that is passed directly to the [launch](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#puppeteerlaunchoptions)
|
78
|
+
Puppeteer method and as such takes the same arguments.
|
79
|
+
|
80
|
+
Example: Adds '--no-sandbox' flag and turns off headless mode.
|
81
|
+
```ruby
|
82
|
+
Pdfgen.new(html).launch_options(args: ['--no-sandbox'], headless: false).to_pdf
|
83
|
+
```
|
84
|
+
|
85
|
+
### set_viewport(viewport_options)
|
86
|
+
|
87
|
+
Configure the viewport. *viewport_options* is a hash that is passed directly to the
|
88
|
+
[setViewport](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pagesetviewportviewport)
|
89
|
+
Puppeteer method and as such takes the same arguments.
|
90
|
+
|
91
|
+
Example: Sets the viewport width and height to 1024x768.
|
92
|
+
```ruby
|
93
|
+
Pdfgen.new(html).set_viewport(width: 1024, height: 768).to_pdf
|
94
|
+
```
|
95
|
+
|
96
|
+
### url_options(url_options)
|
97
|
+
|
98
|
+
When using a URL, this configures the navigation options. It is mainly used to configure what to wait for. *url_options* is
|
99
|
+
a hash that is passed directly as the second argument to [goto](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pagegotourl-options)
|
100
|
+
Puppeteer method and as such takes the same arguments. Defaults to `waitUntil: 'networkidle0'` which will wait until there are
|
101
|
+
0 active network connections in the past 500 milliseconds.
|
102
|
+
|
103
|
+
Example:
|
104
|
+
```ruby
|
105
|
+
Pdfgen.new('https://www.google.com').url_options(waitUntil: 'networkidle0').to_pdf
|
106
|
+
```
|
107
|
+
|
108
|
+
### wait_for_timeout(wait_for_timeout)
|
109
|
+
|
110
|
+
Configure an optional timeout to wait for with the browser loaded before the PDF will be saved specified in
|
111
|
+
milliseconds. Used to allow the page to finish rendering if the default prints the PDF to fast.
|
112
|
+
|
113
|
+
Example: Sets the wait timeout to 1.5 seconds.
|
114
|
+
```ruby
|
115
|
+
Pdfgen.new(html).wait_for_timeout(1500).to_pdf
|
116
|
+
```
|
117
|
+
|
118
|
+
## PDF rendering methods
|
119
|
+
|
120
|
+
### to_pdf(opts)
|
121
|
+
|
122
|
+
Configure the options for making the PDF. It allows for setting margins, a scale, specific page ranges, configuring
|
123
|
+
the paper type, and more. *opts* is a hash that is passed directly to the [pdf](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pagepdfoptions)
|
124
|
+
Puppeteer method and as such takes the same arguments.
|
125
|
+
|
126
|
+
Example: Configures the margins to be 1 inch all around.
|
127
|
+
```ruby
|
128
|
+
Pdfgen.new(html).to_pdf(margin: {top: '1in', right: '1in', bottom: '1in', left: '1in'})
|
129
|
+
```
|
130
|
+
|
131
|
+
# Limitations
|
132
|
+
|
133
|
+
#### It only works with inline Javascript, CSS, and images.
|
134
|
+
|
135
|
+
Currently, there is a limitation that requires inline assets. This is because the setContent method in Puppeteer does not load links to
|
136
|
+
assets. There is a workaround possible since Puppeteer allows adding script tags and style tags and those methods do take URLs but Pdfgen
|
137
|
+
does not yet support them.
|
33
138
|
|
34
139
|
# Future Development
|
35
|
-
In the future, allowing use of more features of Puppeteer is desired. These include taking a URL and
|
140
|
+
In the future, allowing use of more features of Puppeteer is desired. These include taking a URL and
|
36
141
|
setting cookies. Instead of using a fixed make_pdf.js script, it will probably make sense to convert
|
37
142
|
to generating that javascript file on the fly using templates since additional options like allowing
|
38
|
-
the setting of cookies will require calling more functions than are currently being called.
|
143
|
+
the setting of cookies will require calling more functions than are currently being called.
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.4.0
|
@@ -19,18 +19,28 @@ stdin.on('end', function () {
|
|
19
19
|
var media_type = options['emulate_media'];
|
20
20
|
var launch_options = options['launch_options'];
|
21
21
|
var wait_for_timeout = options['wait_for_timeout'];
|
22
|
+
var url = options['url'];
|
23
|
+
var url_options = options['url_options'];
|
24
|
+
var debug_mode = options['debug_mode'];
|
22
25
|
|
23
26
|
module.paths.push(current_path + '/node_modules');
|
24
27
|
|
25
28
|
const puppeteer = require('puppeteer');
|
26
29
|
const fs = require('fs');
|
27
|
-
|
30
|
+
|
31
|
+
if (typeof url === 'undefined') {
|
32
|
+
var html = fs.readFileSync(process.argv[2], 'utf8');
|
33
|
+
}
|
28
34
|
|
29
35
|
(async() => {
|
30
36
|
const browser = await puppeteer.launch(launch_options);
|
31
37
|
const page = await browser.newPage();
|
32
38
|
|
33
|
-
|
39
|
+
if (typeof url !== 'undefined' && url) {
|
40
|
+
await page.goto(url, url_options);
|
41
|
+
} else {
|
42
|
+
await page.setContent(html);
|
43
|
+
}
|
34
44
|
|
35
45
|
if (typeof media_type !== 'undefined' && media_type) {
|
36
46
|
await page.emulateMedia(media_type);
|
@@ -44,8 +54,11 @@ stdin.on('end', function () {
|
|
44
54
|
await page.waitFor(wait_for_timeout);
|
45
55
|
}
|
46
56
|
|
47
|
-
|
48
|
-
|
57
|
+
if (typeof debug_mode === 'undefined') {
|
58
|
+
const pdf_output = await page.pdf(pdf_options);
|
59
|
+
stdout.write(pdf_output);
|
60
|
+
}
|
61
|
+
|
49
62
|
await browser.close();
|
50
63
|
})();
|
51
64
|
});
|
data/lib/pdfgen.rb
CHANGED
@@ -9,12 +9,20 @@ raise 'This gem requires node be installed and available on the PATH' unless sta
|
|
9
9
|
MAKE_PDF_COMMAND = File.expand_path('../javascript_bin/make_pdf.js', __FILE__)
|
10
10
|
|
11
11
|
class Pdfgen
|
12
|
-
def initialize(
|
13
|
-
|
12
|
+
def initialize(html_or_url)
|
13
|
+
if html_or_url =~ /^http/
|
14
|
+
@url = html_or_url
|
15
|
+
@html = nil
|
16
|
+
else
|
17
|
+
@url = nil
|
18
|
+
@html = html_or_url
|
19
|
+
end
|
14
20
|
@viewport_options = nil
|
15
21
|
@emulate_media = nil
|
16
22
|
@launch_options = Hash.new
|
17
23
|
@wait_for_timeout = nil
|
24
|
+
@debug_time = nil
|
25
|
+
@url_options = { waitUntil: 'networkidle0' }
|
18
26
|
end
|
19
27
|
|
20
28
|
def set_viewport(viewport_options)
|
@@ -38,16 +46,42 @@ class Pdfgen
|
|
38
46
|
self
|
39
47
|
end
|
40
48
|
|
49
|
+
def debug_mode(debug_time)
|
50
|
+
raise TypeError.new("Timeout must be an integer or respond to #to_i") unless debug_time.kind_of?(Integer) || (debug_time.respond_to?(:to_i) && debug_time.to_i)
|
51
|
+
@debug_time = debug_time
|
52
|
+
self
|
53
|
+
end
|
54
|
+
|
55
|
+
def url_options(url_options)
|
56
|
+
@url_options = @url_options.merge(url_options)
|
57
|
+
self
|
58
|
+
end
|
59
|
+
|
41
60
|
def to_pdf(opts = {})
|
42
|
-
stdin_options = { pdf_options: opts, current_path: Dir.pwd
|
61
|
+
stdin_options = { pdf_options: opts, current_path: Dir.pwd }
|
43
62
|
stdin_options = stdin_options.merge(viewport_options: @viewport_options) if @viewport_options
|
44
63
|
stdin_options = stdin_options.merge(emulate_media: @emulate_media) if @emulate_media
|
45
64
|
stdin_options = stdin_options.merge(wait_for_timeout: @wait_for_timeout) if @wait_for_timeout
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
65
|
+
if @debug_time
|
66
|
+
stdin_options = stdin_options.merge(wait_for_timeout: @debug_time)
|
67
|
+
stdin_options = stdin_options.merge(launch_options: @launch_options.merge(headless: false))
|
68
|
+
stdin_options = stdin_options.merge(debug_mode: true)
|
69
|
+
end
|
70
|
+
|
71
|
+
pdf_output = nil
|
72
|
+
status = nil
|
73
|
+
if @html
|
74
|
+
file = Tempfile.new('input_html')
|
75
|
+
file.write(@html)
|
76
|
+
file.close
|
77
|
+
pdf_output, status = Open3.capture2(MAKE_PDF_COMMAND, file.path, stdin_data: stdin_options.to_json)
|
78
|
+
file.unlink
|
79
|
+
else
|
80
|
+
stdin_options = stdin_options.merge(url: @url)
|
81
|
+
stdin_options = stdin_options.merge(url_options: @url_options)
|
82
|
+
pdf_output, status = Open3.capture2(MAKE_PDF_COMMAND, stdin_data: stdin_options.to_json)
|
83
|
+
end
|
84
|
+
|
51
85
|
unless status.success?
|
52
86
|
raise 'There was an unknown error running node to create the pdf. Check your logs for output that might assist in debugging.'
|
53
87
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pdfgen
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.4.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Daniel Fox
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-
|
11
|
+
date: 2018-05-12 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: minitest
|
@@ -31,6 +31,7 @@ executables: []
|
|
31
31
|
extensions: []
|
32
32
|
extra_rdoc_files: []
|
33
33
|
files:
|
34
|
+
- CHANGELOG.md
|
34
35
|
- LICENSE
|
35
36
|
- README.md
|
36
37
|
- Rakefile
|