Class: Utopia::Middleware::Static::LocalFile
- Defined in:
- lib/utopia/middleware/static.rb
Instance Attribute Summary collapse
-
#etag ⇒ Object
readonly
Returns the value of attribute etag.
-
#path ⇒ Object
readonly
Returns the value of attribute path.
-
#range ⇒ Object
readonly
Returns the value of attribute range.
-
#root ⇒ Object
readonly
Returns the value of attribute root.
Instance Method Summary collapse
- #each ⇒ Object
- #full_path ⇒ Object
-
#initialize(root, path) ⇒ LocalFile
constructor
A new instance of LocalFile.
- #modified?(env) ⇒ Boolean
- #mtime_date ⇒ Object
- #serve(env, response_headers) ⇒ Object
- #size ⇒ Object
-
#to_path ⇒ Object
Fit in with Rack::Sendfile.
Constructor Details
Instance Attribute Details
#etag ⇒ Object (readonly)
Returns the value of attribute etag.
79 80 81 |
# File 'lib/utopia/middleware/static.rb', line 79 def etag @etag end |
#path ⇒ Object (readonly)
Returns the value of attribute path.
78 79 80 |
# File 'lib/utopia/middleware/static.rb', line 78 def path @path end |
#range ⇒ Object (readonly)
Returns the value of attribute range.
80 81 82 |
# File 'lib/utopia/middleware/static.rb', line 80 def range @range end |
Instance Method Details
#each ⇒ Object
99 100 101 102 103 104 105 106 107 108 109 110 111 112 |
# File 'lib/utopia/middleware/static.rb', line 99 def each File.open(full_path, "rb") do |file| file.seek(@range.begin) remaining = @range.end - @range.begin+1 while remaining > 0 break unless part = file.read([8192, remaining].min) remaining -= part.length yield part end end end |
#full_path ⇒ Object
87 88 89 |
# File 'lib/utopia/middleware/static.rb', line 87 def full_path File.join(@root, @path.components) end |
#modified?(env) ⇒ Boolean
114 115 116 117 118 119 120 121 122 123 124 125 |
# File 'lib/utopia/middleware/static.rb', line 114 def modified?(env) if modified_since = env['HTTP_IF_MODIFIED_SINCE'] return false if File.mtime(full_path) <= Time.parse(modified_since) end if = env['HTTP_IF_NONE_MATCH'] = .split(/\s*,\s*/) return false if .include?(etag) || .include?('*') end return true end |
#mtime_date ⇒ Object
91 92 93 |
# File 'lib/utopia/middleware/static.rb', line 91 def mtime_date File.mtime(full_path).httpdate end |
#serve(env, response_headers) ⇒ Object
127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 |
# File 'lib/utopia/middleware/static.rb', line 127 def serve(env, response_headers) ranges = Rack::Utils.byte_ranges(env, size) response = [200, response_headers, self] # LOG.info("Requesting ranges: #{ranges.inspect} (#{size})") if ranges.nil? || ranges.length > 1 # No ranges, or multiple ranges (which we don't support): # TODO: Support multiple byte-ranges response[0] = 200 response[1]["Content-Length"] = size.to_s @range = 0..size-1 elsif ranges.empty? # Unsatisfiable. Return error, and file size: response = Middleware::failure(416, "Invalid range specified.") response[1]["Content-Range"] = "bytes */#{size}" return response else # Partial content: @range = ranges[0] response[0] = 206 response[1]["Content-Range"] = "bytes #{@range.begin}-#{@range.end}/#{size}" response[1]["Content-Length"] = (@range.end - @range.begin+1).to_s size = @range.end - @range.begin + 1 end # LOG.info("Response for #{self.full_path}: #{response.inspect}") LOG.info "Serving file #{full_path.inspect}, range #{@range.inspect}" return response end |
#size ⇒ Object
95 96 97 |
# File 'lib/utopia/middleware/static.rb', line 95 def size File.size(full_path) end |
#to_path ⇒ Object
Fit in with Rack::Sendfile
83 84 85 |
# File 'lib/utopia/middleware/static.rb', line 83 def to_path full_path end |