plezi 0.12.22 → 0.14.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.
Files changed (108) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +18 -0
  3. data/LICENSE.txt +17 -18
  4. data/README.md +54 -698
  5. data/Rakefile +7 -4
  6. data/bin/config.ru +22 -0
  7. data/{test → bin}/console +4 -6
  8. data/bin/hello_world +52 -0
  9. data/bin/setup +8 -0
  10. data/exe/plezi +145 -0
  11. data/lib/plezi.rb +24 -137
  12. data/lib/plezi/activation.rb +28 -0
  13. data/lib/plezi/api.rb +62 -0
  14. data/lib/plezi/controller/controller.rb +259 -0
  15. data/lib/plezi/controller/controller_class.rb +176 -0
  16. data/lib/plezi/controller/cookies.rb +40 -0
  17. data/lib/plezi/helpers.rb +60 -0
  18. data/lib/plezi/rake.rb +2 -24
  19. data/lib/plezi/render/erb.rb +34 -0
  20. data/lib/plezi/render/has_cache.rb +36 -0
  21. data/lib/plezi/render/markdown.rb +63 -0
  22. data/lib/plezi/render/render.rb +49 -0
  23. data/lib/plezi/render/sass.rb +55 -0
  24. data/lib/plezi/render/slim.rb +33 -0
  25. data/lib/plezi/router/adclient.rb +23 -0
  26. data/lib/plezi/router/assets.rb +67 -0
  27. data/lib/plezi/router/errors.rb +29 -0
  28. data/lib/plezi/router/route.rb +112 -0
  29. data/lib/plezi/router/router.rb +120 -0
  30. data/lib/plezi/version.rb +1 -1
  31. data/lib/plezi/websockets/message_dispatch.rb +91 -0
  32. data/lib/plezi/websockets/redis.rb +55 -0
  33. data/plezi.gemspec +25 -16
  34. data/resources/404.erb +5 -4
  35. data/resources/500.erb +5 -4
  36. data/resources/{500.html → 503.html} +8 -9
  37. data/resources/client.js +253 -0
  38. data/resources/config.ru +5 -36
  39. data/resources/ctrlr.rb +34 -0
  40. data/resources/gemfile +4 -0
  41. data/resources/mini_app.rb +28 -82
  42. data/resources/mini_exec +7 -0
  43. data/resources/mini_welcome_page.html +0 -0
  44. data/resources/procfile +3 -0
  45. data/resources/rakefile +4 -8
  46. data/resources/routes.rb +9 -26
  47. data/resources/{websockets.js → simple-client.js} +3 -3
  48. metadata +60 -85
  49. data/bin/plezi +0 -104
  50. data/docs/async_helpers.md +0 -245
  51. data/docs/controllers.md +0 -27
  52. data/docs/logging.md +0 -49
  53. data/docs/routes.md +0 -209
  54. data/docs/websockets.md +0 -213
  55. data/lib/plezi/builders/ac_model.rb +0 -59
  56. data/lib/plezi/builders/app_builder.rb +0 -137
  57. data/lib/plezi/builders/builder.rb +0 -43
  58. data/lib/plezi/builders/form_builder.rb +0 -27
  59. data/lib/plezi/common/api.rb +0 -92
  60. data/lib/plezi/common/cache.rb +0 -122
  61. data/lib/plezi/common/defer.rb +0 -21
  62. data/lib/plezi/common/dsl.rb +0 -94
  63. data/lib/plezi/common/redis.rb +0 -65
  64. data/lib/plezi/common/renderer.rb +0 -141
  65. data/lib/plezi/common/settings.rb +0 -52
  66. data/lib/plezi/handlers/controller_core.rb +0 -106
  67. data/lib/plezi/handlers/controller_magic.rb +0 -284
  68. data/lib/plezi/handlers/http_router.rb +0 -205
  69. data/lib/plezi/handlers/placebo.rb +0 -112
  70. data/lib/plezi/handlers/route.rb +0 -216
  71. data/lib/plezi/handlers/session.rb +0 -109
  72. data/lib/plezi/handlers/stubs.rb +0 -156
  73. data/lib/plezi/handlers/ws_identity.rb +0 -253
  74. data/lib/plezi/handlers/ws_object.rb +0 -308
  75. data/lib/plezi/helpers/http_sender.rb +0 -84
  76. data/lib/plezi/helpers/magic_helpers.rb +0 -104
  77. data/lib/plezi/helpers/mime_types.rb +0 -1995
  78. data/lib/plezi/oauth.rb +0 -5
  79. data/lib/plezi/oauth/auth_controller.rb +0 -229
  80. data/logo/dark.png +0 -0
  81. data/logo/light.png +0 -0
  82. data/logo/sign.png +0 -0
  83. data/resources/404.haml +0 -121
  84. data/resources/404.html +0 -124
  85. data/resources/404.slim +0 -120
  86. data/resources/500.haml +0 -120
  87. data/resources/500.slim +0 -120
  88. data/resources/Gemfile +0 -86
  89. data/resources/code.rb +0 -8
  90. data/resources/controller.rb +0 -142
  91. data/resources/database.yml +0 -33
  92. data/resources/db_ac_config.rb +0 -59
  93. data/resources/db_dm_config.rb +0 -51
  94. data/resources/db_sequel_config.rb +0 -33
  95. data/resources/en.yml +0 -204
  96. data/resources/haml_config.rb +0 -6
  97. data/resources/i18n_config.rb +0 -14
  98. data/resources/initialize.rb +0 -49
  99. data/resources/mini_exec.rb +0 -7
  100. data/resources/oauth_config.rb +0 -24
  101. data/resources/plezi_client.js +0 -198
  102. data/resources/plezi_websockets.html +0 -47
  103. data/resources/redis_config.rb +0 -42
  104. data/resources/slim_config.rb +0 -11
  105. data/resources/welcome_page.html +0 -272
  106. data/test/dispatch +0 -58
  107. data/test/hello_world +0 -13
  108. data/test/plezi_tests.rb +0 -581
@@ -1,59 +0,0 @@
1
- require 'plezi/builders/builder'
2
-
3
- module Plezi
4
-
5
- module Base
6
-
7
-
8
- module ACModelBuilder
9
- @gem_root = ::Plezi::Builder::GEM_ROOT
10
-
11
- # ActiveRecord::Base.connection.tables
12
- # # Checks for existence of kittens table (Kitten model)
13
- # ActiveRecord::Base.connection.table_exists? 'kittens'
14
-
15
- # # Tells you all migrations run
16
- # ActiveRecord::Migrator.get_all_versions
17
- # # Tells you the current schema version
18
- # ActiveRecord::Migrator.current_version
19
-
20
- # # Check a column exists
21
- # column_exists?(:suppliers, :name)
22
-
23
- # # Check a column exists of a particular type
24
- # column_exists?(:suppliers, :name, :string)
25
-
26
- # # Check a column exists with a specific definition
27
- # column_exists?(:suppliers, :name, :string, limit: 100)
28
- # column_exists?(:suppliers, :name, :string, default: 'default')
29
- # column_exists?(:suppliers, :name, :string, null: false)
30
- # column_exists?(:suppliers, :tax, :decimal, precision: 8, scale: 2)
31
-
32
- def self.parse_args
33
- return unless ARGS[0][0] == 'g'
34
- struct = {}
35
- ARGS[1..-1].each do |s|
36
- s = s.split /[\:\.]/
37
- raise "Cannot parse parameters - need to be defined as name.type or name:type." if s.count !=2
38
- struct[s[0]] = DB_TYPES[s[1].downcase] || (raise "Unrecognized type #{s[1]}.")
39
- end
40
- struct
41
- end
42
- end
43
-
44
- # require 'sequel'
45
-
46
- # ## Connect to the database
47
- # DB = Sequel.sqlite('./ex1.db')
48
-
49
- # unless DB.table_exists? :posts
50
- # DB.create_table :posts do
51
- # primary_key :id
52
- # varchar :title
53
- # text :body
54
- # end
55
- # end
56
-
57
-
58
- end
59
- end
@@ -1,137 +0,0 @@
1
- require 'plezi/builders/builder'
2
- module Plezi
3
-
4
- module Base
5
-
6
- class AppBuilder
7
- def initialize
8
- @end_comments = []
9
- @app_tree ||= {}
10
- @root = ::Plezi::Base::Builder::GEM_ROOT
11
- end
12
- def app_tree
13
- @app_tree ||= {}
14
- end
15
- def build_mini app_name = ARGV[1]
16
- require 'plezi/version'
17
- app_tree["#{app_name}"] ||= IO.read( File.join(@root, "resources" ,"mini_exec.rb")).gsub('appname', app_name)
18
- app_tree["#{app_name}.rb"] ||= IO.read( File.join(@root, "resources" ,"mini_app.rb")).gsub('appname', app_name).gsub('appsecret', "#{app_name}_#{SecureRandom.hex}")
19
- app_tree["Procfile"] ||= String.new
20
- app_tree["Procfile"] << "\nweb: bundle exec ruby ./#{app_name} -p $PORT\n"
21
- app_tree["Gemfile"] ||= String.new
22
- app_tree["Gemfile"] << "source 'https://rubygems.org'\n\n####################\n# core gems\n\n# include the basic plezi framework and server\ngem 'plezi', '~> #{Plezi::VERSION}'\n"
23
- app_tree["Gemfile"] << "\n\n\nruby '#{RUBY_VERSION}'\n"
24
- app_tree["rakefile"] ||= IO.read(File.join(@root,"resources" ,"rakefile")).sub('initialize.rb', "#{app_name}.rb")
25
- app_tree["templates"] ||= {}
26
- app_tree["templates"]["404.html.erb"] ||= IO.read(File.join(@root, "resources" ,"404.erb"))
27
- app_tree["templates"]["500.html.erb"] ||= IO.read(File.join(@root, "resources" ,"500.erb"))
28
- app_tree["templates"]["welcome.html.erb"] ||= IO.read(File.join(@root, "resources" ,"mini_welcome_page.html")).gsub('appname', app_name)
29
- app_tree["assets"] ||= {}
30
- app_tree["assets"]["websocket.js"] ||= IO.read(File.join(@root, "resources" ,"websockets.js")).gsub('appname', app_name)
31
- app_tree["assets"]["plezi_client.js"] ||= IO.read(File.join(@root,"resources" ,"plezi_client.js")).gsub('appname', app_name)
32
- finalize app_name
33
- end
34
-
35
- def build app_name = ARGV[1]
36
- require 'plezi/version'
37
- # plezi run script
38
- app_tree["#{app_name}"] ||= IO.read File.join(@root,"resources" ,"code.rb")
39
-
40
- # set up application files
41
- app_tree["app"] ||= {}
42
- app_tree["app"]["controllers"] ||= {}
43
- app_tree["app"]["controllers"]["sample_controller.rb"] ||= IO.read(File.join(@root,"resources" ,"controller.rb"))
44
- app_tree["app"]["models"] ||= {}
45
- app_tree["app"]["views"] ||= {}
46
-
47
- # set up templates for status error codes
48
- app_tree["app"]["views"]["404.html"] ||= IO.read(File.join(@root,"resources" ,"404.html"))
49
- app_tree["app"]["views"]["500.html"] ||= IO.read(File.join(@root,"resources" ,"500.html"))
50
- app_tree["app"]["views"]["404.html.erb"] ||= IO.read(File.join(@root,"resources" ,"404.erb"))
51
- app_tree["app"]["views"]["500.html.erb"] ||= IO.read(File.join(@root,"resources" ,"500.erb"))
52
- app_tree["app"]["views"]["404.html.slim"] ||= IO.read(File.join(@root,"resources" ,"404.slim"))
53
- app_tree["app"]["views"]["500.html.slim"] ||= IO.read(File.join(@root,"resources" ,"500.slim"))
54
- app_tree["app"]["views"]["404.html.haml"] ||= IO.read(File.join(@root,"resources" ,"404.haml"))
55
- app_tree["app"]["views"]["500.html.haml"] ||= IO.read(File.join(@root,"resources" ,"500.haml"))
56
-
57
- # set up the assets folder
58
- app_tree["assets"] ||= {}
59
- app_tree["assets"]["stylesheets"] ||= {}
60
- app_tree["assets"]["javascripts"] ||= {}
61
- app_tree["assets"]["javascripts"]["websocket.js"] ||= IO.read(File.join(@root,"resources" ,"websockets.js")).gsub('appname', app_name)
62
- app_tree["assets"]["javascripts"]["plezi_client.js"] ||= IO.read(File.join(@root,"resources" ,"plezi_client.js")).gsub('appname', app_name)
63
- app_tree["assets"]["welcome.html"] ||= IO.read(File.join(@root,"resources" ,"welcome_page.html")).gsub('appname', app_name)
64
-
65
- # app core files.
66
- app_tree["initialize.rb"] ||= IO.read File.join(@root,"resources" ,"initialize.rb").gsub('appname', app_name)
67
- app_tree["routes.rb"] ||= IO.read File.join(@root,"resources" ,"routes.rb")
68
- app_tree["rakefile"] ||= IO.read File.join(@root,"resources" ,"rakefile")
69
- app_tree["Procfile"] ||= ""
70
- app_tree["Procfile"] << "\nweb: bundle exec ruby ./#{app_name} -p $PORT\n"
71
- app_tree["Gemfile"] ||= ''
72
- app_tree["Gemfile"] << "source 'https://rubygems.org'\n\n####################\n# core gems\n\n# include the basic plezi framework and server\ngem 'plezi', '~> #{Plezi::VERSION}'\n"
73
- app_tree["Gemfile"] << IO.read( File.join(@root,"resources" ,"Gemfile"))
74
- app_tree["Gemfile"] << "\n\n\nruby '#{RUBY_VERSION}'\n"
75
-
76
- # set up config files
77
- app_tree["initialize"] ||= {}
78
- app_tree["initialize"]["oauth.rb"] ||= IO.read(File.join(@root,"resources" ,"oauth_config.rb"))
79
- app_tree["initialize"]["active_record.rb"] ||= IO.read(File.join(@root,"resources" ,"db_ac_config.rb"))
80
- app_tree["initialize"]["sequel.rb"] ||= IO.read(File.join(@root,"resources" ,"db_sequel_config.rb"))
81
- app_tree["initialize"]["datamapper.rb"] ||= IO.read(File.join(@root,"resources" ,"db_dm_config.rb"))
82
- app_tree["initialize"]["haml.rb"] ||= IO.read(File.join(@root,"resources" ,"haml_config.rb"))
83
- app_tree["initialize"]["slim.rb"] ||= IO.read(File.join(@root,"resources" ,"slim_config.rb"))
84
- app_tree["initialize"]["i18n.rb"] ||= IO.read(File.join(@root,"resources" ,"i18n_config.rb"))
85
- app_tree["initialize"]["redis.rb"] ||= (IO.read(File.join(@root,"resources" ,"redis_config.rb"))).gsub('appsecret', "#{app_name}_#{SecureRandom.hex}")
86
-
87
- #set up database stub folders
88
- app_tree["db"] ||= {}
89
- app_tree["db"]["migrate"] ||= {}
90
- app_tree["db"]["fixtures"] ||= {}
91
- app_tree["db"]["config.yml"] ||= IO.read(File.join(@root,"resources" ,"database.yml"))
92
-
93
- #set up the extras folder, to be filled with future goodies.
94
- # app_tree["extras"] ||= {}
95
- # app_tree["extras"]["config.ru"] ||= IO.read File.join(@root,"resources" ,"config.ru")
96
-
97
- #set up I18n stub
98
- app_tree["locales"] ||= {}
99
- app_tree["locales"]["en.yml"] ||= IO.read File.join(@root,"resources" ,"en.yml")
100
-
101
- # create library, log and tmp folders
102
- app_tree["logs"] ||= {}
103
- app_tree["lib"] ||= {}
104
- app_tree["tmp"] ||= {}
105
-
106
-
107
- # set up a public folder for static file service
108
- app_tree["public"] ||= {}
109
- app_tree["public"]["assets"] ||= {}
110
- app_tree["public"]["assets"]["stylesheets"] ||= {}
111
- app_tree["public"]["assets"]["javascripts"] ||= {}
112
- app_tree["public"]["images"] ||= {}
113
- finalize app_name
114
- end
115
- def finalize app_name = ARGV[1]
116
- begin
117
- Dir.mkdir app_name
118
- puts "created the #{app_name} application directory.".green
119
- rescue => e
120
- puts "the #{app_name} application directory exists - trying to rebuild (no overwrite).".pink
121
- end
122
- Dir.chdir app_name
123
- puts "starting to write template data...".red
124
- puts ""
125
- Builder.write_files app_tree
126
- File.chmod 0775, "#{app_name}" rescue true
127
- puts "done."
128
- puts "\n#{@end_comments.join("\n")}" unless @end_comments.empty?
129
- puts ""
130
- puts "please change directory into the app directory: cd #{app_name}"
131
- puts ""
132
- puts "run the #{app_name} app using: ./#{app_name} or using: plezi s"
133
- puts ""
134
- end
135
- end
136
- end
137
- end
@@ -1,43 +0,0 @@
1
- module Plezi
2
- module Base
3
- module Builder
4
-
5
- GEM_ROOT = ::File.expand_path(File.join(File.dirname(__FILE__), '..', '..', '..'))
6
-
7
- def self.write_files files, parent = "."
8
- if files.is_a? Hash
9
- files.each do |k, v|
10
- if v.is_a? Hash
11
- begin
12
- Dir.mkdir k
13
- puts " created #{parent}/#{k}".green
14
- rescue => e
15
- puts " exists #{parent}/#{k}".red
16
- end
17
- Dir.chdir k
18
- write_files v, (parent + "/" + k)
19
- Dir.chdir ".."
20
- elsif v.is_a? String
21
- if ::File.exists? k
22
- if false #%w{Gemfile rakefile.rb}.include? k
23
- # old = IO.read k
24
- # old = (old.lines.map {|l| "\##{l}"}).join
25
- # IO.write k, "#####################\n#\n# OLD DATA COMMENTED OUT - PLEASE REVIEW\n#\n##{old}\n#{v}"
26
- # puts " #{parent}/#{k} WAS OVERWRITTEN, old data was preserved by comenting it out.".pink
27
- # puts " #{parent}/#{k} PLEASE REVIEW.".pink
28
- # @end_comments << "#{parent}/#{k} WAS OVERWRITTEN, old data was preserved by comenting it out. PLEASE REVIEW."
29
- else
30
- puts " EXISTS(!) #{parent}/#{k}".red
31
- end
32
- else
33
- IO.write k, v
34
- puts " wrote #{parent}/#{k}".yellow
35
- end
36
- end
37
- end
38
- end
39
- end
40
- end
41
- end
42
-
43
- end
@@ -1,27 +0,0 @@
1
- require 'plezi/builders/builder'
2
-
3
- module Plezi
4
-
5
- module Base
6
-
7
- module FormBuilder
8
-
9
- FORM_BUILDERS = %w{ Slim ERB }
10
- MODEL_BUILDERS = %w{ Squel }
11
-
12
- DB_TYPES = %w{primary_key string text integer float decimal datetime time date binary boolean}
13
-
14
- @gem_root = ::Plezi::Builder::GEM_ROOT
15
- def self.parse_args
16
- return unless ARGS[0][0] == 'g'
17
- struct = {}
18
- ARGS[1..-1].each do |s|
19
- s = s.split /[\:\.]/
20
- raise "Cannot parse parameters - need to be defined as name.type or name:type." if s.count !=2
21
- struct[s[0]] = DB_TYPES[s[1].downcase] || (raise "Unrecognized type #{s[1]}.")
22
- end
23
- struct
24
- end
25
- end
26
- end
27
- end
@@ -1,92 +0,0 @@
1
-
2
- module Plezi
3
-
4
- module_function
5
-
6
- # Defines methods used to set up the Plezi app.
7
-
8
- # Deprecated. use {Plezi.host}.
9
- def listen parameters = {}
10
- Iodine.warn "listen is deprecated. use `Plezi.host` instead."
11
- host parameters.delete(:host) || :default, parameters
12
- end
13
-
14
- # adds a route to the last server created
15
- def route(path, controller = nil, &block)
16
- if controller == :client
17
- client_path = File.expand_path(File.join('..','..','..','..','resources','plezi_client.js'), __FILE__)
18
- controller = nil
19
- block = Proc.new { Plezi.cache_needs_update?(client_path) ? Plezi.reload_file(client_path) : Plezi.load_file(client_path) }
20
- end
21
- ::Plezi::Base::HTTPRouter.add_route path, controller, &block
22
- end
23
-
24
-
25
- # adds a shared route to all existing services and hosts.
26
- def shared_route(path, controller = nil, &block)
27
- ::Plezi::Base::HTTPRouter.add_shared_route path, controller, &block
28
- end
29
-
30
- # public API to add or setup domain names related to the application.
31
- #
32
- # A default host can be created or accessed by using `:default` of false for the host name.
33
- #
34
- # Accepts:
35
- # host_name:: (optional, can be omitted) the name (domain name) of the host as a String object. Use the Symbol `:default` for the catch-all domain name.
36
- # options_hash:: see further detail.
37
- #
38
- #
39
- # The options is a Hash object with any of the following options (Hash keys):
40
- # host:: the ost name to be used if one isn't supplied as a direct argument. Defaults to the `:default` host.
41
- # alias:: a String or an Array of Strings which represent alternative host names (i.e. `alias: ["admin.google.com", "admin.gmail.com"]`).
42
- # public:: the public root folder. if this is defined, static files will be served from this folder and all it's sub-folders. Plezi does NOT support file indexing.
43
- # assets:: the assets root folder. defaults to nil (no assets support). if the path is defined, assets will be served from `/assets/...` (or the public_asset path defined) before any static files. assets will not be served if the file in the /public/assets folder if up to date (a rendering attempt will be made for systems that allow file writing).
44
- # assets_public:: the assets public uri location (uri format, NOT a file path). defaults to `/assets`. `save_assets` will set if assets should be saved to the assets public folder as static files (defaults to false).
45
- # assets_callback:: a method that accepts two parameters: (request, response) and renders any custom assets. the method should return `false` unless it had set the response.
46
- # save_assets:: saves the rendered assets to the filesystem, under the public folder. defaults to false.
47
- # templates:: the templates root folder. defaults to nil (no template support). templates can be rendered by a Controller class, using the `render` method.
48
- #
49
- # Assets:
50
- #
51
- # Assets support will render `.sass`, `.scss` and `.coffee` and save them as local files (`.css`, `.css`, and `.js` respectively)
52
- # before sending them as static files.
53
- #
54
- # Should you need to render a different type of asset, you can define an assets_callback (or submit a pull request with a patch).
55
- #
56
- # templates:
57
- #
58
- # Plezi's controller.render ERB, Slim and Haml are natively supported.
59
- #
60
- # @return [::Plezi::Base::HTTPRouter]
61
- #
62
- def host(host_name, params = {})
63
- ::Plezi::Base::HTTPRouter.add_host host_name, params
64
- end
65
-
66
- # This allows you to use the Plezi framework's code inside your existing Rack application - WITHOUT running the actual server.
67
- #
68
- # The server will not be initiatet and instead you will be able to use Plezi controllers and the Redis auto-config
69
- # to broadcast Plezi messages to other Plezi processes - allowing for scalable intigration of Plezi into existing Rack applications.
70
- def start_placebo receiver = nil
71
- # force start Iodine only if Iodine isn't used as the server
72
- if ::Iodine.protocol == ::Iodine::Http::Http1 && (defined?(::Rack::VERSION) ? (::Rack::Handler.default == ::Iodine::Http::Rack rescue true) : true)
73
- Iodine.log("* `start_placebo` Placebo directive ignored, as this seems to be the main application.\n")
74
- # just initialize the receiver class (no instance) and return
75
- Plezi::Placebo.new(receiver, false) if receiver
76
- return false
77
- end
78
- unless @placebo_initialized
79
- raise "Placebo fatal error: Redis connection failed to load - make sure gem is required and `ENV['PL_REDIS_URL']` is set." unless redis # make sure the redis connection is activated
80
- Iodine.log "* Plezi #{Plezi::VERSION} Services will start with no Server - This is the Placebo application\n"
81
- ::Iodine.protocol = :no_server
82
- Iodine.force_start!
83
- @placebo_initialized = true
84
- end
85
- receiver ? Plezi::Placebo.new(receiver) : true
86
- end
87
-
88
- # deprecation notice
89
- def start_rack
90
- Iodine.warn "`start_rack` is deprecated. There is no need to call this method."
91
- end
92
- end
@@ -1,122 +0,0 @@
1
-
2
- module Plezi
3
-
4
- # File and Object Caching for Plezi
5
- #
6
- # Be aware that the cache is local, per process. It's possible to limit file caching by limiting the supported_types in Plezi::Cache::CACHABLE.
7
- #
8
- # Template rendering engines are always cached.
9
- module Cache
10
- # contains the cached data, in the format: CACHE_STORE["filename"] = CacheObject
11
- CACHE_STORE = {}
12
- CACHE_LOCK = Mutex.new
13
- CACHABLE = (%w{cache object slim haml css map js html scss sass coffee txt xml json yaml rb}).to_set
14
-
15
- # this class holds cached objects (data and modification times)
16
- class CacheObject
17
- # Cached attributes
18
- attr_accessor :data, :mtime
19
-
20
- # initialize a Cached object
21
- def initialize d = nil, t = Time.now
22
- @data = d
23
- @mtime = t
24
- end
25
- end
26
-
27
- # load the file from the cache (if exists) or the file system (if it doesn't)
28
- def load_file filename
29
- cached?(filename) ? get_cached(filename) : reload_file(filename)
30
- end
31
- # review a file's modification time
32
- def file_mtime filename
33
- return CACHE_STORE[filename].mtime if cached?(filename)
34
- File.mtime(filename)
35
- end
36
-
37
- # force a file onto the cache (only if it is cachable - otherwise will load the file but will not cache it).
38
- def reload_file filename
39
- if CACHABLE.include? filename.match(/\.([^\.]+)$/)[1]
40
- return cache_data filename, IO.binread(filename), File.mtime(filename)
41
- else
42
- return IO.binread(filename)
43
- end
44
- end
45
- # places data into the cache, and attempts to save the data to a file name.
46
- def save_file filename, data, save_to_disk = false
47
- cache_data filename, data if CACHABLE.include? filename.match(/\.([^\.]+)$/)[1]
48
- begin
49
- IO.binwrite filename, data if save_to_disk
50
- rescue
51
- Plezi.warn("File couldn't be written (#{filename}) - file system error?")
52
- end
53
- data
54
- end
55
-
56
- # places data into the cache, under an identifier ( file name ).
57
- def cache_data filename, data, mtime = Iodine.time
58
- CACHE_LOCK.synchronize { CACHE_STORE[filename] = CacheObject.new( data, mtime ) }
59
- data
60
- end
61
-
62
- # Get data from the cache. will throw an exception if there is no data in the cache.
63
- #
64
- # If a block is passed to the method, it will allows you to modify the protected cache in a thread safe manner.
65
- #
66
- # This is useful for manipulating strings or arrays that are stored in the cache.
67
- def get_cached filename
68
- return CACHE_STORE[filename].data unless block_given?
69
- data = CACHE_STORE[filename].data
70
- CACHE_LOCK.synchronize { yield(data) }
71
- end
72
-
73
- # Remove data from the cache, if it exists.
74
- def clear_cached filename
75
- CACHE_LOCK.synchronize { CACHE_STORE.delete filename } # if CACHE_STORE[filename]
76
- end
77
-
78
- # clears all cached data.
79
- def clear_cache! filename
80
- CACHE_LOCK.synchronize { CACHE_STORE.clear } # if CACHE_STORE[filename]
81
- end
82
-
83
- # returns true if the filename is cached.
84
- def cached? filename
85
- CACHE_STORE[filename] && true
86
- end
87
-
88
- # returns true if the file exists on disk or in the cache.
89
- def file_exists? filename
90
- ( CACHE_STORE[filename] || File.exist?(filename) ) && true
91
- end
92
-
93
- # returns true if the {#allow_cache_update?} is true and the file has been update since data was last cached.
94
- def cache_needs_update? filename
95
- return true if CACHE_STORE[filename].nil? || (CACHE_STORE[filename].mtime < File.mtime(filename))
96
- false
97
- end
98
-
99
- # # # The following was discarded because benchmarks show the difference is negligible
100
- # @refresh_cache ||= (ENV['ENV'] != 'production')
101
- # # get the cache refresh directive for {#cache_needs_update}. Defaults to ENV['ENV'] != 'production'
102
- # def allow_cache_update?
103
- # @refresh_cache ||= (ENV['ENV'] != 'production')
104
- # end
105
- # # set the cache refresh directive for {#cache_needs_update}
106
- # def allow_cache_update= val
107
- # @refresh_cache = val
108
- # end
109
- # # returns true if the {#allow_cache_update?} is true and the file has been update since data was last cached.
110
- # def cache_needs_update? filename
111
- # return true if CACHE_STORE[filename].nil? || (allow_cache_update? && (CACHE_STORE[filename].mtime < File.mtime(filename)))
112
- # false
113
- # end
114
-
115
-
116
-
117
- end
118
-
119
- public
120
-
121
- extend Plezi::Cache
122
- end