padrino-core 0.9.29 → 0.10.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -15,7 +15,7 @@ module Padrino
15
15
  method_option :host, :type => :string, :aliases => "-h", :required => true, :default => "0.0.0.0", :desc => "Bind to HOST address"
16
16
  method_option :port, :type => :numeric, :aliases => "-p", :required => true, :default => 3000, :desc => "Use PORT"
17
17
  method_option :daemonize, :type => :boolean, :aliases => "-d", :desc => "Run daemonized in the background"
18
- method_option :pid, :type => :string, :aliases => "-p", :desc => "File to store pid"
18
+ method_option :pid, :type => :string, :aliases => "-i", :desc => "File to store pid"
19
19
  method_option :debug, :type => :boolean, :desc => "Set debugging flags"
20
20
  def start
21
21
  prepare :start
@@ -24,6 +24,11 @@ module Padrino
24
24
  Padrino::Cli::Adapter.start(options)
25
25
  end
26
26
 
27
+ desc "s", "Starts the Padrino application"
28
+ def s
29
+ invoke :start
30
+ end
31
+
27
32
  desc "stop", "Stops the Padrino application"
28
33
  method_option :pid, :type => :string, :aliases => "-p", :desc => "File to store pid", :default => 'tmp/pids/server.pid'
29
34
  def stop
@@ -80,10 +85,16 @@ module Padrino
80
85
  puts "<= You need padrino-gen! Run: gem install padrino-gen"
81
86
  end
82
87
  end
88
+
83
89
  desc "g", "Executes the Padrino generator with given options."
84
- alias :g :generate
90
+ def g(*args)
91
+ invoke(:generate, args)
92
+ end
93
+
85
94
  desc "gen", "Executes the Padrino generator with given options."
86
- alias :gen :generate
95
+ def gen(*args)
96
+ invoke(:generate, args)
97
+ end
87
98
 
88
99
  desc "version", "Show current Padrino Version"
89
100
  map "-v" => :version, "--version" => :version
@@ -138,4 +149,4 @@ module Padrino
138
149
  alias :silence :capture
139
150
  end # Base
140
151
  end # Cli
141
- end # Padrino
152
+ end # Padrino
@@ -56,4 +56,4 @@ task :gen do
56
56
  PadrinoTasks.init
57
57
  RUBY
58
58
  end
59
- end
59
+ end
@@ -49,7 +49,7 @@ module Padrino
49
49
  @_called_from = first_caller
50
50
  Padrino.set_encoding
51
51
  Padrino.set_load_paths(*load_paths) # We set the padrino load paths
52
- Padrino.logger # Initialize our logger
52
+ Padrino::Logger.setup! # Initialize our logger
53
53
  Padrino.require_dependencies("#{root}/config/database.rb", :nodeps => true) # Be sure to don't remove constants from dbs.
54
54
  Padrino::Reloader.lock! # Now we can remove constant from here to down
55
55
  Padrino.before_load.each(&:call) # Run before hooks
@@ -0,0 +1,30 @@
1
+ hu:
2
+ date:
3
+ formats:
4
+ # Use the strftime parameters for formats.
5
+ # When no format has been given, it uses default.
6
+ # You can provide other formats here if you like!
7
+ default: "%Y-%m-%d"
8
+ short: "%b. %d."
9
+ long: "%Y. %B %d."
10
+
11
+ day_names: [vasárnap, hétfő, kedd, szerda, csütörtök, péntek, szombat]
12
+ abbr_day_names: [vas, hét, kedd, sze, csüt, pén, szo]
13
+ month_names: [~, január, február, március, április, május, június, július, augusztus, szeptember, oktober, november, december]
14
+ abbr_month_names: [~, jan, febr, márc, ápr, máj, jún, júl, aug, szept, okt, nov, dec]
15
+ order: [ :year, :month, :day ]
16
+
17
+ time:
18
+ formats:
19
+ default: "%Y. %B %d. %H:%M:%S %z, %A"
20
+ short: "%B %d. %H:%M"
21
+ long: "%Y. %B %d. %H:%M"
22
+ am: "de"
23
+ pm: "du"
24
+
25
+ # Used in array.to_sentence.
26
+ support:
27
+ array:
28
+ words_connector: ", "
29
+ two_words_connector: " és "
30
+ last_word_connector: " és "
@@ -12,7 +12,8 @@ module Padrino
12
12
  # logger.warn "bar"
13
13
  #
14
14
  def self.logger
15
- Thread.current[:padrino_logger] ||= Padrino::Logger.setup!
15
+ Padrino::Logger.setup! if Thread.current[:padrino_logger].nil?
16
+ Thread.current[:padrino_logger]
16
17
  end
17
18
 
18
19
  ##
@@ -85,8 +85,8 @@ module Padrino
85
85
  def named_routes
86
86
  app_obj.routes.map { |route|
87
87
  name_array = "(#{route.named.to_s.split("_").map { |piece| %Q[:#{piece}] }.join(", ")})"
88
- request_method = route.as_options[:conditions][:request_method][0]
89
- full_path = File.join(self.uri_root, route.path)
88
+ request_method = route.conditions[:request_method][0]
89
+ full_path = File.join(uri_root, route.original_path)
90
90
  next if route.named.blank? || request_method == 'HEAD'
91
91
  OpenStruct.new(:verb => request_method, :identifier => route.named, :name => name_array, :path => full_path)
92
92
  }.compact
@@ -13,7 +13,7 @@ module Padrino
13
13
  # only when explicitly invoked.
14
14
  #
15
15
  MTIMES = {}
16
- FILES_LOADED = {}
16
+ LOADED_FILES = {}
17
17
  LOADED_CLASSES = {}
18
18
 
19
19
  class << self
@@ -52,7 +52,7 @@ module Padrino
52
52
  # We skip to next file if it is not new and not modified
53
53
  next unless new_file || mtime > previous_mtime
54
54
  # Now we can reload our file
55
- apps = get_apps(file)
55
+ apps = mounted_apps_of(file)
56
56
  if apps.present?
57
57
  apps.each { |app| app.app_obj.reload! }
58
58
  else
@@ -74,7 +74,7 @@ module Padrino
74
74
  klasses.each { |klass| remove_constant(klass) }
75
75
  LOADED_CLASSES.delete(file)
76
76
  end
77
- FILES_LOADED.each do |file, dependencies|
77
+ LOADED_FILES.each do |file, dependencies|
78
78
  dependencies.each { |dependency| $LOADED_FEATURES.delete(dependency) }
79
79
  $LOADED_FEATURES.delete(file)
80
80
  end
@@ -109,6 +109,7 @@ module Padrino
109
109
  def safe_load(file, options={})
110
110
  force, file = options[:force], figure_path(file)
111
111
 
112
+ # Check if file was changed or if force a reload
112
113
  reload = MTIMES[file] && File.mtime(file) > MTIMES[file]
113
114
  return if !force && !reload && MTIMES[file]
114
115
 
@@ -117,22 +118,47 @@ module Padrino
117
118
  klasses.each { |klass| remove_constant(klass) }
118
119
  end
119
120
 
120
- # Duplicate objects and loaded features in the file
121
+ # Remove all loaded fatures with our file
122
+ if features = LOADED_FILES[file]
123
+ features.each { |feature| $LOADED_FEATURES.delete(feature) }
124
+ end
125
+
126
+ # Duplicate objects and loaded features before load file
121
127
  klasses = ObjectSpace.classes.dup
128
+ files = $LOADED_FEATURES.dup
129
+
130
+ # Now we can reload dependencies of our file
131
+ if features = LOADED_FILES.delete(file)
132
+ features.each { |feature| safe_load(feature, :force => true) }
133
+ end
122
134
 
123
- # And finally reload the specified file
135
+ # And finally load the specified file
124
136
  begin
125
- logger.devel "Loading #{file}#{' with force' if force}" if !reload
126
- logger.debug "Reloading #{file}" if reload
137
+ logger.devel "Loading #{file}" if !reload
138
+ logger.debug "Reloading #{file}" if reload
127
139
  $LOADED_FEATURES.delete(file)
140
+ verbosity_was, $-v = $-v, nil
141
+ loaded = false
128
142
  require(file)
143
+ loaded = true
129
144
  MTIMES[file] = File.mtime(file)
130
- rescue SyntaxError => ex
131
- logger.error "Cannot require #{file} because of syntax error: #{ex.message}"
132
- end
145
+ rescue SyntaxError => e
146
+ logger.error "Cannot require #{file} because of syntax error: #{e.message}"
147
+ ensure
148
+ $-v = verbosity_was
149
+ new_constants = (ObjectSpace.classes - klasses).uniq
150
+ if loaded
151
+ # Store the file details
152
+ LOADED_CLASSES[file] = new_constants
153
+ LOADED_FILES[file] = ($LOADED_FEATURES - files - [file]).uniq
154
+ # Track only features in our Padrino.root
155
+ LOADED_FILES[file].delete_if { |feature| !in_root?(feature) }
156
+ else
157
+ logger.devel "Failed to load #{file}; removing partially defined constants"
158
+ new_constants.each { |klass| remove_constant(klass) }
159
+ end
133
160
 
134
- # Store the file details after successful loading
135
- LOADED_CLASSES[file] ||= (ObjectSpace.classes - klasses).uniq
161
+ end
136
162
  end
137
163
 
138
164
  ##
@@ -151,26 +177,36 @@ module Padrino
151
177
  # Removes the specified class and constant.
152
178
  #
153
179
  def remove_constant(const)
154
- return if Padrino::Reloader.exclude_constants.any? { |base| (const.to_s =~ %r{^#{base}}) } &&
155
- !Padrino::Reloader.include_constants.any? { |base| (const.to_s =~ %r{^#{base}}) }
180
+ return if exclude_constants.compact.uniq.any? { |c| (const.to_s =~ %r{^#{Regexp.escape(c)}}) } &&
181
+ !include_constants.compact.uniq.any? { |c| (const.to_s =~ %r{^#{Regexp.escape(c)}}) }
156
182
  begin
157
183
  parts = const.to_s.split("::")
158
184
  base = parts.size == 1 ? Object : parts[0..-2].join("::").constantize
159
185
  object = parts[-1].to_s
160
- logger.devel "Remove constant: #{const}"
161
186
  base.send(:remove_const, object)
187
+ logger.devel "Removed constant: #{const}"
162
188
  rescue NameError; end
163
189
  end
164
190
 
165
191
  private
166
192
  ##
167
- # Return the mounted_app providing the app location
193
+ # Return the mounted_apps providing the app location
194
+ # Can be an array because in one app.rb we can define multiple Padrino::Appplications
168
195
  #
169
- def get_apps(file)
196
+ def mounted_apps_of(file)
170
197
  file = figure_path(file)
171
198
  Padrino.mounted_apps.find_all { |app| File.identical?(file, app.app_file) }
172
199
  end
173
200
 
201
+ ##
202
+ # Returns true if file is in our Padrino.root
203
+ #
204
+ def in_root?(file)
205
+ # This is better but slow:
206
+ # Pathname.new(Padrino.root).find { |f| File.identical?(Padrino.root(f), figure_path(file)) }
207
+ figure_path(file) =~ %r{^#{Regexp.escape(Padrino.root)}}
208
+ end
209
+
174
210
  ##
175
211
  # Searches Ruby files in your +Padrino.load_paths+ , Padrino::Application.load_paths
176
212
  # and monitors them for any changes.
@@ -178,10 +214,10 @@ module Padrino
178
214
  def rotation
179
215
  files = Padrino.load_paths.map { |path| Dir["#{path}/**/*.rb"] }.flatten
180
216
  files = files | Padrino.mounted_apps.map { |app| app.app_file }
181
- files = files | Padrino.mounted_apps.map { |app| app.app_obj.dependencies }.flatten
217
+ files = files | Padrino.mounted_apps.map { |app| app.app_obj.dependencies }.flatten
182
218
  files.uniq.map { |file|
183
219
  file = File.expand_path(file)
184
- next if Padrino::Reloader.exclude.any? { |base| file =~ %r{^#{base}} } || !File.exist?(file)
220
+ next if Padrino::Reloader.exclude.any? { |base| file =~ %r{^#{Regexp.escape(base)}} } || !File.exist?(file)
185
221
  yield(file, File.mtime(file))
186
222
  }.compact
187
223
  end
@@ -193,23 +229,17 @@ module Padrino
193
229
  # during which no further action will be taken.
194
230
  #
195
231
  class Rack
196
- def initialize(app, cooldown = 1)
232
+ def initialize(app, cooldown=1)
197
233
  @app = app
198
234
  @cooldown = cooldown
199
235
  @last = (Time.now - cooldown)
200
236
  end
201
237
 
202
238
  def call(env)
203
- if @cooldown and Time.now > @last + @cooldown
204
- if Thread.list.size > 1
205
- Thread.exclusive { Padrino.reload! }
206
- else
207
- Padrino.reload!
208
- end
209
-
239
+ if @cooldown && Time.now > @last + @cooldown
240
+ Thread.list.size > 1 ? Thread.exclusive { Padrino.reload! } : Padrino.reload!
210
241
  @last = Time.now
211
242
  end
212
-
213
243
  @app.call(env)
214
244
  end
215
245
  end
@@ -6,7 +6,7 @@ module Padrino
6
6
  # ==== Examples
7
7
  #
8
8
  # Padrino.run! # with these defaults => host: "localhost", port: "3000", adapter: the first found
9
- # Padrino.run!("localhost", "4000", "mongrel") # use => host: "localhost", port: "3000", adapter: "mongrel"
9
+ # Padrino.run!("localhost", "4000", "mongrel") # use => host: "0.0.0.0", port: "3000", adapter: "mongrel"
10
10
  #
11
11
  def self.run!(options={})
12
12
  Padrino.load!
@@ -23,8 +23,8 @@ module Padrino
23
23
  def self.start(app, opts={})
24
24
  options = {}.merge(opts) # We use a standard hash instead of Thor::CoreExt::HashWithIndifferentAccess
25
25
  options.symbolize_keys!
26
- options[:Host] = options.delete(:host)
27
- options[:Port] = options.delete(:port)
26
+ options[:Host] = options.delete(:host) || '0.0.0.0'
27
+ options[:Port] = options.delete(:port) || 3000
28
28
  options[:AccessLog] = []
29
29
  if options[:daemonize]
30
30
  options[:pid] = options[:pid].blank? ? File.expand_path('tmp/pids/server.pid') : opts[:pid]
@@ -1,26 +1,89 @@
1
1
  ##
2
2
  # This file loads certain extensions required by Padrino from ActiveSupport.
3
3
  #
4
- require 'active_support/core_ext/string/conversions' unless String.method_defined?(:to_date)
5
- require 'active_support/core_ext/kernel' unless Kernel.method_defined?(:silence_warnings)
6
- require 'active_support/core_ext/module' unless Module.method_defined?(:alias_method_chain)
7
- require 'active_support/core_ext/class/attribute_accessors' unless Class.method_defined?(:cattr_reader)
8
- require 'active_support/core_ext/hash/keys' unless Hash.method_defined?(:symbolize_keys!)
9
- require 'active_support/core_ext/hash/deep_merge' unless Hash.method_defined?(:deep_merge)
10
- require 'active_support/core_ext/hash/reverse_merge' unless Hash.method_defined?(:reverse_merge)
11
- require 'active_support/core_ext/hash/slice' unless Hash.method_defined?(:slice)
12
- require 'active_support/core_ext/object/blank' unless Object.method_defined?(:present?)
13
- require 'active_support/core_ext/array' unless Array.method_defined?(:from)
14
- require 'active_support/ordered_hash' unless defined?(ActiveSupport::OrderedHash)
15
- require 'active_support/inflector' unless String.method_defined?(:humanize)
16
- require 'active_support/core_ext/float/rounding' unless Float.method_defined?(:round)
17
- require 'active_support/option_merger' unless defined?(ActiveSupport::OptionMerger)
18
- require 'active_support/core_ext/object/with_options' unless Object.method_defined?(:with_options)
4
+ require 'active_support/core_ext/kernel' # silence_warnings
5
+ require 'active_support/core_ext/module/aliasing' # alias_method_chain
6
+ require 'active_support/core_ext/class/attribute_accessors' # cattr_reader
7
+ require 'active_support/core_ext/hash/keys' # symbolize_keys
8
+ require 'active_support/core_ext/hash/reverse_merge' # reverse_merge
9
+ require 'active_support/core_ext/hash/slice' # slice
10
+ require 'active_support/core_ext/object/blank' # present?
11
+ require 'active_support/core_ext/array/extract_options' # extract_options
12
+ require 'active_support/inflector/methods' # constantize
13
+ require 'active_support/inflector/inflections' # pluralize
14
+ require 'active_support/inflections' # load default inflections
19
15
 
20
16
  ##
21
- # Used to know if this file has already been required
17
+ # This is a small version of active_support/core_ext/string/inflections.rb
18
+ # to prevent to load a lot of dependencies including I18n gem
19
+ #
20
+ # Issue: https://github.com/rails/rails/issues/1526
22
21
  #
23
- module SupportLite; end
22
+ class String
23
+ # Returns the plural form of the word in the string.
24
+ #
25
+ # "post".pluralize # => "posts"
26
+ # "octopus".pluralize # => "octopi"
27
+ # "sheep".pluralize # => "sheep"
28
+ # "words".pluralize # => "words"
29
+ # "the blue mailman".pluralize # => "the blue mailmen"
30
+ # "CamelOctopus".pluralize # => "CamelOctopi"
31
+ def pluralize
32
+ ActiveSupport::Inflector.pluralize(self)
33
+ end
34
+
35
+ # +constantize+ tries to find a declared constant with the name specified
36
+ # in the string. It raises a NameError when the name is not in CamelCase
37
+ # or is not initialized.
38
+ #
39
+ # Examples
40
+ # "Module".constantize # => Module
41
+ # "Class".constantize # => Class
42
+ def constantize
43
+ ActiveSupport::Inflector.constantize(self)
44
+ end
45
+
46
+ # By default, +camelize+ converts strings to UpperCamelCase. If the argument to camelize
47
+ # is set to <tt>:lower</tt> then camelize produces lowerCamelCase.
48
+ #
49
+ # +camelize+ will also convert '/' to '::' which is useful for converting paths to namespaces.
50
+ #
51
+ # "active_record".camelize # => "ActiveRecord"
52
+ # "active_record".camelize(:lower) # => "activeRecord"
53
+ # "active_record/errors".camelize # => "ActiveRecord::Errors"
54
+ # "active_record/errors".camelize(:lower) # => "activeRecord::Errors"
55
+ def camelize(first_letter = :upper)
56
+ case first_letter
57
+ when :upper then ActiveSupport::Inflector.camelize(self, true)
58
+ when :lower then ActiveSupport::Inflector.camelize(self, false)
59
+ end
60
+ end
61
+ alias_method :camelcase, :camelize
62
+
63
+ # The reverse of +camelize+. Makes an underscored, lowercase form from the expression in the string.
64
+ #
65
+ # +underscore+ will also change '::' to '/' to convert namespaces to paths.
66
+ #
67
+ # "ActiveRecord".underscore # => "active_record"
68
+ # "ActiveRecord::Errors".underscore # => active_record/errors
69
+ def underscore
70
+ ActiveSupport::Inflector.underscore(self)
71
+ end
72
+
73
+ # Create a class name from a plural table name like Rails does for table names to models.
74
+ # Note that this returns a string and not a class. (To convert to an actual class
75
+ # follow +classify+ with +constantize+.)
76
+ #
77
+ # "egg_and_hams".classify # => "EggAndHam"
78
+ # "posts".classify # => "Post"
79
+ #
80
+ # Singular names are not handled correctly.
81
+ #
82
+ # "business".classify # => "Busines"
83
+ def classify
84
+ ActiveSupport::Inflector.classify(self)
85
+ end
86
+ end
24
87
 
25
88
  module ObjectSpace
26
89
  class << self
@@ -64,4 +127,9 @@ YAML::ENGINE.yamler = "syck" if defined?(YAML::ENGINE)
64
127
  ##
65
128
  # Loads our locale configuration files
66
129
  #
67
- I18n.load_path += Dir["#{File.dirname(__FILE__)}/locale/*.yml"] if defined?(I18n)
130
+ I18n.load_path += Dir["#{File.dirname(__FILE__)}/locale/*.yml"] if defined?(I18n)
131
+
132
+ ##
133
+ # Used to know if this file has already been required
134
+ #
135
+ module SupportLite; end
@@ -5,7 +5,7 @@
5
5
  # without include full padrino core.
6
6
  #
7
7
  module Padrino
8
- VERSION = '0.9.29' unless defined?(Padrino::VERSION)
8
+ VERSION = '0.10.0' unless defined?(Padrino::VERSION)
9
9
  ##
10
10
  # Return the current Padrino version
11
11
  #
@@ -1,4 +1,6 @@
1
- # -*- encoding: utf-8 -*-
1
+ #!/usr/bin/env gem build
2
+ # encoding: utf-8
3
+
2
4
  require File.expand_path("../lib/padrino-core/version.rb", __FILE__)
3
5
 
4
6
  Gem::Specification.new do |s|
@@ -20,14 +22,17 @@ Gem::Specification.new do |s|
20
22
  s.require_paths = ["lib"]
21
23
  s.rdoc_options = ["--charset=UTF-8"]
22
24
 
23
-
24
25
  # TODO remove after a couple versions
25
- s.post_install_message = "\e[32m When upgrading, please 'enable :sessions' for each application"
26
- s.post_install_message << " as shown here:\e[0m http://bit.ly/kODKMx"
26
+ s.post_install_message = "\e[32m" + ("*" * 20)
27
+ s.post_install_message << "\n UPGRADE NOTES\n\n\e[31m When upgrading, please 'enable :sessions' for each application"
28
+ s.post_install_message << " as shown here:\e[0m http://bit.ly/kODKMx\n"
29
+ s.post_install_message << "\e[31m When upgrading, please 'register Padrino::Rendering' for each application"
30
+ s.post_install_message << " as shown here:\e[0m https://gist.github.com/1d36a35794dbbd664ea4"
31
+ s.post_install_message << "\n\e[32m" + ("*" * 20) + "\n\e[0m"
27
32
 
28
33
  s.add_dependency("tilt", "~> 1.3.0")
29
34
  s.add_dependency("sinatra", "~> 1.2.6")
30
- s.add_dependency("http_router", "~> 0.7.8")
31
- s.add_dependency("thor", ">=0.14.3")
32
- s.add_dependency("activesupport", ">= 3.0.0")
35
+ s.add_dependency("http_router", "~> 0.8.10")
36
+ s.add_dependency("thor", "~> 0.14.3")
37
+ s.add_dependency("activesupport", "~> 3.0.0")
33
38
  end