Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[SR-7014] Protocol with associated type, conforming with inherited protocol not supported? #49562

Closed
swift-ci opened this issue Feb 16, 2018 · 3 comments
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior. compiler The Swift compiler in itself conformances Feature → protocol: protocol conformances feature A feature request or implementation type checker Area → compiler: Semantic analysis

Comments

@swift-ci
Copy link
Collaborator

Previous ID SR-7014
Radar None
Original Reporter itsthejb (JIRA User)
Type Bug
Status Closed
Resolution Won't Do

Attachment: Download

Environment
  • Version 9.2 (9C40b)

  • Version 9.3 beta 2 (9Q107o)

Additional Detail from JIRA
Votes 0
Component/s Compiler
Labels Bug, LanguageFeatureRequest, ProtocolConformance, TypeChecker
Assignee None
Priority Medium

md5: 739e1ec6d472d9d86106f459ee676496

Issue Description:

Hi all,

Really unsure whether or not this is a bug, limitation, or I'm doing something stupid, but I've tried hard to resolve this and this seems like something that should be supported, but is not. Code:

import UIKit

protocol ContentViewController: class {
  var view: UIView! { get set }
}

protocol MapViewController: ContentViewController {}

protocol ContainerTabbleViewController: class {
  associatedtype HeaderViewController: ContentViewController
  var headerViewController: ContentViewController? { get set }
}

final class ViewController: UIViewController, ContainerTabbleViewController {
    typealias HeaderViewController = MapViewController
    var headerViewController: MapViewController?
}

I have a protocol that will be used to abstract some layout behaviour. It should work for any child view controller, but in the concrete implementation (ViewController) I would still like to have headerViewController expressed using a protocol (which as far as I can see, correctly inherits from the base protocol). This does not work, however:

error: type 'ViewController' does not conform to protocol 'ContainerTabbleViewController'
final class ViewController: UIViewController, ContainerTabbleViewController {
            ^
note: possibly intended match 'ViewController.HeaderViewController' (aka 'MapViewController') does not conform to 'ContentViewController'
    typealias HeaderViewController = MapViewController
              ^
note: protocol requires nested type 'HeaderViewController'; do you want to add it?
    associatedtype HeaderViewController: ContentViewController
                   ^

The odd part is the middle error: possibly intended match 'ViewController.HeaderViewController' (aka 'MapViewController') does not conform to 'ContentViewController'. However, in my implementation the MapViewController protocol certainly does inherit from ContentViewController. So it would seem that conforming to the protocol with a subtype of the protocol is not supported. This seems like it should work. I would like to use an extension to ContainerTabbleViewController to do the layout, which would only rely on the availability of the view property, which is expressed in ContentViewController. Then, in the context of ViewController I ought to be able to refer to the characteristics of my protocol subtype, providing it inherits from the correct protocol to satisfy ContainerTabbleViewController

Apologies in advance if I'm making an error here, but this certainly seems wrong and ought to be supported. Many thanks!

@belkadan
Copy link
Contributor

There's a difference between MapViewController the protocol and a specific type that conforms to MapViewController. Types that conform to MapViewController also conform to ContentViewController, but MapViewController itself doesn't.

This might seem like needless pedantry, but imagine if ContentViewController had an init() requirement. If you tried to use it with HeaderViewController(), what type would you get?

@swift-ci
Copy link
Collaborator Author

Comment by Jonathan Crooke (JIRA)

Hi @belkadan. Thanks for your input. Yes, you make a good point. In fact, I hadn't considered the point about a protocol itself not conforming to the base protocol. Of course, this does work with concrete types adhearing to the protocol. Perhaps the simple solution in this case is just to define a base class for the view controllers that adhere to the protocol... That should work. I'll close this, then, unless it seems worthwhile to leave it open for any other input?

@swift-ci
Copy link
Collaborator Author

Comment by Jonathan Crooke (JIRA)

Ok, I ended up using a base class. Still a bit limited, since it's not possible to have a generic base class due to the view controller property. Still, good enough and perhaps there is no better solution. Closing

@swift-ci swift-ci transferred this issue from apple/swift-issues Apr 25, 2022
This issue was closed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior. compiler The Swift compiler in itself conformances Feature → protocol: protocol conformances feature A feature request or implementation type checker Area → compiler: Semantic analysis
Projects
None yet
Development

No branches or pull requests

2 participants