Fileboost is a Rails gem that provides seamless integration with the Fileboost.dev image optimization service. It offers drop-in replacement helpers for Rails' native image helpers with automatic optimization, HMAC authentication, and comprehensive transformation support for ActiveStorage objects.
- Features
- Requirements
- Installation
- Configuration
- Usage
- Error Handling
- Security
- Development
- Testing
- Contributing
- License
- Support
- π Drop-in replacement for Rails
image_tag
with zero code changes (NEW in v0.2.0) - π¨ Full ActiveStorage Variant support with automatic transformation mapping (NEW in v0.2.0)
- π Secure HMAC authentication with Fileboost.dev service
- π± ActiveStorage only - works exclusively with ActiveStorage attachments
- ποΈ Comprehensive transformations - resize, quality, format conversion, and more
- π§ Simple configuration - just project ID and token required
- π Automatic fallback - non-ActiveStorage images work exactly as before
- Ruby 3.0+
- Rails 7+
- ActiveStorage
Register an account at Fileboost.dev and obtain your project ID and token.
Add this line to your application's Gemfile:
gem "fileboost"
And then execute:
$ bundle install
Generate the initializer:
$ rails generate fileboost:install
Set your environment variables:
export FILEBOOST_PROJECT_ID="your-project-id"
export FILEBOOST_TOKEN="your-secret-token"
Or configure directly in your initializer:
# config/initializers/fileboost.rb
Fileboost.configure do |config|
config.project_id = ENV["FILEBOOST_PROJECT_ID"]
config.token = ENV["FILEBOOST_TOKEN"]
# Optional: Enable drop-in replacement for Rails image_tag (default: false)
config.patch_image_tag = true
end
Enable
patch_image_tag
in your configuration to automatically optimize ActiveStorage images with your existingimage_tag
calls:
# config/initializers/fileboost.rb
Fileboost.configure do |config|
config.project_id = ENV["FILEBOOST_PROJECT_ID"]
config.token = ENV["FILEBOOST_TOKEN"]
config.patch_image_tag = true # Enable automatic optimization
end
With this enabled, your existing Rails code automatically gets Fileboost optimization:
<!-- This now automatically uses Fileboost for ActiveStorage objects -->
<%= image_tag user.avatar, resize: { w: 300, h: 300 }, alt: "Avatar" %>
<%= image_tag post.featured_image, resize: { width: 800, quality: 85 }, class: "hero" %>
<!-- ActiveStorage variants work seamlessly -->
<%= image_tag user.avatar.variant(resize_to_limit: [100, 100]), alt: "Thumbnail" %>
<%= image_tag post.image.variant(:thumb), alt: "Post thumbnail" %>
<!-- Non-ActiveStorage images work exactly as before -->
<%= image_tag "/assets/logo.png", alt: "Logo" %>
<%= image_tag "https://example.com/image.jpg", alt: "External" %>
Benefits:
- Zero code changes required for existing ActiveStorage images
- Full ActiveStorage variant support with automatic transformation mapping
- Automatic fallback to Rails behavior for non-ActiveStorage assets
- Gradual migration path - enable/disable with single configuration option
Alternatively, use fileboost_image_tag
explicitly for ActiveStorage objects:
<!-- Before (Rails) -->
<%= image_tag user.avatar, width: 300, height: 300, alt: "Avatar" %>
<!-- After (Fileboost) -->
<%= fileboost_image_tag user.avatar, resize: { w: 300, h: 300 }, alt: "Avatar" %>
Note: Fileboost only works with ActiveStorage objects. String paths and external URLs are not supported.
Generate optimized URLs directly:
<div style="background-image: url(<%= fileboost_url_for(banner.image, resize: { w: 1200, h: 400 }) %>)">
<!-- content -->
</div>
Fileboost supports comprehensive image transformations:
<%= fileboost_image_tag post.image,
resize: {
width: 800, # Resize width
height: 600, # Resize height
quality: 85, # JPEG/WebP quality (1-100)
format: "jpg", # Force specific format (jpg, png, webp, avif)
blur: 5, # Blur effect (0-100)
brightness: 110, # Brightness adjustment (0-200, 100 = normal)
contrast: 120, # Contrast adjustment (0-200, 100 = normal)
rotation: 90, # Rotation in degrees (0-359)
fit: :cover # Resize behavior (cover, contain, fill, scale-down, crop, pad)
},
class: "hero-image", # Standard Rails options work too
alt: "Hero image" %>
<!-- Short parameter names also work -->
<%= fileboost_image_tag post.image,
resize: { w: 800, h: 600, q: 85, f: "jpg" },
class: "hero-image" %>
Use short or long parameter names within the resize parameter:
# These are equivalent:
fileboost_image_tag(image, resize: { w: 400, h: 300, q: 85, f: "jpg" })
fileboost_image_tag(image, resize: { width: 400, height: 300, quality: 85, format: "jpg" })
π― Smart Optimization: Fileboost's CDN automatically detects and delivers the optimal image format (WebP, AVIF, JPEG, etc.) based on browser capabilities, device type, and connection speed for maximum performance.
format
parameter should only be used in non-browser-facing scenarios (API responses, webhooks, server-to-server communication, etc.). For browser-facing images, omit the format parameter to allow Fileboost to automatically serve the best format for each user's browser and connection.
Works seamlessly with all ActiveStorage attachment types:
<!-- has_one_attached -->
<%= fileboost_image_tag user.avatar, resize: { w: 150, h: 150, fit: :cover } %>
<!-- has_many_attached -->
<% post.images.each do |image| %>
<%= fileboost_image_tag image, resize: { width: 400, quality: 90 } %>
<% end %>
<!-- Direct blob access -->
<%= fileboost_image_tag post.featured_image.blob, resize: { w: 800 } %>
Fileboost now provides full support for ActiveStorage variants with automatic transformation mapping:
<!-- Basic variants with automatic transformation mapping -->
<%= image_tag user.avatar.variant(resize_to_limit: [200, 200]) %>
<!-- β Automatically becomes: w=200&h=200&fit=scale-down -->
<%= image_tag post.image.variant(resize_to_fit: [400, 300]) %>
<!-- β Automatically becomes: w=400&h=300&fit=contain -->
<%= image_tag hero.banner.variant(resize_to_fill: [800, 400]) %>
<!-- β Automatically becomes: w=800&h=400&fit=cover -->
<!-- Complex variants with multiple transformations -->
<%= image_tag post.image.variant(
resize_to_limit: [600, 400],
quality: 85
) %>
<!-- β Automatically becomes: w=600&h=400&fit=scale-down&q=85 -->
<!-- Named variants work seamlessly -->
<%= image_tag user.avatar.variant(:thumb) %>
<!-- β Uses predefined variant transformations -->
Fileboost automatically maps ActiveStorage variant transformations to optimized URL parameters:
ActiveStorage Variant | Fileboost Parameters | Description |
---|---|---|
resize_to_limit: [w, h] |
w=W&h=H&fit=scale-down |
Resize within bounds, preserving aspect ratio |
resize_to_fit: [w, h] |
w=W&h=H&fit=contain |
Resize to fit exactly, with letterboxing if needed |
resize_to_fill: [w, h] |
w=W&h=H&fit=cover |
Resize and crop to fill exactly |
resize_and_pad: [w, h] |
w=W&h=H&fit=pad |
Resize with padding |
quality: 85 |
q=85 |
JPEG/WebP quality (1-100) |
rotate: "-90" |
r=-90 |
Rotation in degrees |
You can combine variant transformations with additional Fileboost options:
<!-- Variant transformations + additional options -->
<%= image_tag user.avatar.variant(resize_to_limit: [200, 200]),
resize: { blur: 5, brightness: 110 } %>
<!-- β Combines variant params with additional blur and brightness -->
<!-- Override variant parameters -->
<%= image_tag post.image.variant(resize_to_limit: [400, 300]),
resize: { w: 500 } %>
<!-- β Uses h=300&fit=scale-down from variant, but overrides width to 500 -->
Generate multiple sizes for responsive designs:
# In your controller or helper
@responsive_urls = fileboost_responsive_urls(hero.image, [
{ width: 400, suffix: "sm" },
{ width: 800, suffix: "md" },
{ width: 1200, suffix: "lg" }
], resize: { quality: 85 })
# Returns: { "sm" => "url1", "md" => "url2", "lg" => "url3" }
<!-- In your view -->
<img src="<%= @responsive_urls['md'] %>"
srcset="<%= @responsive_urls['sm'] %> 400w,
<%= @responsive_urls['md'] %> 800w,
<%= @responsive_urls['lg'] %> 1200w"
sizes="(max-width: 400px) 400px, (max-width: 800px) 800px, 1200px"
alt="Responsive image">
Fileboost handles errors gracefully:
- Configuration errors: Logs warnings about missing configuration and returns empty strings/nil
- Invalid assets: Logs errors when non-ActiveStorage objects are passed and returns empty strings/nil
- Signature errors: Returns nil when HMAC generation fails
Fileboost uses HMAC-SHA256 signatures to secure your image transformations:
- URLs are signed with your secret token
- Prevents unauthorized image manipulation
- Signatures include all transformation parameters
- Uses secure comparison to prevent timing attacks
After checking out the repo, run:
$ bundle install
$ bundle exec rspec
To test against the dummy Rails application:
$ cd test/dummy
$ rails server
Run the test suite:
$ bundle exec rspec
Run RuboCop:
$ bundle exec rubocop
- Fork it
- Create your feature branch (
git checkout -b my-new-feature
) - Write tests for your changes
- Ensure all tests pass (
rake test
) - Commit your changes (
git commit -am 'Add some feature'
) - Push to the branch (
git push origin my-new-feature
) - Create new Pull Request
The gem is available as open source under the terms of the MIT License.