premailer 1.23.0 → 1.29.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 +4 -4
- data/README.md +118 -29
- data/bin/premailer +1 -1
- data/lib/premailer/adapter/nokogiri.rb +33 -32
- data/lib/premailer/adapter/nokogiri_fast.rb +42 -44
- data/lib/premailer/adapter/nokogumbo.rb +33 -35
- data/lib/premailer/adapter/rgb_to_hex.rb +4 -3
- data/lib/premailer/adapter.rb +10 -13
- data/lib/premailer/cached_rule_set.rb +1 -0
- data/lib/premailer/executor.rb +12 -11
- data/lib/premailer/html_to_plain_text.rb +20 -17
- data/lib/premailer/premailer.rb +162 -125
- data/lib/premailer/version.rb +2 -1
- data/lib/premailer.rb +1 -0
- metadata +12 -133
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: fa4f38aaadca592e45c38537b54ad6e88bd15c0c43c07efed0beb25af8194766
|
|
4
|
+
data.tar.gz: cde54fad4ac9397bd09b88509aa2b5a22daaa1721172a7c98e0e78c94e8707ad
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: bc0358601f237a6ec2cf74764dfb28e5d800cf1ca486d88ca44a7e4d3913ade8ff00b76b98017fa6f565f5812bd6f9c3e66be819708a2764a70fca051458f09f
|
|
7
|
+
data.tar.gz: 9ea81979f54bd5fd9d8edb2e390e5900d53b7462064bc1465999dba639218db5a479c74e93e6e179d6d6a51abbf066685a21b033d5003899ab037a021db385f7
|
data/README.md
CHANGED
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
|
|
5
5
|
For the best HTML e-mail delivery results, CSS should be inline. This is a
|
|
6
6
|
huge pain and a simple newsletter becomes un-managable very quickly. This
|
|
7
|
-
|
|
7
|
+
gem is a solution.
|
|
8
8
|
|
|
9
9
|
* CSS styles are converted to inline style attributes
|
|
10
10
|
- Checks `style` and `link[rel=stylesheet]` tags and preserves existing inline attributes
|
|
@@ -12,35 +12,26 @@ script is my solution.
|
|
|
12
12
|
- Checks links in `href`, `src` and CSS `url('')`
|
|
13
13
|
* CSS properties are checked against e-mail client capabilities
|
|
14
14
|
- Based on the Email Standards Project's guides
|
|
15
|
-
* A [plain text version](
|
|
15
|
+
* A [plain text version](#plain-text-version) is created (optional)
|
|
16
16
|
|
|
17
17
|
## Installation
|
|
18
18
|
|
|
19
|
-
Install the Premailer gem from RubyGems.
|
|
20
|
-
|
|
21
19
|
```bash
|
|
22
20
|
gem install premailer
|
|
23
21
|
```
|
|
24
22
|
|
|
25
|
-
or add it to your `Gemfile` and run `bundle`.
|
|
26
|
-
|
|
27
23
|
## Example
|
|
28
24
|
|
|
29
25
|
```ruby
|
|
30
26
|
require 'premailer'
|
|
31
27
|
|
|
32
|
-
premailer = Premailer.new('http://example.com/myfile.html', :
|
|
28
|
+
premailer = Premailer.new('http://example.com/myfile.html', warn_level: Premailer::Warnings::SAFE)
|
|
33
29
|
|
|
34
|
-
# Write the plain-text output
|
|
35
|
-
|
|
36
|
-
File.open("output.txt", "w") do |fout|
|
|
37
|
-
fout.puts premailer.to_plain_text
|
|
38
|
-
end
|
|
30
|
+
# Write the plain-text output (must come before to_inline_css)
|
|
31
|
+
File.write "output.txt", premailer.to_plain_text
|
|
39
32
|
|
|
40
33
|
# Write the HTML output
|
|
41
|
-
File.
|
|
42
|
-
fout.puts premailer.to_inline_css
|
|
43
|
-
end
|
|
34
|
+
File.write "output.html", premailer.to_inline_css
|
|
44
35
|
|
|
45
36
|
# Output any CSS warnings
|
|
46
37
|
premailer.warnings.each do |w|
|
|
@@ -50,17 +41,13 @@ end
|
|
|
50
41
|
|
|
51
42
|
## Adapters
|
|
52
43
|
|
|
53
|
-
Premailer's default adapter is nokogiri if both nokogiri and nokogumbo are included in the Gemfile list. However, if you want to use a different adapter, you can choose to.
|
|
54
|
-
|
|
55
|
-
There are three adapters in total (as of premailer 1.10.0)
|
|
56
|
-
|
|
57
44
|
1. nokogiri (default)
|
|
58
|
-
2. nokogiri_fast
|
|
45
|
+
2. nokogiri_fast (20x speed, more memory)
|
|
59
46
|
3. nokogumbo
|
|
60
47
|
|
|
61
|
-
hpricot adapter removed
|
|
48
|
+
(hpricot adapter removed, use `~>1.9.0` version if you need it)
|
|
62
49
|
|
|
63
|
-
|
|
50
|
+
Picking an adapter:
|
|
64
51
|
|
|
65
52
|
```ruby
|
|
66
53
|
Premailer::Adapter.use = :nokogiri_fast
|
|
@@ -97,22 +84,125 @@ will result in
|
|
|
97
84
|
<table cellspacing='5' width='500'>
|
|
98
85
|
```
|
|
99
86
|
|
|
100
|
-
##
|
|
87
|
+
## Plain text version
|
|
88
|
+
|
|
89
|
+
Premailer can generate a plain text version of your HTML. Links and images will be inlined.
|
|
90
|
+
|
|
91
|
+
For example
|
|
92
|
+
|
|
93
|
+
```html
|
|
94
|
+
<a href="https://example.com" >
|
|
95
|
+
<img src="https://github.com/premailer.png" alt="Premailer Logo" />
|
|
96
|
+
</a>
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
will become
|
|
100
|
+
|
|
101
|
+
```text
|
|
102
|
+
Premailer Logo ( https://example.com )
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
To ignore/omit a section of HTML content from the plain text version, wrap it with the following comments.
|
|
101
106
|
|
|
102
|
-
|
|
107
|
+
```html
|
|
108
|
+
<!-- start text/html -->
|
|
109
|
+
<p>This will be omitted from the plain text version.</p>
|
|
110
|
+
<p>
|
|
111
|
+
This is extremely helpful for <strong>removing email headers and footers</strong>
|
|
112
|
+
that aren't needed in the text version.
|
|
113
|
+
</p>
|
|
114
|
+
<!-- end text/html -->
|
|
115
|
+
```
|
|
103
116
|
|
|
104
|
-
|
|
117
|
+
## Configuration options
|
|
105
118
|
|
|
119
|
+
For example:
|
|
106
120
|
```ruby
|
|
107
|
-
|
|
121
|
+
Premailer.new(
|
|
122
|
+
html, # html as string
|
|
123
|
+
with_html_string: true,
|
|
124
|
+
drop_unmergeable_css_rules: true
|
|
125
|
+
)
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
[available options](https://premailer.github.io/premailer/Premailer.html#initialize-instance_method)
|
|
129
|
+
|
|
130
|
+
## Support for CSS variables
|
|
131
|
+
|
|
132
|
+
The gem does not automatically replace CSS variables with their static values.
|
|
133
|
+
|
|
134
|
+
For example, if a variable is used to set the `font-weight` of an `h1` element, the result will be
|
|
135
|
+
```html
|
|
136
|
+
<h1 style="
|
|
137
|
+
font-size:3rem;
|
|
138
|
+
font-weight:var(--bulma-content-heading-weight);">
|
|
139
|
+
Title</h1>
|
|
140
|
+
```
|
|
141
|
+
|
|
142
|
+
This causes the `font-weight` value to be the CSS variable call `var(--bulma-content-heading-weight);` instead of its static value.
|
|
143
|
+
|
|
144
|
+
### Replace CSS variable calls with their static values
|
|
145
|
+
|
|
146
|
+
The following section instructs how to replace CSS variables with their static value in the context of a Ruby on Rails application.
|
|
147
|
+
|
|
148
|
+
Install the `postcss-css-variables` plugin for PostCSS to process the CSS variables.
|
|
149
|
+
|
|
150
|
+
```shell
|
|
151
|
+
yarn add postcss postcss-cli postcss-css-variables
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
To configure the plugin, create the file `postcss.config.js` in the root directory with the content:
|
|
155
|
+
|
|
156
|
+
```javascript
|
|
157
|
+
module.exports = {
|
|
158
|
+
plugins: [
|
|
159
|
+
// https://github.com/MadLittleMods/postcss-css-variables to transform the css
|
|
160
|
+
require("postcss-css-variables")({
|
|
161
|
+
preserve: false, // Set to false to replace variables with static values
|
|
162
|
+
}),
|
|
163
|
+
],
|
|
164
|
+
};
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
In the `package.json` file, add the new "build:emails" to the scripts.<br>Replace `./app/assets/stylesheets/emails.css` with your file path:
|
|
168
|
+
```json
|
|
169
|
+
"scripts": {
|
|
170
|
+
"build:emails": "postcss ./app/assets/stylesheets/emails.css -o ./app/assets/builds/emails.css"
|
|
171
|
+
}
|
|
108
172
|
```
|
|
109
173
|
|
|
110
|
-
|
|
174
|
+
The previous script processes and overwrites the file at `./app/assets/stylesheets/emails.css` with PostCSS using its `postcss-css-variables` plugin, replacing the CSS variables with their static value.
|
|
111
175
|
|
|
176
|
+
If the file to be processed is not `.css`, but `.scss`, it needs to be converted first to `.css`, then have its variables replaced. The script would then be
|
|
177
|
+
|
|
178
|
+
```json
|
|
179
|
+
"scripts": {
|
|
180
|
+
"build:emails": "sass ./app/assets/stylesheets/emails.scss:./app/assets/builds/emails.css --no-source-map --load-path=node_modules && postcss ./app/assets/builds/emails.css -o ./app/assets/builds/emails.css"
|
|
181
|
+
}
|
|
182
|
+
```
|
|
183
|
+
|
|
184
|
+
Next, to execute the script when running `bin/dev`, add the following line in the file `Procfile.dev`
|
|
185
|
+
|
|
186
|
+
```
|
|
187
|
+
emails_css: yarn build:emails --watch
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
The srcipt can also be executed separately with the command
|
|
191
|
+
|
|
192
|
+
```shell
|
|
193
|
+
yarn build:emails
|
|
194
|
+
```
|
|
195
|
+
|
|
196
|
+
### Caveat
|
|
197
|
+
|
|
198
|
+
The variables must be declared before use. Otherwise, their values when called will be set to `undefined`.
|
|
112
199
|
|
|
113
200
|
## Contributions
|
|
114
201
|
|
|
115
|
-
Contributions are most welcome.
|
|
202
|
+
Contributions are most welcome.
|
|
203
|
+
Premailer was rotting away in a private SVN repository for too long and could use some TLC.
|
|
204
|
+
Fork and patch to your heart's content.
|
|
205
|
+
Please don't increment the version numbers.
|
|
116
206
|
|
|
117
207
|
A few areas that are particularly in need of love:
|
|
118
208
|
|
|
@@ -129,4 +219,3 @@ and to [Campaign Monitor](https://www.campaignmonitor.com/) for supporting the w
|
|
|
129
219
|
The source code can be found on [GitHub](https://github.com/premailer/premailer).
|
|
130
220
|
|
|
131
221
|
Copyright by Alex Dunae (dunae.ca, e-mail 'code' at the same domain), 2007-2017. See [LICENSE.md](https://github.com/premailer/premailer/blob/master/LICENSE.md) for license details.
|
|
132
|
-
|
data/bin/premailer
CHANGED
|
@@ -1,9 +1,11 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
1
2
|
require 'nokogiri'
|
|
2
3
|
|
|
3
4
|
class Premailer
|
|
4
5
|
module Adapter
|
|
5
6
|
# Nokogiri adapter
|
|
6
7
|
module Nokogiri
|
|
8
|
+
WIDTH_AND_HIGHT = ['width', 'height'].freeze
|
|
7
9
|
|
|
8
10
|
include AdapterHelper::RgbToHex
|
|
9
11
|
# Merge CSS into the HTML document.
|
|
@@ -21,19 +23,19 @@ class Premailer
|
|
|
21
23
|
# Iterate through the rules and merge them into the HTML
|
|
22
24
|
@css_parser.each_selector(:all) do |selector, declaration, specificity, media_types|
|
|
23
25
|
# Save un-mergable rules separately
|
|
24
|
-
selector.gsub!(/:link([\s]*)+/i) { |
|
|
26
|
+
selector.gsub!(/:link([\s]*)+/i) { |_m| $1 }
|
|
25
27
|
|
|
26
28
|
# Convert element names to lower case
|
|
27
|
-
selector.gsub!(/([\s]|^)([\w]+)/) { |
|
|
29
|
+
selector.gsub!(/([\s]|^)([\w]+)/) { |_m| $1.to_s + $2.to_s.downcase }
|
|
28
30
|
|
|
29
|
-
if Premailer.
|
|
30
|
-
@unmergable_rules.add_rule_set!(CssParser::RuleSet.new(selector, declaration), media_types) unless @options[:preserve_styles]
|
|
31
|
+
if Premailer.media_query?(media_types) || selector =~ Premailer::RE_UNMERGABLE_SELECTORS
|
|
32
|
+
@unmergable_rules.add_rule_set!(CssParser::RuleSet.new(selectors: selector, block: declaration), media_types) unless @options[:preserve_styles]
|
|
31
33
|
else
|
|
32
34
|
begin
|
|
33
|
-
if selector
|
|
35
|
+
if Premailer::RE_RESET_SELECTORS.match?(selector) && !!@options[:preserve_reset]
|
|
34
36
|
# this is in place to preserve the MailChimp CSS reset: http://github.com/mailchimp/Email-Blueprints/
|
|
35
37
|
# however, this doesn't mean for testing pur
|
|
36
|
-
@unmergable_rules.add_rule_set!(CssParser::RuleSet.new(selector, declaration))
|
|
38
|
+
@unmergable_rules.add_rule_set!(CssParser::RuleSet.new(selectors: selector, block: declaration))
|
|
37
39
|
end
|
|
38
40
|
|
|
39
41
|
# Change single ID CSS selectors into xpath so that we can match more
|
|
@@ -41,14 +43,14 @@ class Premailer
|
|
|
41
43
|
selector.gsub!(/\A\#([\w_\-]+)\Z/, '*[@id=\1]')
|
|
42
44
|
|
|
43
45
|
doc.search(selector).each do |el|
|
|
44
|
-
if el.elem?
|
|
46
|
+
if el.elem? && ((el.name != 'head') && (el.parent.name != 'head'))
|
|
45
47
|
# Add a style attribute or append to the existing one
|
|
46
48
|
block = "[SPEC=#{specificity}[#{declaration}]]"
|
|
47
49
|
el['style'] = (el.attributes['style'].to_s ||= '') + ' ' + block
|
|
48
50
|
end
|
|
49
51
|
end
|
|
50
52
|
rescue ::Nokogiri::SyntaxError, RuntimeError, ArgumentError
|
|
51
|
-
|
|
53
|
+
warn "CSS syntax error with selector: #{selector}" if @options[:verbose]
|
|
52
54
|
next
|
|
53
55
|
end
|
|
54
56
|
end
|
|
@@ -61,8 +63,8 @@ class Premailer
|
|
|
61
63
|
doc.search("*[@style]").each do |el|
|
|
62
64
|
style = el.attributes['style'].to_s
|
|
63
65
|
|
|
64
|
-
declarations = style.scan(/\[SPEC
|
|
65
|
-
rs = Premailer::CachedRuleSet.new(
|
|
66
|
+
declarations = style.scan(/\[SPEC=([\d]+)\[(.[^\]]*)\]\]/m).filter_map do |declaration|
|
|
67
|
+
rs = Premailer::CachedRuleSet.new(block: declaration[1].to_s, specificity: declaration[0].to_i)
|
|
66
68
|
rs.expand_shorthand!
|
|
67
69
|
rs
|
|
68
70
|
rescue ArgumentError => e
|
|
@@ -78,9 +80,9 @@ class Premailer
|
|
|
78
80
|
end
|
|
79
81
|
|
|
80
82
|
# Duplicate CSS attributes as HTML attributes
|
|
81
|
-
if Premailer::RELATED_ATTRIBUTES.
|
|
83
|
+
if Premailer::RELATED_ATTRIBUTES.key?(el.name) && @options[:css_to_attributes]
|
|
82
84
|
Premailer::RELATED_ATTRIBUTES[el.name].each do |css_attr, html_attr|
|
|
83
|
-
if el[html_attr].nil?
|
|
85
|
+
if el[html_attr].nil? && !merged[css_attr].empty?
|
|
84
86
|
new_val = merged[css_attr].dup
|
|
85
87
|
|
|
86
88
|
# Remove url() function wrapper
|
|
@@ -90,7 +92,7 @@ class Premailer
|
|
|
90
92
|
new_val.gsub!(/;$|\s*!important/, '').strip!
|
|
91
93
|
|
|
92
94
|
# For width and height tags, remove px units
|
|
93
|
-
new_val.gsub!(/(\d+)px/, '\1') if
|
|
95
|
+
new_val.gsub!(/(\d+)px/, '\1') if WIDTH_AND_HIGHT.include?(html_attr)
|
|
94
96
|
|
|
95
97
|
# For color-related tags, convert RGB to hex if specified by options
|
|
96
98
|
new_val = ensure_hex(new_val) if css_attr.end_with?('color') && @options[:rgb_to_hex_attributes]
|
|
@@ -99,7 +101,7 @@ class Premailer
|
|
|
99
101
|
end
|
|
100
102
|
|
|
101
103
|
unless @options[:preserve_style_attribute]
|
|
102
|
-
merged.instance_variable_get(
|
|
104
|
+
merged.instance_variable_get(:@declarations).tap do |declarations|
|
|
103
105
|
declarations.delete(css_attr)
|
|
104
106
|
end
|
|
105
107
|
end
|
|
@@ -115,9 +117,9 @@ class Premailer
|
|
|
115
117
|
|
|
116
118
|
doc = write_unmergable_css_rules(doc, @unmergable_rules) unless @options[:drop_unmergeable_css_rules]
|
|
117
119
|
|
|
118
|
-
if @options[:remove_classes]
|
|
120
|
+
if @options[:remove_classes] || @options[:remove_comments]
|
|
119
121
|
doc.traverse do |el|
|
|
120
|
-
if el.comment?
|
|
122
|
+
if el.comment? && @options[:remove_comments]
|
|
121
123
|
el.remove
|
|
122
124
|
elsif el.element?
|
|
123
125
|
el.remove_attribute('class') if @options[:remove_classes]
|
|
@@ -129,7 +131,7 @@ class Premailer
|
|
|
129
131
|
# find all anchor's targets and hash them
|
|
130
132
|
targets = []
|
|
131
133
|
doc.search("a[@href^='#']").each do |el|
|
|
132
|
-
target = el.get_attribute('href')[1
|
|
134
|
+
target = el.get_attribute('href')[1..]
|
|
133
135
|
targets << target
|
|
134
136
|
el.set_attribute('href', "#" + Digest::SHA256.hexdigest(target))
|
|
135
137
|
end
|
|
@@ -151,7 +153,7 @@ class Premailer
|
|
|
151
153
|
end
|
|
152
154
|
|
|
153
155
|
@processed_doc = doc
|
|
154
|
-
if
|
|
156
|
+
if xhtml?
|
|
155
157
|
# we don't want to encode carriage returns
|
|
156
158
|
@processed_doc.to_xhtml(:encoding => @options[:output_encoding]).gsub(/&\#(xD|13);/i, "\r")
|
|
157
159
|
else
|
|
@@ -173,17 +175,16 @@ class Premailer
|
|
|
173
175
|
style_tag.content = styles
|
|
174
176
|
doc.add_child(style_tag)
|
|
175
177
|
else
|
|
176
|
-
style_tag = doc.create_element "style",
|
|
178
|
+
style_tag = doc.create_element "style", styles.to_s
|
|
177
179
|
head = doc.at_css('head')
|
|
178
|
-
head ||= doc.root.first_element_child.add_previous_sibling(doc.create_element
|
|
179
|
-
head ||= doc.add_child(doc.create_element
|
|
180
|
+
head ||= doc.root.first_element_child.add_previous_sibling(doc.create_element("head")) if doc.root&.first_element_child
|
|
181
|
+
head ||= doc.add_child(doc.create_element("head"))
|
|
180
182
|
head << style_tag
|
|
181
183
|
end
|
|
182
184
|
end
|
|
183
185
|
doc
|
|
184
186
|
end
|
|
185
187
|
|
|
186
|
-
|
|
187
188
|
# Converts the HTML document to a format suitable for plain-text e-mail.
|
|
188
189
|
#
|
|
189
190
|
# If present, uses the <body> element as its base; otherwise uses the whole document.
|
|
@@ -193,17 +194,17 @@ class Premailer
|
|
|
193
194
|
html_src = ''
|
|
194
195
|
begin
|
|
195
196
|
html_src = @doc.at("body").inner_html
|
|
196
|
-
rescue
|
|
197
|
+
rescue StandardError
|
|
197
198
|
end
|
|
198
199
|
|
|
199
|
-
html_src = @doc.to_html unless html_src
|
|
200
|
+
html_src = @doc.to_html unless html_src && !html_src.empty?
|
|
200
201
|
convert_to_text(html_src, @options[:line_length], @html_encoding)
|
|
201
202
|
end
|
|
202
203
|
|
|
203
204
|
# Gets the original HTML as a string.
|
|
204
205
|
# @return [String] HTML.
|
|
205
206
|
def to_s
|
|
206
|
-
if
|
|
207
|
+
if xhtml?
|
|
207
208
|
@doc.to_xhtml(:encoding => nil)
|
|
208
209
|
else
|
|
209
210
|
@doc.to_html(:encoding => nil)
|
|
@@ -217,13 +218,13 @@ class Premailer
|
|
|
217
218
|
thing = nil
|
|
218
219
|
|
|
219
220
|
# TODO: duplicate options
|
|
220
|
-
if @options[:with_html_string]
|
|
221
|
+
if @options[:with_html_string] || @options[:inline] || input.respond_to?(:read)
|
|
221
222
|
thing = input
|
|
222
223
|
elsif @is_local_file
|
|
223
224
|
@base_dir = File.dirname(input)
|
|
224
225
|
thing = File.open(input, 'r')
|
|
225
226
|
else
|
|
226
|
-
thing = URI.
|
|
227
|
+
thing = URI.parse(input).open
|
|
227
228
|
end
|
|
228
229
|
|
|
229
230
|
if thing.respond_to?(:read)
|
|
@@ -234,7 +235,8 @@ class Premailer
|
|
|
234
235
|
doc = nil
|
|
235
236
|
|
|
236
237
|
# Handle HTML entities
|
|
237
|
-
if @options[:replace_html_entities] == true
|
|
238
|
+
if (@options[:replace_html_entities] == true) && thing.is_a?(String)
|
|
239
|
+
thing = +thing
|
|
238
240
|
HTML_ENTITIES.map do |entity, replacement|
|
|
239
241
|
thing.gsub! entity, replacement
|
|
240
242
|
end
|
|
@@ -243,21 +245,20 @@ class Premailer
|
|
|
243
245
|
doc = if @options[:html_fragment]
|
|
244
246
|
::Nokogiri::HTML.fragment(thing, encoding)
|
|
245
247
|
else
|
|
246
|
-
::Nokogiri::HTML(thing, nil, encoding
|
|
248
|
+
::Nokogiri::HTML(thing, nil, encoding, &:recover)
|
|
247
249
|
end
|
|
248
250
|
|
|
249
251
|
# Fix for removing any CDATA tags from both style and script tags inserted per
|
|
250
252
|
# https://github.com/sparklemotion/nokogiri/issues/311 and
|
|
251
253
|
# https://github.com/premailer/premailer/issues/199
|
|
252
|
-
|
|
254
|
+
['style', 'script'].each do |tag|
|
|
253
255
|
doc.search(tag).children.each do |child|
|
|
254
|
-
child.swap(child.text
|
|
256
|
+
child.swap(child.text) if child.cdata?
|
|
255
257
|
end
|
|
256
258
|
end
|
|
257
259
|
|
|
258
260
|
doc
|
|
259
261
|
end
|
|
260
|
-
|
|
261
262
|
end
|
|
262
263
|
end
|
|
263
264
|
end
|