repertoire-assets 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,5 @@
1
+ .DS_Store
2
+ *~
3
+ pkg
4
+ doc
5
+ *.gem
data/FAQ ADDED
@@ -0,0 +1,90 @@
1
+ Repertoire Assets FAQ
2
+ =====================
3
+
4
+ Q. If I use repertoire-assets for all of my javascript and css, none of my
5
+ html templates have <script...> or <link...>!
6
+
7
+ A. Yes, exactly.
8
+
9
+
10
+
11
+ Q. My application is not loading javascript or css files. There is nothing
12
+ about them in the log.
13
+
14
+ A. You have not installed the Rack middleware in your application's rackup
15
+ file. The middleware is automatically loaded for Rails 3.0 when you add
16
+ repertoire-assets to your Gemfile - but not for other frameworks. Consult
17
+ the README.
18
+
19
+
20
+
21
+ Q. I'm getting a Could not process '//= require <foo/bar>' error. But foo is
22
+ listed as a known library!
23
+
24
+ A. Are you also getting a "Multiple libraries for <foo>" warning? If so, the
25
+ one it's using doesn't provide the <foo/bar> sublibrary. You can fix this by
26
+ eliminating the spurious version of <foo>.
27
+
28
+
29
+
30
+ Q. My HTML looks like the following, but the middleware is not expanding
31
+ javascript require statements.
32
+
33
+ <script language='javascript'>
34
+ //- require <jquery>
35
+ //- require <widgets>
36
+ </script>
37
+
38
+ A. require and require instructions are only preprocessed in free-standing
39
+ javascript files. Instead, use:
40
+
41
+ public/javascripts/application.js:
42
+ ...
43
+ //- require <jquery>
44
+ //- require <widgets>
45
+
46
+
47
+
48
+ Q. I have compress set to true, but in my deployed application
49
+ digest.js or digest.css aren't YUI compressed.
50
+
51
+ A. You are probably using an uncompressable Javascript syntax. Try compressing
52
+ by hand on the command-line and YUI compressor will give you an error
53
+ statement. This should also appear in the application's log.
54
+ [ If using Rails 3, use rake 'assets:build' to compress the files by hand. ]
55
+
56
+
57
+
58
+ Q. Why do gem assets appear mixed into the same url space? Wouldn't it be
59
+ better to namespace them by the gem's name?
60
+
61
+ A. So that gems can specify in which directory in the host application they
62
+ appear. e.g., 'foo_gem-0.0.1/public/images/foo/bar.png' is served as though it
63
+ were '<host app>/public/images/foo/bar.png'.
64
+
65
+ This way, existing image_tag and other helpers in Rails can be used
66
+ with assets pulled from gems.
67
+
68
+
69
+
70
+ Q. I want to bundle different sets of javascript and css for different pages,
71
+ or different browsers.
72
+
73
+ A. This was considered, but isn't implemented. Issue a feature request.
74
+
75
+
76
+
77
+ Q. Repertoire assets seems like sprockets or juicer. How is it different?
78
+
79
+ A. Only Repertoire assets addresses distributing javascript and css via
80
+ rubygems. Its syntax is borrowed from sprockets, but it has better css support
81
+ than sprockets, and better provisions for debugging than either since you can
82
+ develop on unbundled source files.
83
+
84
+
85
+
86
+ Q. Can I use repertoire-assets together with merb-assets?
87
+
88
+ A. Yes. It replaces merb-asset's bundling and javascript/stylesheet helpers,
89
+ but the remaining helpers can be used with assets from either the main app or
90
+ assets in gems.
data/INSTALL ADDED
@@ -0,0 +1,35 @@
1
+ Repertoire Assets
2
+ =================
3
+
4
+
5
+ (1) Make sure your application loads the middleware. For Rails 3.0,
6
+ including repertoire-assets in your Gemfile does this automatically.
7
+
8
+ For Merb and others, you will need to alter your rackup file. The
9
+ middleware takes two optional arguments: a configuration hash and
10
+ the system logger.
11
+
12
+ <app>/config/rack.rb (Mongrel)
13
+ <app>/config.ru (Passenger)
14
+
15
+ * require 'repertoire-assets'
16
+ * use Repertoire::Assets::Processor, Merb::Config, Merb.logger
17
+
18
+ run Merb::Rack::Application.new
19
+
20
+
21
+ (2) Turn on precaching and compression in your production environment,
22
+ so gem assets are served by your web server. e.g. for Rails:
23
+
24
+ <app>/config/environments/production.rb:
25
+
26
+ * config.repertoire_assets.compress = true
27
+
28
+ Or in Merb:
29
+
30
+ <app>/config/environments/production.rb:
31
+
32
+ * c[:compress] = true
33
+
34
+ For other options that can be used in the configuration hash, see the
35
+ documentation for Repertoire::Assets::Processor.
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2009-2010 MIT Hyperstudio
2
+
3
+ Permission is hereby granted, free of charge, to any person
4
+ obtaining a copy of this software and associated documentation
5
+ files (the "Software"), to deal in the Software without
6
+ restriction, including without limitation the rights to use,
7
+ copy, modify, merge, publish, distribute, sublicense, and/or sell
8
+ copies of the Software, and to permit persons to whom the
9
+ Software is furnished to do so, subject to the following
10
+ conditions:
11
+
12
+ The above copyright notice and this permission notice shall be
13
+ included in all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
17
+ OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
19
+ HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
20
+ WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21
+ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
22
+ OTHER DEALINGS IN THE SOFTWARE.
data/README ADDED
@@ -0,0 +1,234 @@
1
+ Repertoire Assets
2
+ =================
3
+
4
+ Repertoire Assets is software for developing and distributing Javascript and
5
+ CSS components for re-use in ruby web projects. It helps you manage large
6
+ javascript codebases by dividing code among many files, and allows you to
7
+ publish your javascript libraries (and their css and images) via ruby gems.
8
+ You can then require them in other javascript web applications, and the asset
9
+ software will manage any dependencies among the libraries so that you can
10
+ focus on writing your own code.
11
+
12
+ While you're developing, the Repertoire middleware ensures that any javascript
13
+ and css you've required appear seamlessly in your own application's url space--
14
+ even though they're loaded from elsewhere. You can step through javascript
15
+ code file by file, just as it appears in your application and gems. When a
16
+ javascript source file changes, it is reloaded automatically and its
17
+ dependencies re-analyzed.
18
+
19
+ Finally, when you have packaged your app for production use, the asset
20
+ software bundles and compresses javascripts and stylesheets, and copies any
21
+ associated binary assets into your application's public directory. This way,
22
+ all the assets will be served directly by your web server, only one compressed
23
+ javascript and one css file are downloaded to the client. This yields a much
24
+ more responsive user experience.
25
+
26
+ If you want to distribute your javascript component for use in non-ruby frame-
27
+ works, repertoire assets can also be used to build and bundle the files. This
28
+ gives you the flexibility of developing and deploying components easily for use
29
+ within ruby frameworks, but also distributing your code to a wider audience.
30
+
31
+
32
+
33
+ *Architecture*
34
+
35
+ The software consists of two components:
36
+
37
+ (1) A preprocessor that assembles javascript based on dependencies in your
38
+ code, much like C's #include directive or ruby's "require" method. For
39
+ example, you could require the "shapes" javascript library from a ruby gem by
40
+ including '//= require <shapes>' your javascript source. The preprocessor will
41
+ find the library and load it and its depedencies into your web page before
42
+ your own code, in the proper order. If a given code library has already been
43
+ sourced, it is not loaded again.
44
+
45
+ This is accomplished by compiling an ordered manifest of all the javascript
46
+ files required by your code, and then inserting the appropriate <script> and
47
+ <link> tags into your pages' html. Because it uses a rack filter, the system
48
+ is largely transparent to your application. Whether it's written in Rails,
49
+ Merb, Sinatra, or another ruby web framework, the javascript and css will
50
+ still work.
51
+
52
+
53
+ (2) A pair of rack filters: one that intercepts http requests for assets in
54
+ the manifest and serves them directly, and another that inserts the manifest
55
+ into html pages right before they are served. In a production environment, the
56
+ filters collect all of your application's required assets, compress those they
57
+ can, and cache them in your application's public asset directory.
58
+
59
+
60
+
61
+ *Preparing your application*
62
+
63
+ You can use javascript components packaged with Repertoire Assets in any ruby
64
+ web application based on Rack (this includes Rails, Merb, Sinatra and others).
65
+
66
+ The javascript gem libraries can either be bundled with your application, or
67
+ reside in the system rubygems repository. Likewise, the repertoire-assets gem
68
+ may be in either place.
69
+
70
+ For Rails 3.0, no configuration is necessary for development use. Production
71
+ environments require a single line of configuration. See the INSTALL file
72
+ for details.
73
+
74
+
75
+
76
+ *Importing Javascript Libraries and Files*
77
+
78
+ Repertoire-assets works by scanning a set of javascript source files in your
79
+ application on startup and locating any required libraries (and their
80
+ dependents) on the ruby load path. In development mode, the files will be
81
+ re-scanned whenever a dependency is modified.
82
+
83
+ Files are sourced in the following order:
84
+
85
+ <app>/public/javascripts/application.js
86
+ <app>/public/javascripts/*.js
87
+
88
+ In these files, you can use preprocessor directives similar to C's:
89
+
90
+ //= require <shapes> /* search for a library shapes.js in gems load path */
91
+ //= require "drawing/scene" /* load ./drawing/scene.js relative to the current file */
92
+ //= require "../stylesheets/red-theme.css" /* load css relative to the current file */
93
+
94
+ The relevant <script> and <link> tags for any file you 'require' are added to
95
+ your application's outgoing html automatically. Any dependencies are added
96
+ in logical order.
97
+
98
+
99
+
100
+ *Structuring Your Application's Javascript*
101
+
102
+ It's best to establish a layout similar to most ruby or C code, where files
103
+ require any dependencies at their head and a single application file starts
104
+ everything off.
105
+
106
+ For example, a paint application might look like:
107
+
108
+ <app>/public/javascripts/application.js:
109
+ //= require "drawing/scene"
110
+ //= require "accounts/user"
111
+ ...
112
+ <app>/public/javascripts/drawing/graph.js
113
+ <app>/public/javascripts/drawing/scene.js:
114
+ //= require "graph"
115
+ ...
116
+ <app>/public/javascripts/accounts/user.js
117
+
118
+ The asset preprocessor will figure out what order to load files, so you don't
119
+ have to. But when you debug using Firebug or Webkit, your code will still
120
+ appear in the file layout you're used to rather than jumbled together
121
+ (something other javascript asset bundlers commonly do).
122
+
123
+
124
+
125
+ *Developing Javascript and CSS Gem Components*
126
+
127
+ Repertoire assets javascript libraries are ordinary rubygems packages. Say
128
+ you wanted to create a javascript drawing package to support the painting
129
+ application above. Here is the suggested gem source structure:
130
+
131
+ superdraw/README
132
+ superdraw/Rakefile # see below
133
+ superdraw/superdraw.gemspec # generated by Rakefile
134
+ superdraw/lib/superdraw.rb # empty file (required for rubygems)
135
+ superdraw/public/javascripts
136
+ superdraw/public/javascripts/superdraw.js # the superdraw library file
137
+ superdraw/public/javascripts/superdraw/circle.js
138
+ superdraw/public/javascripts/superdraw/polyhedron.js
139
+ superdraw/public/javascripts/superdraw/square.js
140
+ superdraw/public/stylesheets/superdraw.css # required css
141
+ superdraw/public/images/superdraw/anchor.png # provided image assets
142
+ superdraw/public/images/superdraw/crosshairs.png
143
+ superdraw/LICENSE
144
+ superdraw/TODO
145
+
146
+ As you can see, a Javascript component gem has the same structure as a Rails
147
+ or Merb application. You may also include ruby library code in lib/ if you wish.
148
+
149
+ The asset loader will find any library in $LOAD_PATH/../public/javascripts/*.js,
150
+ in this case 'superdraw.js'. This file might look something like the following:
151
+
152
+ //= require "superdraw/circle" # load private source files
153
+ //= require "superdraw/polyhedron"
154
+ //= require "superdraw/square"
155
+ //= require "../stylesheets/superdraw.css" # the library's main css file
156
+ //= provide "../images/splashscreen.jpeg" # ancillary assets
157
+ //= provide "../images/superdraw/**/*"
158
+
159
+ If the circle, polyhedron or square files use other javascript libraries --
160
+ say, the Processing javascript framework -- they will include require
161
+ directives of their own.
162
+
163
+ The provide directive is used to specify additional assets that should be
164
+ available in the host application's url space. You can reference these files
165
+ in your css, and any relative urls will be rewritten appropriately when the
166
+ css files are bundled together and moved to a new location in the host app.
167
+
168
+ Unix-style file globs can be used in any require or provide statement, as seen
169
+ in the final provide statement above. Also, you can combine search and
170
+ relative file paths to load sub-libraries (e.g. 'require <superdraw/circle>').
171
+
172
+ Keep in mind that files under /public may appear in your host app's URL
173
+ space. Hence, it is advantageous to namespace your materials in directories
174
+ named after your library (e.g. /images/superdraw/circle.png rather than
175
+ /images/circle.png).
176
+
177
+ For security reasons, the system will never serve a file that was not
178
+ explicitly required or provided.
179
+
180
+ If you are using Rails and would like to preview the manifest or generate
181
+ digests by hand, use 'rake assets:list' and 'rake assets:build'.
182
+
183
+
184
+
185
+ *Debugging Javascript Dependencies*
186
+
187
+ When your web application starts up, the asset manager logs a record of which
188
+ javascript and css files have been required, by which libraries, and what url
189
+ each is served at. For example:
190
+
191
+ ~ Requiring /javascripts/application.js (/Users/yorkc/facet-example-app/public/javascripts/application.js)
192
+ ~ Requiring /stylesheets/master.css (/Users/yorkc/facet-example-app/public/stylesheets/master.css)
193
+ ~ Requiring /javascripts/rep.faceting.js (repertoire_faceting-0.3.4)
194
+ ~ Requiring /javascripts/jquery.js (jquery-1.3.2)
195
+ ~ Requiring /javascripts/jquery/jquery-1.3.2.js (jquery-1.3.2)
196
+ ~ Requiring /stylesheets/rep.faceting.css (repertoire_faceting-0.3.4)
197
+ ~ Providing /images (repertoire_faceting-0.3.4)
198
+ ~ Requiring /javascripts/rep.protovis-facets.js (repertoire_faceting-0.3.4)
199
+ ~ Requiring /javascripts/protovis.js (repertoire_faceting-0.3.4)
200
+ ~ Requiring /javascripts/protovis/protovis-d3.1.js (repertoire_faceting-0.3.4)
201
+ ~ Assets processed: 1 source files, 5 libraries available, 10 assets provided, 9 files in manifest
202
+
203
+ Requiring a file that cannot be found is a fatal error, as in Ruby or C. If
204
+ two libraries are found that satisfy a requirement, you will be informed of
205
+ the conflict and told which one is being used.
206
+
207
+
208
+ *Deployment Options*
209
+
210
+ The following options are available for production configurations.
211
+
212
+ - precache [false] # copy and bundle assets into host application?
213
+ - compress [false] # compress bundled javascript & stylesheets? (implies :precache)
214
+ - disable_rack_assets [false] # don't interpolate <script> and <link> tags
215
+ - path_prefix [''] # prefix for all generated urls
216
+
217
+ In general, 'compress' is preferred. This copies all binary assets into
218
+ your host application, bundles together all required javascript and css into
219
+ files named '/digest.js' and '/digest.css', and compresses these files using
220
+ YUI compressor. Use 'precache' if you do not want to compress the files.
221
+
222
+ In both cases, the asset mirroring middleware is disabled, and your app's
223
+ webserver serves all assets directly from the filesystem.
224
+
225
+ If desired, you may also disable the <script> and <link> middleware in your
226
+ production install while still precaching and compressing all assets. Set the
227
+ 'disable_rack_assets' configuration option to true, and add the following to
228
+ your html header:
229
+
230
+ <link rel='stylesheet' type='text/css' href='/digest.css'/>
231
+ <script language='javascript' type='text/javascript' src='/digest.js'></script>
232
+
233
+ Note, however, that the server performance gain from 'disable_rack_assets' is
234
+ minimal.
data/Rakefile ADDED
@@ -0,0 +1,10 @@
1
+ require __FILE__ + '/../lib/repertoire-assets'
2
+
3
+ gemspec = eval(File.read("repertoire-assets.gemspec"))
4
+
5
+ task :build => "#{gemspec.full_name}.gem"
6
+
7
+ file "#{gemspec.full_name}.gem" => gemspec.files + ["repertoire-assets.gemspec"] do
8
+ system "gem build repertoire-assets.gemspec"
9
+ system "gem install repertoire-assets-#{Repertoire::Assets::VERSION}.gem"
10
+ end
data/TODO ADDED
@@ -0,0 +1,52 @@
1
+ - tainted files need to check css
2
+
3
+ - rails3. rework rake tasks to use Rails configuration DONE
4
+ - rails3. use middleware automatically via a railtie DONE
5
+ - rails3. use rails-style gemspec configuration DONE
6
+
7
+ - create digests based on the gem name for asset builds DONE
8
+ - test exclude functionality DONE
9
+ - test asset build config DONE
10
+ - test old functionality, using facet ex app DONE
11
+ - document asset build feature DONE
12
+
13
+ - write method to copy over cached files DONE
14
+ - write method to preprocess/require a source file DONE
15
+ - write method to css insert a source file DONE
16
+ - yui compress the cached files DONE
17
+ - convert to using a manifest instead of includes DONE
18
+ - helpers for generating the manifests NOT NECESSARY
19
+ - try running in an actual app DONE
20
+ - check digesting DONE
21
+ - verify works with prefix_path DONE
22
+ - check runs unbundled DONE
23
+ - provisions for digesting and compressing css DONE
24
+ - gems should be able to register their own load_paths NOT NECESSARY
25
+ - when caching, stat mtimes first (multiple merbs) DONE
26
+ - write a merb-specific rack for options NOT NECESSARY
27
+ - combine middleware? DONE
28
+ - separate out cache? NOT TO DO
29
+ - convert to use nokogiri SAX NOT POSSIBLE
30
+ - convert to use regexp DONE
31
+ - make log output pretty DONE
32
+ - optimise checking if update needed on cache DONE
33
+ - clean task? NOT TO DO
34
+ - option to disable manifester & provider DONE
35
+ - improve configuration param names DONE
36
+ - avoid multiple processes compressing digest DONE
37
+ - optimise the code DONE
38
+ - in code documentation DONE
39
+ - dump load path when cannot resolve a dependency DONE
40
+ - support for //= require <jquery/ui/accordion> DONE
41
+ - support for //= require "foo/*.js" (globs) DONE
42
+ - test suite? NOT FOR NOW
43
+ - find streaming XML module for manifest filter NOT FOR NOW
44
+ - convert to simplest regexp that fit HTML 4.0 DTD DONE
45
+ - asset-gen binary NOT FOR NOW
46
+ - README DONE
47
+
48
+ - provision for http://foo.com in require?
49
+
50
+ - source files should not be libraries DONE
51
+ - README needs info on bundling/gem requires
52
+ - README needs note on empty ruby libary file DONE
@@ -0,0 +1,8 @@
1
+ module Repertoire
2
+ module Assets
3
+ class Error < ::StandardError; end
4
+ class ConfigurationError < Error; end
5
+ class UnknownAssetError < Error; end
6
+ class UnknownDirectiveError < Error; end
7
+ end
8
+ end