minirails 0.1.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.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 771b7f597898182a1fa53aface49303f6eb3185f
4
+ data.tar.gz: af5236b60849641f505d8a2a81fceccdfa12896f
5
+ SHA512:
6
+ metadata.gz: 89cb680f0c831cabb870674a5ecf0a4bf67ddd90c22b283168bcc192681e121ab79a1e74c4bff83082a6d30af82199106cc4e7b72057175db4e951eb4df1db91
7
+ data.tar.gz: 37fe4d4613b58e30f15e22a24b39aaff7b5503940ad222f6407cbd27c63c2327334b7849846ad20b7ecfb7ab54d21a44159158ee5fe58354a4fbe0f84106dde4
data/.gitignore ADDED
@@ -0,0 +1,9 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /coverage/
6
+ /doc/
7
+ /pkg/
8
+ /spec/reports/
9
+ /tmp/
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in minirails.gemspec
4
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2015 Tymon Tobolski
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,138 @@
1
+ # Minirails
2
+
3
+ > Run example rails app from single file
4
+
5
+ Inspired by [The Smallest Rails App](http://thesmallestrailsapp.com/), I wanted to easily try various concepts inside rails apps without having to deal with all that bloat from standard rails directory structure.
6
+
7
+ I went even further, not only reducing full rails app into single file (that has already been done) but to reducing a set of rails apps into single file :sunglasses:
8
+
9
+ More seriously, you can now create whole microservice architecture within a singe file and somebody else will be able to grasp it all and execute it locally. Or you can easily make a single file app and post it to StackOverflow (and people can actually run this code)
10
+
11
+ Just think about it. Proof of Concepts. Asking questions. Explaining concepts.
12
+
13
+ ## Installation
14
+
15
+ ```
16
+ $ gem install minirails
17
+ ```
18
+
19
+ ## Basic usage
20
+
21
+ Create a file `myapp.rb` with the following content
22
+
23
+ ```ruby
24
+ # myapp.rb
25
+ define do |app|
26
+ class ::MainController < ActionController::Base
27
+ def index
28
+ render text: "Hello"
29
+ end
30
+ end
31
+
32
+ app.routes.draw do
33
+ get "/", to: "main#index"
34
+ end
35
+ end
36
+ ```
37
+
38
+ then run
39
+ ```
40
+ $ minirails myapp.rb
41
+ ```
42
+
43
+ and that's it - you now have fully functional rails app running on port 5000!
44
+
45
+ ## Advanced usage
46
+
47
+ ### Multiple apps
48
+
49
+ You can run multiple applications from singe file
50
+
51
+ ```ruby
52
+ # file: multiple.rb
53
+ # usage: $ minirails multiple.rb
54
+ define "one" do |app|
55
+ app.routes.draw do
56
+ get "/", to: proc {|*| [200, {}, "Hello".lines] }
57
+ end
58
+ end
59
+
60
+ define "two" do |app|
61
+ app.routes.draw do
62
+ get "/", to: proc {|*| [200, {}, "World".lines] }
63
+ end
64
+ end
65
+ ```
66
+
67
+ They will be run on ports 5000 and 5100 (and 5200 etc.)
68
+
69
+ ### Database setup
70
+
71
+ You can also use full ActiveRecord capabilities.
72
+ The database (specified with `ENV["DATABASE_URL"]`) will be recreated (drop & create & migrate) on every run
73
+
74
+ ```ruby
75
+ # file: database.rb
76
+ # usage: $ minirails database.rb
77
+ define "source" do |app|
78
+ # Configuration
79
+ ENV["DATABASE_URL"] = "postgresql://localhost/minirails_test"
80
+
81
+ # Migrations
82
+ class CreateUsers < ActiveRecord::Migration
83
+ def change
84
+ create_table :users do |t|
85
+ t.string :name
86
+ t.string :email
87
+ end
88
+ end
89
+ end
90
+
91
+ # Seeds (using migartions)
92
+ class CreateSomeUsersToStartWith < ActiveRecord::Migration
93
+ def change
94
+ User.create! [
95
+ {name: "Jon", email: "jon@example.com"},
96
+ {name: "Hodor", email: "hodor@example.com"}
97
+ ]
98
+ end
99
+ end
100
+
101
+
102
+ # Models
103
+ class User < ActiveRecord::Base
104
+ end
105
+
106
+ # Controllers
107
+ class UsersController < ActionController::Base
108
+ def index
109
+ render json: User.all
110
+ end
111
+ end
112
+
113
+ # Routes
114
+ app.routes.draw do
115
+ resources :users
116
+ end
117
+ end
118
+ ```
119
+
120
+ ## FAQ
121
+
122
+ - **How to speed up loading?**
123
+
124
+ Run `$ minirails --fast` and then use `bin/minirails myapp.rb` instead
125
+
126
+
127
+ - **I'm getting "constant not found" errors!**
128
+
129
+ You need to prefix your classes with `::` to put them in top level scope
130
+
131
+
132
+ ## Contributing
133
+
134
+ 1. Fork it ( https://github.com/teamon/minirails/fork )
135
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
136
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
137
+ 4. Push to the branch (`git push origin my-new-feature`)
138
+ 5. Create a new Pull Request
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ require "bundler/gem_tasks"
2
+
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "minirails"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start
data/bin/setup ADDED
@@ -0,0 +1,7 @@
1
+ #!/bin/bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+
5
+ bundle install
6
+
7
+ # Do any other automated setup that you need to do here
data/exe/minirails ADDED
@@ -0,0 +1,6 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ $: << File.expand_path("../../lib", __FILE__)
4
+ require "minirails"
5
+
6
+ Minirails.run(ARGV)
@@ -0,0 +1,3 @@
1
+ module Minirails
2
+ VERSION = "0.1.0"
3
+ end
data/lib/minirails.rb ADDED
@@ -0,0 +1,165 @@
1
+ require "minirails/version"
2
+
3
+ module Minirails
4
+ class << self
5
+ def run(argv)
6
+ case argv[0]
7
+ when "--init"
8
+ init
9
+ when "--fast"
10
+ fast
11
+ when "--help", nil
12
+ help
13
+ else
14
+ if argv[0].start_with?("--")
15
+ help
16
+ else
17
+ start(argv[0], argv[1])
18
+ end
19
+ end
20
+ end
21
+
22
+ def help
23
+ puts <<-EOS
24
+ Usage: #$0 [OPTIONS] [FILE]
25
+
26
+ $ #$0 myapp.rb
27
+
28
+ OPTIONS:
29
+ --help Show this message
30
+ --init Create new sample app
31
+ --fast Setup faster app loading
32
+ EOS
33
+ end
34
+
35
+ def init
36
+ File.open("myapp.rb", "w") do |f|
37
+ f.write File.read(File.expand_path("../../test/apps/hello.rb", __FILE__))
38
+ end
39
+
40
+ puts "You new app has been created! You can strat it with $ minirails myapp.rb"
41
+ end
42
+
43
+ def fast
44
+ File.open("Gemfile", "w") do |f|
45
+ f.puts %Q|source "https://rubygems.org"|
46
+ f.puts %Q|gem "minirails"|
47
+ end
48
+
49
+ system "bundle install"
50
+ system "bundle binstubs minirails --force"
51
+
52
+ puts "Now you can use much faster bin/minirails instead of minirails"
53
+ end
54
+
55
+ def start(specfile, num = nil)
56
+ builder = Builder.new(specfile)
57
+ num ? builder.start(num.to_i) : builder.spawn
58
+ end
59
+ end
60
+
61
+
62
+ class Builder < Struct.new(:specfile)
63
+ # DSL API
64
+ def define(name = nil, &block)
65
+ apps << App.new(name, block)
66
+ end
67
+
68
+ # internals
69
+ def start(num)
70
+ boot
71
+
72
+ $stderr.puts "--> loading rails"
73
+ require "action_controller"
74
+ require "rails"
75
+ $stderr.puts "--> loading app"
76
+
77
+ Rack::Handler::WEBrick.run(endpoint(num), :Port => ENV["PORT"])
78
+ end
79
+
80
+ def endpoint(num)
81
+ apps[num].endpoint
82
+ rescue NameError => e
83
+ # autoloading has some crazy weird error
84
+ # and we can't just require activerecord upfront
85
+ # because if app is not using it there will
86
+ # be no database configuration
87
+ case e.message
88
+ when /uninitialized constant.*ActiveRecord/
89
+ $stderr.puts "--> loading activerecord"
90
+ require "active_record/railtie"
91
+ else
92
+ raise e
93
+ end
94
+
95
+ endpoint(num)
96
+ end
97
+
98
+ def spawn
99
+ boot
100
+
101
+ require "foreman/engine/cli"
102
+
103
+ engine = Foreman::Engine::CLI.new
104
+ apps.each.with_index do |app, index|
105
+ engine.register(
106
+ app.name || "web-#{index}",
107
+ "#{File.expand_path($0)} #{File.expand_path(specfile)} #{index}",
108
+ cwd: Dir.pwd
109
+ )
110
+ end
111
+
112
+ engine.start
113
+ end
114
+
115
+ protected
116
+
117
+ def apps
118
+ @apps ||= []
119
+ end
120
+
121
+ def boot
122
+ eval File.read(specfile)
123
+ end
124
+ end
125
+
126
+ class App < Struct.new(:name, :block)
127
+ def build
128
+ # basic rails app bootstrap
129
+ app = Class.new(Rails::Application) do
130
+ config.eager_load = false
131
+ config.secret_key_base = SecureRandom.hex
132
+ config.logger = Logger.new(STDERR)
133
+ end
134
+
135
+ # ActiveRecord specific configuration
136
+ if app.config.respond_to?(:active_record)
137
+ app.config.active_record.dump_schema_after_migration = false
138
+ end
139
+
140
+ # initialize app
141
+ app.initialize!
142
+
143
+ # execute 'define' block
144
+ block.call(app)
145
+
146
+ # ActiveRecord post functions
147
+ if app.config.respond_to?(:active_record)
148
+ # load rake tasks
149
+ app.load_tasks
150
+
151
+ # create and migrate database
152
+ Rake::Task["db:drop"].invoke
153
+ Rake::Task["db:create"].invoke
154
+ ActiveRecord::Migration.descendants.each {|e| e.migrate :up }
155
+ end
156
+
157
+ # and finally return app object
158
+ app
159
+ end
160
+
161
+ def endpoint
162
+ @endpoint ||= build
163
+ end
164
+ end
165
+ end
data/minirails.gemspec ADDED
@@ -0,0 +1,30 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'minirails/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "minirails"
8
+ spec.version = Minirails::VERSION
9
+ spec.authors = ["Tymon Tobolski"]
10
+ spec.email = ["i@teamon.eu"]
11
+
12
+ spec.summary = %q{Smallest Rails Apps launcher}
13
+ spec.description = %q{Smallest Rails Apps launcher}
14
+ spec.homepage = "http://github.com/teamon/minirails"
15
+ spec.license = "MIT"
16
+
17
+ spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
18
+ spec.bindir = "exe"
19
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
20
+ spec.require_paths = ["lib"]
21
+
22
+ spec.add_dependency "foreman", "~> 0.78.0"
23
+ spec.add_dependency "rack", "~> 1.6.4"
24
+ spec.add_dependency "railties", "~> 4.2.4"
25
+ spec.add_dependency "activerecord", "~> 4.2.4"
26
+ spec.add_dependency "pg", "~> 0.18.3"
27
+
28
+ spec.add_development_dependency "bundler", "~> 1.8"
29
+ spec.add_development_dependency "rake", "~> 10.0"
30
+ end
metadata ADDED
@@ -0,0 +1,154 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: minirails
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Tymon Tobolski
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2015-12-08 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: foreman
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: 0.78.0
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: 0.78.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: rack
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: 1.6.4
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: 1.6.4
41
+ - !ruby/object:Gem::Dependency
42
+ name: railties
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: 4.2.4
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: 4.2.4
55
+ - !ruby/object:Gem::Dependency
56
+ name: activerecord
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: 4.2.4
62
+ type: :runtime
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: 4.2.4
69
+ - !ruby/object:Gem::Dependency
70
+ name: pg
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
74
+ - !ruby/object:Gem::Version
75
+ version: 0.18.3
76
+ type: :runtime
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: 0.18.3
83
+ - !ruby/object:Gem::Dependency
84
+ name: bundler
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - "~>"
88
+ - !ruby/object:Gem::Version
89
+ version: '1.8'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - "~>"
95
+ - !ruby/object:Gem::Version
96
+ version: '1.8'
97
+ - !ruby/object:Gem::Dependency
98
+ name: rake
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - "~>"
102
+ - !ruby/object:Gem::Version
103
+ version: '10.0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - "~>"
109
+ - !ruby/object:Gem::Version
110
+ version: '10.0'
111
+ description: Smallest Rails Apps launcher
112
+ email:
113
+ - i@teamon.eu
114
+ executables:
115
+ - minirails
116
+ extensions: []
117
+ extra_rdoc_files: []
118
+ files:
119
+ - ".gitignore"
120
+ - Gemfile
121
+ - LICENSE.txt
122
+ - README.md
123
+ - Rakefile
124
+ - bin/console
125
+ - bin/setup
126
+ - exe/minirails
127
+ - lib/minirails.rb
128
+ - lib/minirails/version.rb
129
+ - minirails.gemspec
130
+ homepage: http://github.com/teamon/minirails
131
+ licenses:
132
+ - MIT
133
+ metadata: {}
134
+ post_install_message:
135
+ rdoc_options: []
136
+ require_paths:
137
+ - lib
138
+ required_ruby_version: !ruby/object:Gem::Requirement
139
+ requirements:
140
+ - - ">="
141
+ - !ruby/object:Gem::Version
142
+ version: '0'
143
+ required_rubygems_version: !ruby/object:Gem::Requirement
144
+ requirements:
145
+ - - ">="
146
+ - !ruby/object:Gem::Version
147
+ version: '0'
148
+ requirements: []
149
+ rubyforge_project:
150
+ rubygems_version: 2.4.5.1
151
+ signing_key:
152
+ specification_version: 4
153
+ summary: Smallest Rails Apps launcher
154
+ test_files: []