如何通过 multipart/form-data 和 Lua 发送文件?

how to send a file by multipart/form-data with Lua?

这是我的代码:

    http = require("socket.http")
    ltn12 = require("ltn12")
    lfs = require "lfs"

    respbody = {}

    local _start = [[--abcd]]..'\r\n'..[[Content-Disposition: form-data; name="file"; filename="test.png"]]..'\r\n'..[[Content-Type: image/jpeg]]..'\r\n\r\n'
    local _end = '\r\n'..[[--abcd--]]..'\r\n'

    local file= io.open('./test.png')

    local fileSize = lfs.attributes('./test.png').size

    local  body, code, headers, status = http.request {
    method = "POST",
    url = 'http://127.0.0.1:826/api/upload',
    headers = {
        ["Content-Type"] =  "multipart/form-data; boundary=abcd",
        ["Content-Length"] = fileSize + #_start + #_end
    },
    source = ltn12.source.cat(ltn12.source.string(_start),ltn12.source.file(file),ltn12.source.string(_end)),
    sink = ltn12.sink.table(respbody)
}

    print(body, code, headers, status, respbody)

我用这个演示来发送文件,但是我没有收到!这是结果:

  1. 您需要以二进制方式读取文件
  2. 有一次我放弃了这个:ltn12.source.file 并使用 ltn12.source.string ,因为文件长度不正确

像您一样尝试我的解决方案:

PS:您还需要确保在服务器端文件字段被命名为在客户端:basename ($ _ FILES ['file'] ['name' ]);

http = require("socket.http")
ltn12 = require("ltn12")
lfs = require "lfs"
http.TIMEOUT = 5


local function upload_file ( url, filename )
    local fileHandle = io.open( filename,"rb") 
    if (fileHandle) then 
        local fileContent = fileHandle:read( "*a" )
        fileHandle:close()
        local  boundary = 'abcd'
        local  header_b = 'Content-Disposition: form-data; name="file"; filename="' .. filename .. '"\r\nContent-Type: text/plain\r\n'
        local  fileContent =  '--' ..boundary .. '\r\n' ..header_b ..'\r\n'.. fileContent .. '\r\n--' .. boundary ..'--\r\n'
        local   response_body = { }
        local   _, code = http.request {
            url = url , 
            method = "POST",
            headers = {    ["Content-Length"] =  fileContent:len(), 
                           ['Content-Type'] = 'multipart/form-data; boundary=' .. boundary    
                         },
            source = ltn12.source.string(fileContent) ,         
            sink = ltn12.sink.table(response_body),
                }
     return code, table.concat(response_body)  
    else
     return false, "File Not Found"
    end
end

 local rc,content = upload_file ('http://127.0.0.1:826/api/upload', 'test.png' ) 
 print(rc,content)