Module: Controllers::Webpackable
- Extended by:
- ActiveSupport::Concern
- Included in:
- ApplicationController
- Defined in:
- app/concerns/controllers/webpackable.rb
Overview
Webpackable - Rails concern for webpack asset management
This module provides helpers for including webpack assets (JS/CSS) in Rails views.
It uses WebpackManifestLoader to get fresh asset URLs from the webpack manifest,
avoiding stale cache issues that can occur with traditional Rails caching.
Key Features:
- Fresh manifest loading (no stale cache issues)
- Development webpack dev server support
- Font preloading for custom typography
- Error handling and fallbacks
Usage in Controllers:
include Controllers::Webpackable
Usage in Views:
<%= webpack_js_include 'www' %>
<%= webpack_css_include 'crm' %>
<%= preload_webpack_fonts %>
<% if wpd_is_running? %>...<% end %>
Dependencies:
- WebpackManifestLoader (config/initializers/webpack_manifest.rb)
- Webpack assets built to public/javascripts/webpack/
Instance Method Summary collapse
-
#preload_webpack_fonts ⇒ void
Preloads custom typography fonts for better performance.
-
#webpack_css_include(webpack_file, track: false, exclude: []) ⇒ String
Generates link tags for webpack CSS bundles.
-
#webpack_css_url(webpack_file, exclude: []) ⇒ Array<String>
Returns the URL(s) for a webpack CSS bundle.
-
#webpack_js_include(webpack_file, async: false, defer: false, track: false) ⇒ String
Generates script tags for webpack JavaScript bundles.
-
#wpd_is_running? ⇒ Boolean
Checks if webpack dev server is running in development.
Instance Method Details
#preload_webpack_fonts ⇒ void
This method returns an undefined value.
Preloads custom typography fonts for better performance
Preloads Sofia Pro fonts (light, regular, semibold) and Orpheus Pro fonts
(normal, medium, bold) to prevent font loading delays and improve perceived
performance. Font Awesome 7 Pro+ uses SVG+JS so no font preloading is needed for icons.
Example:
<%= preload_webpack_fonts %>
136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 |
# File 'app/concerns/controllers/webpackable.rb', line 136 def preload_webpack_fonts # Font Awesome 7 Pro+ now uses SVG+JS - no font preloading needed # Only preload custom typography fonts (Sofia Pro, Orpheus Pro, Inter, Playfair Display) # Skip preloading in development to avoid warnings return if Rails.env.development? && wpd_is_running? # Only preload the two fonts needed above the fold. The remaining fonts # (semibold, Orpheus Pro, Inter, Playfair Display) load via @font-face # with font-display:swap and no longer compete with the LCP image for # bandwidth on the critical path (~200 KB freed from the Link header). custom_fonts = %w[ sofiapro-light-webfont sofiapro-regular-webfont ] # Preload custom typography fonts custom_fonts.each do |font| url = Array(get_hashed_name_from_manifest(font, 'woff2')).first next if url.blank? helpers.preload_link_tag( ensure_absolute_wpd_url(url, wpd_is_running? ? dev_server_origin : nil), as: :font, type: 'font/woff2', crossorigin: :anonymous, nopush: false, skip_pipeline: true ) rescue StandardError => e Rails.logger.warn "Custom font preload failed for #{font}: #{e.}" end end |
#webpack_css_include(webpack_file, track: false, exclude: []) ⇒ String
Generates link tags for webpack CSS bundles
Example:
<%= webpack_css_include 'crm', track: true %> # layout main bundle
<%= webpack_css_include 'rpStyles' %> # per-page bundle
91 92 93 94 95 96 97 98 99 100 101 102 103 |
# File 'app/concerns/controllers/webpackable.rb', line 91 def webpack_css_include(webpack_file, track: false, exclude: []) names = get_hashed_name_from_manifest(webpack_file, 'css') origin = wpd_is_running? ? dev_server_origin : nil = names.filter_map do |url| next if exclude.any? { |e| url.include?(e) } full_url = ensure_absolute_wpd_url(url, origin) helpers.tag.link(rel: 'stylesheet', href: full_url, media: 'all', **turbo_track_attr(track)) end safe_join(, "\n") rescue StandardError => e Rails.logger.error "webpack_css_include error: #{e.}" '' end |
#webpack_css_url(webpack_file, exclude: []) ⇒ Array<String>
Returns the URL(s) for a webpack CSS bundle
Example:
webpack_css_url('www') # => ["/javascripts/webpack/www-abc123.css"]
113 114 115 116 117 118 119 120 121 122 123 |
# File 'app/concerns/controllers/webpackable.rb', line 113 def webpack_css_url(webpack_file, exclude: []) names = get_hashed_name_from_manifest(webpack_file, 'css') origin = wpd_is_running? ? dev_server_origin : nil names.filter_map do |url| next if exclude.any? { |e| url.include?(e) } ensure_absolute_wpd_url(url, origin) end rescue StandardError => e Rails.logger.error "webpack_css_url error: #{e.}" [] end |
#webpack_js_include(webpack_file, async: false, defer: false, track: false) ⇒ String
Generates script tags for webpack JavaScript bundles
Example:
<%= webpack_js_include 'crm', track: true %> # layout main bundle
<%= webpack_js_include 'reports' %> # per-page bundle
61 62 63 64 65 66 67 68 69 70 71 72 73 |
# File 'app/concerns/controllers/webpackable.rb', line 61 def webpack_js_include(webpack_file, async: false, defer: false, track: false) names = get_hashed_name_from_manifest(webpack_file, 'js') # Prefix dev-server origin in development when WDS is running origin = wpd_is_running? ? dev_server_origin : nil = names.map do |url| full_url = ensure_absolute_wpd_url(url, origin) helpers.javascript_include_tag(full_url, async: async, defer: defer, **turbo_track_attr(track)) end safe_join(, "\n") rescue StandardError => e Rails.logger.error "webpack_js_include error: #{e.}" '' end |
#wpd_is_running? ⇒ Boolean
Checks if webpack dev server is running in development
Example:
<% if wpd_is_running? %>
<% end %>
177 178 179 |
# File 'app/concerns/controllers/webpackable.rb', line 177 def wpd_is_running? webpack_dev_server_running? end |