Comments (15)
Actually, I'm not sure that failable initializers is the best approach. I suspect most users are expecting that most GCD calls succeed, so they will use unwrapped values without checking for nil.
Probably, it would be better to provide an error handler that would be invoked when libdispatch call returns NULL. Such error handler could be set by the user, its possible behavior could be either assert/fail (this is the default), or log message, or ignore error completely. If the error is ignored, than we can fallback to failable initializer when feasible, or use non-failable initializer otherwise.
With an error handler, failable initializers can be safely defined as "init!" which would preserve compatibility and likely annoy users as little as possible.
from dispatchkit.
While I agree that implicitly unwrapped failable initializers would be the right choice, I'm not sure if an error handler is the way to go about it. What would the error handler really do?
from dispatchkit.
Default error handler could call assertionFailure()
or preconditionFailure()
. Another error handler could do nothing and allow control flow to proceed to failable initializer.
from dispatchkit.
One possible way to illustrate this:
typealias ErrorHandler = (String, StaticString, UInt) -> Void
var errorHandler: ErrorHandler = defaultErrorHandler
func defaultErrorHandler(message: String, file: StaticString, line: UInt) {
preconditionFailure(message, file: file, line: line)
}
func invokeErrorHandler(message: String, file: StaticString = __FILE__, line: UInt = __LINE__) {
errorHandler(message, file, line)
}
func dispatch_api_example() -> Int? { return nil }
struct Wrapper {
let value: Int
init!() {
if let result = dispatch_api_example() {
self.value = result
} else {
invokeErrorHandler("it happens")
return nil
}
}
}
from dispatchkit.
Alright that makes sense. I'd imagine we'd want the error handler to be a constructor parameter that defaults to the default error handler?
from dispatchkit.
No, I expect the global variable errorHandler, or even the static variable within the Dispatch struct.
More important is that I'm not sure we need failable initializers once we have error handler. I suspect it would be better to avoid failable initializers at all and stick to error handler mechanism.
from dispatchkit.
I see a HUGE problem with that approach. If module A
depends on B
, and both A
and B
make use of DispatchKit, then only one of them can have an error handler.
Moreover, I'm not sure it makes sense that every usage of these methods should require the use of the same error handler. Shouldn't different scenarios call for different handling?
Also, I'm just not seeing why the error handler is necessary at all. If we want to generate some kind of runtime error, we can throw an ErrorType
of some kind. This can be caught, handled case-by-case, and provides any necessary details to the catcher.
Finally, I don't see why any of this is better than just having a failable initializer. It'd be different if we were able to provide detailed error information. But if all we're doing is artificially producing an error and calling a handler or throwing or whatever, how is that different than a failable initializer? If the user wants to use some global handler, they can just surround these methods with their own
guard let x = DispatchType(args...) else {
errorHandler()
}
Overall, it makes most sense to me to forego error handlers entirely in favor of idiomatic swift, with optionals.
from dispatchkit.
OK then, every initializer that wraps GCD API should be defined as init!
, what's special about DispatchData
initializers?
BTW, what do you think about eliminating duplicate data members like DispatchQueue.queue
in favor of DispatchQueue.rawValue
?
from dispatchkit.
I just mentioned DispatchData because it has a lot of different initializers and methods which call underlying dispatch methods.
from dispatchkit.
As for eliminating duplicates, I could be wrong, but I'm fairly sure that types that implement a protocol can't change the type of a computed property to a subtype.
Although I supposed it could be genericized.
protocol DispatchObject {
typealias RawType: dispatch_object_t
public var rawValue: RawValue
...
}
from dispatchkit.
It seems promising. Then we are to deprecate init(raw:)
too.
The summary of changes proposed so far:
protocol _DispatchObject {
typealias RawValue : dispatch_object_t
var rawValue : RawValue { get }
}
struct _DispatchQueue : _DispatchObject {
@available(*, unavailable, renamed="rawValue")
var queue: dispatch_queue_t { return rawValue }
@available(*, unavailable, renamed="_DispatchQueue(rawValue:")
init!(raw value: dispatch_queue_t) { return nil }
let rawValue: dispatch_queue_t
init(rawValue: dispatch_queue_t) {
self.rawValue = rawValue
}
init!() {
if let queue = dispatch_queue_create(nil, nil) {
self.rawValue = queue
} else {
return nil
}
}
}
from dispatchkit.
Looks good to me. And of course introducing the same change to the other Dispatch types.
from dispatchkit.
Do you want me to work on a pull request for this? Or have you already started?
from dispatchkit.
Actually, I will not be able to actively maintain this until Dec 22, at least.
I would be happy if you'll get this done.
from dispatchkit.
No problem. I'll get right on it.
from dispatchkit.
Related Issues (5)
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from dispatchkit.