Doing an HTTP Post with headers and a body

蓝咒 提交于 2019-12-09 17:30:16

问题


Right, so I've been working on something which requires basic authentication through headers, and passing some variables via HTTP Post. This is a terminal app.

This is what my code looks like:

import 'package:http/http.dart' as http;
import 'dart:io';
void main() {
  var url = "http://httpbin.org/post";
  var client = new http.Client();
  var request = new http.Request('POST', Uri.parse(url));
  var body = {'content':'this is a test', 'email':'john@doe.com', 'number':'441276300056'};
  request.headers[HttpHeaders.CONTENT_TYPE] = 'application/json; charset=utf-8';
  request.headers[HttpHeaders.AUTHORIZATION] = 'Basic 021215421fbe4b0d27f:e74b71bbce';
  request.body = body;
  var future = client.send(request).then((response) => response.stream.bytesToString().then((value) => print(value.toString()))).catchError((error) => print(error.toString()));
}

I'm using httpbin as an echo server, so it tells me what I'm passing in. My code works correctly if I don't pass a body, or if I pass a string as the body.

Obviously that's because the body attribute in http.Request only accepts strings, and I'm trying to pass a map to it.

I could convert that to a string, and it would probably work, but I still think my code could be improved. Not from a syntax point of view, or from how it's handling the future, but I'm not certain using http.dart is the right thing to do.

Could someone point me in the right direction?

Thanks in advance.


回答1:


JSON is a String. You need to encode your map to JSON and pass it as a String.

You can use bodyFields instead of body to pass a Map.
This way your content-type is fixed to "application/x-www-form-urlencoded".

The DartDoc for post says:

/// If [body] is a Map, it's encoded as form fields using [encoding]. The
/// content-type of the request will be set to
/// `"application/x-www-form-urlencoded"`; this cannot be overridden.

I was able to send JSON data this way a while ago

return new http.Client()
  .post(url, headers: {'Content-type': 'application/json'},
      body: JSON.encoder.convert({"distinct": "users","key": "account","query": {"active":true}}))
      .then((http.Response r) => r.body)
      .whenComplete(() => print('completed'));

EDIT

import 'package:http/http.dart' as http;
import 'dart:io';
void main() {
  var url = "http://httpbin.org/post";
  var client = new http.Client();
  var request = new http.Request('POST', Uri.parse(url));
  var body = {'content':'this is a test', 'email':'john@doe.com', 'number':'441276300056'};
//  request.headers[HttpHeaders.CONTENT_TYPE] = 'application/json; charset=utf-8';
  request.headers[HttpHeaders.AUTHORIZATION] = 'Basic 021215421fbe4b0d27f:e74b71bbce';
  request.bodyFields = body;
  var future = client.send(request).then((response)
      => response.stream.bytesToString().then((value)
          => print(value.toString()))).catchError((error) => print(error.toString()));
}

produces

{
  "args": {}, 
  "data": "", 
  "files": {}, 
  "form": {
    "content": "this is a test", 
    "email": "john@doe.com", 
    "number": "441276300056"
  }, 
  "headers": {
    "Accept-Encoding": "gzip", 
    "Authorization": "Basic 021215421fbe4b0d27f:e74b71bbce", 
    "Connection": "close", 
    "Content-Length": "63", 
    "Content-Type": "application/x-www-form-urlencoded; charset=utf-8", 
    "Host": "httpbin.org", 
    "User-Agent": "Dart/1.5 (dart:io)", 
    "X-Request-Id": "b108713b-d746-49de-b9c2-61823a93f629"
  }, 
  "json": null, 
  "origin": "91.118.62.43", 
  "url": "http://httpbin.org/post"
}


来源:https://stackoverflow.com/questions/24183716/doing-an-http-post-with-headers-and-a-body

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!