mongrel 0.3.12.3 → 0.3.12.4

Sign up to get free protection for your applications and to get access to all the features.
@@ -7,7 +7,7 @@ require 'mongrel/handlers'
7
7
  require 'mongrel/command'
8
8
  require 'mongrel/tcphack'
9
9
  require 'yaml'
10
-
10
+ require 'time'
11
11
 
12
12
  # Mongrel module containing all of the classes (include C extensions) for running
13
13
  # a Mongrel web server. It contains a minimalist HTTP server with just enough
@@ -99,7 +99,7 @@ module Mongrel
99
99
  # The original URI requested by the client. Passed to URIClassifier to build PATH_INFO and SCRIPT_NAME.
100
100
  REQUEST_URI='REQUEST_URI'.freeze
101
101
 
102
- MONGREL_VERSION="0.3.12.3".freeze
102
+ MONGREL_VERSION="0.3.12.4".freeze
103
103
 
104
104
  # The standard empty 404 response for bad requests. Use Error4040Handler for custom stuff.
105
105
  ERROR_404_RESPONSE="HTTP/1.1 404 Not Found\r\nConnection: close\r\nServer: #{MONGREL_VERSION}\r\n\r\nNOT FOUND".freeze
@@ -116,9 +116,6 @@ module Mongrel
116
116
  # this, but we'd also like to do this as well.
117
117
  MAX_HEADER=1024 * (80 + 32)
118
118
 
119
- # Format to generate a correct RFC 1123 date. rdoc for Time is wrong, there is no httpdate function.
120
- RFC_1123_DATE_FORMAT="%a, %d %B %Y %H:%M:%S GMT".freeze
121
-
122
119
  # A frozen format for this is about 15% faster
123
120
  STATUS_FORMAT = "HTTP/1.1 %d %s\r\nContent-Length: %d\r\nConnection: close\r\n".freeze
124
121
  CONTENT_TYPE = "Content-Type".freeze
@@ -268,7 +265,7 @@ module Mongrel
268
265
  @body = StringIO.new
269
266
  @status = 404
270
267
  @header = HeaderOut.new(StringIO.new)
271
- @header[Const::DATE] = HttpServer.httpdate(Time.now)
268
+ @header[Const::DATE] = Time.now.httpdate
272
269
  @body_sent = false
273
270
  @header_sent = false
274
271
  @status_sent = false
@@ -573,11 +570,6 @@ module Mongrel
573
570
  stopper.priority = 10
574
571
  end
575
572
 
576
- # Given the a time object it converts it to GMT and applies the RFC1123 format to it.
577
- def HttpServer.httpdate(date)
578
- date.gmtime.strftime(Const::RFC_1123_DATE_FORMAT)
579
- end
580
-
581
573
  end
582
574
 
583
575
 
@@ -129,7 +129,7 @@ module RequestLog
129
129
 
130
130
  def process(request,response)
131
131
  p = request.params
132
- STDERR.puts "#{p['REMOTE_ADDR']} - [#{Mongrel::HttpServer.httpdate(Time.now)}] \"#{p['REQUEST_METHOD']} #{p["REQUEST_URI"]} HTTP/1.1\""
132
+ STDERR.puts "#{p['REMOTE_ADDR']} - [#{Time.now.httpdate}] \"#{p['REQUEST_METHOD']} #{p["REQUEST_URI"]} HTTP/1.1\""
133
133
  end
134
134
  end
135
135
 
@@ -70,7 +70,15 @@ module Mongrel
70
70
  # converting all paths to an absolute expanded path, and then making sure
71
71
  # that the final expanded path includes the root path. If it doesn't
72
72
  # than it simply gives a 404.
73
+ #
74
+ # The default content type is "text/plain; charset=ISO-8859-1" but you
75
+ # can change it anything you want using the DirHandler.default_content_type
76
+ # attribute.
73
77
  class DirHandler < HttpHandler
78
+ attr_reader :default_content_type
79
+ attr_writer :default_content_type
80
+ attr_reader :path
81
+
74
82
  MIME_TYPES = {
75
83
  ".css" => "text/css",
76
84
  ".gif" => "image/gif",
@@ -86,13 +94,12 @@ module Mongrel
86
94
 
87
95
  ONLY_HEAD_GET="Only HEAD and GET allowed.".freeze
88
96
 
89
- attr_reader :path
90
-
91
97
  # You give it the path to the directory root and an (optional)
92
98
  def initialize(path, listing_allowed=true, index_html="index.html")
93
99
  @path = File.expand_path(path)
94
100
  @listing_allowed=listing_allowed
95
101
  @index_html = index_html
102
+ @default_content_type = "text/plain; charset=ISO-8859-1".freeze
96
103
  end
97
104
 
98
105
  # Checks if the given path can be served and returns the full path (or nil if not).
@@ -162,22 +169,22 @@ module Mongrel
162
169
 
163
170
  # first we setup the headers and status then we do a very fast send on the socket directly
164
171
  response.status = 200
172
+ stat = File.stat(req)
173
+ header = response.header
174
+
175
+ # Set the last modified times as well and etag for all files
176
+ header[Const::LAST_MODIFIED] = stat.mtime.httpdate
177
+ # Calculated the same as apache, not sure how well the works on win32
178
+ header[Const::ETAG] = Const::ETAG_FORMAT % [stat.mtime.to_i, stat.size, stat.ino]
165
179
 
166
180
  # set the mime type from our map based on the ending
167
- dot_at = req.rindex(".")
181
+ dot_at = req.rindex(".")
168
182
  if dot_at
169
- ext = req[dot_at .. -1]
170
- if MIME_TYPES[ext]
171
- stat = File.stat(req)
172
- response.header[Const::CONTENT_TYPE] = MIME_TYPES[ext] || "text"
173
- # TODO: Confirm this works for rfc 1123
174
- response.header[Const::LAST_MODIFIED] = HttpServer.httpdate(stat.mtime)
175
- # TODO that this is a valid way to calculate an etag
176
- response.header[Const::ETAG] = Const::ETAG_FORMAT % [stat.mtime.to_i, stat.size, stat.ino]
177
- end
183
+ header[Const::CONTENT_TYPE] = MIME_TYPES[req[dot_at .. -1]] || @default_content_type
178
184
  end
179
185
 
180
- response.send_status(File.size(req))
186
+ # send a status with out content length
187
+ response.send_status(stat.size)
181
188
  response.send_header
182
189
 
183
190
  if not header_only
@@ -187,8 +194,9 @@ module Mongrel
187
194
  else
188
195
  File.open(req, "rb") { |f| response.socket.write(f.read) }
189
196
  end
190
- rescue EOFError,Errno::ECONNRESET,Errno::EPIPE,Errno::EINVAL
197
+ rescue EOFError,Errno::ECONNRESET,Errno::EPIPE,Errno::EINVAL,Errno::EBADF
191
198
  # ignore these since it means the client closed off early
199
+ STDERR.puts "Client closed socket requesting file #{req}: #$!"
192
200
  end
193
201
  else
194
202
  response.send_body # should send nothing
metadata CHANGED
@@ -3,8 +3,8 @@ rubygems_version: 0.8.11
3
3
  specification_version: 1
4
4
  name: mongrel
5
5
  version: !ruby/object:Gem::Version
6
- version: 0.3.12.3
7
- date: 2006-04-06 00:00:00 -04:00
6
+ version: 0.3.12.4
7
+ date: 2006-04-10 00:00:00 -04:00
8
8
  summary: A small fast HTTP library and server that runs Rails, Camping, and Nitro apps.
9
9
  require_paths:
10
10
  - lib