Mercurial > prosody-modules
comparison mod_http_upload/mod_http_upload.lua @ 3378:aefd64629e29
mod_http_upload: Relocate function definition to avoid traceback
author | Matthew Wild <mwild1@gmail.com> |
---|---|
date | Sun, 18 Nov 2018 12:16:47 +0000 |
parents | 683365d370d8 |
children | f1c1f6bc4892 |
comparison
equal
deleted
inserted
replaced
3377:683365d370d8 | 3378:aefd64629e29 |
---|---|
228 -- module:measure was added in 0.10 | 228 -- module:measure was added in 0.10 |
229 measure_upload = module:measure("upload", "sizes"); | 229 measure_upload = module:measure("upload", "sizes"); |
230 end | 230 end |
231 | 231 |
232 -- http service | 232 -- http service |
233 local function upload_data(event, path) | |
234 set_cross_domain_headers(event.response); | |
235 | |
236 local uploader = pending_slots[path]; | |
237 if not uploader then | |
238 module:log("warn", "Attempt to upload to unknown slot %q", path); | |
239 return; -- 404 | |
240 end | |
241 local random_dir, filename = path:match("^([^/]+)/([^/]+)$"); | |
242 if not random_dir then | |
243 module:log("warn", "Invalid file path %q", path); | |
244 return 400; | |
245 end | |
246 if #event.request.body > file_size_limit then | |
247 module:log("warn", "Uploaded file too large %d bytes", #event.request.body); | |
248 return 400; | |
249 end | |
250 pending_slots[path] = nil; | |
251 local full_filename = join_path(storage_path, random_dir, filename); | |
252 if lfs.attributes(full_filename) then | |
253 module:log("warn", "File %s exists already, not replacing it", full_filename); | |
254 return 409; | |
255 end | |
256 local fh, ferr = io.open(full_filename, "w"); | |
257 if not fh then | |
258 module:log("error", "Could not open file %s for upload: %s", full_filename, ferr); | |
259 return 500; | |
260 end | |
261 local ok, err = fh:write(event.request.body); | |
262 if not ok then | |
263 module:log("error", "Could not write to file %s for upload: %s", full_filename, err); | |
264 os.remove(full_filename); | |
265 return 500; | |
266 end | |
267 ok, err = fh:close(); | |
268 if not ok then | |
269 module:log("error", "Could not write to file %s for upload: %s", full_filename, err); | |
270 os.remove(full_filename); | |
271 return 500; | |
272 end | |
273 measure_upload(#event.request.body); | |
274 module:log("info", "File uploaded by %s to slot %s", uploader, random_dir); | |
275 return 201; | |
276 end | |
277 | |
278 -- FIXME Duplicated from net.http.server | |
279 | |
280 local codes = require "net.http.codes"; | |
281 local headerfix = setmetatable({}, { | |
282 __index = function(t, k) | |
283 local v = "\r\n"..k:gsub("_", "-"):gsub("%f[%w].", s_upper)..": "; | |
284 t[k] = v; | |
285 return v; | |
286 end | |
287 }); | |
288 | |
289 local function set_cross_domain_headers(response) | 233 local function set_cross_domain_headers(response) |
290 local headers = response.headers; | 234 local headers = response.headers; |
291 headers.access_control_allow_methods = "GET, PUT, POST, OPTIONS"; | 235 headers.access_control_allow_methods = "GET, PUT, POST, OPTIONS"; |
292 headers.access_control_allow_headers = "Content-Type"; | 236 headers.access_control_allow_headers = "Content-Type"; |
293 headers.access_control_max_age = "7200"; | 237 headers.access_control_max_age = "7200"; |
294 headers.access_control_allow_origin = response.request.headers.origin or "*"; | 238 headers.access_control_allow_origin = response.request.headers.origin or "*"; |
295 return response; | 239 return response; |
296 end | 240 end |
241 | |
242 local function upload_data(event, path) | |
243 set_cross_domain_headers(event.response); | |
244 | |
245 local uploader = pending_slots[path]; | |
246 if not uploader then | |
247 module:log("warn", "Attempt to upload to unknown slot %q", path); | |
248 return; -- 404 | |
249 end | |
250 local random_dir, filename = path:match("^([^/]+)/([^/]+)$"); | |
251 if not random_dir then | |
252 module:log("warn", "Invalid file path %q", path); | |
253 return 400; | |
254 end | |
255 if #event.request.body > file_size_limit then | |
256 module:log("warn", "Uploaded file too large %d bytes", #event.request.body); | |
257 return 400; | |
258 end | |
259 pending_slots[path] = nil; | |
260 local full_filename = join_path(storage_path, random_dir, filename); | |
261 if lfs.attributes(full_filename) then | |
262 module:log("warn", "File %s exists already, not replacing it", full_filename); | |
263 return 409; | |
264 end | |
265 local fh, ferr = io.open(full_filename, "w"); | |
266 if not fh then | |
267 module:log("error", "Could not open file %s for upload: %s", full_filename, ferr); | |
268 return 500; | |
269 end | |
270 local ok, err = fh:write(event.request.body); | |
271 if not ok then | |
272 module:log("error", "Could not write to file %s for upload: %s", full_filename, err); | |
273 os.remove(full_filename); | |
274 return 500; | |
275 end | |
276 ok, err = fh:close(); | |
277 if not ok then | |
278 module:log("error", "Could not write to file %s for upload: %s", full_filename, err); | |
279 os.remove(full_filename); | |
280 return 500; | |
281 end | |
282 measure_upload(#event.request.body); | |
283 module:log("info", "File uploaded by %s to slot %s", uploader, random_dir); | |
284 return 201; | |
285 end | |
286 | |
287 -- FIXME Duplicated from net.http.server | |
288 | |
289 local codes = require "net.http.codes"; | |
290 local headerfix = setmetatable({}, { | |
291 __index = function(t, k) | |
292 local v = "\r\n"..k:gsub("_", "-"):gsub("%f[%w].", s_upper)..": "; | |
293 t[k] = v; | |
294 return v; | |
295 end | |
296 }); | |
297 | 297 |
298 local function send_response_sans_body(response, body) | 298 local function send_response_sans_body(response, body) |
299 if response.finished then return; end | 299 if response.finished then return; end |
300 response.finished = true; | 300 response.finished = true; |
301 response.conn._http_open_response = nil; | 301 response.conn._http_open_response = nil; |