broadway 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/README.textile ADDED
@@ -0,0 +1,300 @@
1
+ h1. Broadway
2
+
3
+ TODO: Tests. I've just extracted this out of a project and now I'll write tests.
4
+
5
+ "html2haml":http://html2haml.heroku.com/
6
+
7
+ "JAVASCRIPT <script src=":http://github.com/HenrikJoreteg/jquery-magic-labels/raw/master/jquery.magiclabels.min.js
8
+
9
+ This is the source for my blog. I develop the themes in Sinatra, and convert them into Jekyll for posts. I'm only doing this until _someone_ gives Jekyll some HAML support so I can use it with Github... Or I find that it's really not that good of an investment to use Github Pages.
10
+
11
+ h2. The Goal
12
+
13
+ The goal of this project is to make it easy to manage 20 public software projects at once. This way, anyone developing their thing on github can easily post new examples and documentation as they develop their project, without anything out of their ordinary workflow.
14
+
15
+ h2. Sinatra, HAML, JQuery, Textile
16
+
17
+ "About this Blog":http://blog.peepcode.com/tutorials/2010/about-this-blog
18
+
19
+ h2. Jekyll and Sinatra
20
+
21
+ I use Jekyll for the static page generation (spits out all the pages, essentially pre-compiling everything into raw HTML). I don't use Jekyll because it uses Liquid. Liquid might be nice for someone who doesn't want to learn programming but would like to have fun with a few variables, and reuse some code. But for a programmer who takes pride in efficiency, clean code, and being DRY, HAML and full Ruby access is much better; it gives me freedom to _do_. I can:
22
+
23
+ # Format the HTML perfectly (using HAML with Textmate)
24
+ # Have Ruby hooks to conditionally link in elements throughout (getting rid of YAML headers)
25
+ # Use Ruby to dynamically process other URLs
26
+ # Extend the application to do other things like file uploading, all the while
27
+ # Keeping everything DRY and clean.
28
+
29
+ You can use @_posts@ without any layout! And they can be raw HTML files!
30
+
31
+ h3. Notes
32
+
33
+ * Any folder starting with an underscore is private in terms of browser access
34
+
35
+ h2. Directory Structure
36
+
37
+ <pre>
38
+ .
39
+ |-- _config.yml
40
+ |-- _layouts
41
+ |-- _posts (generated output)
42
+ |-- _site (github's place)
43
+ |-- _source (sinatra application for development)
44
+ | |-- files (blog files to-be published)
45
+ | |-- posts (blog files)
46
+ | |-- lib (sinatra helpers)
47
+ | `-- public (sinatra public directory)
48
+ |-- shared (javascripts, css, media, etc.)
49
+ |-- index.html
50
+ |-- robots.txt (what google should ignore)
51
+ `-- sitemap.xml (google's sitemap from jekyll)
52
+ </pre>
53
+
54
+ h2. Configuration
55
+
56
+ h3. Default Configuration
57
+
58
+ <pre>
59
+ permalink:
60
+ if post's name is "entry": /path/to (index.haml)
61
+ if post's name is "something-else": /path/to/something-else
62
+ those are "directory" styled permalinks
63
+ title: Path - To - Index
64
+ keywords: nil
65
+ description: nil
66
+ </pre>
67
+
68
+ h4. Permalink Styles
69
+
70
+ directory: /path/to/index or /path/to/title
71
+ date: /year/month/day/title
72
+ category: /root/child/childer/title
73
+
74
+ If directories have underscores, they are subtracted from the path:
75
+
76
+ /path/to/_some_way_of_organizing_my_posts/my-post.textile
77
+ => /path/to/my-post
78
+
79
+ Preference:
80
+
81
+ # If directory contains all of [index.haml, entry.textile], it will render index.haml
82
+ # If directory contains all of [entry.textile], it will render entry.textile
83
+
84
+ h2. The Rendering Process
85
+
86
+ # Startup Sinatra
87
+ # Generate URLs from Post metadata, or, by default, directory to index.html or index.haml. Also collect all tags and categories in the application
88
+ # Now we have all: urls, tags, categories. But we haven't read all of the files into memory which can be a problem
89
+ # Go to a URL via Sinatra, render HAML
90
+ # Read post for that URL into memory
91
+ # Save HAML to HTML file
92
+
93
+ h2. Themes
94
+
95
+ When you make a request to a url, it renders out the template from the public/themes directory, but your content goes in public/posts. In public/posts, you can add HAML/HTML files to customize the base of the them (via 'yield'), but you don't need to. Instead, you just create your posts and they will be given a url. The default layout for anything in your public/posts directory is the root directory it's in. That's because you're likely to initially structure your posts according to the theme's RESTful page structure. But if you specify a <code>layout</code> in the header of your file, it will use that from the theme.
96
+
97
+ ln -s ~/viatropos/shared/themes ~/viatropos/_source/public/shared
98
+
99
+ h2. Posts
100
+
101
+ There are 3 types of posts:
102
+
103
+ # Blog Posts
104
+ # Index Posts
105
+ # Regular Posts
106
+
107
+ Blog posts are dated, so they must be prefixed with a date (2010-03-11-my-blog-post.textile). Index posts describe the default page and metadata, and they must be named "index" (index.textile). Regular posts are posts that don't care about date (such as wiki posts or just simple pages for a portfolio site), and they are named however (my-service-page.textile). Each post has metadata defined in a YAML header. The metadata can be wired explicitly to a themes implementation because, eventually, we'll all come to some sort of consensus on what should and shouldn't be included in the page metadata definition.
108
+
109
+ h2. View Variables
110
+
111
+ Inside your view you have access to quite a lot of variables:
112
+
113
+ # @metadata@: Hash of all the config variables defined for your header metadata.
114
+ # @config@: Hash of global config values
115
+ # @params@: Hash of values passed in through the URL
116
+ # @site@: site object, which has these properties
117
+ ## @posts@: array of posts
118
+ ## @categories@: array of categories @{:name => post}@
119
+ ## @pages@: array of pages (TBD)
120
+ # @post@: Post object, if applicable
121
+ ## @data@: Hash of metadata specific to this post (symbolized keys)
122
+ ## @title@: Post title
123
+ ## @url@: Relative URL to Post
124
+ ## @date@: Date post was created
125
+ ## @published@: Whether or not it's been officially published
126
+ ## @tags@
127
+ ## @categories@
128
+
129
+ ALL HASH KEYS ARE SYMBOLS, NOT STRINGS!
130
+
131
+ h2. Layouts
132
+
133
+ There are quite a few layouts available in each project:
134
+
135
+ # Overview
136
+ # Blog
137
+ # Post w/ column
138
+ # Post w/o column
139
+ # Portfolio: two column grid
140
+ # Portfolio: three column grid
141
+ # Testimonials
142
+ # two column list
143
+ # Contact
144
+
145
+ h2. TODO
146
+
147
+ # CycleHelper for easier haml repeaters
148
+
149
+ h2. Theme Development
150
+
151
+ "html2haml":http://html2haml.heroku.com/
152
+
153
+ Create a folder called shared/themes/my-theme-name. In there, create folders for html, touch, and flash. In the html folder, you need the following
154
+
155
+ <pre>
156
+ .
157
+ |-- index.haml # home page (layout.haml is somewhere else entirely)
158
+ |-- about
159
+ |-- blog
160
+ |-- features
161
+ |-- demos
162
+ |-- download
163
+ |-- support
164
+ |-- community
165
+ |-- shared
166
+ | |-- stylesheets
167
+ | |-- javascripts
168
+ | |-- images
169
+ | `-- partials
170
+ | |-- _head.haml
171
+ | `-- _header.haml
172
+ </pre>
173
+
174
+ There are two ways the posts/pages can be constructed:
175
+
176
+ # They have a date prefixing their name
177
+ # They are in an XML file
178
+
179
+ Dates specify an order, so do XML files. In the end, we have an xml file for each root directory that lists all of the posts in a tree. Whether they were from being in the "_posts" directory or because they were in an XML file, it doesn't matter.
180
+
181
+ If the content of the post doesn't need more than a few lines, you can specify it in XML (each item in XML is converted to a Post). Saves on space.
182
+
183
+ The end result is that we have 1 xml file for each category of posts, which can be imported into Flex.
184
+
185
+ h2. Posts vs. Pages
186
+
187
+ Posts are pages that can be mass produced, such as wiki pages, blog entries, and forum posts. They may have these extra defined properties:
188
+
189
+ # date
190
+ # categories
191
+ # tags
192
+
193
+ However, Pages can also have categories and tags and dates, but they are not used the same way as posts.
194
+
195
+ A major difference between pages and posts however is that Posts cannot be nested; Pages can be nested.
196
+
197
+ h3. So how do we define the difference between Pages and Posts in Broadway?
198
+
199
+ # Posts and Pages can be written with a date in their name: 2010-03-30-my-post.textile.
200
+ # Directories determine _some_ of the categories of Posts and Pages (you can define additional ones)
201
+ # Posts are basically subclasses of Page, which we can define in two ways:
202
+ ## Placing Posts into the __posts_ directory
203
+ ## Adding a @category@ to a Page called "post"
204
+ # Related Posts have the same layout, while related pages may have completely different layouts
205
+
206
+ So what we do is say, _all Posts are leaf items_. If a file is called @index.textile@, however, it is considered a Page for the corresponding directory. Thus, the following directory structure:
207
+
208
+ |-- overview
209
+ | |-- index.textile
210
+ | |-- screenshots.textile
211
+ | |-- performance.textile
212
+
213
+ ...corresponds to this XML structure:
214
+
215
+ <pre><code>
216
+ <page url="/overview">
217
+ <post url="/overview/screenshots"/>
218
+ <post url="/overview/performance"/>
219
+ </page>
220
+ </code></pre>
221
+
222
+ ...which corresponds to these ruby objects
223
+
224
+ <pre><code>
225
+ page = Page.new(:url => "/overview")
226
+ page.posts << Post.new(:url => "/overview/screenshots")
227
+ page.posts << Post.new(:url => "/overview/performance")
228
+ </pre></code>
229
+
230
+ Posts can have dates, categories, and tags, while pages can only have categories and tags.
231
+
232
+ h2. Post Properties
233
+
234
+ # title
235
+ # url
236
+ # has_one: image
237
+ # tooltip
238
+ # content
239
+ # description
240
+ # categories (directory)
241
+ # tags
242
+ # slug (identifier)
243
+ # published
244
+ # author
245
+ # comments
246
+ # attachments
247
+
248
+ h2. Attachment Properties
249
+
250
+ id - Integer
251
+ url - String
252
+ slug - String
253
+ title - String
254
+ description - String
255
+ caption - String
256
+ parent - Integer
257
+ mime_type - String
258
+ images - Object
259
+
260
+ - Go through public directory
261
+ - look for .xml and .textile/.markdown/.html
262
+ - Can go arbitrary levels deep
263
+ - Pages are for each directory
264
+ - if no page, then it will render an error page
265
+ - if index.haml, it will render that
266
+ - Posts are organized by category, which map directly to their directory
267
+ - Posts also have tags
268
+ - Themes can sort posts based on categories
269
+ - There is a global list of tags and categories
270
+ - Posts unique id is the slug
271
+ - posts can't be nested
272
+ - pages can't be nested, but the urls can be
273
+ - there are config files for random variables
274
+ - posts are stored into xml files by page (root level)
275
+ - posts can have 1 image, plus any random content in the post
276
+ - snippets are config items, which can be textile/markdown/html
277
+
278
+ If there is an index.xml in a folder, it is appended to the child matching that url node in the root index.xml file
279
+ - Content is either in XML, or in the index.textile file of a folder, or the name of the url dot textile.
280
+ - overview/index.textile
281
+ - overview.textile
282
+ - The Post (textile file) or XML node can specify the layout:
283
+ - <item layout="guides".../>
284
+ - layout: guides
285
+ If no layout is specified, it will check for these files:
286
+ - path/to/post/index.haml
287
+ - theme/path/index.haml
288
+ - error
289
+
290
+ h2. Defining Posts and Pages
291
+
292
+ Posts can be created in two ways: XML or text
293
+
294
+ h3. Posts from Text (HTML, Textile, Markdown)
295
+
296
+ Post objects are built out of the path to the file
297
+
298
+ h3. Posts from XML
299
+
300
+ Post objects are built out of everything in the XML. If the XML node is referencing a file outside of itself, then it falls into the first category.
data/Rakefile ADDED
@@ -0,0 +1,80 @@
1
+ require 'rake'
2
+ require "rake/rdoctask"
3
+ require 'rake/gempackagetask'
4
+ require File.join(File.expand_path(File.dirname(__FILE__)), 'lib', 'broadway', 'base')
5
+
6
+ def files(path, from = __FILE__, &block)
7
+ Dir.glob(File.join(File.dirname(from), path)) {|file| yield file}
8
+ end
9
+
10
+ APP_ROOT = defined?(RAILS_ROOT) ? RAILS_ROOT : File.dirname(__FILE__)
11
+ RAILS_ROOT = File.dirname(__FILE__)
12
+
13
+ # http://docs.rubygems.org/read/chapter/20
14
+ spec = Gem::Specification.new do |s|
15
+ s.name = "broadway"
16
+ s.author = "Lance Pollard"
17
+ s.version = Broadway::VERSION
18
+ s.date = "Mon Mar 22 20:12:47 -0700 2010"
19
+ s.summary = "More than Syncing Rails Apps with the Google Data API"
20
+ s.homepage = "http://github.com/viatropos/broadway"
21
+ s.email = "lancejpollard@gmail.com"
22
+ s.description = "Broadway: A New Way of Googling"
23
+ s.has_rdoc = true
24
+ s.rubyforge_project = "broadway"
25
+ s.platform = Gem::Platform::RUBY
26
+ s.files = %w(README.textile Rakefile) +
27
+ Dir["{broadway,lib,spec}/**/*"] -
28
+ Dir["spec/tmp"]
29
+ s.extra_rdoc_files = %w(README.textile)
30
+ s.require_path = "lib"
31
+ s.add_dependency("nokogiri")
32
+ s.add_dependency("activesupport", ">= 2.3.5")
33
+ s.add_dependency("activerecord", ">= 2.3.5")
34
+ end
35
+
36
+ desc "Create .gemspec file (useful for github)"
37
+ task :gemspec do
38
+ File.open("#{spec.name}.gemspec", "w") do |f|
39
+ f.puts spec.to_ruby
40
+ end
41
+ end
42
+
43
+ desc "Build the gem into the current directory"
44
+ task :gem => :gemspec do
45
+ `gem build #{spec.name}.gemspec`
46
+ end
47
+
48
+ desc "Print a list of the files to be put into the gem"
49
+ task :manifest => :clean do
50
+ File.open("Manifest", "w") do |f|
51
+ spec.files.each do |file|
52
+ f.puts file
53
+ end
54
+ end
55
+ end
56
+
57
+ Rake::GemPackageTask.new(spec) do |pkg|
58
+ pkg.gem_spec = spec
59
+ end
60
+
61
+ desc "Install the gem locally"
62
+ task :install => [:package] do
63
+ sh %{sudo gem install pkg/broadway-#{Broadway::VERSION} --no-ri --no-rdoc}
64
+ end
65
+
66
+ desc "Generate the rdoc"
67
+ Rake::RDocTask.new do |rdoc|
68
+ files = ["README.textile", "lib/**/*.rb"]
69
+ rdoc.rdoc_files.add(files)
70
+ rdoc.main = "README.textile"
71
+ rdoc.title = "Broadway: A New Way of Googling"
72
+ end
73
+
74
+ desc "Run the rspec"
75
+ task :default => :spec
76
+
77
+ desc "Run Broadway Benchmarks"
78
+ task :benchmark do
79
+ files("spec/benchmarks/*") {|file| system("ruby #{file}") }
80
+ end
data/lib/broadway.rb ADDED
@@ -0,0 +1,7 @@
1
+ libdir = File.dirname(__FILE__)
2
+ $LOAD_PATH.unshift(libdir) unless $LOAD_PATH.include?(libdir)
3
+
4
+ require 'broadway/base'
5
+ require 'broadway/main'
6
+
7
+ # http://en.wikipedia.org/wiki/Lists_of_musicals
@@ -0,0 +1,51 @@
1
+ module Broadway
2
+ module API
3
+
4
+ def Post.to_xml(site)
5
+ xml = Nokogiri::XML::Builder.new { |xml|
6
+ xml.send("posts", :type => "array") {
7
+ site.posts.each do |post|
8
+ xml.post {
9
+ xml.title post.data["title"]
10
+ xml.url post.url
11
+ xml.categories post.categories.join(",")
12
+ xml.date(:type => "date") {
13
+ xml.text post.date.to_s
14
+ }
15
+ xml.slug post.slug
16
+ xml.published(:type => "boolean") {
17
+ xml.text post.published.to_s
18
+ }
19
+ xml.tags post.tags.join(",")
20
+ }
21
+ end
22
+ }
23
+ }
24
+ xml.to_xml
25
+ end
26
+
27
+ def Page.to_xml(site)
28
+ xml = Nokogiri::XML::Builder.new { |xml|
29
+ xml.send("pages", :type => "array") {
30
+ site.pages.each do |post|
31
+ xml.page {
32
+ xml.title post.data["title"]
33
+ xml.url post.url
34
+ xml.categories post.categories.join(",")
35
+ xml.date(:type => "date") {
36
+ xml.text post.date.to_s
37
+ }
38
+ xml.slug post.slug
39
+ xml.published(:type => "boolean") {
40
+ xml.text post.published.to_s
41
+ }
42
+ xml.tags post.tags.join(",")
43
+ }
44
+ end
45
+ }
46
+ }
47
+ xml.to_xml
48
+ end
49
+
50
+ end
51
+ end
@@ -0,0 +1,17 @@
1
+ module Broadway
2
+
3
+ class Asset
4
+ attr_accessor :url, :title, :tooltip, :thumb
5
+
6
+ def initialize(options = {})
7
+ options.each do |k,v|
8
+ self.send "#{k}=", v
9
+ end
10
+ end
11
+
12
+ def inspect
13
+ "#<Broadway:Asset @url=#{self.url.inspect} @title=#{self.title.inspect}>"
14
+ end
15
+ end
16
+
17
+ end