Skip to content

Commit

Permalink
Add prepend_javascript_pack_tag helper (shakacode#235)
Browse files Browse the repository at this point in the history
* Add Webpack::Helper.prepend_javascript_pack_tag
  • Loading branch information
paypro-leon authored Jan 31, 2023
1 parent 9deec04 commit e13d841
Show file tree
Hide file tree
Showing 5 changed files with 84 additions and 13 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ _Please add entries here for your pull requests that are not yet released._
### Fixed
- Upgrade several JS dependencies to fix security issues. [PR 243](https://github.com/shakacode/shakapacker/pull/243) by [ahangarha](https://github.com/ahangarha).

- Added `prepend_javascript_pack_tag` to helpers. Allows to move an entry to the top of queue. Handy when calling from the layout to make sure an entry goes before the view and partial `append_javascript_pack_tag` entries. [PR 235](https://github.com/shakacode/shakapacker/pull/235) by [paypro-leon](https://github.com/paypro-leon).

## [6.5.6] - January 15, 2023
### Fixed
- Remove duplicate yarn installs. [PR 238](https://github.com/shakacode/shakapacker/pull/238) by [justin808](https://github/justin808).
Expand Down
30 changes: 27 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ Here's a testimonial of how ShakaCode can help, from [Florian Gößler](https://
- [Configuration and Code](#configuration-and-code)
- [View Helpers](#view-helpers)
- [View Helpers `javascript_pack_tag` and `stylesheet_pack_tag`](#view-helpers-javascript_pack_tag-and-stylesheet_pack_tag)
- [View Helper `append_javascript_pack_tag` and `append_stylesheet_pack_tag`](#view-helper-append_javascript_pack_tag-and-append_stylesheet_pack_tag)
- [View Helpers `append_javascript_pack_tag`, `prepend_javascript_pack_tag` and `append_stylesheet_pack_tag`](#view-helper-append_javascript_pack_tag-prepend_javascript_pack_tag-and-append_stylesheet_pack_tag)
- [View Helper: `asset_pack_path`](#view-helper-asset_pack_path)
- [View Helper: `image_pack_tag`](#view-helper-image_pack_tag)
- [View Helper: `favicon_pack_tag`](#view-helper-favicon_pack_tag)
Expand Down Expand Up @@ -267,7 +267,7 @@ While this also generally applies to `stylesheet_pack_tag`, you may use multiple
<%= stylesheet_pack_tag 'print', media: 'print' %>
```

#### View Helper `append_javascript_pack_tag` and `append_stylesheet_pack_tag`
#### View Helper `append_javascript_pack_tag`, `prepend_javascript_pack_tag` and `append_stylesheet_pack_tag`

If you need configure your script pack names or stylesheet pack names from the view for a route or partials, then you will need some logic to ensure you call the helpers only once with multiple arguments. The new view helpers, `append_javascript_pack_tag` and `append_stylesheet_pack_tag` can solve this problem. The helper `append_javascript_pack_tag` will queue up script packs when the `javascript_pack_tag` is finally used. Similarly,`append_stylesheet_pack_tag` will queue up style packs when the `stylesheet_pack_tag` is finally used.

Expand Down Expand Up @@ -300,7 +300,7 @@ However, you typically can't do that in the main layout, as the view and partial

Thus, you can distribute the logic of what packs are needed for any route. All the magic of splitting up the code and CSS was automatic!

**Important:** Both `append_(javascript/stylesheet)_pack_tag` helpers can be used anywhere in your application as long as they are executed BEFORE `(javascript/stylesheet)_pack_tag` respectively. If you attempt to call one of the `append_(javascript/stylesheet)_pack_tag` helpers after the respective `(javascript/stylesheet)_pack_tag`, an error will be raised.
**Important:** These helpers can be used anywhere in your application as long as they are executed BEFORE `(javascript/stylesheet)_pack_tag` respectively. If you attempt to call one of these helpers after the respective `(javascript/stylesheet)_pack_tag`, an error will be raised.

The typical issue is that your layout might reference some partials that need to configure packs. A good way to solve this problem is to use `content_for` to ensure that the code to render your partial comes before the call to `javascript_pack_tag`.

Expand All @@ -313,6 +313,30 @@ The typical issue is that your layout might reference some partials that need to
<%= content_for :footer %>
```

There is also `prepend_javascript_pack_tag` that will put the entry at the front of the queue. This is handy when you want an entry in the main layout to go before the partial and main layout `append_javascript_pack_tag` entries.

Main view:
```erb
<% append_javascript_pack_tag 'map' %>
```

Some partial:
```erb
<% append_javascript_pack_tag 'map' %>
```

And the main layout has:
```erb
<% prepend_javascript_pack_tag 'main' %>
<%= javascript_pack_tag 'application' %>
```

is the same as using this in the main layout:

```erb
<%= javascript_pack_tag 'main', 'calendar', 'map', application' %>
```

For alternative options of setting the additional packs, [see this discussion](https://github.com/shakacode/shakapacker/issues/39).

#### View Helper: `asset_pack_path`
Expand Down
29 changes: 20 additions & 9 deletions lib/webpacker/helper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -169,7 +169,7 @@ def stylesheet_pack_tag(*names, **options)
def append_stylesheet_pack_tag(*names)
if @stylesheet_pack_tag_loaded
raise "You can only call append_stylesheet_pack_tag before stylesheet_pack_tag helper. " \
"Please refer to https://github.com/shakacode/shakapacker/blob/master/README.md#view-helper-append_javascript_pack_tag-and-append_stylesheet_pack_tag for the usage guide"
"Please refer to https://github.com/shakacode/shakapacker/blob/master/README.md#view-helper-append_javascript_pack_tag-prepend_javascript_pack_tag-and-append_stylesheet_pack_tag for the usage guide"
end

@stylesheet_pack_tag_queue ||= []
Expand All @@ -180,20 +180,31 @@ def append_stylesheet_pack_tag(*names)
end

def append_javascript_pack_tag(*names, defer: true)
if @javascript_pack_tag_loaded
raise "You can only call append_javascript_pack_tag before javascript_pack_tag helper. " \
"Please refer to https://github.com/shakacode/shakapacker/blob/master/README.md#view-helper-append_javascript_pack_tag-and-append_stylesheet_pack_tag for the usage guide"
update_javascript_pack_tag_queue(defer: defer) do |hash_key|
javascript_pack_tag_queue[hash_key] |= names
end
end

hash_key = defer ? :deferred : :non_deferred
javascript_pack_tag_queue[hash_key] |= names

# prevent rendering Array#to_s representation when used with <%= … %> syntax
nil
def prepend_javascript_pack_tag(*names, defer: true)
update_javascript_pack_tag_queue(defer: defer) do |hash_key|
javascript_pack_tag_queue[hash_key].unshift(*names)
end
end

private

def update_javascript_pack_tag_queue(defer:)
if @javascript_pack_tag_loaded
raise "You can only call #{caller_locations(1..1).first.label} before javascript_pack_tag helper. " \
"Please refer to https://github.com/shakacode/shakapacker/blob/master/README.md#view-helper-append_javascript_pack_tag-prepend_javascript_pack_tag-and-append_stylesheet_pack_tag for the usage guide"
end

yield(defer ? :deferred : :non_deferred)

# prevent rendering Array#to_s representation when used with <%= … %> syntax
nil
end

def javascript_pack_tag_queue
@javascript_pack_tag_queue ||= {
deferred: [],
Expand Down
28 changes: 27 additions & 1 deletion spec/helper_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -106,17 +106,43 @@ def base_url
expect(javascript_pack_tag("application")).to eq expected
end

it "#javascript_pack_tag generates correct prepended tag" do
append_javascript_pack_tag("bootstrap")
prepend_javascript_pack_tag("main")

expected = <<~HTML.chomp
<script src="/packs/main-e323a53c7f30f5d53cbb.js" defer="defer"></script>
<script src="/packs/bootstrap-300631c4f0e0f9c865bc.js" defer="defer"></script>
<script src="/packs/vendors~application~bootstrap-c20632e7baf2c81200d3.chunk.js" defer="defer"></script>
<script src="/packs/vendors~application-e55f2aae30c07fb6d82a.chunk.js" defer="defer"></script>
<script src="/packs/application-k344a6d59eef8632c9d1.js" defer="defer"></script>
HTML

expect(javascript_pack_tag("application")).to eq expected
end

it "#append_javascript_pack_tag raises error if called after calling #javascript_pack_tag" do
expected_error_message = \
"You can only call append_javascript_pack_tag before javascript_pack_tag helper. " +
"Please refer to https://github.com/shakacode/shakapacker/blob/master/README.md#view-helper-append_javascript_pack_tag-and-append_stylesheet_pack_tag for the usage guide"
"Please refer to https://github.com/shakacode/shakapacker/blob/master/README.md#view-helper-append_javascript_pack_tag-prepend_javascript_pack_tag-and-append_stylesheet_pack_tag for the usage guide"

expect {
javascript_pack_tag("application")
append_javascript_pack_tag("bootstrap", defer: false)
}.to raise_error(expected_error_message)
end

it "#prepend_javascript_pack_tag raises error if called after calling #javascript_pack_tag" do
expected_error_message = \
"You can only call prepend_javascript_pack_tag before javascript_pack_tag helper. " +
"Please refer to https://github.com/shakacode/shakapacker/blob/master/README.md#view-helper-append_javascript_pack_tag-prepend_javascript_pack_tag-and-append_stylesheet_pack_tag for the usage guide"

expect {
javascript_pack_tag("application")
prepend_javascript_pack_tag("bootstrap", defer: false)
}.to raise_error(expected_error_message)
end

it "#javascript_pack_tag generates correct tags by passing `defer: true`" do
expected = <<~HTML.chomp
<script src="/packs/vendors~application~bootstrap-c20632e7baf2c81200d3.chunk.js" defer="defer"></script>
Expand Down
8 changes: 8 additions & 0 deletions spec/test_app/public/packs/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
"bootstrap.css": "/packs/bootstrap-c38deda30895059837cf.css",
"application.css": "/packs/application-dd6b1cd38bfa093df600.css",
"bootstrap.js": "/packs/bootstrap-300631c4f0e0f9c865bc.js",
"main.js": "/packs/main-e323a53c7f30f5d53cbb.js",
"application.js": "/packs/application-k344a6d59eef8632c9d1.js",
"application.png": "/packs/application-k344a6d59eef8632c9d1.png",
"fonts/fa-regular-400.woff2": "/packs/fonts/fa-regular-400-944fb546bd7018b07190a32244f67dc9.woff2",
Expand Down Expand Up @@ -31,6 +32,13 @@
]
}
},
"main": {
"assets": {
"js": [
"/packs/main-e323a53c7f30f5d53cbb.js"
]
}
},
"hello_stimulus": {
"assets": {
"css": [
Expand Down

0 comments on commit e13d841

Please sign in to comment.