Different result type using Parameter Packs in a result builder

Oh nice find/hack! I was just struggling with this last night.

Weirdly it worked when I wrote out the steps manually:

@resultBuilder public enum TupleBuilder {
    public static func buildPartialBlock<T>(first: T) -> (T) {
        return first
    }

    public static func buildPartialBlock<each A, B>(accumulated: (repeat each A), next: B) -> (repeat each A, B) {
        return (repeat each accumulated, next)
    }

}

func builder<each A>(@TupleBuilder content: ()->(repeat each A)) -> (repeat each A) {
    return content()
}

func testManual() -> (String, Int, String, String) {
    let a = TupleBuilder.buildPartialBlock(first: "a")
    let b = TupleBuilder.buildPartialBlock(accumulated: a, next: 2)
    let c = TupleBuilder.buildPartialBlock(accumulated: b, next: "b")
    return TupleBuilder.buildPartialBlock(accumulated: c, next: "c")
}

// Cannot convert return expression of type '(((String, Int), String), String)' to return type '(String, Int, String, String)'
func testBuilder() -> (String, Int, String, String) {
    return builder {
        ""
        1
        ""
        ""
    }
}

It took me writing this out (and double-checking the original proposal) to realize my buildPartialBlock was probably correct. This is my first experience with Parameter Packs, so I was driving myself crazy trying to rearrange the syntax.

It seems like maybe the generated code isn’t being type-checked/having its types resolved in the same way as hand-written code. It seems like the type structure of parameters packs is terrifyingly ~vague~ flexible, because all of these are valid:

func testManual() -> ((String, Int, String), String) {
    let a = TupleBuilder.buildPartialBlock(first: "a")
    let b = TupleBuilder.buildPartialBlock(accumulated: a, next: 2)
    let c = TupleBuilder.buildPartialBlock(accumulated: b, next: "b")
    return TupleBuilder.buildPartialBlock(accumulated: c, next: "c")
}


let tuplized: (String) = TupleBuilder.buildPartialBlock(first: "a")
let standalone: String = TupleBuilder.buildPartialBlock(first: "a")
let detuplized: String = TupleBuilder.buildPartialBlock(first: ("a"))

Maybe there’s an issue/bug in the result builder type checking casusing it to not emit all possible options for parameter packs?