module HTTP::FormData
 
  Overview
Contains utilities for parsing multipart/form-data messages, which are
commonly used for encoding HTML form data.
NOTE  To use FormData, you must explicitly import it with require "http"
Examples
Commonly, you'll want to parse a from response from a HTTP request, and process it. An example server which performs this task is shown below.
require "http"
server = HTTP::Server.new do |context|
  name = nil
  file = nil
  HTTP::FormData.parse(context.request) do |part|
    case part.name
    when "name"
      name = part.body.gets_to_end
    when "file"
      file = File.tempfile("upload") do |file|
        IO.copy(part.body, file)
      end
    end
  end
  unless name && file
    context.response.respond_with_status(:bad_request)
    next
  end
  context.response << file.path
end
server.bind_tcp 8085
server.listenTo test the server, use the curl command below.
$ curl http://localhost:8085/ -F name=foo -F file=@/path/to/test.file
/tmp/upload.Yxn7ccAnother common case is sending formdata to a server using HTTP::Client. Here is an example showing how to upload a file to the server above in crystal.
require "http"
IO.pipe do |reader, writer|
  channel = Channel(String).new(1)
  spawn do
    HTTP::FormData.build(writer) do |formdata|
      channel.send(formdata.content_type)
      formdata.field("name", "foo")
      File.open("foo.png") do |file|
        metadata = HTTP::FormData::FileMetadata.new(filename: "foo.png")
        headers = HTTP::Headers{"Content-Type" => "image/png"}
        formdata.file("file", file, metadata, headers)
      end
    end
    writer.close
  end
  headers = HTTP::Headers{"Content-Type" => channel.receive}
  response = HTTP::Client.post("http://localhost:8085/", body: reader, headers: headers)
  puts "Response code #{response.status_code}"
  puts "File path: #{response.body}"
endDefined in:
http/formdata.crhttp/formdata/builder.cr
http/formdata/parser.cr
http/formdata/part.cr
Class Method Summary
- 
        .build(response : HTTP::Server::Response, boundary = MIME::Multipart.generate_boundary, &)
        
          Builds a multipart/form-data message, yielding a FormData::Builderobject to the block which writes to response using *boundary.
- 
        .build(io, boundary = MIME::Multipart.generate_boundary, &)
        
          Builds a multipart/form-data message, yielding a FormData::Builderobject to the block which writes to io using boundary.
- 
        .parse(io, boundary, &)
        
          Parses a multipart/form-data message, yielding a FormData::Part.
- 
        .parse(request : HTTP::Request, &)
        
          Parses a multipart/form-data message, yielding a FormData::Part.
- 
        .parse_content_disposition(content_disposition) : Tuple(String, FileMetadata)
        
          Parses a Content-Dispositionheader string into a field name andFileMetadata.
Class Method Detail
Builds a multipart/form-data message, yielding a FormData::Builder
object to the block which writes to response using *boundary.
Content-Type is set on response and Builder#finish is called on the
builder when the block returns.
require "http"
io = IO::Memory.new
response = HTTP::Server::Response.new io
HTTP::FormData.build(response, "boundary") do |builder|
  builder.field("foo", "bar")
end
response.close
response.headers["Content-Type"] # => "multipart/form-data; boundary=\"boundary\""
io.to_s                          # => "HTTP/1.1 200 OK\r\nContent-Type: multipart/form-data; boundary=\"boundary\"\r\nContent-Length: 75\r\n\r\n--boundary\r\nContent-Disposition: form-data; name=\"foo\"\r\n\r\nbar\r\n--boundary--"See: FormData::Builder
Builds a multipart/form-data message, yielding a FormData::Builder
object to the block which writes to io using boundary.
Builder#finish is called on the builder when the block returns.
require "http"
io = IO::Memory.new
HTTP::FormData.build(io, "boundary") do |builder|
  builder.field("foo", "bar")
end
io.to_s # => "--boundary\r\nContent-Disposition: form-data; name=\"foo\"\r\n\r\nbar\r\n--boundary--"See: FormData::Builder
Parses a multipart/form-data message, yielding a FormData::Part.
require "http"
form_data = "--aA40\r\nContent-Disposition: form-data; name=\"field1\"\r\n\r\nfield data\r\n--aA40--"
HTTP::FormData.parse(IO::Memory.new(form_data), "aA40") do |part|
  part.name             # => "field1"
  part.body.gets_to_end # => "field data"
endSee: FormData::Parser
Parses a multipart/form-data message, yielding a FormData::Part.
require "http"
headers = HTTP::Headers{"Content-Type" => "multipart/form-data; boundary=aA40"}
body = "--aA40\r\nContent-Disposition: form-data; name=\"field1\"\r\n\r\nfield data\r\n--aA40--"
request = HTTP::Request.new("POST", "/", headers, body)
HTTP::FormData.parse(request) do |part|
  part.name             # => "field1"
  part.body.gets_to_end # => "field data"
endSee: FormData::Parser
Parses a Content-Disposition header string into a field name and
FileMetadata. Please note that the Content-Disposition header for
multipart/form-data is not compatible with the original definition in
RFC 2183, but are instead specified
in RFC 2388.