Image.network throw error even after defining errorBuilder in Flutter
Yes, you are correct with the implementation. So the thing is, NetworkImage tries to load the image and fails to load it. And hence, the _loadAsync()
method rethrows
the exception. Now, as you have provided errorBuilder
, the framework uses that widget to show when an exception occurs. Hence, you are getting an exception that is rethrown from the framework but is handled as you have provided errorBuilder
. Now, if you remove the errorBuilder
you will get the exception logged in debug console, as well as the user, will be able to see that red exception screen if in debug mode and grey screen in release mode.
So, you are correct with the implementation as well as your doubt, but you missed the exact explanation of errorBuilder
.
I hope this made your doubt clear!
Gtslix
Updated on January 03, 2023Comments
-
Gtslix over 1 year
I am facing some issues with loading images from URLs in Flutter. Here is my code:
@override Widget build(BuildContext context) { return ClipRRect( borderRadius: BorderRadius.circular(8.0), child: Center( child: Image.network( 'https://www.example.com/no-image.jpg', // this image doesn't exist fit: BoxFit.cover, errorBuilder: (context, error, stackTrace) { return Container( color: Colors.amber, alignment: Alignment.center, child: const Text( 'Whoops!', style: TextStyle(fontSize: 30), ), ); }, ), ), ); }
I am using
Image.network
to receive images from a given URL but as the URL does not exist the widget throws a 404 exception, even though theerrorBuilder
parameter is defined. It is not only for 404 exceptions but any network connection errors.Source of exception (flutter file:
.../_network_image_io.dart
):Future<ui.Codec> _loadAsync( NetworkImage key, StreamController<ImageChunkEvent> chunkEvents, image_provider.DecoderCallback decode, ) async { try { assert(key == this); final Uri resolved = Uri.base.resolve(key.url); final HttpClientRequest request = await _httpClient.getUrl(resolved); headers?.forEach((String name, String value) { request.headers.add(name, value); }); final HttpClientResponse response = await request.close(); if (response.statusCode != HttpStatus.ok) { // The network may be only temporarily unavailable, or the file will be // added on the server later. Avoid having future calls to resolve // fail to check the network again. await response.drain<List<int>>(<int>[]); throw image_provider.NetworkImageLoadException( statusCode: response.statusCode, uri: resolved); } final Uint8List bytes = await consolidateHttpClientResponseBytes( response, onBytesReceived: (int cumulative, int? total) { chunkEvents.add(ImageChunkEvent( cumulativeBytesLoaded: cumulative, expectedTotalBytes: total, )); }, ); if (bytes.lengthInBytes == 0) throw Exception('NetworkImage is an empty file: $resolved'); return decode(bytes); } catch (e) { // Depending on where the exception was thrown, the image cache may not // have had a chance to track the key in the cache at all. // Schedule a microtask to give the cache a chance to add the key. scheduleMicrotask(() { PaintingBinding.instance!.imageCache!.evict(key); }); print(e); rethrow; // <<<<<<<< Exception throw here: NetworkImageLoadException (HTTP request failed, statusCode: 404, https://www.example.com/no-image.jpg) } finally { chunkEvents.close(); } }
I am wondering if it is a bug or I've made a mistake.
-
Dipak Prajapati about 2 yearsits not throwing error to me.
-
Gtslix about 2 yearsWell, that is wired @DipakPrajapati
-
ibhavikmakwana about 2 yearsThe image URL works fine for me, can you please share the exception along with the question?
-
Gtslix about 2 yearsI've found out it was just a debug exception and can get ignored, so my problem has been solved. Thanks for your comment @ibhavikmakwana
-