[swift-evolution] [Proposal][Discussion] Qualified Imports

Xiaodi Wu xiaodi.wu at gmail.com
Wed Jul 20 14:08:22 CDT 2016


As Joe and others mentioned in the previous thread, this syntax could be
greatly simplified in ways that resemble analogous facilities in other
languages. In particular I think it's alarmingly asymmetrical that, in your
proposal, `import Swift using (String)` imports *only* String while `import
Swift hiding (String)` imports *everything but* String. This becomes
evident when chained together:

```
import Swift using (String, Int)
// imports only String and Int
import Swift using (String, Int) hiding (String)
// imports only Int
import Swift hiding (String, Int)
// imports everything except String and Int
import Swift hiding (String, Int) using (String)
// imports *nothing*? nothing except String? everything except Int?
confusing.
```

By contrast, Joe's proposed syntax (with some riffs) produces something
much more terse *and* much more clear:

```
import Swift.*
import Swift.(Int as MyInt, *)
import Swift.(Int as _, *)
```


On Wed, Jul 20, 2016 at 1:52 PM, Robert Widmann via swift-evolution <
swift-evolution at swift.org> wrote:

> Hello all,
>
> I’d like to thank the members of the community that have guided the
> revisions of this proposal.  We have decided to heed the advice of the
> community and break down our original proposal on modules and qualified
> imports into source-breaking (qualified imports) and additive (modules)
> proposals.  As qualified imports is the change most suited to Swift 3, we
> are pushing that proposal now as our final draft.
>
> It can be had inline with this email, on Github
> <https://github.com/apple/swift-evolution/pull/440>, or as a gist
> <https://gist.github.com/CodaFi/42e5e5e94d857547abc381d9a9d0afd6>.
>
> Thanks,
>
> ~Robert Widmann
>
> Qualified Imports Revisited
>
>    - Proposal: SE-NNNN
>    <https://gist.github.com/CodaFi/NNNN-first-class-qualified-imports.md>
>    - Authors: Robert Widmann <https://github.com/codafi>, TJ Usiyan
>    <https://github.com/griotspeak>
>    - Status: Awaiting review
>    - Review manager: TBD
>
>
> <https://gist.github.com/CodaFi/42e5e5e94d857547abc381d9a9d0afd6#introduction>
> Introduction
>
> We propose a complete overhaul of the qualified imports syntax and
> semantics.
>
> <https://gist.github.com/CodaFi/42e5e5e94d857547abc381d9a9d0afd6#motivation>
> Motivation
>
> The existing syntax for qualified imports from modules is needlessly
> explicit, does not compose, and has a default semantics that dilutes the
> intended meaning of the very operation itself. Today, a qualified import
> looks something like this
>
> import class Foundation.Date
>
> This means that clients of Foundation that wish to see only Date must
> know the exact kind of declaration that identifier is. In addition, though
> this import specifies exactly one class be imported from Foundation, the
> actual semantics mean Swift will recursively open all of Foundation's
> submodules so you can see, and use, every other identifier anyway - and
> they are not filtered from code completion. Qualified imports deserve to be
> first-class in Swift, and that is what we intend to make them with this
> proposal.
>
> <https://gist.github.com/CodaFi/42e5e5e94d857547abc381d9a9d0afd6#proposed-solution>Proposed
> solution
>
> The grammar and semantics of qualified imports will change completely with
> the addition of *import qualifiers* and *import directives*. We also
> introduce two new contextual keywords: using and hiding, to facilitate
> fine-grained usage of module contents.
>
> <https://gist.github.com/CodaFi/42e5e5e94d857547abc381d9a9d0afd6#detailed-design>Detailed
> design
>
> Qualified import syntax will be revised to the following
>
> import-decl -> import <import-path> <(opt) import-directive-list>
> import-path -> <identifier>
>             -> <identifier>.<identifier>
> import-directive-list -> <import-directive>
>                       -> <import-directive> <import-directive-list>
> import-directive -> using (<identifier>, ...)
>                  -> hiding (<identifier>, ...)
>
> This introduces the concept of an import *directive*. An import directive
> is a file-local modification of an imported identifier. A directive can be
> one of 2 operations:
>
> 1) *using*: The *using* directive is followed by a list of identifiers
> for non-member nominal declarations within the imported module that should
> be exposed to this file.
>
> // The only visible parts of Foundation in this file are // Foundation.Date, Foundation.DateFormatter, and Foundation.DateComponents//// Previously, this was// import class Foundation.Date// import class Foundation.DateFormatter// import class Foundation.DateComponentsimport Foundation using (Date, DateFormatter, DateComponents)
>
> 2) *hiding*: The hiding directive is followed by a list of identifiers
> for non-member nominal declarations within the imported module that should
> be hidden from this file.
>
> // Imports all of Foundation except `Date`import Foundation hiding (Date)
>
> As today, all hidden identifiers do not hide the type, they merely hide
> that type’s members and its declaration. For example, this means values of
> hidden types are still allowed. Unlike the existing implementation, using
> their members is forbidden.
>
> // Imports `DateFormatter` but the declaration of `Date` is hidden.import Foundation using (DateFormatter)
> var d = DateFormatter().date(from: "...") // Validvar dt : Date = DateFormatter().date(from: "...") // Invalid: Cannot use name of hidden type.
> d.addTimeInterval(5.0) // Invalid: Cannot use members of hidden type.
>
> Import directives chain to one another and can be used to create a
> fine-grained module import:
>
> // This imports Swift.Int, Swift.Double, and Swift.String but hides Swift.String.UTF8Viewimport Swift using (String, Int, Double)
>              hiding (String.UTF8View)
>
> Directive chaining occurs left-to-right:
>
> // This says to 1) Use Int 2) Hide String 3) rename Double to Triple.  It is invalid// because 1) Int is available 2) String is not, error.import Swift using (Int) hiding (String)// Valid.  This will be merged as `using (Int)`import Swift using () using (Int)// Valid.  This will be merged as `hiding (String, Double)`import Swift hiding (String) hiding (Double) hiding ()// Valid (if redundant). This will be merged as `using ()`import Swift using (String) hiding (String)
>
> Because import directives are file-local, they will never be exported
> along with the module that declares them.
>
> <https://gist.github.com/CodaFi/42e5e5e94d857547abc381d9a9d0afd6#impact-on-existing-code>Impact
> on existing code
>
> Existing code that is using qualified module import syntax (import
> {func|class|typealias|class|struct|enum|protocol} <qualified-name>) will
> be deprecated and should be removed or migrated.
>
> <https://gist.github.com/CodaFi/42e5e5e94d857547abc381d9a9d0afd6#alternatives-considered>Alternatives
> considered
> A previous iteration of this proposal introduced an operation to allow the
> renaming of identifiers, especially members. The original intent was to
> allow file-local modifications of APIs consumers felt needed to conform to
> their specific coding style. On review, we felt the feature was not as
> significant as to warrant inclusion and was ripe for abuse in large
> projects.
>
> _______________________________________________
> swift-evolution mailing list
> swift-evolution at swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.swift.org/pipermail/swift-evolution/attachments/20160720/9b1d8a08/attachment.html>


More information about the swift-evolution mailing list