Module: Padrino::Reloader

Extended by:
Reloader
Included in:
Reloader
Defined in:
padrino-core/lib/padrino-core/reloader.rb,
padrino-core/lib/padrino-core/reloader/rack.rb,
padrino-core/lib/padrino-core/reloader/storage.rb

Overview

High performance source code reloader middleware

Defined Under Namespace

Modules: Storage Classes: Rack

Constant Summary collapse

MTIMES =

The modification times for every file in a project.

{}

Instance Method Summary collapse

Instance Method Details

#changed?Boolean

Returns true if any file changes are detected.

Returns:

  • (Boolean)


66
67
68
69
70
# File 'padrino-core/lib/padrino-core/reloader.rb', line 66

def changed?
  rotation do |file|
    break true if file_changed?(file)
  end
end

#clear!Object

Remove files and classes loaded with stat



58
59
60
61
# File 'padrino-core/lib/padrino-core/reloader.rb', line 58

def clear!
  MTIMES.clear
  Storage.clear!
end

#excludeObject

Specified folders can be excluded from the code reload detection process. Default excluded directories at Padrino.root are: test, spec, features, tmp, config, db and public



26
27
28
# File 'padrino-core/lib/padrino-core/reloader.rb', line 26

def exclude
  @_exclude ||= Set.new %w(test spec tmp features config public db).map{ |path| Padrino.root(path) }
end

#exclude_constantsObject

Specified constants can be excluded from the code unloading process.



33
34
35
# File 'padrino-core/lib/padrino-core/reloader.rb', line 33

def exclude_constants
  @_exclude_constants ||= Set.new
end

#include_constantsObject

Specified constants can be configured to be reloaded on every request. Default included constants are: [none]



41
42
43
# File 'padrino-core/lib/padrino-core/reloader.rb', line 41

def include_constants
  @_include_constants ||= Set.new
end

#lock!Object

We lock dependencies sets to prevent reloading of protected constants



75
76
77
78
79
80
81
82
# File 'padrino-core/lib/padrino-core/reloader.rb', line 75

def lock!
  klasses = Storage.send(:object_classes) do |klass|
    original_klass_name = constant_name(klass)
    original_klass_name.split('::').first if original_klass_name
  end
  klasses |= Padrino.mounted_apps.map(&:app_class)
  exclude_constants.merge(klasses)
end

#reload!Object

Reload apps and files with changes detected.



48
49
50
51
52
53
# File 'padrino-core/lib/padrino-core/reloader.rb', line 48

def reload!
  rotation do |file|
    next unless file_changed?(file)
    reload_special(file) || reload_regular(file)
  end
end

#remove_constant(const) ⇒ Object

Removes the specified class and constant.



112
113
114
115
116
117
118
119
# File 'padrino-core/lib/padrino-core/reloader.rb', line 112

def remove_constant(const)
  return if constant_excluded?(const)
  base, _, object = const.to_s.rpartition('::')
  base = base.empty? ? Object : base.constantize
  base.send :remove_const, object
  logger.devel "Removed constant #{const} from #{base}"
rescue NameError
end

#remove_feature(file) ⇒ Object

Remove a feature from $LOADED_FEATURES so it can be required again.



124
125
126
# File 'padrino-core/lib/padrino-core/reloader.rb', line 124

def remove_feature(file)
  $LOADED_FEATURES.delete(file) unless feature_excluded?(file)
end

#safe_load(file, options = {}) ⇒ Object

A safe Kernel::require which issues the necessary hooks depending on results



87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
# File 'padrino-core/lib/padrino-core/reloader.rb', line 87

def safe_load(file, options={})
  began_at = Time.now
  file     = figure_path(file)
  return unless options[:force] || file_changed?(file)
  return require(file) if feature_excluded?(file)

  Storage.prepare(file) # might call #safe_load recursively
  logger.devel(file_new?(file) ? :loading : :reload, began_at, file)
  begin
    with_silence{ require(file) }
    Storage.commit(file)
    update_modification_time(file)
  rescue Exception => exception
    unless options[:cyclic]
      logger.exception exception, :short
      logger.error "Failed to load #{file}; removing partially defined constants"
    end
    Storage.rollback(file)
    raise
  end
end

#special_filesObject

Returns the list of special tracked files for Reloader.



131
132
133
# File 'padrino-core/lib/padrino-core/reloader.rb', line 131

def special_files
  @special_files ||= Set.new
end

#special_files=(files) ⇒ Object

Sets the list of special tracked files for Reloader.



138
139
140
# File 'padrino-core/lib/padrino-core/reloader.rb', line 138

def special_files=(files)
  @special_files = Set.new(files)
end