Extensions & Themes
This guide provides an overview of extensions and themes in Spree and how they are implemented using standard Rails techniques. You should refer to the customization guide for a more specific technical details on customizing Spree.
After this guide you should understand:
- The important role extensions play in Spree
- The differences between extensions and themes
- How to install a third party extension
- How to install a third party theme
- Extensions refer to discrete packages of code that provide new functionality to a Spree application. While extensions may affect the appearance of a Spree application they generally only provide additional interfaces to enable users to interact with the new functionality provided.
- Themes are discrete packages of code that only affect the appearance of a Spree application (and generally only the front-end store). Themes do not generally include any logic customizations.
Both Extensions and Themes are created as standard Rails 3.0 (or later) Engines, and the terms extension, theme and engine essentially mean the same thing from a Rails perspective within Spree.
Extensions are the primary mechanism for customizing a Spree site. They provide a convenient mechanism for Spree developers to share reusable code with one another. Even if you do not plan on sharing your extensions with the community they can still be a useful way to reuse code within your organization. Extensions are also a convenient mechanism for organizing and isolating discrete chunks of functionality.
WARNING: If you are using a version of Spree prior to version 0.30.x then you should be aware that there have been significant changes to the extension system. These changes represent a major improvement over the way things used to be done. For instance, you no longer are required to put your application logic and themes within a “site” extension.
Spree Extensions and Themes are based on Rails Engines. Rails Engines have been around since Rails 2.3 but Rails 3.0 was the first version of Rails that really embraced the concept of engines being advocated by projects such as Spree and Radiant. If you are familiar with the concept of a Rails Plugin then you should have no problem working with extensions.
The Rails Engine support allows developers to ship code as stand-alone Rubygems that can be added to any Rails application. These gems can in turn be installed, managed and deployed using the very excellent bundler tool. A full discussion of gems and bundler is beyond the scope of this document.
In Rails, an Engine behaves almost identically to a full Rails application. It has all of the awesome features of Rails including:
- Models, views and controllers
- Database migrations
- Public assets
- Rake tasks
Engines therefore become the natural mechanism for providing the same types of modularity for Spree. In fact a Spree extension is really no more than a Rails engine. The one common aspect of most Spree extensions, however, is that they all have a dependency on the gem. This means they build on certain basic Spree functionality not present in a regular Rails application.
INFO: The gem is itself a Rails engine and so the entire Spree “stack” is essentially a Rails application built on engines.
The “Core” Extensions
Spree is actually composed of several so-called “core” extensions. They are referred to as “core” because they provide the core functionality of Spree. The core extensions are as follows
Please see the Source Code Guide for a more in-depth discussion of the core extensions.
Now that we’ve discussed some of the rationale behind extensions, it’s time to get started using them. You may also want to refer to the Creating Extensions guide for a tutorial that will walk you through a detailed example of creating and publishing your own extension.
Installing an Extension or Theme
Since extensions/themes are created as engines in Rails, using them is as simple as working with standard plugin gems. A standard Rails application running Spree will have a . This is a special file which is used by bundler to manage the gem dependencies for your application.
WARNING: The dependencies should be specified in a specific order. Always specify , followed by the various spree extensions and then the required theme(s) at the very end of . This is to ensure the proper classes are defined for extensions, and also so Deface Overrides are loaded in the proper order.
WARNING: Prior to Spree 0.30.0 extensions were not managed as gems. They were typically installed from the command line using . They were then added to the Git repository of the application itself and deployed on the server. This is no longer supported. You must convert your old extension into a gem in order to use it in Spree.
For a gem that is already published on Rubygems.org you can add it to your as follows:gem ‘spree_related_products’, ‘3.0.2’
Alternatively, you can also use the edge version of a gem stored in a Git repository.gem ‘spree_related_products’, ‘3.0.2’, :git => ‘git://github.com/spree/spree_related_products.git’
Finally, you could work with the extension / theme directly from your local file system.gem ‘spree_related_products’, ‘3.0.2’, :path => ‘../spree_related_products’
NOTE: Using the directive is an excellent option when actively developing an extension or theme.
Selecting the correct extension / theme version
As Spree releases new versions the underlying code can change and this necessitates extensions and themes to be updated to account for the changes in Spree. To help match the correct version of an extension / theme with the Spree version you should refer to the Versionfile, normally located in the root of the engine’s Git repository.
The Spree Extension Registry also presents the contents of an engine’s Versionfile, and suggests the correct line to add your Gemfile when you click on the “Install” link beside the relevant Spree version number.
NOTE: Not all extensions / themes include a Versionfile so this option may not be present for all extensions included in the Extension Registry.
Installing the Gem
After you’ve added the extension to your (using one of the techniques outlined above) you then install the gem as follows:$ bundle install
Most extensions are so-called “third party” extensions. They are written by a party other than the developer working on a particular Spree site and they are intended to be shared with other developers. Many (but not all) extensions are listed in the Spree Extension Registry. This is an excellent source of information on which extensions are available and which versions of Spree they are known (or suspected) to be compatible with.