Repository navigation
Conversation
cross_file 0.4.0 removes the XFile(path, name:, bytes:) constructor and resolves every XFile through a registered CrossFilePlatform. The Android, Darwin, Linux and Windows platform files now build their XFile lazily with XFile.fileSystem for file URIs and XFile.scopedStorage otherwise, instead of eagerly in their factories. The unused bytes parameter of LinuxPlatformFile.fromPath and WindowsPlatformFile.fromPath is removed. cross_file 0.4.0 also raises the minimums to Flutter 3.41, Dart 3.11, Android SDK 24 and macOS 10.15, so the constraints, minSdk and deployment targets follow. Each package gets a test that reads a real temporary file through cross_file_io. Refs #2224
PlatformFile does not expose preloaded bytes, so withData, withReadStream and readSequential only decided when the content was read, and the eager paths were the source of the large file failures. They are removed from FilePickerWebOptions, which keeps cancelUploadOnWindowBlur only. Picked files are no longer read at pick time. Each File is wrapped in a cross_file_web XFile created from the Blob, and WebPlatformFile delegates readAsBytes(), readAsByteStream() and length() to it. This replaces the hand written FileReader, chunked stream and fetch helpers, and drops the bytes and readStream parameters of WebPlatformFile. Read errors still propagate. The object URL is created without auto revocation so PlatformFile.uri stays valid for as long as the page is open, as before. Refs #2224
Bump every package to a new major for the cross_file 0.4.0 migration: file_picker 14.0.0, file_picker_platform_interface 5.0.0, android_file_picker, file_picker_darwin, file_picker_linux and windows_file_picker 3.0.0, and file_picker_web 5.0.0, with their changelogs and raised constraints. Add the Migrating to v14 guide covering the new minimum versions, the new XFile API and the removed web reading options. The unreleased 4.0.1, 2.0.1 and 2.0.2 sections are kept so those patches can still be published from main before this lands. Refs #2224
|
Hey @navaronbracke! 👋 Whenever you have a moment, this one is ready for review. It's the big one, so no rush at all 🙂 The parts I'd love a second pair of eyes on:
CI is fully green, including the browser tests from #2235 and both Android lanes. Thank you! 💙 |
xFile.openRead() reads through Blob.stream(), whose chunk sizes are irregular. Consumers that rely on evenly sized buffers, such as RamFileData.fromStream from the archive package, used to get them from withReadStream, which sliced the file into fixed chunks. readAsByteStream() now slices the picked Blob into WebPlatformFile.streamChunkSize (1 MiB) pieces with slice() and arrayBuffer(), so every chunk but the last has the same size. It falls back to openRead() for an XFile without a Blob. Refs #2223
| - **BREAKING CHANGE**: Migrated to `cross_file` 0.4.0. `PlatformFile.xFile` now returns the new `XFile` API. See the [migration guide](https://github.com/vicajilau/flutter_file_picker/tree/main/packages/file_picker#migrating-to-v14). [#2224](https://github.com/vicajilau/flutter_file_picker/issues/2224) | ||
| - **BREAKING CHANGE**: Requires Flutter 3.41, Dart 3.11, Android SDK 24 and macOS 10.15. | ||
| - **BREAKING CHANGE**: Removed `withData`, `withReadStream` and `readSequential` from `FilePickerWebOptions` (`file_picker_web 5.0.0`). | ||
| - Raised lower bounds of all platform implementation packages: `file_picker_platform_interface ^5.0.0`, `android_file_picker ^3.0.0`, `file_picker_darwin ^3.0.0`, `file_picker_linux ^3.0.0`, `windows_file_picker ^3.0.0`, and `file_picker_web ^5.0.0`. |
There was a problem hiding this comment.
This last line is redundant? Consumers will pick this up in their lockfiles anyway.
There was a problem hiding this comment.
Good point, the pubspecs already say it. Removed in 476d9a4.
|
|
||
| 2. **`PlatformFile.xFile` Uses `cross_file` 0.4.0**: | ||
| * `XFile.path`, `XFile.mimeType`, `XFile.saveTo()` and `XFile.fromData` no longer exist, and `XFile.name` is now `Future<String?> name()`. | ||
| * Use `PlatformFile.path`, `PlatformFile.name`, `readAsBytes()` and `readAsByteStream()` when you do not need an `XFile`. For a file system path, check for a `FileSystemXFile`: `final path = switch (file.xFile) { FileSystemXFile(:final path) => path, _ => null };` (`FileSystemXFile` comes from `package:cross_file/cross_file.dart`). |
There was a problem hiding this comment.
Can this be a multiline code sample in triple backticks?
There was a problem hiding this comment.
Much more readable, thanks! Done in 476d9a4, with the import in the block too.
| _xFile ?? | ||
| (uri.scheme == 'file' | ||
| ? XFile.fileSystem(path: uri.toFilePath()) | ||
| : XFile.scopedStorage(uri: uri.toString())); |
There was a problem hiding this comment.
The latter one is a content URI, right?
There was a problem hiding this comment.
Yes, exactly! Anything outside the file scheme is a Storage Access Framework content:// URI. I documented it on the getter in 476d9a4 so it doesn't need explaining again 🙂
| const size = | ||
| WebPlatformFile.streamChunkSize * 2 + | ||
| WebPlatformFile.streamChunkSize ~/ 2; | ||
| final large = Uint8List.fromList(List.generate(size, (i) => i % 251)); |
There was a problem hiding this comment.
Should this not be 255/256?
There was a problem hiding this comment.
Good question! It's 251 on purpose: being prime, the byte pattern doesn't line up with the chunk boundaries, which are a multiple of 256. With % 256 every chunk would start with the same bytes, so swapped or repeated chunks would still pass. I added a comment explaining it in 476d9a4.
# Conflicts: # packages/file_picker_darwin/CHANGELOG.md # packages/file_picker_darwin/pubspec.yaml
Co-authored-by: Navaron Bracke <brackenavaron@gmail.com>
Drop the redundant lower bounds line from the file_picker changelog, show the FileSystemXFile path lookup in the migration guide as a code block, document that AndroidPlatformFile.xFile wraps a content URI outside the file scheme, and explain why the chunking test uses a prime modulus.
|
Converting this to draft on purpose, it's ready but should not land yet.
So the plan is:
|
# Conflicts: # packages/file_picker_web/CHANGELOG.md # packages/file_picker_web/lib/src/file_picker_web.dart # packages/file_picker_web/lib/src/file_picker_web_options.dart # packages/file_picker_web/lib/src/platform_file_web_fetch.dart # packages/file_picker_web/lib/src/web_platform_file.dart # packages/file_picker_web/pubspec.yaml # packages/file_picker_web/test/file_picker_web_pick_test.dart
|
@vicajilau thanks for all your work on that release ❤️ it looks great. About this:
I'm wondering why you would hold off on 14.0.0 / 5.0.0, is it to save the trouble for users bumping into dependencies problems? Personally I know I'll wait for the cross_file bump in my other dependencies before I upgrade, but maybe some other users who don't use those blocking dependencies would be able to upgrade earlier? The Just a thought :-) |
|
Personally I don't see why we would hold off on releasing it. There isn't really much new from v13, except for the new cross_file usage |
Fixes #2224
Major release for every package. This is a breaking change on all platforms, so please review it carefully. The points that most deserve attention are marked with⚠️ .
Changes
Migrate to
cross_file0.4.0PlatformFile.xFilereturns anXFile, so its API is part of ours.cross_file0.4.0 removesXFile(path, name:, bytes:),XFile.path,mimeType,saveTo()andfromData, and turnsnameintoFuture<String?> name().XFilelazily withXFile.fileSystemfor file URIs andXFile.scopedStorageotherwise. It used to be built eagerly in the factories, but in 0.4.0 everyXFileneeds thecross_fileplugin to be registered, so it is now only created when requested.bytesparameter ofLinuxPlatformFile.fromPath()andWindowsPlatformFile.fromPath()is removed.cross_file0.4.0 is now a federated plugin with native code (cross_file_android,cross_file_darwin,cross_file_io,cross_file_web), and it raises the minimums:minSdk,Package.swiftand the podspec follow.Web: remove
withData,withReadStreamandreadSequentialPlatformFiledoes not expose preloaded bytes, so these options only decided when the content was read, and the eager paths were the source of the large file failures (#2223). They are removed fromFilePickerWebOptions, which keepscancelUploadOnWindowBluronly.Picked files are no longer read at pick time. Each
Fileis wrapped in across_file_webXFilecreated from theBlob, andWebPlatformFiledelegatesreadAsBytes(),readAsByteStream()andlength()to it. This replaces the hand writtenFileReader, chunked stream andfetchhelpers (about 250 lines and three internal files), and drops thebytesandreadStreamparameters ofWebPlatformFile. Read errors still propagate, as fixed in #2229.autoRevokeObjectUrl: false, soPlatformFile.uristays valid for as long as the page is open, as before.readAsByteStream()on web emits evenly sized chunks ofWebPlatformFile.streamChunkSize(1 MiB), except the last one, by slicing the pickedBlobwithslice()andarrayBuffer().xFile.openRead()goes throughBlob.stream(), whose chunk sizes are irregular, and #2223 showed a real consumer (RamFileData.fromStreamfrom thearchivepackage) that needs evenly sized buffers, which it used to get fromwithReadStream. Removing that option without this would have broken it.Versions and docs
file_picker14.0.0,file_picker_platform_interface5.0.0,android_file_picker,file_picker_darwin,file_picker_linuxandwindows_file_picker3.0.0,file_picker_web5.0.0, with short changelogs.file_pickerREADME, linked from the root README.Testing
flutter analyzeis clean across the workspace.cross_file_io.CrossFileWebregistered automatically) and macOS locally.agp-8.xAndroid lane was reproduced locally with Java 17, sincecross_file_androiddeclares Kotlin 2.3.0 while that lane uses 2.2.20, and it builds.The facade check and
facade_constraints_testskip themselves until the new majors are published, as designed for release branches.