How to upload images and file to a server in Flutter?

171,939

Solution 1

Your workaround should work; many servers will accept application/x-www-form-urlencoded as an alternative (although data is encoded moderately inefficiently).

However, it is possible to use dart:http to do this. Instead of using http.post, you'll want to use a http.MultipartFile object.

From the dart documentation:

var request = new http.MultipartRequest("POST", url);
request.fields['user'] = '[email protected]';
request.files.add(http.MultipartFile.fromPath(
    'package',
    'build/package.tar.gz',
    contentType: new MediaType('application', 'x-tar'),
));
request.send().then((response) {
  if (response.statusCode == 200) print("Uploaded!");
});

Solution 2

I'd like to recommend dio package to you , dio is a powerful Http client for Dart/Flutter, which supports Interceptors, FormData, Request Cancellation, File Downloading, Timeout etc.

dio is very easy to use, in this case you can:

Sending FormData:

FormData formData = new FormData.from({
   "name": "wendux",
   "file1": new UploadFileInfo(new File("./upload.jpg"), "upload1.jpg")
});
response = await dio.post("/info", data: formData)

More details please refer to dio

Solution 3

This can be achieved using the MultipartRequest class (https://pub.dev/documentation/http/latest/http/MultipartRequest-class.html)

Change the media type and uri as needed.

uploadFile() async {
    var postUri = Uri.parse("<APIUrl>");
    var request = new http.MultipartRequest("POST", postUri);
    request.fields['user'] = 'blah';
    request.files.add(new http.MultipartFile.fromBytes('file', await File.fromUri("<path/to/file>").readAsBytes(), contentType: new MediaType('image', 'jpeg')))

    request.send().then((response) {
      if (response.statusCode == 200) print("Uploaded!");
    });
  }

Solution 4

I found a working example without using any external plugin , this only uses

import 'package:http/http.dart' as http;
import 'dart:io';
import 'package:path/path.dart';
import 'package:async/async.dart';
import 'dart:convert';

Code

var stream =
        new http.ByteStream(DelegatingStream.typed(imageFile.openRead()));
    // get file length
    var length = await imageFile.length(); //imageFile is your image file
    Map<String, String> headers = {
      "Accept": "application/json",
      "Authorization": "Bearer " + token
    }; // ignore this headers if there is no authentication

    // string to uri
    var uri = Uri.parse(Constants.BASE_URL + "api endpoint here");

    // create multipart request
    var request = new http.MultipartRequest("POST", uri);

  // multipart that takes file
    var multipartFileSign = new http.MultipartFile('profile_pic', stream, length,
        filename: basename(imageFile.path));

    // add file to multipart
    request.files.add(multipartFileSign);

    //add headers
    request.headers.addAll(headers);

    //adding params
    request.fields['loginId'] = '12';
    request.fields['firstName'] = 'abc';
   // request.fields['lastName'] = 'efg';

    // send
    var response = await request.send();

    print(response.statusCode);

    // listen for response
    response.stream.transform(utf8.decoder).listen((value) {
      print(value);

    });

Solution 5

How to upload image file using restAPI in flutter/dart.

This work for me.

var postUri = Uri.parse("apiUrl");

http.MultipartRequest request = new http.MultipartRequest("POST", postUri);

http.MultipartFile multipartFile = await http.MultipartFile.fromPath(
    'file', filePath); 

request.files.add(multipartFile);

http.StreamedResponse response = await request.send();


print(response.statusCode);
Share:
171,939

Related videos on Youtube

Mneckoee
Author by

Mneckoee

Updated on January 10, 2022

Comments

  • Mneckoee
    Mneckoee over 2 years

    I use a web service for image processing , it works well in Postman:

    postman screenshot

    Now I want to make http request in flutter with Dart:

    import 'package:http/http.dart' as http;
    
    static ocr(File image) async {
        var url = '${API_URL}ocr';
        var bytes = image.readAsBytesSync();
    
        var response = await http.post(
            url,
            headers:{ "Content-Type":"multipart/form-data" } ,
            body: { "lang":"fas" , "image":bytes},
            encoding: Encoding.getByName("utf-8")
        );
    
        return response.body;
    
      }
    

    but I don't know how to upload the image file, in above code I get exception: Bad state: Cannot set the body fields of a Request with content-type "multipart/form-data".
    How should I write the body of request?

    • Mneckoee
      Mneckoee about 6 years
      for a workaround: I ask my server guys to change server api to accept base64 encoded image instead. so I put the base64 encoded image as a string in body with content type of header equal to application/x-www-form-urlencoded and it works.
    • Aravind Vemula
      Aravind Vemula almost 6 years
      Similar question answered here stackoverflow.com/questions/44841729/…
    • Mneckoee
      Mneckoee almost 6 years
      @AravindVemula I don't want to send base64 encoded bytes
    • Mneckoee
      Mneckoee almost 6 years
      this answer helped me stackoverflow.com/a/49645074/6133481
    • Kind Contributor
      Kind Contributor almost 4 years
      Have you tried with content-type "application/octet-stream". I always avoid "multipart/form-data" wherever I can. The best designed file-upload APIs accept "application/octet-stream" in the POST body, and any parameters are in the URI.
  • Ignacio Ara
    Ignacio Ara about 6 years
    Please write here the solution instead of including a link that could be broken in the future. Thanks!
  • Kiana
    Kiana about 6 years
    The docs are wrong per this github issues
  • rmtmckenzie
    rmtmckenzie about 6 years
    Thanks @Kiana, I didn't notice that. It's fixed now. Although the master of dart.http is much different than the currently released 0.11.3+16, so I would expect this to eventually become incorrect.
  • Shashank Pujari
    Shashank Pujari about 5 years
    Thx bro your code helped me to solve sending fields (string) in MultipartFile in Flutter
  • Admin
    Admin about 5 years
    can to change image file name using DIO?
  • Pritish
    Pritish almost 5 years
    @rmtmckenzie what is the 'package' and 'build/package.tar.gz' parameters in MultipartFile.fromPath
  • rmtmckenzie
    rmtmckenzie almost 5 years
    Package is the name of the field (if it was a form on the web it'd be the name of the input), and build/package.tar.gz is the path. That example was really more specific to a server though; you could use one of MultipartFile's other constructors like .fromBytes or the one that uses a stream instead.
  • rashmi chachan
    rashmi chachan almost 5 years
    Worked like a charm. :) tnq so much :) just to add:- please add " import 'package:http_parser/http_parser.dart'; " for contentType
  • yubaraj poudel
    yubaraj poudel over 4 years
    works for me, just changed File.fromUri("<path/to/File">) to File.fromUri(Uri.parse("<path/to/file>"))
  • dipgirl
    dipgirl about 4 years
    @wendu Can I know where UploadFileInfo() function come from?
  • dipgirl
    dipgirl about 4 years
    Hi, if I want to upload video, I can use this method also?
  • rmtmckenzie
    rmtmckenzie about 4 years
    @dipgirl As long as your server accepts and knows what the data you're sending it (and you should set the MediaType to the right thing), you can send anything. The example in the code isn't even sending an image but rather a tar file
  • Prasath
    Prasath about 4 years
    what do you mean by basename
  • Quick learner
    Quick learner about 4 years
    import this package import 'package:path/path.dart';
  • ugurerkan
    ugurerkan almost 4 years
    @dipgirl The UploadFileInfo is deprecated, right now there is MultiPartFromFile class for to do this. Here is a sample github.com/flutterchina/dio#sending-formdata
  • Kanwarpreet Singh
    Kanwarpreet Singh almost 4 years
    can you add this method definition lookupMimeType()..
  • Bagus Aji Santoso
    Bagus Aji Santoso over 3 years
    Why the response doesn't have response.body
  • Logemann
    Logemann over 3 years
    To increase answer quality in the future, think about adding some text for some context and your thoughts about the code provided.
  • poring91
    poring91 over 3 years
    @BagusAjiSantoso request.send doesn't return Future<Response>, It returns Future<StreamedResponse>. See this question stackoverflow.com/questions/55520829/…
  • zia sultan
    zia sultan about 3 years
    I tried this but not working file is not receiving in server final request = http.MultipartRequest( 'POST', Uri.parse('yurr.app/api/register-celebrity')); request.fields['title'] = title.text; request.fields['sub_title'] = subTitle.text; request.files .add(await http.MultipartFile.fromPath('profile_photo', photo.path)); request.files .add(await http.MultipartFile.fromPath('profile_video', video.path)); var response = await request.send(); var responseString = await response.stream.bytesToString(); print(responseString);
  • SilenceCodder
    SilenceCodder almost 3 years
    which plugin are you using?
  • ABM
    ABM almost 3 years
    I get error at "MediaType". Am I missing any imports?
  • perymerdeka
    perymerdeka almost 3 years
    how to PUT data?
  • Charitha Goonewardena
    Charitha Goonewardena almost 3 years
    What did you mean by PUT data? if you mean data by just a field then imageUploadRequest.fields['fieldName'] = 'your value';
  • Oliver Dixon
    Oliver Dixon almost 3 years
    Where are you important "MediaType" from?
  • pmadhu
    pmadhu over 2 years
    Improve your answer with supporting information, like explaining the code for better understanding.
  • Tuhin
    Tuhin over 2 years
    I'm struggling to put my image file path. Image I'm getting form imagePicker File.fromUri("<path/to/file>" [ stackoverflow.com/questions/69204607/… ]
  • vietstone
    vietstone over 2 years
    @OliverDixon import package http_parser
  • AWESOME WORLD
    AWESOME WORLD over 2 years
    import 'package:http_parser/http_parser.dart'; this should solve your issue.
  • Admin
    Admin over 2 years
    Your answer could be improved with additional supporting information. Please edit to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers in the help center.
  • User
    User about 2 years
    How can I convert back to image