serve 0.11.7 → 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG.rdoc +12 -0
- data/Gemfile +15 -10
- data/Gemfile.lock +30 -16
- data/LICENSE +2 -1
- data/README.rdoc +78 -47
- data/Rakefile +1 -3
- data/VERSION +1 -1
- data/lib/serve/application.rb +95 -12
- data/lib/serve/javascripts.rb +62 -0
- data/lib/serve/out.rb +38 -0
- data/lib/serve/project.rb +176 -0
- data/lib/serve/templates/LICENSE +20 -0
- data/lib/serve/templates/README.markdown +46 -0
- data/lib/serve/templates/_layout.html.erb +11 -0
- data/lib/serve/templates/application.sass +12 -0
- data/lib/serve/templates/compass.config +28 -0
- data/lib/serve/templates/config.ru +35 -0
- data/lib/serve/templates/gitignore +24 -0
- data/lib/serve/templates/hello.html.erb +3 -0
- data/lib/serve/templates/index.redirect +1 -0
- data/lib/serve/templates/view_helpers.rb +5 -0
- data/spec/application_spec.rb +36 -7
- data/spec/project_spec.rb +107 -0
- data/spec/spec_helper.rb +1 -6
- metadata +64 -17
- data/spec/spec.opts +0 -1
@@ -0,0 +1,62 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'open-uri'
|
3
|
+
|
4
|
+
module Serve
|
5
|
+
module JavaScripts
|
6
|
+
|
7
|
+
# JavaScript Versions
|
8
|
+
GOOGLE_AJAX_APIS = 'http://ajax.googleapis.com/ajax/libs'
|
9
|
+
JQUERY_VERSION = '1' # the latest stable version of 1.x.x
|
10
|
+
JQUERY_UI_VERSION = '1'
|
11
|
+
PROTOTYPE_VERSION = '1'
|
12
|
+
SCRIPTACULOUS_VERSION = '1'
|
13
|
+
MOOTOOLS_VERSION = '1'
|
14
|
+
|
15
|
+
JAVASCRIPT_FRAMEWORKS = %w(jquery jquery-ui mootools prototype scriptaculous)
|
16
|
+
|
17
|
+
def fetch_javascript(framework, download_path)
|
18
|
+
filename = javascript_filename(framework, download_path)
|
19
|
+
framework_url = javascript_framework_url(framework)
|
20
|
+
lines = open(framework_url) { |io| io.read }
|
21
|
+
open(filename, "w+") { |io| io.write(lines) }
|
22
|
+
end
|
23
|
+
|
24
|
+
def supported_javascript_frameworks
|
25
|
+
JAVASCRIPT_FRAMEWORKS
|
26
|
+
end
|
27
|
+
|
28
|
+
def valid_javascript_framework?(framework)
|
29
|
+
framework = framework.downcase
|
30
|
+
JAVASCRIPT_FRAMEWORKS.include?(framework)
|
31
|
+
end
|
32
|
+
|
33
|
+
def javascript_filename(framework, path)
|
34
|
+
File.join(path, "#{framework}.js")
|
35
|
+
end
|
36
|
+
|
37
|
+
def javascript_framework_url(framework)
|
38
|
+
self.send(framework.tr('-', '_') + "_url")
|
39
|
+
end
|
40
|
+
|
41
|
+
def jquery_url
|
42
|
+
"#{GOOGLE_AJAX_APIS}/jquery/#{JQUERY_VERSION}/jquery.min.js"
|
43
|
+
end
|
44
|
+
|
45
|
+
def jquery_ui_url
|
46
|
+
"#{GOOGLE_AJAX_APIS}/jqueryui/#{JQUERY_UI_VERSION}/jquery-ui.min.js"
|
47
|
+
end
|
48
|
+
|
49
|
+
def mootools_url
|
50
|
+
"#{GOOGLE_AJAX_APIS}/mootools/#{MOOTOOLS_VERSION}/mootools-yui-compressed.js"
|
51
|
+
end
|
52
|
+
|
53
|
+
def prototype_url
|
54
|
+
"#{GOOGLE_AJAX_APIS}/prototype/#{PROTOTYPE_VERSION}/prototype.js"
|
55
|
+
end
|
56
|
+
|
57
|
+
def scriptaculous_url
|
58
|
+
"#{GOOGLE_AJAX_APIS}/scriptaculous/#{SCRIPTACULOUS_VERSION}/scriptaculous.js"
|
59
|
+
end
|
60
|
+
|
61
|
+
end
|
62
|
+
end
|
data/lib/serve/out.rb
ADDED
@@ -0,0 +1,38 @@
|
|
1
|
+
module Serve #:nodoc:
|
2
|
+
|
3
|
+
# Utility methods for handling output to the terminal
|
4
|
+
module Out #:nodoc:
|
5
|
+
|
6
|
+
def stdout
|
7
|
+
@stdout ||= $stdout
|
8
|
+
end
|
9
|
+
|
10
|
+
def stdout=(value)
|
11
|
+
@stdout = value
|
12
|
+
end
|
13
|
+
|
14
|
+
def stderr
|
15
|
+
@stderr ||= $stderr
|
16
|
+
end
|
17
|
+
|
18
|
+
def stderr=(value)
|
19
|
+
@stderr = value
|
20
|
+
end
|
21
|
+
|
22
|
+
def puts(*args)
|
23
|
+
stdout.puts(*args)
|
24
|
+
end
|
25
|
+
|
26
|
+
def print(*args)
|
27
|
+
stderr.print(*args)
|
28
|
+
end
|
29
|
+
|
30
|
+
def log_action(name, message)
|
31
|
+
print " " * (12 - name.length)
|
32
|
+
print name
|
33
|
+
print " "
|
34
|
+
puts message
|
35
|
+
end
|
36
|
+
|
37
|
+
end
|
38
|
+
end
|
@@ -0,0 +1,176 @@
|
|
1
|
+
require 'pathname'
|
2
|
+
require 'serve/out'
|
3
|
+
require 'serve/javascripts'
|
4
|
+
|
5
|
+
module Serve #:nodoc:
|
6
|
+
#
|
7
|
+
# Serve::Project.new(options).create
|
8
|
+
# Serve::Project.new(options).convert
|
9
|
+
#
|
10
|
+
class Project #:nodoc:
|
11
|
+
attr_reader :name, :location, :framework
|
12
|
+
|
13
|
+
def initialize(options)
|
14
|
+
@name = options[:name]
|
15
|
+
@location = normalize_location(options[:directory], @name)
|
16
|
+
@full_name = git_config('user.name') || 'Your Full Name'
|
17
|
+
@framework = options[:framework]
|
18
|
+
end
|
19
|
+
|
20
|
+
# Create a new Serve project
|
21
|
+
def create
|
22
|
+
setup_base
|
23
|
+
%w(
|
24
|
+
public/images
|
25
|
+
public/javascripts
|
26
|
+
public/stylesheets
|
27
|
+
sass
|
28
|
+
).each { |path| make_path path }
|
29
|
+
create_file 'sass/application.sass', read_template('application.sass')
|
30
|
+
create_file 'views/_layout.html.erb', read_template('_layout.html.erb')
|
31
|
+
create_file 'views/hello.html.erb', read_template('hello.html.erb')
|
32
|
+
create_file 'views/view_helpers.rb', read_template('view_helpers.rb')
|
33
|
+
create_file 'views/index.redirect', read_template('index.redirect')
|
34
|
+
install_javascript_framework @framework
|
35
|
+
end
|
36
|
+
|
37
|
+
# Convert an existing Compass project to a Serve project
|
38
|
+
def convert
|
39
|
+
setup_base
|
40
|
+
move_file 'images', 'public/'
|
41
|
+
move_file 'stylesheets', 'public/'
|
42
|
+
if File.directory? 'javascripts'
|
43
|
+
move_file 'javascripts', 'public/'
|
44
|
+
else
|
45
|
+
make_path 'public/javascripts'
|
46
|
+
end
|
47
|
+
move_file 'src', 'sass'
|
48
|
+
install_javascript_framework @framework
|
49
|
+
note_old_compass_config
|
50
|
+
end
|
51
|
+
|
52
|
+
private
|
53
|
+
|
54
|
+
include Serve::Out
|
55
|
+
|
56
|
+
include Serve::JavaScripts
|
57
|
+
|
58
|
+
# Files required for both a new server project and for an existing compass project.
|
59
|
+
def setup_base
|
60
|
+
%w(
|
61
|
+
.
|
62
|
+
public
|
63
|
+
tmp
|
64
|
+
views
|
65
|
+
).each { |path| make_path path }
|
66
|
+
create_file 'config.ru', read_template('config.ru')
|
67
|
+
create_file 'LICENSE', read_template('LICENSE')
|
68
|
+
create_file '.gitignore', read_template('gitignore')
|
69
|
+
create_file 'compass.config', read_template('compass.config')
|
70
|
+
create_file 'README.markdown', read_template('README.markdown')
|
71
|
+
create_empty_file 'tmp/restart.txt'
|
72
|
+
end
|
73
|
+
|
74
|
+
# Install a JavaScript framework if one was specified
|
75
|
+
def install_javascript_framework(framework)
|
76
|
+
if framework
|
77
|
+
if valid_javascript_framework?(framework)
|
78
|
+
path = normalize_path(@location, "public/javascripts")
|
79
|
+
filename = javascript_filename(framework, path)
|
80
|
+
if File.exists? filename
|
81
|
+
log_action 'exists', filename
|
82
|
+
else
|
83
|
+
log_action 'install', filename
|
84
|
+
fetch_javascript framework, path
|
85
|
+
end
|
86
|
+
else
|
87
|
+
puts "*** #{framework} javascript framework not supported. ***"
|
88
|
+
puts "Supported frameworks: #{ supported_javascript_frameworks.join(', ') }"
|
89
|
+
end
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
# Display note about old compass config if it exists
|
94
|
+
def note_old_compass_config
|
95
|
+
old_config = normalize_path(@location, 'config.rb')
|
96
|
+
if File.exists? old_config
|
97
|
+
puts ""
|
98
|
+
puts "============================================================================"
|
99
|
+
puts " Please Note: You still need to copy your unique settings from config.rb to "
|
100
|
+
puts " compass.config. Remove config.rb when you are finished."
|
101
|
+
puts "============================================================================"
|
102
|
+
puts ""
|
103
|
+
end
|
104
|
+
end
|
105
|
+
|
106
|
+
# Read and eval a template by name
|
107
|
+
def read_template(name)
|
108
|
+
contents = IO.read(normalize_path(File.dirname(__FILE__), "templates", name))
|
109
|
+
instance_eval "%{#{contents}}"
|
110
|
+
end
|
111
|
+
|
112
|
+
# Create a file with contents
|
113
|
+
def create_file(file, contents)
|
114
|
+
path = normalize_path(@location, file)
|
115
|
+
unless File.exists? path
|
116
|
+
log_action "create", path
|
117
|
+
File.open(path, 'w+') { |f| f.puts contents }
|
118
|
+
else
|
119
|
+
log_action "exists", path
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
# Create an empty file
|
124
|
+
def create_empty_file(file)
|
125
|
+
path = normalize_path(@location, file)
|
126
|
+
FileUtils.touch(path)
|
127
|
+
end
|
128
|
+
|
129
|
+
# Make every directory in a given path
|
130
|
+
def make_path(path)
|
131
|
+
path = normalize_path(@location, path)
|
132
|
+
unless File.exists? path
|
133
|
+
log_action "create", path
|
134
|
+
FileUtils.mkdir_p(path)
|
135
|
+
else
|
136
|
+
log_action "exists", path
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
# Move a file from => to (relative to the project location)
|
141
|
+
def move_file(from, to)
|
142
|
+
from_path = normalize_path(@location, from)
|
143
|
+
to_path = normalize_path(@location, to)
|
144
|
+
if File.exists? from_path
|
145
|
+
to = to + from if to[-1..-1] == "/"
|
146
|
+
log_action "move", "#{@location}/{#{from} => #{to}}"
|
147
|
+
FileUtils.mv from_path, to_path
|
148
|
+
end
|
149
|
+
end
|
150
|
+
|
151
|
+
# Convert dashes and spaces to underscores
|
152
|
+
def underscore(string)
|
153
|
+
string.gsub(/-|\s+/, '_')
|
154
|
+
end
|
155
|
+
|
156
|
+
# Grab data by key from the git config file if it exists
|
157
|
+
def git_config(key)
|
158
|
+
value = `git config #{key}`.chomp
|
159
|
+
value.empty? ? nil : value
|
160
|
+
end
|
161
|
+
|
162
|
+
# Normalize the path of the target directory
|
163
|
+
def normalize_location(path, name = nil)
|
164
|
+
path = File.join(path, underscore(name)) if name
|
165
|
+
path = normalize_path(path)
|
166
|
+
path
|
167
|
+
end
|
168
|
+
|
169
|
+
# Normalize a path relative to the current working directory
|
170
|
+
def normalize_path(*paths)
|
171
|
+
path = File.join(*paths)
|
172
|
+
Pathname.new(File.expand_path(path)).relative_path_from(Pathname.new(Dir.pwd)).to_s
|
173
|
+
end
|
174
|
+
|
175
|
+
end
|
176
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) #{Time.now.year} #{@full_name}
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
@@ -0,0 +1,46 @@
|
|
1
|
+
What is this?
|
2
|
+
=============
|
3
|
+
|
4
|
+
This is a simple HTML prototype written in HAML or ERB that is designed to be
|
5
|
+
viewed with Serve.
|
6
|
+
|
7
|
+
What is Serve? Serve is a rapid prototyping framework for Rails applications.
|
8
|
+
It is designed to compliment Rails development and enforce a strict separation
|
9
|
+
of concerns between designer and developer. Using Serve with Rails allows the
|
10
|
+
designer to happily work in his own space creating an HTML prototype of the
|
11
|
+
application, while the developer works on the Rails application and copies
|
12
|
+
over HTML from the prototype as needed. This allows the designer to focus on
|
13
|
+
presentation and flow while the developer can focus on the implementation.
|
14
|
+
|
15
|
+
|
16
|
+
How do I install and run Serve?
|
17
|
+
-------------------------------
|
18
|
+
|
19
|
+
Serve is distributed as a gem to make it easy to get up and running. To
|
20
|
+
install, type the following at the command prompt:
|
21
|
+
|
22
|
+
gem install serve
|
23
|
+
|
24
|
+
(OSX and Unix users may need to prefix the command with `sudo`.)
|
25
|
+
|
26
|
+
After Serve is installed, you can start it up in a given directory like this:
|
27
|
+
|
28
|
+
serve
|
29
|
+
|
30
|
+
This will start Serve on port 4000. You can now view the prototype in your
|
31
|
+
Web browser at this URL:
|
32
|
+
|
33
|
+
<http://localhost:4000>
|
34
|
+
|
35
|
+
Click around. You will find that Serve enables you to prototype most
|
36
|
+
functionality without writing a single line of backend code.
|
37
|
+
|
38
|
+
|
39
|
+
Rack and Passenger
|
40
|
+
------------------
|
41
|
+
|
42
|
+
Astute users may notice that this project is also a simple Rack application.
|
43
|
+
This means that it is easy to deploy it on Passenger or rack it up with the
|
44
|
+
`rackup` command. For more information about using Serve and Passenger see:
|
45
|
+
|
46
|
+
<http://bit.ly/serve-and-passenger>
|
@@ -0,0 +1,28 @@
|
|
1
|
+
#
|
2
|
+
# Compass Configuration
|
3
|
+
#
|
4
|
+
|
5
|
+
# HTTP paths
|
6
|
+
http_path = '/'
|
7
|
+
http_stylesheets_path = '/stylesheets'
|
8
|
+
http_images_path = '/images'
|
9
|
+
http_javascripts_path = '/javascripts'
|
10
|
+
|
11
|
+
# File system locations
|
12
|
+
sass_dir = 'sass'
|
13
|
+
css_dir = 'public/stylesheets'
|
14
|
+
images_dir = 'public/images'
|
15
|
+
javascripts_dir = 'public/javascripts'
|
16
|
+
|
17
|
+
# Set to true for easier debugging
|
18
|
+
line_comments = false
|
19
|
+
|
20
|
+
# CSS output style - :nested, :expanded, :compact, or :compressed
|
21
|
+
output_style = :expanded
|
22
|
+
|
23
|
+
# Determine whether Compass asset helper functions generate relative
|
24
|
+
# or absolute paths
|
25
|
+
relative_assets = true
|
26
|
+
|
27
|
+
# Learn more:
|
28
|
+
# http://compass-style.org/docs/tutorials/configuration-reference/
|
@@ -0,0 +1,35 @@
|
|
1
|
+
#\\ -p 4000
|
2
|
+
|
3
|
+
gem 'activesupport'
|
4
|
+
gem 'serve'
|
5
|
+
|
6
|
+
require 'serve'
|
7
|
+
require 'serve/rack'
|
8
|
+
|
9
|
+
require 'sass/plugin/rack'
|
10
|
+
require 'compass'
|
11
|
+
|
12
|
+
# The project root directory
|
13
|
+
root = ::File.dirname(__FILE__)
|
14
|
+
|
15
|
+
# Compass
|
16
|
+
Compass.add_project_configuration(root + '/compass.config')
|
17
|
+
Compass.configure_sass_plugin!
|
18
|
+
|
19
|
+
# Rack Middleware
|
20
|
+
use Rack::ShowStatus # Nice looking 404s and other messages
|
21
|
+
use Rack::ShowExceptions # Nice looking errors
|
22
|
+
use Sass::Plugin::Rack # Compile Sass on the fly
|
23
|
+
|
24
|
+
# Rack Application
|
25
|
+
if ENV['SERVER_SOFTWARE'] =~ /passenger/i
|
26
|
+
# Passendger only needs the adapter
|
27
|
+
run Serve::RackAdapter.new(root + '/views')
|
28
|
+
else
|
29
|
+
# We use Rack::Cascade and Rack::Directory on other platforms to handle static
|
30
|
+
# assets
|
31
|
+
run Rack::Cascade.new([
|
32
|
+
Serve::RackAdapter.new(root + '/views'),
|
33
|
+
Rack::Directory.new(root + '/public')
|
34
|
+
])
|
35
|
+
end
|