sinatra-exstatic-assets 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,6 @@
1
+ module Sinatra
2
+ module Exstatic
3
+ # Library version
4
+ VERSION = "2.0.0"
5
+ end
6
+ end
@@ -0,0 +1,20 @@
1
+ # -*- encoding: utf-8 -*-
2
+
3
+ $:.push File.expand_path("../lib", __FILE__)
4
+ require "sinatra/exstatic_assets/version"
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = "sinatra-exstatic-assets"
8
+ s.version = Sinatra::Exstatic::VERSION
9
+ s.authors = ["Włodek Bzyl", "Iain Barnett"]
10
+ s.email = ["iainspeed@gmail.com"]
11
+ s.homepage = "https://github.com/yb66/sinatra-exstatic-assets"
12
+ s.summary = %q{A Sinatra extension of helpers for static assets.}
13
+ s.description = %q{Helpers for writing the HTML and caching of static assets. A fork of Sinatra Static Assets.}
14
+
15
+ s.add_dependency 'sinatra'
16
+
17
+ s.files = `git ls-files`.split("\n")
18
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
19
+ s.require_paths = ["lib"]
20
+ end
@@ -0,0 +1,38 @@
1
+ # encoding: UTF-8
2
+
3
+ require 'rspec'
4
+ Spec_dir = File.expand_path( File.dirname __FILE__ )
5
+
6
+
7
+ # code coverage
8
+ require 'simplecov'
9
+ SimpleCov.start do
10
+ add_filter "/vendor/"
11
+ add_filter "/bin/"
12
+ end
13
+
14
+ require "rack/test"
15
+ ENV['RACK_ENV'] ||= 'test'
16
+ ENV["EXPECT_WITH"] ||= "racktest"
17
+
18
+
19
+ require "logger"
20
+ logger = Logger.new STDOUT
21
+ logger.level = Logger::DEBUG
22
+ logger.datetime_format = '%a %d-%m-%Y %H%M '
23
+ LOgger = logger
24
+
25
+
26
+ Dir[ File.join( Spec_dir, "/support/**/*.rb")].each do |f|
27
+ logger.info "requiring #{f}"
28
+ require f
29
+ end
30
+
31
+ require 'rack/test/accepts'
32
+
33
+ RSpec.configure do |config|
34
+ config.treat_symbols_as_metadata_keys_with_true_values = true
35
+
36
+ config.include Rack::Test::Accepts, :type => :request
37
+ end
38
+
@@ -0,0 +1,156 @@
1
+ require 'spec_helper'
2
+ require_relative "../lib/sinatra/exstatic_assets.rb"
3
+
4
+ module Sinatra
5
+ module Exstatic
6
+
7
+ describe Asset, :time_sensitive do
8
+ let(:asset_dir) { "app/public" }
9
+ subject(:asset){ Asset.new filename, asset_dir }
10
+ context "Given a file" do
11
+ let(:fullpath) { File.join asset_dir, filename }
12
+ before do
13
+ File.stub(:"exists?").with(fullpath).and_return(true)
14
+ File.stub(:mtime).with(fullpath).and_return(Time.now)
15
+ end
16
+ let(:filename) { "image.jpg" }
17
+ let(:expected) { "image.jpg" }
18
+ it { should_not be_nil }
19
+ it { should == expected }
20
+ its(:fullpath) { should == fullpath }
21
+ its(:timestamp) { should == Time.now.to_i }
22
+ its(:"is_uri?") { should be_false }
23
+ its(:querystring) { should == "?ts=#{Time.now.to_i}" }
24
+ end
25
+ context "Given a url" do let(:filename) { "http://code.jquery.com/jquery-1.9.1.min.js" }
26
+ let(:expected) { "http://code.jquery.com/jquery-1.9.1.min.js" }
27
+ it { should_not be_nil }
28
+ it { should == expected }
29
+ its(:fullpath) { should be_nil }
30
+ its(:timestamp) { should == false }
31
+ its(:"is_uri?") { should be_true }
32
+ its(:querystring) { should be_nil }
33
+ end
34
+ end
35
+
36
+ describe Tag do
37
+ subject { tag }
38
+ context "Given a group of options" do
39
+ let(:tag) {
40
+ Tag.new "link",
41
+ { :type => "text/css",
42
+ :charset => "utf-8",
43
+ :media => "projection",
44
+ :rel => "stylesheet",
45
+ :href => "/bar/stylesheets/winter.css"
46
+ }
47
+ }
48
+ let(:expected) { %Q!<link charset="utf-8" href="/bar/stylesheets/winter.css" media="projection" rel="stylesheet" type="text/css" />! }
49
+ it { should == expected }
50
+
51
+ context "That include closed=false" do
52
+ let(:tag) {
53
+ Tag.new "link",
54
+ { :type => "text/css",
55
+ :charset => "utf-8",
56
+ :media => "projection",
57
+ :rel => "stylesheet",
58
+ :href => "/bar/stylesheets/winter.css",
59
+ :closed => false
60
+ }
61
+ }
62
+ let(:expected) { %Q!<link charset="utf-8" href="/bar/stylesheets/winter.css" media="projection" rel="stylesheet" type="text/css">! }
63
+ it { should == expected }
64
+ end
65
+ end
66
+ end
67
+
68
+
69
+ class FakeObject
70
+ include Sinatra::Exstatic::Private
71
+ def uri( addr, absolute, script_tag )
72
+ script_tag ? File.join( ENV["SCRIPT_NAME"], addr) : addr
73
+ end
74
+ def settings
75
+ self
76
+ end
77
+ def public_folder
78
+ "app/public"
79
+ end
80
+ end
81
+ describe "Private methods", :time_sensitive do
82
+ let(:o) {
83
+ # A double, I couldn't get RSpec's to work with this
84
+ # probably because they're not well documented
85
+ # hint hint RSpec team
86
+ o = FakeObject.new
87
+ }
88
+ let(:script_name) { "/bar" }
89
+ let(:fullpath) { File.join asset_dir, filename }
90
+ let(:asset_dir) { "app/public/" }
91
+ let(:time) { Time.now.to_i }
92
+ before do
93
+ ENV["SCRIPT_NAME"] = script_name
94
+ File.stub(:"exists?").with(fullpath).and_return(true)
95
+ File.stub(:mtime).with(fullpath).and_return(time)
96
+ end
97
+ context "Stylesheets" do
98
+ let(:url) { "/stylesheets/winter.css" }
99
+ let(:filename) { "/stylesheets/winter.css" }
100
+ let(:expected) { %Q!<link charset="utf-8" href="/bar/stylesheets/winter.css?ts=#{time}" media="screen" rel="stylesheet" />! }
101
+ subject { o.send :sss_stylesheet_tag, url }
102
+ it { should_not be_nil }
103
+ it { should == expected }
104
+ end
105
+ context "Javascripts" do
106
+ let(:url) { "/js/get_stuff.js" }
107
+ let(:filename) { "/js/get_stuff.js" }
108
+ let(:expected) { %Q!<script charset="utf-8" src="/bar/js/get_stuff.js?ts=#{time}"></script>! }
109
+ subject { o.send :sss_javascript_tag, url }
110
+ it { should_not be_nil }
111
+ it { should == expected }
112
+ end
113
+ context "Images" do
114
+ let(:url) { "/images/foo.png" }
115
+ let(:filename) { "/images/foo.png" }
116
+ let(:expected) { %Q!<img src="/bar/images/foo.png?ts=#{time}" />! }
117
+ subject { o.send :sss_image_tag, url }
118
+ it { should_not be_nil }
119
+ it { should == expected }
120
+ end
121
+ end
122
+
123
+ end # Exstatic
124
+ end # Sinatra
125
+
126
+ describe "Using them with a Sinatra app", :time_sensitive do
127
+ include_context "All routes"
128
+ let(:expected) { File.read File.expand_path(fixture_file, File.dirname(__FILE__)) }
129
+ before do
130
+ Sinatra::Exstatic::Asset.any_instance
131
+ .stub(:exists?)
132
+ .and_return(true)
133
+
134
+ Sinatra::Exstatic::Asset.any_instance
135
+ .stub(:mtime_int)
136
+ .and_return(1367612251)
137
+ end
138
+ context "Main" do
139
+ let(:fixture_file) { "./support/fixtures/main.txt" }
140
+ before do
141
+ get "/"
142
+ end
143
+ it_should_behave_like "Any route"
144
+ subject { last_response.body }
145
+ it { should == expected }
146
+ end
147
+ context "Sub" do
148
+ let(:fixture_file) { "./support/fixtures/app2.txt" }
149
+ before do
150
+ get "/app2"
151
+ end
152
+ it_should_behave_like "Any route"
153
+ subject { last_response.body }
154
+ it { should == expected }
155
+ end
156
+ end
@@ -0,0 +1,144 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <meta charset="utf-8" />
5
+ <title>Example</title>
6
+ <link href="/favicon.ico" rel="icon" />
7
+ <link charset="utf-8" href="http://fonts.googleapis.com/css?family=Quicksand|Faster+One|Cherry+Swash:700|Titillium+Web" media="screen" rel="stylesheet" type="text/css" />
8
+ <link charset="utf-8" href="/app2/css/base.css?ts=1367612251" media="screen" rel="stylesheet" />
9
+ <link charset="utf-8" href="/app2/css/screen.css?ts=1367612251" media="screen" rel="stylesheet" />
10
+ <script charset="utf-8" src="http://code.jquery.com/jquery-1.9.1.min.js"></script>
11
+
12
+ </head>
13
+
14
+ <body>
15
+ <header role='banner'>
16
+ <a href="http://www.flickr.com/photos/tjt195/12470738/" title="Greased Lightning by tarotastic, on Flickr"><img alt="Greased Lightning" height="375" src="http://farm1.staticflickr.com/10/12470738_fc0212bf8c.jpg" width="500" /></a>
17
+ <hgroup>
18
+ <h1>Sinatra Exstatic Assets</h1>
19
+ <h2>Helpers for your JS, CSS and anything static</h2>
20
+ </hgroup>
21
+ </header>
22
+
23
+ <nav>
24
+ <ul>
25
+ <li><a href="/">Main app</a></li>
26
+ <li><a href="/app2">App 2</a></li>
27
+ <li><a href="https://rubygems.org/gems/sinatra-exstatic-assets">Rubygems</a></li>
28
+ <li><a href="https://github.com/yb66/sinatra-exstatic-assets">Source code</a></li>
29
+ </ul>
30
+ </nav>
31
+ <article>
32
+ <header>
33
+ <h1>
34
+ <a href="#" title="Link to this post"
35
+ rel="bookmark">Usage</a>
36
+ </h1>
37
+ </header>
38
+ <p>Note that there is a Main App and an App2. This is to demonstrate that you can give links relative to the app, but if they are mounted with an extra prefix (using Rack#map, for example) the helper will respect that and produce the right href attribute.</p>
39
+ <section><header><h2>Installation and loading</h2></header>
40
+ <p>Start by installing:</p>
41
+ <code>gem 'sinatra-exstatic-assets'</code>
42
+ <p>Then require it in your Sinatra app.</p>
43
+ <code>require 'sinatra/exstatic_assets'</code>
44
+ </section>
45
+ <section>
46
+ <header><h2>The helpers</h2></header>
47
+ <p>Use these helpers in your views.</p>
48
+ <p>To add an attribute to a helper, pass it as an option, e.g. <code>width: "500"</code></p>
49
+ <p>Sometimes, you won't want the script tag (e.g. "/app2") prepended to the url, like in the case of a favicon. In that case you can pass in <code>url_options: {script_tag: false}</code> to the helper, e.g. <code>favicon_tag url_options: {script_tag: false}</code></p>
50
+ <section id='stylesheet_tag'>
51
+ <header>
52
+ <h3>stylesheet_tag</h3>
53
+ </header>
54
+ <p>The code:
55
+ </p>
56
+ <code>stylesheet_tag "/css/screen.css"</code>
57
+ <p>Output:</p>
58
+ <samp>
59
+ &lt;link charset=&quot;utf-8&quot; href=&quot;&#x2F;app2&#x2F;css&#x2F;screen.css?ts=1367612251&quot; media=&quot;screen&quot; rel=&quot;stylesheet&quot; &#x2F;&gt;
60
+ </samp>
61
+ <footer><p>Also known as:
62
+ <ul>
63
+ <li><code>css_tag</code></li>
64
+ <li><code>stylesheet</code></li>
65
+ </ul>
66
+ </footer>
67
+ </section>
68
+ <section id='javascript_tag'>
69
+ <header>
70
+ <h3>javascript_tag</h3>
71
+ </header>
72
+ <p>The code:
73
+ </p>
74
+ <code>javascript_tag "http://code.jquery.com/jquery-1.9.1.min.js"</code>
75
+ <p>Output:</p>
76
+ <samp>
77
+ &lt;script charset=&quot;utf-8&quot; src=&quot;http:&#x2F;&#x2F;code.jquery.com&#x2F;jquery-1.9.1.min.js&quot;&gt;&lt;&#x2F;script&gt;
78
+ </samp>
79
+ <p>The code:
80
+ </p>
81
+ <code>javascript_tag "/js/helpers.js"</code>
82
+ <p>Output:</p>
83
+ <samp>
84
+ &lt;script charset=&quot;utf-8&quot; src=&quot;&#x2F;app2&#x2F;js&#x2F;helpers.js?ts=1367612251&quot;&gt;&lt;&#x2F;script&gt;
85
+ </samp>
86
+ <footer><p>Also known as:
87
+ <ul>
88
+ <li><code>javascript_include_tag</code></li>
89
+ <li><code>js_tag</code></li>
90
+ <li><code>script_tag</code></li>
91
+ </ul>
92
+ </footer>
93
+ </section>
94
+ <section id='image_tag'>
95
+ <header>
96
+ <h3>image_tag</h3>
97
+ </header>
98
+ <p>The code:
99
+ </p>
100
+ <code>image_tag "http://farm1.staticflickr.com/10/12470738_fc0212bf8c.jpg", width: "500", height: "375", alt: "Greased Lightning"</code>
101
+ <p>Output:</p>
102
+ <samp>
103
+ &lt;img alt=&quot;Greased Lightning&quot; height=&quot;375&quot; src=&quot;http:&#x2F;&#x2F;farm1.staticflickr.com&#x2F;10&#x2F;12470738_fc0212bf8c.jpg&quot; width=&quot;500&quot; &#x2F;&gt;
104
+ </samp>
105
+ <p>The code:
106
+ </p>
107
+ <code>image_tag "/images/turnip.jpg", width: "500", height: "375", alt: "Turnip"</code>
108
+ <p>Output:</p>
109
+ <samp>
110
+ &lt;img alt=&quot;Turnip&quot; height=&quot;375&quot; src=&quot;&#x2F;app2&#x2F;images&#x2F;turnip.jpg?ts=1367612251&quot; width=&quot;500&quot; &#x2F;&gt;
111
+ </samp>
112
+ <footer><p>Also known as:
113
+ <ul>
114
+ <li><code>img_tag</code></li>
115
+ <li><code>img</code></li>
116
+ </ul>
117
+ </footer>
118
+ </section>
119
+ <section id='favicon_tag'>
120
+ <header>
121
+ <h3>favicon_tag</h3>
122
+ </header>
123
+ <p>The code:
124
+ </p>
125
+ <code>favicon_tag</code>
126
+ <p>Output:</p>
127
+ <samp>
128
+ &lt;link href=&quot;&#x2F;favicon.ico&quot; rel=&quot;icon&quot; &#x2F;&gt;
129
+ </samp>
130
+ <footer><p>Also known as:
131
+ <ul>
132
+ <li><code>favicon</code></li>
133
+ </ul>
134
+ </footer>
135
+ </section>
136
+ </section>
137
+ </article>
138
+
139
+
140
+ <footer>
141
+ <p>&copy; 2013 See the LICENCE file for more.</p>
142
+ </footer>
143
+ </body>
144
+ </html>
@@ -0,0 +1,129 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <meta charset="utf-8" />
5
+ <title>Example</title>
6
+ <link href="/favicon.ico" rel="icon" />
7
+ <link charset="utf-8" href="http://fonts.googleapis.com/css?family=Quicksand|Faster+One|Cherry+Swash:700|Titillium+Web" media="screen" rel="stylesheet" type="text/css" />
8
+ <link charset="utf-8" href="/css/base.css?ts=1367612251" media="screen" rel="stylesheet" />
9
+ <link charset="utf-8" href="/css/screen.css?ts=1367612251" media="screen" rel="stylesheet" />
10
+ <script charset="utf-8" src="http://code.jquery.com/jquery-1.9.1.min.js"></script>
11
+
12
+ </head>
13
+
14
+ <body>
15
+ <header role='banner'>
16
+ <a href="http://www.flickr.com/photos/28931095@N03/3609420787/" title="Magic Ball by Sam Bald, on Flickr"><img alt="Magic Ball" height="375" src="http://farm3.staticflickr.com/2474/3609420787_f7fc0e53c7.jpg" width="500" /></a>
17
+ <hgroup>
18
+ <h1>Sinatra Exstatic Assets</h1>
19
+ <h2>Helpers for your JS, CSS and anything static</h2>
20
+ </hgroup>
21
+ </header>
22
+
23
+ <nav>
24
+ <ul>
25
+ <li><a href="/">Main app</a></li>
26
+ <li><a href="/app2">App 2</a></li>
27
+ <li><a href="https://rubygems.org/gems/sinatra-exstatic-assets">Rubygems</a></li>
28
+ <li><a href="https://github.com/yb66/sinatra-exstatic-assets">Source code</a></li>
29
+ </ul>
30
+ </nav>
31
+ <article>
32
+ <header>
33
+ <h1>
34
+ <a href="#" title="Link to this post"
35
+ rel="bookmark">Usage</a>
36
+ </h1>
37
+ </header>
38
+ <p>Note that there is a Main App and an App2. This is to demonstrate that you can give links relative to the app, but if they are mounted with an extra prefix (using Rack#map, for example) the helper will respect that and produce the right href attribute.</p>
39
+ <section><header><h2>Installation and loading</h2></header>
40
+ <p>Start by installing:</p>
41
+ <code>gem 'sinatra-exstatic-assets'</code>
42
+ <p>Then require it in your Sinatra app.</p>
43
+ <code>require 'sinatra/exstatic_assets'</code>
44
+ </section>
45
+ <section>
46
+ <section>
47
+ <header><h2>The helpers</h2></header>
48
+ <p>Use these helpers in your views.<p>
49
+ <section id='stylesheet_tag'>
50
+ <header>
51
+ <h3>stylesheet_tag</h3>
52
+ </header>
53
+ <p>The code:
54
+ </p>
55
+ <code>stylesheet_tag "/css/screen.css"</code>
56
+ <p>Output:</p>
57
+ <samp>
58
+ &lt;link charset=&quot;utf-8&quot; href=&quot;&#x2F;css&#x2F;screen.css?ts=1367612251&quot; media=&quot;screen&quot; rel=&quot;stylesheet&quot; &#x2F;&gt;
59
+ </samp>
60
+ <footer><p>Also known as:
61
+ <ul>
62
+ <li><code>css_tag</code></li>
63
+ <li><code>stylesheet</code></li>
64
+ </ul>
65
+ </footer>
66
+ </section>
67
+ <section id='javascript_tag'>
68
+ <header>
69
+ <h3>javascript_tag</h3>
70
+ </header>
71
+ <p>The code:
72
+ </p>
73
+ <code>javascript_tag "http://code.jquery.com/jquery-1.9.1.min.js"</code>
74
+ <p>Output:</p>
75
+ <samp>
76
+ &lt;script charset=&quot;utf-8&quot; src=&quot;http:&#x2F;&#x2F;code.jquery.com&#x2F;jquery-1.9.1.min.js&quot;&gt;&lt;&#x2F;script&gt;
77
+ </samp>
78
+ <footer><p>Also known as:
79
+ <ul>
80
+ <li><code>javascript_include_tag</code></li>
81
+ <li><code>js_tag</code></li>
82
+ <li><code>script_tag</code></li>
83
+ </ul>
84
+ </footer>
85
+ </section>
86
+ <section id='image_tag'>
87
+ <header>
88
+ <h3>image_tag</h3>
89
+ </header>
90
+ <p>The code:
91
+ </p>
92
+ <code>image_tag "http://farm3.staticflickr.com/2474/3609420787_f7fc0e53c7.jpg", width: "500", height: "375", alt: "Magic Ball"</code>
93
+ <p>Output:</p>
94
+ <samp>
95
+ &lt;img alt=&quot;Magic Ball&quot; height=&quot;375&quot; src=&quot;http:&#x2F;&#x2F;farm3.staticflickr.com&#x2F;2474&#x2F;3609420787_f7fc0e53c7.jpg&quot; width=&quot;500&quot; &#x2F;&gt;
96
+ </samp>
97
+ <footer><p>Also known as:
98
+ <ul>
99
+ <li><code>img_tag</code></li>
100
+ <li><code>img</code></li>
101
+ </ul>
102
+ </footer>
103
+ </section>
104
+ <section id='favicon_tag'>
105
+ <header>
106
+ <h3>favicon_tag</h3>
107
+ </header>
108
+ <p>The code:
109
+ </p>
110
+ <code>favicon_tag</code>
111
+ <p>Output:</p>
112
+ <samp>
113
+ &lt;link href=&quot;&#x2F;favicon.ico&quot; rel=&quot;icon&quot; &#x2F;&gt;
114
+ </samp>
115
+ <footer><p>Also known as:
116
+ <ul>
117
+ <li><code>favicon</code></li>
118
+ </ul>
119
+ </footer>
120
+ </section>
121
+ </section>
122
+ </article>
123
+
124
+
125
+ <footer>
126
+ <p>&copy; 2013 See the LICENCE file for more.</p>
127
+ </footer>
128
+ </body>
129
+ </html>