Declaring a method that strongly transfers `self`?

SE-0430 introduced sending parameters, which are an absolute blessing in that they relax the requirements on methods like Synchronization.Mutex. So you can now have an API like:

class NonSendable {}

func wrap(_ value: sending NonSendable) -> Mutex<NonSendable> {
  Mutex(value)
}

My question is, is there a way to spell the above API as a method instead? What I would like to write is something closer to

class NonSendable {
  sending func wrapped() -> Mutex<NonSendable> {
    Mutex(self)
  }
}

I feel like this would be much nicer for discovery as well as ergonomics: in my case, I'm actually creating an ActorIsolatedAsyncSequence that allows any AsyncSequence to become Sendable by wrapping it in an actor, and it would be a lot nicer to say e.g. someAsyncSequence().map { ... }.isolated() than isolate(someSequence().map { ... }) since the former is much more in line with other AsyncSequence operators.

Do let me know if something like this already exists — and if not, I would be happy to work on a pitch!

PS: When discussing this in the Swift Open Source Slack, @lukasa brought up that the Swift CC typically requires that self is strongly owned for the duration of a method call. However seeing as consuming already exists as a carve-out to this rule, I wonder whether the same could be applied here.

3 Likes