Skip to content
Cecil edited this page Oct 31, 2015 · 1 revision

Shoes 3.2.23 has a new scheme for pre-compiled gems for inclusion with Shoes. The gem source code (perhaps a github clone?) does not have to live in the Shoes source tree (req/ et all) is still there for now - expect that to change. However, binary gems do have to be built for or with the Ruby that is included in Shoes. Shoes also needs to know certain things that gem developers don't worry about or have used some strategies that make Shoes rakefiles seem simple. Some gems are bloated with things that Shoes can never use. Wait, there's more - I hate having to compile gems every time Shoes is built (* 5 platforms). Same complaint for the ext's - they never change and their relationship to Shoes building is pretty slim.

Currently [April 17, 2015], it's still simplistic and only implemented for Windows and Raspberry pi builds, so far. Basically you get some new rake tasks to build the gems any time you like and their binary bits get put in a built/{arch} directory. When you do a simple rake (or rake build) it copies from the built/{arch} instead of recompiling every damn time.

Along with that, you can (MUST) specify the exts and gems to be included in Shoes and where they live. There are defaults - using the req/ directory and including ftsearch, chipmunk, hpricot and sqlite3. If you want to distribute a different Shoes then you should create a {arch}-custom.yaml. Here's the one for the xwin7 target.

Deps: /home/ccoupe/Projects/shoesdeps/mingw
Ruby: /home/ccoupe/Projects/shoesdeps/mingw/usr/local
Gemloc: /home/ccoupe/Projects/gems/shoes
Extloc: /home/ccoupe/Projects/gems/shoes
Exts:
  - ftsearch
  - chipmunk
Gems:
  - hpricot
  - sqlite3
MS-Theme: true 
Debug: false

I suggest you keep both the extensions and gems in the same place. The new code takes pains to treat them correctly. See make//gems.rb and the changes in make//task.rb

  • rake shoesgems builds the extensions and gems to include with Shoes. Just the things in the Exts and Gems array. Note that after compiling and copying to the built directory, it cleans up. No clean step should be required when switching Shoes targets.
  • rake gemsclean removes all the binary based stuff in all the ext's & gems in the directory. Brute force.
  • rake gems - This barely behaved brute just compiles everything in the gem directory except the extensions. This task will change as we attempt to build nokogiri and picky and all their dependencies.

[Update: May 6, 2015] It was necessary to add another hash to the *-custom.yaml. Ext: and Gems: specify the gems for rake shoesgems. For a lot of reasons, you do not want to deal with compiling something like nokogiri that way. First reason being that it won't work for OSX and Linux in the manner that Shoes needs. What does work is to gem install this-gem on a the system and ruby you care about and then copy the gems files to the GemLoc: place. Then, when Shoes is built for that platform, the build copy files from Gemloc: in Shoes. For that to happen we need a list of gems to include and we do that in *-custom-yaml. Here's the x86_64_linux-custom.yaml

Ruby: /usr/local
Deps: 
Gemloc: /home/ccoupe/Projects/gems/shoes
Extloc: /home/ccoupe/Projects/gems/shoes
Exts:
  - ftsearch
  - chipmunk
Gems:
  - sqlite3
  - hpricot
InclGems: 
  - sqlite3
  - mini_portile-0.6.2
  - nokogiri-1.6.6.2
  - bluecloth-2.2.0
Debug: false
Gtk:  gtk+-2.0

InclGems: are the gems in Gemloc: that you want to include in Shoes. There should be a list of gems to not include if we see them but we aren't there yet. My gemloc: dir is a NFS and CIFS mounted directory/share but you could use any process that copies the files into GemLoc: with the proper names and locations.

Here's the ruby script I use to copy a Gem:

#!/usr/bin/env ruby
# copy an installed gem from some ruby (rvm perhaps) to Shoes built/
# first arg - path to specificiation
#   ~/.rvm/gems/ruby-2.1.5/specifications/nokogiri-1.6.6.2.gemspec
# second arg - path to gems/shoes/{arch}/built
# Note: the shell makes ~/ into an abs path.
require 'fileutils'
include FileUtils::Verbose
specpath = ARGV[0]
destpath = ARGV[1]
#puts "Using #{specpath}"
spec = eval(File.read(specpath))
puts "copy #{spec.full_name} to #{destpath}"
mkdir_p(File.join(destpath, spec.full_name))
cp specpath, File.join(destpath, spec.full_name,'gemspec')
parts = specpath.split('/')
parts[-2] = 'gems'
parts[-1] = spec.full_name
#parts << 'lib' # just copy 'lib'
libp = File.join parts
#puts "lib is #{libp}"
mkdir_p File.join(destpath, spec.full_name)
cp_r libp, File.join(destpath, spec.full_name)

We just need the lib/ but for now, everything in copied into Gemloc:/shoes/built/{platform}. When the Shoes build copies from Gemloc: it only copies the lib/ and the gemspec. See make/gems.rb(copy_gems)

Note: it could copy or touch the extensions/arch/rubyv/gem.build-complete but thats a future enhancement. For now, when building Shoes, the gemspec file gets copied into the Ruby specifications/default/ along with bigdecimal and json (and similar Ruby built-ins).

You might notice that the process would allow unique binary gems to be included into a Shoes packaged app and put in the users Shoes gem directory instead of inside Ruby. You might even think the process could use a Shoes gui App or Window or Panel in Cobbler or the Packaging screens. Even if your app uses binary gems that the user is unlikely to have the compile setup for, your app could run. Crazy talk!

Clone this wiki locally