Skip to content

Commit 75b39fa

Browse files
committed
Add Progress Control feature (v9.4.0)
Adds built-in progress tracking, status messages, and cooperative cancellation to commands via ProgressHandle. New Features: - ProgressHandle class with progress (0.0-1.0), statusMessage, and isCanceled properties - 8 new factory methods: createAsyncWithProgress and createUndoableWithProgress variants - New Command properties: progress, statusMessage, isCanceled, cancel() - MockCommand progress simulation support with updateMockProgress(), updateMockStatusMessage(), mockCancel() - Zero-overhead design: Commands without progress use static default notifiers Technical Details: - Non-nullable API using static default notifiers for commands without handles - Cooperative cancellation pattern (ValueListenable-based for external integration) - Full test coverage: 23 passing tests including MockCommand simulation - Compatible with external cancellation tokens (e.g., Dio CancelToken) Breaking Changes: None (fully backward compatible)
1 parent 3e356e6 commit 75b39fa

File tree

6 files changed

+1449
-1
lines changed

6 files changed

+1449
-1
lines changed

CHANGELOG.md

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,59 @@
1+
[9.4.0] - 2024-11-24
2+
3+
### New Features
4+
5+
- **Progress Control**: Commands now support built-in progress tracking, status messages, and cooperative cancellation through the new `ProgressHandle` class.
6+
7+
**New Factory Methods** (8 variants):
8+
- `Command.createAsyncWithProgress<TParam, TResult>()` - Async command with progress tracking
9+
- `Command.createAsyncNoParamWithProgress<TResult>()` - No-param async with progress
10+
- `Command.createAsyncNoResultWithProgress<TParam>()` - Void-return async with progress
11+
- `Command.createAsyncNoParamNoResultWithProgress()` - No-param, void-return async with progress
12+
- `Command.createUndoableWithProgress<TParam, TResult, TUndoState>()` - Undoable with progress
13+
- `Command.createUndoableNoParamWithProgress<TResult, TUndoState>()` - No-param undoable with progress
14+
- `Command.createUndoableNoResultWithProgress<TParam, TUndoState>()` - Void-return undoable with progress
15+
- `Command.createUndoableNoParamNoResultWithProgress<TUndoState>()` - No-param, void-return undoable with progress
16+
17+
**New Command Properties**:
18+
- `progress` - Observable progress value (0.0-1.0) via `ValueListenable<double>`
19+
- `statusMessage` - Observable status text via `ValueListenable<String?>`
20+
- `isCanceled` - Observable cancellation flag via `ValueListenable<bool>`
21+
- `cancel()` - Request cooperative cancellation
22+
23+
**MockCommand Progress Support**:
24+
- `withProgressHandle` constructor parameter to enable progress simulation
25+
- `updateMockProgress(double)` - Simulate progress updates in tests
26+
- `updateMockStatusMessage(String?)` - Simulate status message updates
27+
- `mockCancel()` - Simulate cancellation
28+
29+
**Example Usage**:
30+
```dart
31+
final uploadCommand = Command.createAsyncWithProgress<File, String>(
32+
(file, handle) async {
33+
for (int i = 0; i <= 100; i += 10) {
34+
if (handle.isCanceled.value) return 'Canceled';
35+
36+
await uploadChunk(file, i);
37+
handle.updateProgress(i / 100.0);
38+
handle.updateStatusMessage('Uploading: $i%');
39+
}
40+
return 'Complete';
41+
},
42+
initialValue: '',
43+
);
44+
45+
// In UI:
46+
watchValue((MyService s) => s.uploadCommand.progress) // 0.0 to 1.0
47+
watchValue((MyService s) => s.uploadCommand.statusMessage) // Status text
48+
uploadCommand.cancel(); // Request cancellation
49+
```
50+
51+
**Benefits**:
52+
- Zero-overhead: Commands without progress use static default notifiers (no memory cost)
53+
- Type-safe: Progress properties available on all commands via non-nullable API
54+
- Cooperative cancellation: Works with external cancellation tokens (e.g., Dio's CancelToken)
55+
- Test-friendly: MockCommand supports full progress simulation
56+
157
[9.3.0] - 2025-01-23
258

359
### Added

0 commit comments

Comments
 (0)