grass 0.0.1

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.
Files changed (74) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +17 -0
  3. data/.sass-cache/e3d4c2039fc7a8446e752aad5ac08f85d7457f92/(__TEMPLATE__)c +0 -0
  4. data/.travis.yml +3 -0
  5. data/Gemfile +4 -0
  6. data/LICENSE.txt +22 -0
  7. data/README.md +29 -0
  8. data/Rakefile +10 -0
  9. data/bin/grass +89 -0
  10. data/config/grass.rb +27 -0
  11. data/db/migrate/1_create_grass_sources.rb +24 -0
  12. data/grass.gemspec +43 -0
  13. data/lib/grass.rb +68 -0
  14. data/lib/grass/cache.rb +52 -0
  15. data/lib/grass/core_ext/kernel.rb +8 -0
  16. data/lib/grass/endpoints/api.rb +70 -0
  17. data/lib/grass/endpoints/front.rb +122 -0
  18. data/lib/grass/file_sync.rb +70 -0
  19. data/lib/grass/goliath/rack/auth_barrier.rb +109 -0
  20. data/lib/grass/goliath/rack/cache.rb +37 -0
  21. data/lib/grass/goliath/rack/cors.rb +45 -0
  22. data/lib/grass/goliath/rack/secure_headers.rb +20 -0
  23. data/lib/grass/goliath/rack/validator.rb +52 -0
  24. data/lib/grass/helpers/i18n_helper.rb +91 -0
  25. data/lib/grass/helpers/render_helper.rb +35 -0
  26. data/lib/grass/key.rb +137 -0
  27. data/lib/grass/render.rb +27 -0
  28. data/lib/grass/render/layout.rb +11 -0
  29. data/lib/grass/render/page.rb +31 -0
  30. data/lib/grass/render/renderer.rb +35 -0
  31. data/lib/grass/render/script.rb +27 -0
  32. data/lib/grass/render/stylesheet.rb +13 -0
  33. data/lib/grass/render/text.rb +11 -0
  34. data/lib/grass/render/view.rb +34 -0
  35. data/lib/grass/render/yui_renderer.rb +27 -0
  36. data/lib/grass/source.rb +107 -0
  37. data/lib/grass/tasks/db.rake +67 -0
  38. data/lib/grass/version.rb +3 -0
  39. data/lib/templates/app/Gemfile +9 -0
  40. data/lib/templates/app/Procfile +3 -0
  41. data/lib/templates/app/Rakefile +7 -0
  42. data/lib/templates/app/app/assets/scripts/application.en.js.coffee +1 -0
  43. data/lib/templates/app/app/assets/stylesheets/application.en.css.scss +4 -0
  44. data/lib/templates/app/app/content/pages/about.en.html.erb +3 -0
  45. data/lib/templates/app/app/content/pages/index.en.md.erb +5 -0
  46. data/lib/templates/app/app/views/layouts/application.en.html.erb +14 -0
  47. data/lib/templates/app/app/views/pages/show.en.html.erb +4 -0
  48. data/lib/templates/app/app/views/shared.en.html.erb +9 -0
  49. data/lib/templates/app/config/cache.yml +20 -0
  50. data/lib/templates/app/config/database.yml +35 -0
  51. data/lib/templates/app/config/grass.rb +27 -0
  52. data/lib/templates/app/db/migrate/1_create_grass_sources.rb +24 -0
  53. data/lib/templates/app/haproxy.cfg +43 -0
  54. data/lib/templates/app/public/favicon.ico +0 -0
  55. data/lib/templates/app/public/robots.txt +2 -0
  56. data/lib/templates/app/server.rb +7 -0
  57. data/test/dummy/app/content/texts/testapi.en.txt +1 -0
  58. data/test/dummy/config/cache.yml +23 -0
  59. data/test/dummy/config/database.yml +35 -0
  60. data/test/dummy/config/dummy.rb +1 -0
  61. data/test/dummy/config/haproxy.cfg +37 -0
  62. data/test/dummy/public/favicon.ico +0 -0
  63. data/test/dummy/public/robots.txt +2 -0
  64. data/test/minitest_helper.rb +38 -0
  65. data/test/support/grass.rb +21 -0
  66. data/test/support/test.jpg +0 -0
  67. data/test/test_api.rb +74 -0
  68. data/test/test_front.rb +52 -0
  69. data/test/test_key.rb +118 -0
  70. data/test/test_source.rb +51 -0
  71. data/test/test_source_file.rb +47 -0
  72. data/test/test_source_render.rb +54 -0
  73. data/vendor/yuicompressor-2.4.8.jar +0 -0
  74. metadata +399 -0
@@ -0,0 +1,27 @@
1
+ require "yui/compressor"
2
+ require 'grass/render/renderer'
3
+ module Grass
4
+ module Render
5
+ module YuiRenderer
6
+
7
+ include Renderer
8
+
9
+ YUI_JAR_FILE = "#{Grass.gem_root}/vendor/yuicompressor-2.4.8.jar"
10
+ CSS = YUI::CssCompressor.new({jar_file: YUI_JAR_FILE})
11
+ JS = YUI::JavaScriptCompressor.new({jar_file: YUI_JAR_FILE, munge: true})
12
+
13
+ def render
14
+ compress(super)
15
+ end
16
+
17
+ def compress source
18
+ compressor.compress(source)
19
+ end
20
+
21
+ def compressor
22
+ raise NotImplementedError
23
+ end
24
+
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,107 @@
1
+ require 'active_record'
2
+ require 'grass/key'
3
+ require 'grass/file_sync'
4
+ require 'grass/render'
5
+ require 'grass/cache'
6
+ require 'mime/types'
7
+
8
+ module Grass
9
+
10
+
11
+ ##
12
+ # Source is smallest data object
13
+
14
+ class Source < ActiveRecord::Base
15
+
16
+ MIMES = {
17
+ 'text' => 'text/plain',
18
+ 'view' => 'text/html',
19
+ 'layout' => 'text/html',
20
+ 'page' => 'text/html',
21
+ 'script' => 'application/javascript',
22
+ 'stylesheet' => 'text/css'
23
+ }
24
+
25
+ cattr_accessor :fallback
26
+
27
+ self.fallback = true
28
+ self.primary_key = :keyid
29
+ self.table_name = :grass_sources
30
+
31
+ attr_accessor :key
32
+
33
+ after_initialize :convert_key
34
+
35
+ def self.[](*keys)
36
+ keys.flatten.map{|key|
37
+
38
+ key = Key.new(id: key.dup)
39
+
40
+ file = self.find_by(locale: key.locale, dir: key.dir, path: key.path)
41
+ if file.nil? && self.fallback
42
+ file = self.find_by(locale: I18n.default_locale, dir: key.dir, path: key.path)
43
+ end
44
+ file
45
+
46
+ }.compact
47
+ end
48
+
49
+ scope :locale, -> (locale) { unscoped.where(locale: locale.to_s) }
50
+ default_scope -> { where(hidden: false) }
51
+
52
+ include FileSync
53
+ include Render
54
+ include Cache
55
+
56
+ attr_reader :data
57
+
58
+ serialize :pairs, Array
59
+
60
+ after_initialize :set_mime_type
61
+ before_save :set_mime_type
62
+
63
+ def read
64
+ self.binary || self.result || self.raw
65
+ end
66
+
67
+ def write value
68
+ # self.file.write(value)
69
+ self.update(raw: value)
70
+ end
71
+
72
+ def type
73
+ @type ||= self.key.dir.split("/").last.singularize
74
+ end
75
+
76
+ def hide!
77
+ self.update!(hidden: true)
78
+ end
79
+
80
+ def show!
81
+ self.update!(hidden: false)
82
+ end
83
+
84
+ private
85
+
86
+ def set_mime_type
87
+ self.mime_type ||= MIMES[self.type] || MIME::Types.type_for(self.binary.nil? ? self.format : self.filepath).first.to_s
88
+ end
89
+
90
+ def convert_key
91
+ if self.key.nil?
92
+ self.key = self.filepath ? Key.new(filepath: self.filepath) : Key.new(id: self.keyid)
93
+ elsif self.key.is_a? String
94
+ self.key = Key.new(id: self.key)
95
+ end
96
+
97
+ Key::ATTR_TYPES.each do |attr|
98
+ unless attr == :id
99
+ write_attribute(attr,self.key.public_send(attr))
100
+ end
101
+ end
102
+ self.keyid = self.key.id
103
+ end
104
+
105
+ end
106
+
107
+ end
@@ -0,0 +1,67 @@
1
+ require 'pg'
2
+ require 'erb'
3
+ require 'active_record'
4
+ require 'yaml'
5
+ require 'active_support/core_ext/hash'
6
+
7
+ namespace :db do
8
+
9
+ desc "erases and rewinds all dbs"
10
+ task :rewind do
11
+ %w(development test).each do |env|
12
+ ENV['RACK_ENV']=env
13
+ Rake::Task["db:drop"].reenable
14
+ Rake::Task["db:create"].reenable
15
+ Rake::Task["db:migrate"].reenable
16
+ Rake::Task["db:drop"].invoke
17
+ Rake::Task["db:create"].invoke
18
+ Rake::Task["db:migrate"].invoke
19
+ end
20
+ end
21
+
22
+ desc "loads database configuration in for other tasks to run"
23
+ task :load_config do
24
+
25
+ # ActiveRecord::Base.configurations = db_conf
26
+
27
+ # drop and create need to be performed with a connection to the 'postgres' (system) database
28
+ ActiveRecord::Base.establish_connection db_conf.merge('database' => 'postgres',
29
+ 'schema_search_path' => 'public')
30
+ end
31
+
32
+ desc "creates and migrates your database"
33
+ task :setup => :load_config do
34
+ Rake::Task["db:create"].invoke
35
+ Rake::Task["db:migrate"].invoke
36
+ end
37
+
38
+ desc "migrate your database"
39
+ task :migrate do
40
+ ActiveRecord::Base.establish_connection db_conf
41
+
42
+ ActiveRecord::Migrator.migrate(
43
+ ActiveRecord::Migrator.migrations_paths,
44
+ ENV["VERSION"] ? ENV["VERSION"].to_i : nil
45
+ )
46
+ end
47
+
48
+ desc 'Drops the database'
49
+ task :drop => :load_config do
50
+ ActiveRecord::Base.connection.drop_database db_conf['database']
51
+ end
52
+
53
+ desc 'Creates the database'
54
+ task :create => :load_config do
55
+ ActiveRecord::Base.connection.create_database db_conf['database']
56
+ end
57
+
58
+
59
+ def db_conf
60
+ config = YAML.load(ERB.new(File.read("config/database.yml")).result)[env]
61
+ end
62
+
63
+ def env
64
+ ENV['RACK_ENV'] ||= "development"
65
+ end
66
+
67
+ end
@@ -0,0 +1,3 @@
1
+ module Grass
2
+ VERSION = "0.0.1"
3
+ end
@@ -0,0 +1,9 @@
1
+ ruby '2.0.0'
2
+
3
+ source 'https://rubygems.org'
4
+
5
+ gem 'grass', path: '../../../grass'
6
+ gem 'rake'
7
+ group :development, :test do
8
+ gem 'foreman'
9
+ end
@@ -0,0 +1,3 @@
1
+ e_front: bundle exec ruby server.rb front -c ./config/grass.rb -p 4000 -e ${ENV:-development} -sv
2
+ e_api: bundle exec ruby server.rb api -c ./config/grass.rb -p 4001 -e ${ENV:-development} -sv
3
+ haproxy: haproxy -f ./haproxy.cfg
@@ -0,0 +1,7 @@
1
+ $LOAD_PATH.unshift File.expand_path('../', __FILE__)
2
+ load "grass/tasks/db.rake"
3
+ desc "pushes deployed file changes"
4
+ task :deploy do
5
+ system 'bundle exec grass push'
6
+ end
7
+ task :default => :deploy
@@ -0,0 +1 @@
1
+ console.log "hello from Grass!"
@@ -0,0 +1,4 @@
1
+ body{
2
+ background: #f0f0f0;
3
+ color: #333;
4
+ }
@@ -0,0 +1,3 @@
1
+ <!-- START/pages/about.erb.html -->
2
+ <h2> About Page </h2>
3
+ <!-- END/pages/about.erb.html -->
@@ -0,0 +1,5 @@
1
+ <!-- START/pages/index.md.erb.html -->
2
+ # Hello World!
3
+
4
+ Welcome to Grass App!
5
+ <!-- END/pages/index.md.erb.html -->
@@ -0,0 +1,14 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>Grass</title>
5
+ <link rel="stylesheet" href="/stylesheets/application.css" type="text/css" media="screen" title="no title" charset="utf-8">
6
+ </head>
7
+ <body>
8
+
9
+ <!-- START/layouts/application.erb.html -->
10
+ <%= yield %>
11
+ <!-- END/layouts/application.erb.html -->
12
+
13
+ <script type="text/javascript" charset="utf-8" src="/scripts/application.js"></script>
14
+ </body>
@@ -0,0 +1,4 @@
1
+ <!-- START/views/pages.erb.html -->
2
+ <%= render_content %>
3
+ <%= render_partial('/views/shared') %>
4
+ <!-- END/views/pages.erb.html -->
@@ -0,0 +1,9 @@
1
+ <!-- START/views/shared.erb.html -->
2
+ <pre>
3
+ country_info: <%= country_info %>
4
+ language_info: <%= language_info %>
5
+ http_host: <%= http_host %>
6
+ request_path: <%= request_path %>
7
+ params: <%= params %>
8
+ </pre>
9
+ <!-- END/views/shared.erb.html -->
@@ -0,0 +1,20 @@
1
+ development:
2
+ compress: true
3
+ threadsafe: true
4
+ namespace: grass:$app_development
5
+ servers: localhost:11211
6
+ async: true
7
+ test:
8
+ compress: true
9
+ threadsafe: true
10
+ namespace: grass:$app_test
11
+ servers: localhost:11211
12
+ async: true
13
+ production:
14
+ compress: true
15
+ threadsafe: true
16
+ namespace: grass:$app
17
+ servers: <%= ENV['MEMCACHIER_SERVERS'] %>
18
+ password: <%= ENV['MEMCACHIER_PASSWORD'] %>
19
+ username: <%= ENV['MEMCACHIER_USERNAME'] %>
20
+ async: true
@@ -0,0 +1,35 @@
1
+ development:
2
+ adapter: postgresql
3
+ encoding: unicode
4
+ database: $app_development
5
+ username: $username
6
+ password:
7
+ host: localhost
8
+ port: 5432
9
+ # pool: 5
10
+ # connections: 20
11
+
12
+ test:
13
+ adapter: postgresql
14
+ encoding: unicode
15
+ database: $app_test
16
+ username: $username
17
+ password:
18
+ host: localhost
19
+ port: 5432
20
+ # pool: 5
21
+ # connections: 20
22
+
23
+ production:
24
+ <% if db = URI.parse(ENV['DATABASE_URL']) rescue nil %>
25
+ adapter: <%= db.scheme == "postgres" ? "postgresql" : db.scheme %>
26
+ encoding: unicode
27
+ database: <%= db.path[1..-1] %>
28
+ username: <%= db.user %>
29
+ password: <%= db.password %>
30
+ host: <%= db.host %>
31
+ port: <%= db.port %>
32
+ pool: <%= ENV['DB_POOL'] || 5 %>
33
+ connections: <%= ENV['DB_CONNECTIONS'] || 20 %>
34
+ reaping_frequency: <%= ENV['DB_REAP_FREQ'] || 10 %>
35
+ <% end %>
@@ -0,0 +1,27 @@
1
+ require 'i18n'
2
+ require 'grass'
3
+ require 'ip_country'
4
+ require 'active_record'
5
+
6
+ Time.zone = ENV['TIME_ZONE'] || "London"
7
+ I18n.load_path << Dir.glob("#{Grass.root}/config/locales/**/*.yml")
8
+ I18n.enforce_available_locales = false
9
+ I18n.backend.class.send(:include, I18n::Backend::Fallbacks)
10
+ I18n.default_locale = ENV['DEFAULT_LOCALE'] ? ENV['DEFAULT_LOCALE'].to_sym : :en
11
+ I18n.available_locales = ENV['AVAILABLE_LOCALES'] ? ENV['AVAILABLE_LOCALES'].split(",").map(&:to_sym) : [:en]
12
+
13
+ ActiveRecord::Base.establish_connection Grass.load_config('database')
14
+
15
+ if respond_to?(:config)
16
+
17
+ # config['enable_cache_for_development'] = true
18
+
19
+ ENV['GEOIP_FILE'] ||= "#{Grass.root}/db/geo_ip.dat"
20
+ if ::File.exists?(ENV['GEOIP_FILE'])
21
+ IPCountry.init ENV['GEOIP_FILE']
22
+ config['ip_country'] = IPCountry
23
+ end
24
+
25
+ config['dalli'] = Grass.cache
26
+
27
+ end
@@ -0,0 +1,24 @@
1
+ class CreateGrassSources < ActiveRecord::Migration
2
+ def change
3
+ create_table :grass_sources, id: false do |t|
4
+ t.column :keyid, :string, null: false, index: true, primary: true
5
+ t.column :dir, :string
6
+ t.column :path, :string
7
+ t.column :locale, :string
8
+ t.column :format, :string
9
+ t.column :handler, :string
10
+ t.column :filepath, :string
11
+
12
+ t.column :raw, :text
13
+ t.column :result, :text
14
+ t.column :binary, :oid, limit: 2147483648 #:binary
15
+
16
+ t.column :pairs, :string, default: []
17
+ t.column :hidden, :boolean, default: false
18
+ t.column :mime_type, :string
19
+
20
+ t.timestamps
21
+ end
22
+ add_index :grass_sources, [:locale,:dir,:path], unique: true
23
+ end
24
+ end
@@ -0,0 +1,43 @@
1
+ global
2
+ pidfile /var/run/haproxy.pid
3
+ log 127.0.0.1 local0 info
4
+ user root
5
+
6
+ defaults
7
+ mode http
8
+
9
+ clitimeout 600000 # maximum inactivity time on the client side
10
+ srvtimeout 600000 # maximum inactivity time on the server side
11
+ timeout connect 8000 # maximum time to wait for a connection attempt to a server to succeed
12
+
13
+ stats enable
14
+ stats auth admin:password
15
+ stats uri /monitor
16
+ stats refresh 5s
17
+ retries 5
18
+ option httpchk GET /status
19
+ option redispatch
20
+ option httpclose
21
+ option abortonclose
22
+ option forwardfor
23
+
24
+ balance roundrobin # each server is used in turns, according to assigned weight
25
+
26
+ frontend http
27
+ bind :5000
28
+ monitor-uri /haproxy # end point to monitor HAProxy status (returns 200)
29
+
30
+ acl acl_api hdr_beg(host) -i api
31
+ use_backend backend_api if acl_api
32
+
33
+ acl acl_front path_reg ^/?
34
+ use_backend backend_front if acl_front
35
+
36
+ default_backend backend_front
37
+
38
+ backend backend_front
39
+ server srv_index 127.0.0.1:4000
40
+
41
+ backend backend_api
42
+ server srv_donors 127.0.0.1:4001
43
+
@@ -0,0 +1,2 @@
1
+ User-agent: *
2
+ Disallow: /