Question: In React for web, for performance we should not use arrow functions in case `onPress`, `onClick`, etc.

Is this rule also valid for React Native?

Answer: 
I'm just going to post phqb's solution in case the pastebin link goes down:

```
final file = new File(filePath);

final streamedRequest =
    new http.StreamedRequest('POST', Configurations.getUserContentsApiUri('/upload'))
      ..headers.addAll({
        'Cache-Control': 'no-cache',
        'Authorization': 'Bearer $uploadToken',
      });
streamedRequest.contentLength = await file.length();
file.openRead().listen((chunk) {
  print(chunk.length);
  streamedRequest.sink.add(chunk);
}, onDone: () {
  streamedRequest.sink.close();
});

await streamedRequest.send();
print('after response');

```
Update:
-------

A day after posting this I realized that this is not actually measuring the *upload* progress, but only the progress of *reading* the bytes from the local JSON payload, which is almost instantaneous. If/when I figure out how to actually measure the *upload* progress, I'll update this answer.

---

Original Answer:
----------------

This works for me:

```
import 'dart:convert';
import 'package:http/http.dart' as http;

// ...

final jsonPayload = {'base64File': 'abc123', 'something': 'else'};

// We are using a StreamedRequest so we can track the upload progress
final streamedRequest = http.StreamedRequest("POST", apiUri);
streamedRequest.headers['content-type'] = 'application/json';

// Length transferred (to calculate upload progress)
var transferredLength = 0;
// Upload progress (from 0.0 to 1.0)
var uploadProgress = 0.0;
// The stringified JSON payload
var stringEncodedPayload = jsonEncode(jsonPayload);
// Total length (to calculate upload progress)
var totalLength = stringEncodedPayload.length;

// Create a stream of the payload string
Stream.value(stringEncodedPayload)
  // Transform the string-stream to a byte stream (List<int>)
  .transform(utf8.encoder)
  // Start reading the stream in chunks, submitting them to the streamedRequest for upload
  .listen((chunk) {
    transferredLength += chunk.length;
    uploadProgress = transferredLength / totalLength;
    print("Chunk: ${chunk.length}, transferred: $transferredLength, progress: $uploadProgress");
    streamedRequest.sink.add(chunk);
  }, onDone: () {
    print("Done. Total: $totalLength, transferred: $transferredLength, progress: $uploadProgress");
    streamedRequest.sink.close();
  });

final result = await client.send(streamedRequest).then(http.Response.fromStream);

print("----------->");
print(result.statusCode);
print(result.body);
print("<-----------");

```

The output:

```
flutter: Chunk: 1024, transferred: 1024, progress: 0.0008807503580198599
flutter: Chunk: 1024, transferred: 2048, progress: 0.0017615007160397197
flutter: Chunk: 1024, transferred: 3072, progress: 0.0026422510740595796
...
flutter: Chunk: 1024, transferred: 1159168, progress: 0.9970094052784814
flutter: Chunk: 1024, transferred: 1160192, progress: 0.9978901556365013
flutter: Chunk: 1024, transferred: 1161216, progress: 0.9987709059945211
flutter: Chunk: 1024, transferred: 1162240, progress: 0.9996516563525409
flutter: Chunk: 405, transferred: 1162645, progress: 1.0
flutter: Done. Total: 1162645, transferred: 1162645, progress: 1.0

```