Skip to content
3 min read Guides Swift

What's New in Swift SDK 1.1

Swift SDK 1.1 is a small release with one aim: make it harder to point an app at the wrong server. In Swift SDK 1.0, picking the production server meant passing its URL yourself. Version 1.1 lets you name the environment instead, lets each build type carry its own key, and shows the reason a request was rejected.

A note on 1.1.0. The 1.1.0 package does not compile: its new Environment enum hides SwiftUI's @Environment inside the package's own views. Swift SDK 1.1.1 fixes that, and Up to Next Major Version from 1.0.0 or 1.1.0 installs 1.1.1. The code in this post also compiles against 1.1.1.

The short version

  • New: SwiftlyFeedback.configure(environment:key:), so you choose a server by name instead of by URL.
  • New: configureAuto(keys:) with EnvironmentAPIKeys, one key per build type.
  • New: the detail screen shows the reason a Rejected request was turned down, and Feedback has a rejectionReason property.
  • Deprecated: configureAuto(with:). It still works, with a compiler warning.
  • Watch for: the new public type is named Environment, the same name as SwiftUI's property wrapper.

Choose the server by name

A FeedbackKit API key belongs to the server it was created on. Your project lives on the production server, so its key works there and is rejected anywhere else. In 1.0 that meant writing the production URL into your configure call. In 1.1 you write the environment:

// Swift SDK 1.0
SwiftlyFeedback.configure(
    with: "sf_your_api_key",
    baseURL: URL(string: "https://api.feedbackkit.prod.swiftly-developed.com/api/v1")!
)

// Swift SDK 1.1
SwiftlyFeedback.configure(environment: .production, key: "sf_your_api_key")

The environments are .production, .testflight and .development. In 1.1, .development means a FeedbackKit server running on your own Mac at localhost:8080, which matters to you if you run the server yourself. For a project created in the FeedbackKit admin app or the web dashboard, use .production in every build, DEBUG included.

One key per build type

If you do keep projects on more than one server, configureAuto(keys:) picks the key and the server from the build:

SwiftlyFeedback.configureAuto(keys: EnvironmentAPIKeys(
    debug: "sf_local_key",
    testflight: "sf_staging_key",
    production: "sf_production_key"
))
BuildServerKey
DEBUGlocalhost:8080debug, or testflight when debug is nil
TestFlightStagingtestflight
App StoreProductionproduction

The SDK tells TestFlight from App Store builds by asking StoreKit for the app's transaction environment. The older configureAuto(with:), which used one key for all three servers, is now deprecated: a key belongs to one server, so with a single key the other build types could not reach your project.

If you would rather decide in code, the doc comments suggest compiler flags. Add a TESTFLIGHT flag to the build configuration you upload to TestFlight, under Active Compilation Conditions, and branch on it:

#if TESTFLIGHT
SwiftlyFeedback.configure(environment: .testflight, key: "sf_staging_key")
#else
SwiftlyFeedback.configure(environment: .production, key: "sf_production_key")
#endif

Rejection reasons on the detail screen

When your team rejects a request, it can say why, and that reason already goes into the status email. From 1.1, FeedbackDetailView also shows it, under a "Reason for Rejection" heading below the description. The value is on Feedback.rejectionReason if you draw your own screens, and the public Feedback initialiser gained a matching rejectionReason parameter with a default of nil, so existing previews keep compiling.

Telling people why something will not be built is half of closing the loop. Closing the loop with status emails covers the other half.

How FeedbackKit fits in

Statuses are where your team's decisions become visible to your users. In the admin apps and the web dashboard, your team moves each request through the same six statuses that the SDK shows, and can sort the list by the MRR your app reports for each user. Here is how that looks in FeedbackKit, with sample data from a fictional hiking app:

Statuses your users can see

Six built-in statuses on every plan: Pending, Approved, In Progress, TestFlight, Completed and Rejected. Requests can be sorted by the total MRR of the users behind them.

Upgrading from 1.0

  • Set the package rule to Up to Next Minor Version from 1.1.1 and update. The 1.1.0 package does not compile, and Up to Next Major now resolves 1.3.0, which has source-breaking changes despite its minor number.
  • Replace configure(with:baseURL:) with configure(environment: .production, key:) if you like. The old call still works.
  • Replace configureAuto(with:) with configureAuto(keys:) or with an explicit configure(environment:key:), to clear the deprecation warning.
  • Check files that import both SwiftUI and SwiftlyFeedbackKit. The environment enum is a public type named Environment, so in those files the compiler can no longer tell which one @Environment(\.dismiss) means and reports "'Environment' is ambiguous for type lookup". Write @SwiftUI.Environment(\.dismiss) there.

The full reference is in the Swift SDK docs. The next release is Swift SDK 1.1.1. If you are starting today, use the current SwiftUI tutorial.

Every plan includes the Swift SDK. Start free and add the board to your app.

Keep reading

Collect feedback in your own app

FeedbackKit ships SDKs for Swift, Kotlin, React Native, Flutter and JavaScript, and syncs what your users ask for into the tracker your team already uses.