Reputation: 77
I have an application that caters for web, android and ios. I have implemented the packages below
https://pub.dev/packages/image_picker/example
Tasks:
User needs to select multiple images (When debugging thru android, i sometimes receive websocket connection expection, and application exits without any error message. Bonus if youre able to provide some insights to this issue as well)
Clicks submit to upload the images (XFile) to API
class UserAttachments {
List<XFile>? attachments = [];
int userID = 0;
}
Future<String> submitImage(UserAttachments ua) async {
http.MultipartRequest request =
new http.MultipartRequest("POST", Uri.parse(kAttachmentsURI));
Map<String, String> headers = {"Content-Type": "application/json"};
ua.attachments!.forEach((element) async {
var bytes = element.readAsBytes();
request.files.add(new http.MultipartFile.fromBytes('file', await bytes));
});
request.headers.addAll(headers);
request.fields['userID'] = '23';
http.StreamedResponse responseAttachmentSTR = await request.send();
print(responseAttachmentSTR.statusCode);
return "SENT"; // + " - Respomse: " + map.toString();
}
Above code doesn't seem to work. Any solutions that cater for web/android/ios?
Upvotes: 0
Views: 3595
Reputation: 74
This is typically used when uploading files, as shown in the following examples:
import 'dart:io';
import 'package:dio/dio.dart';
import 'package:image_picker/image_picker.dart';
Future<void> uploadXFile(XFile xfile) async {
Dio dio = Dio();
String url = 'https://example.com/upload'; // Replace with your API endpoint
try {
// Convert XFile to MultipartFile
MultipartFile multipartFile = await MultipartFile.fromFile(
xfile.path,
filename: xfile.name, // Optional: Custom file name
);
// Create FormData
FormData formData = FormData.fromMap({
'file': multipartFile,
});
// Send POST request
Response response = await dio.post(
url,
data: formData,
options: Options(
headers: {
"Content-Type": "multipart/form-data", // Required header
},
),
);
print("Response: ${response.data}");
} catch (e) {
print("Upload failed: $e");
}
}
Upvotes: 0
Reputation: 1
You can't use async on forEach, because that will just return an array of promises and won't wait for them. To fix this, you can use a for loop
for asynchronous functions.
for(var i = 0; i < ua.attachments!.length; i++) {
var element = ua.attachments[i];
var bytes = element.readAsBytes();
request.files.add(new http.MultipartFile.fromBytes('file', await bytes));
}
And you can optimize this code using Future.wait
Future<String> submitImage(UserAttachments ua) async {
http.MultipartRequest request =
new http.MultipartRequest("POST", Uri.parse(kAttachmentsURI));
Map<String, String> headers = {"Content-Type": "application/json"};
var bytes = await Future.wait(ua.attachments!.map((el) => el.readAsBytes()));
request.files.addAll(bytes.map((b) => new http.MultipartFile.fromBytes('file', b)));
request.headers.addAll(headers);
request.fields['userID'] = '23';
http.StreamedResponse responseAttachmentSTR = await request.send();
print(responseAttachmentSTR.statusCode);
return "SENT";
}
Upvotes: 0