Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(143)

Side by Side Diff: lib/src/utils.dart

Issue 1947773002: Fix all strong-mode warnings. (Closed) Base URL: git@github.com:dart-lang/barback@master
Patch Set: Code review changes Created 4 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 library barback.utils; 5 library barback.utils;
6 6
7 import 'dart:async'; 7 import 'dart:async';
8 import 'dart:typed_data'; 8 import 'dart:typed_data';
9 9
10 import 'package:async/async.dart';
10 import 'package:stack_trace/stack_trace.dart'; 11 import 'package:stack_trace/stack_trace.dart';
11 12
12 /// A class that represents a value or an error. 13 /// A class that represents a value or an error.
13 class Fallible<E> { 14 class Fallible<E> {
14 /// Whether [this] has a [value], as opposed to an [error]. 15 /// Whether [this] has a [value], as opposed to an [error].
15 final bool hasValue; 16 final bool hasValue;
16 17
17 /// Whether [this] has an [error], as opposed to a [value]. 18 /// Whether [this] has an [error], as opposed to a [value].
18 bool get hasError => !hasValue; 19 bool get hasError => !hasValue;
19 20
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
122 // TODO(nweiz): remove "as" when issue 11080 is fixed. 123 // TODO(nweiz): remove "as" when issue 11080 is fixed.
123 return new Uint8List.view((input as TypedData).buffer); 124 return new Uint8List.view((input as TypedData).buffer);
124 } 125 }
125 return new Uint8List.fromList(input); 126 return new Uint8List.fromList(input);
126 } 127 }
127 128
128 /// Group the elements in [iter] by the value returned by [fn]. 129 /// Group the elements in [iter] by the value returned by [fn].
129 /// 130 ///
130 /// This returns a map whose keys are the return values of [fn] and whose values 131 /// This returns a map whose keys are the return values of [fn] and whose values
131 /// are lists of each element in [iter] for which [fn] returned that key. 132 /// are lists of each element in [iter] for which [fn] returned that key.
132 Map<Object, List> groupBy(Iterable iter, fn(element)) { 133 Map<Object/*=T*/, List/*<S>*/> groupBy/*<S, T>*/(Iterable/*<S>*/ iter,
133 var map = {}; 134 /*=T*/ fn(/*=S*/ element)) {
135 var map = /*<T, List<S>>*/{};
134 for (var element in iter) { 136 for (var element in iter) {
135 var list = map.putIfAbsent(fn(element), () => []); 137 var list = map.putIfAbsent(fn(element), () => []);
136 list.add(element); 138 list.add(element);
137 } 139 }
138 return map; 140 return map;
139 } 141 }
140 142
141 /// Flattens nested lists inside an iterable into a single list containing only 143 /// Flattens nested lists inside an iterable into a single list containing only
142 /// non-list elements. 144 /// non-list elements.
143 List flatten(Iterable nested) { 145 List flatten(Iterable nested) {
144 var result = []; 146 var result = [];
145 helper(list) { 147 helper(list) {
146 for (var element in list) { 148 for (var element in list) {
147 if (element is List) { 149 if (element is List) {
148 helper(element); 150 helper(element);
149 } else { 151 } else {
150 result.add(element); 152 result.add(element);
151 } 153 }
152 } 154 }
153 } 155 }
154 helper(nested); 156 helper(nested);
155 return result; 157 return result;
156 } 158 }
157 159
158 /// Returns the union of all elements in each set in [sets]. 160 /// Returns the union of all elements in each set in [sets].
159 Set unionAll(Iterable<Set> sets) => 161 Set/*<T>*/ unionAll/*<T>*/(Iterable<Set/*<T>*/> sets) =>
160 sets.fold(new Set(), (union, set) => union.union(set)); 162 sets.fold(new Set(), (union, set) => union.union(set));
161 163
162 /// Creates a new map from [map] with new keys and values. 164 /// Creates a new map from [map] with new keys and values.
163 /// 165 ///
164 /// The return values of [keyFn] are used as the keys and the return values of 166 /// The return values of [keyFn] are used as the keys and the return values of
165 /// [valueFn] are used as the values for the new map. 167 /// [valueFn] are used as the values for the new map.
166 Map mapMap(Map map, keyFn(key, value), valueFn(key, value)) => 168 Map/*<K2, V2>*/ mapMap/*<K1, V1, K2, V2>*/(Map/*<K1, V1>*/ map,
169 /*=K2*/ keyFn(/*=K1*/ key, /*=V1*/ value),
170 /*=V2*/ valueFn(/*=K1*/ key, /*=V1*/ value)) =>
167 new Map.fromIterable(map.keys, 171 new Map.fromIterable(map.keys,
168 key: (key) => keyFn(key, map[key]), 172 key: (key) => keyFn(key as dynamic/*=K1*/, map[key]),
169 value: (key) => valueFn(key, map[key])); 173 value: (key) => valueFn(key as dynamic/*=K1*/, map[key]));
170 174
171 /// Creates a new map from [map] with the same keys. 175 /// Creates a new map from [map] with the same keys.
172 /// 176 ///
173 /// The return values of [fn] are used as the values for the new map. 177 /// The return values of [fn] are used as the values for the new map.
174 Map mapMapValues(Map map, fn(key, value)) => mapMap(map, (key, _) => key, fn); 178 Map/*<K, V2>*/ mapMapValues/*<K, V1, V2>*/(Map/*<K, V1>*/ map,
179 /*=V2*/ fn(/*=K*/ key, /*=V1*/ value)) =>
180 // TODO(nweiz): Don't explicitly type [key] when sdk#25490 is fixed.
181 mapMap(map, (/*=K*/ key, _) => key, fn);
175 182
176 /// Creates a new map from [map] with the same keys. 183 /// Creates a new map from [map] with the same keys.
177 /// 184 ///
178 /// The return values of [fn] are used as the keys for the new map. 185 /// The return values of [fn] are used as the keys for the new map.
179 Map mapMapKeys(Map map, fn(key, value)) => mapMap(map, fn, (_, value) => value); 186 Map/*<K2, V>*/ mapMapKeys/*<K1, V, K2>*/(Map/*<K1, V>*/ map,
187 /*=K2*/ fn(/*=K1*/ key, /*=V*/ value)) =>
188 // TODO(nweiz): Don't explicitly type [value] when sdk#25490 is fixed.
189 mapMap(map, fn, (_, /*=V*/ value) => value);
180 190
181 /// Returns whether [set1] has exactly the same elements as [set2]. 191 /// Returns whether [set1] has exactly the same elements as [set2].
182 bool setEquals(Set set1, Set set2) => 192 bool setEquals(Set set1, Set set2) =>
183 set1.length == set2.length && set1.containsAll(set2); 193 set1.length == set2.length && set1.containsAll(set2);
184 194
185 /// Merges [streams] into a single stream that emits events from all sources. 195 /// Merges [streams] into a single stream that emits events from all sources.
186 /// 196 ///
187 /// If [broadcast] is true, this will return a broadcast stream; otherwise, it 197 /// If [broadcast] is true, this will return a broadcast stream; otherwise, it
188 /// will return a buffered stream. 198 /// will return a buffered stream.
189 Stream mergeStreams(Iterable<Stream> streams, {bool broadcast: false}) { 199 Stream/*<T>*/ mergeStreams/*<T>*/(Iterable<Stream/*<T>*/> streams,
200 {bool broadcast: false}) {
190 streams = streams.toList(); 201 streams = streams.toList();
191 var doneCount = 0; 202 var doneCount = 0;
192 // Use a sync stream to preserve the synchrony behavior of the input streams. 203 // Use a sync stream to preserve the synchrony behavior of the input streams.
193 // If the inputs are sync, then this will be sync as well; if the inputs are 204 // If the inputs are sync, then this will be sync as well; if the inputs are
194 // async, then the events we receive will also be async, and forwarding them 205 // async, then the events we receive will also be async, and forwarding them
195 // sync won't change that. 206 // sync won't change that.
196 var controller = broadcast ? new StreamController.broadcast(sync: true) 207 var controller = broadcast
197 : new StreamController(sync: true); 208 ? new StreamController/*<T>*/.broadcast(sync: true)
209 : new StreamController/*<T>*/(sync: true);
198 210
199 for (var stream in streams) { 211 for (var stream in streams) {
200 stream.listen( 212 stream.listen(
201 controller.add, 213 controller.add,
202 onError: controller.addError, 214 onError: controller.addError,
203 onDone: () { 215 onDone: () {
204 doneCount++; 216 doneCount++;
205 if (doneCount == streams.length) controller.close(); 217 if (doneCount == streams.length) controller.close();
206 }); 218 });
207 } 219 }
(...skipping 23 matching lines...) Expand all
231 // We use a delayed future to allow microtask events to finish. The 243 // We use a delayed future to allow microtask events to finish. The
232 // Future.value or Future() constructors use scheduleMicrotask themselves and 244 // Future.value or Future() constructors use scheduleMicrotask themselves and
233 // would therefore not wait for microtask callbacks that are scheduled after 245 // would therefore not wait for microtask callbacks that are scheduled after
234 // invoking this method. 246 // invoking this method.
235 return new Future.delayed(Duration.ZERO, () => pumpEventQueue(times - 1)); 247 return new Future.delayed(Duration.ZERO, () => pumpEventQueue(times - 1));
236 } 248 }
237 249
238 /// Like `new Future`, but avoids issue 11911 by using `new Future.value` under 250 /// Like `new Future`, but avoids issue 11911 by using `new Future.value` under
239 /// the covers. 251 /// the covers.
240 // TODO(jmesserly): doc comment changed to due 14601. 252 // TODO(jmesserly): doc comment changed to due 14601.
241 Future newFuture(callback()) => new Future.value().then((_) => callback()); 253 Future/*<T>*/ newFuture/*<T>*/(/*=T*/ callback()) async => await callback();
242
243 /// Like [Future.sync], but wraps the Future in [Chain.track] as well.
244 Future syncFuture(callback()) => Chain.track(new Future.sync(callback));
245 254
246 /// Returns a buffered stream that will emit the same values as the stream 255 /// Returns a buffered stream that will emit the same values as the stream
247 /// returned by [future] once [future] completes. 256 /// returned by [future] once [future] completes.
248 /// 257 ///
249 /// If [future] completes to an error, the return value will emit that error and 258 /// If [future] completes to an error, the return value will emit that error and
250 /// then close. 259 /// then close.
251 /// 260 ///
252 /// If [broadcast] is true, a broadcast stream is returned. This assumes that 261 /// If [broadcast] is true, a broadcast stream is returned. This assumes that
253 /// the stream returned by [future] will be a broadcast stream as well. 262 /// the stream returned by [future] will be a broadcast stream as well.
254 /// [broadcast] defaults to false. 263 /// [broadcast] defaults to false.
255 Stream futureStream(Future<Stream> future, {bool broadcast: false}) { 264 Stream/*<T>*/ futureStream/*<T>*/(Future<Stream/*<T>*/> future,
256 var subscription; 265 {bool broadcast: false}) {
257 var controller; 266 StreamSubscription/*<T>*/ subscription;
267 StreamController/*<T>*/ controller;
258 268
259 future = future.catchError((e, stackTrace) { 269 future = DelegatingFuture.typed(future.catchError((e, stackTrace) {
260 // Since [controller] is synchronous, it's likely that emitting an error 270 // Since [controller] is synchronous, it's likely that emitting an error
261 // will cause it to be cancelled before we call close. 271 // will cause it to be cancelled before we call close.
262 if (controller != null) controller.addError(e, stackTrace); 272 if (controller != null) controller.addError(e, stackTrace);
263 if (controller != null) controller.close(); 273 if (controller != null) controller.close();
264 controller = null; 274 controller = null;
265 }); 275 }));
266 276
267 onListen() { 277 onListen() {
268 future.then((stream) { 278 future.then((stream) {
269 if (controller == null) return; 279 if (controller == null) return;
270 subscription = stream.listen( 280 subscription = stream.listen(
271 controller.add, 281 controller.add,
272 onError: controller.addError, 282 onError: controller.addError,
273 onDone: controller.close); 283 onDone: controller.close);
274 }); 284 });
275 } 285 }
276 286
277 onCancel() { 287 onCancel() {
278 if (subscription != null) subscription.cancel(); 288 if (subscription != null) subscription.cancel();
279 subscription = null; 289 subscription = null;
280 controller = null; 290 controller = null;
281 } 291 }
282 292
283 if (broadcast) { 293 if (broadcast) {
284 controller = new StreamController.broadcast( 294 controller = new StreamController/*<T>*/.broadcast(
285 sync: true, onListen: onListen, onCancel: onCancel); 295 sync: true, onListen: onListen, onCancel: onCancel);
286 } else { 296 } else {
287 controller = new StreamController( 297 controller = new StreamController/*<T>*/(
288 sync: true, onListen: onListen, onCancel: onCancel); 298 sync: true, onListen: onListen, onCancel: onCancel);
289 } 299 }
290 return controller.stream; 300 return controller.stream;
291 } 301 }
292 302
293 /// Returns a [Stream] that will emit the same values as the stream returned by 303 /// Returns a [Stream] that will emit the same values as the stream returned by
294 /// [callback]. 304 /// [callback].
295 /// 305 ///
296 /// [callback] will only be called when the returned [Stream] gets a subscriber. 306 /// [callback] will only be called when the returned [Stream] gets a subscriber.
297 Stream callbackStream(Stream callback()) { 307 Stream/*<T>*/ callbackStream/*<T>*/(Stream/*<T>*/ callback()) {
298 var subscription; 308 StreamSubscription/*<T>*/ subscription;
299 var controller; 309 StreamController/*<T>*/ controller;
300 controller = new StreamController(onListen: () { 310 controller = new StreamController/*<T>*/(onListen: () {
301 subscription = callback().listen(controller.add, 311 subscription = callback().listen(controller.add,
302 onError: controller.addError, 312 onError: controller.addError,
303 onDone: controller.close); 313 onDone: controller.close);
304 }, 314 },
305 onCancel: () => subscription.cancel(), 315 onCancel: () => subscription.cancel(),
306 onPause: () => subscription.pause(), 316 onPause: () => subscription.pause(),
307 onResume: () => subscription.resume(), 317 onResume: () => subscription.resume(),
308 sync: true); 318 sync: true);
309 return controller.stream; 319 return controller.stream;
310 } 320 }
311 321
312 /// Creates a single-subscription stream from a broadcast stream. 322 /// Creates a single-subscription stream from a broadcast stream.
313 /// 323 ///
314 /// The returned stream will enqueue events from [broadcast] until a listener is 324 /// The returned stream will enqueue events from [broadcast] until a listener is
315 /// attached, then pipe events to that listener. 325 /// attached, then pipe events to that listener.
316 Stream broadcastToSingleSubscription(Stream broadcast) { 326 Stream/*<T>*/ broadcastToSingleSubscription/*<T>*/(Stream/*<T>*/ broadcast) {
317 if (!broadcast.isBroadcast) return broadcast; 327 if (!broadcast.isBroadcast) return broadcast;
318 328
319 // TODO(nweiz): Implement this using a transformer when issues 18588 and 18586 329 // TODO(nweiz): Implement this using a transformer when issues 18588 and 18586
320 // are fixed. 330 // are fixed.
321 var subscription; 331 var subscription;
322 var controller = new StreamController(onCancel: () => subscription.cancel()); 332 var controller = new StreamController/*<T>*/(
333 onCancel: () => subscription.cancel());
323 subscription = broadcast.listen(controller.add, 334 subscription = broadcast.listen(controller.add,
324 onError: controller.addError, 335 onError: controller.addError,
325 onDone: controller.close); 336 onDone: controller.close);
326 return controller.stream; 337 return controller.stream;
327 } 338 }
328 339
329 /// A regular expression to match the exception prefix that some exceptions' 340 /// A regular expression to match the exception prefix that some exceptions'
330 /// [Object.toString] values contain. 341 /// [Object.toString] values contain.
331 final _exceptionPrefix = new RegExp(r'^([A-Z][a-zA-Z]*)?(Exception|Error): '); 342 final _exceptionPrefix = new RegExp(r'^([A-Z][a-zA-Z]*)?(Exception|Error): ');
332 343
333 /// Get a string description of an exception. 344 /// Get a string description of an exception.
334 /// 345 ///
335 /// Many exceptions include the exception class name at the beginning of their 346 /// Many exceptions include the exception class name at the beginning of their
336 /// [toString], so we remove that if it exists. 347 /// [toString], so we remove that if it exists.
337 String getErrorMessage(error) => 348 String getErrorMessage(error) =>
338 error.toString().replaceFirst(_exceptionPrefix, ''); 349 error.toString().replaceFirst(_exceptionPrefix, '');
339 350
340 /// Returns a human-friendly representation of [duration]. 351 /// Returns a human-friendly representation of [duration].
341 String niceDuration(Duration duration) { 352 String niceDuration(Duration duration) {
342 var result = duration.inMinutes > 0 ? "${duration.inMinutes}:" : ""; 353 var result = duration.inMinutes > 0 ? "${duration.inMinutes}:" : "";
343 354
344 var s = duration.inSeconds % 59; 355 var s = duration.inSeconds % 59;
345 var ms = (duration.inMilliseconds % 1000) ~/ 100; 356 var ms = (duration.inMilliseconds % 1000) ~/ 100;
346 return result + "$s.${ms}s"; 357 return result + "$s.${ms}s";
347 } 358 }
OLDNEW
« no previous file with comments | « lib/src/transformer/wrapping_aggregate_transformer.dart ('k') | lib/src/utils/cancelable_future.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698