Files
swift-mirror/test/Migrator/optional_try_migration.swift
3405691582 88167e74d1 [test] diff --strip-trailing-cr is non-standard.
This flag is a GNU extension, and would cause misleading test failures
on other platforms where this extension is not available. However, the
necessity to switch line endings is only required on Windows when
testing. We could use sed to canonicalize line endings before comparing,
but that may cause higher amounts of filesystem traffic on Windows which
would slow down testing.

Instead, move the substitution for diff in SourceKit's lit.local.cfg up
to the top level, and conditionalize the substitution which has the flag
on Windows, but not on other platforms (where it should not be required).
2020-09-13 13:50:15 -04:00

113 lines
3.0 KiB
Swift

// RUN: %empty-directory(%t)
// RUN: %target-swift-frontend -c -swift-version 4 -primary-file %s -emit-migrated-file-path %t/optional_try_migration.result.swift
// RUN: %diff -u %S/optional_try_migration.swift.expected %t/optional_try_migration.result.swift
func fetchOptInt() throws -> Int? {
return 3
}
func fetchInt() throws -> Int {
return 3
}
func fetchAny() throws -> Any {
return 3
}
func testOnlyMigrateChangedBehavior() {
// No migration needed
let _ = try? fetchInt()
// Migration needed
let _ = try? fetchOptInt()
}
func testExplicitCasts() {
// No migration needed, because there's an explicit cast on the try already
let _ = (try? fetchOptInt()) as? Int
// Migration needed; the 'as? Int' is part of the sub-expression
let _ = try? fetchAny() as? Int
// No migration needed; the subexpression is non-optional so behavior has not changed
let _ = (try? fetchAny()) as? Int
// No migration needed, because there's an explicit cast on the try already
let _ = (try? fetchOptInt()) as! Int // expected-warning {{forced cast from 'Int??' to 'Int' only unwraps optionals; did you mean to use '!!'?}}
// No migration needed; the subexpression is non-optional
let _ = try? fetchAny() as! Int
// No migration needed; the subexpression is non-optional so behavior has not changed
let _ = (try? fetchAny()) as! Int
// Migration needed; the explicit cast is not directly on the try?
let _ = String(describing: try? fetchOptInt()) as Any
// No migration needed, because the try's subexpression is non-optional
let _ = String(describing: try? fetchInt()) as Any
}
func testOptionalChaining() {
struct Thing {
func fetchInt() throws -> Int { return 3 }
func fetchOptInt() throws -> Int { return 3 }
}
let thing = Thing()
let optThing: Thing? = Thing()
// Migration needed
let _ = try? optThing?.fetchInt()
// Migration needed
let _ = try? optThing?.fetchOptInt()
// No migration needed
let _ = try? optThing!.fetchOptInt()
// No migration needed, because of the explicit cast
let _ = (try? optThing?.fetchOptInt()) as? Int
// Migration needed
let _ = try? thing.fetchInt()
// Migration needed
let _ = try? thing.fetchOptInt()
// No migration needed, because of the explicit cast
let _ = (try? thing.fetchOptInt()) as! Int // expected-warning {{forced cast from 'Int?' to 'Int' only unwraps optionals; did you mean to use '!'?}}
}
func testIfLet() {
// Migration needed
if let optionalX = try? fetchOptInt(),
let x = optionalX
{
print(x)
}
// Don't change 'try?'s that haven't changed behavior
if let x = try? fetchInt(),
let y = try? fetchInt() {
print(x, y)
}
}
func testCaseMatching() {
// Migration needed
if case let x?? = try? fetchOptInt() {
print(x)
}
// No migration needed
if case let x? = try? fetchInt() {
print(x)
}
}