Skip to content

Commit

Permalink
Merge branch 'armcknight/feat(user-feedback)/iteration' into armcknig…
Browse files Browse the repository at this point in the history
…ht/feat(user-feedback)/envelope
  • Loading branch information
armcknight committed Dec 7, 2024
2 parents 5038ff5 + 4d04a27 commit f84c1c7
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 16 deletions.
10 changes: 8 additions & 2 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,16 @@ jobs:
name: 'Release a new version'
needs: prepare_framework
steps:
- name: Get auth token
id: token
uses: actions/create-github-app-token@5d869da34e18e7287c1daad50e0b8ea0f506ce69 # v1.11.0
with:
app-id: ${{ vars.SENTRY_RELEASE_BOT_CLIENT_ID }}
private-key: ${{ secrets.SENTRY_RELEASE_BOT_PRIVATE_KEY }}
- name: Check out current commit (${{ github.sha }})
uses: actions/checkout@v4
with:
token: ${{ secrets.GH_RELEASE_PAT }}
token: ${{ steps.token.outputs.token }}
fetch-depth: 0

- uses: actions/download-artifact@v4
Expand All @@ -61,7 +67,7 @@ jobs:
- name: Prepare release
uses: getsentry/action-prepare-release@v1
env:
GITHUB_TOKEN: ${{ secrets.GH_RELEASE_PAT }}
GITHUB_TOKEN: ${{ steps.token.outputs.token }}
with:
version: ${{ github.event.inputs.version }}
force: ${{ github.event.inputs.force }}
Expand Down
59 changes: 45 additions & 14 deletions Samples/iOS-Swift/iOS-Swift-UITests/UserFeedbackUITests.swift
Original file line number Diff line number Diff line change
@@ -1,11 +1,18 @@
//swiftlint:disable todo

import XCTest

class UserFeedbackUITests: BaseUITest {
override var automaticallyLaunchAndTerminateApp: Bool { false }

override func setUp() {
super.setUp()

app.launchArguments.append(contentsOf: [
"--io.sentry.feedback.auto-inject-widget",
"--io.sentry.feedback.no-animations",

// since the goal of these tests is only to exercise the UI of the widget and form, disable as much as possible from the SDK to avoid any confounding factors that might fail or crash a test case
"--disable-spotlight",
"--disable-automatic-session-tracking",
"--disable-metrickit-integration",
Expand All @@ -20,13 +27,13 @@ class UserFeedbackUITests: BaseUITest {
"--disable-automatic-breadcrumbs",
"--disable-anr-tracking",
"--disable-auto-performance-tracing",
"--disable-ui-tracing",
"--io.sentry.feedback.auto-inject-widget",
"--io.sentry.feedback.no-animations"
"--disable-ui-tracing"
])
continueAfterFailure = true
}

// MARK: Tests ensuring correct appearance

func testUIElementsWithDefaults() {
launchApp(args: ["--io.sentry.feedback.all-defaults"])
// widget button text
Expand Down Expand Up @@ -90,6 +97,8 @@ class UserFeedbackUITests: BaseUITest {
XCTAssertFalse(app.staticTexts["Thy name (Required)"].exists)
}

// MARK: Tests validating happy path / successful submission

func testSubmitFullyFilledForm() throws {
launchApp(args: ["--io.sentry.feedback.all-defaults"])

Expand All @@ -107,15 +116,13 @@ class UserFeedbackUITests: BaseUITest {
sendButton.tap()

// displaying the form again ensures the widget button still works afterwards; also assert that the fields are in their default state to ensure the entered data is not persisted between displays

widgetButton.tap()

// the placeholder text is returned for XCUIElement.value
XCTAssertEqual(try XCTUnwrap(nameField.value as? String), "Your Name")
XCTAssertEqual(try XCTUnwrap(emailField.value as? String), "[email protected]")

// the UITextView doesn't hav a placeholder, it's a label on top of it. so it is actually empty
XCTAssertEqual(try XCTUnwrap(messageTextView.value as? String), "")
XCTAssertEqual(try XCTUnwrap(messageTextView.value as? String), "", "The UITextView shouldn't have any initial text functioning as a placeholder; as UITextView has no placeholder property, the \"placeholder\" is a label on top of it.")
}

func testSubmitWithOnlyRequiredFieldsFilled() {
Expand All @@ -130,7 +137,9 @@ class UserFeedbackUITests: BaseUITest {
XCTAssert(widgetButton.waitForExistence(timeout: 1))
}

func testCancelFromFormByButton() throws {
// MARK: Tests validating cancellation functions correctly

func testCancelFromFormByButton() {
launchApp(args: ["--io.sentry.feedback.all-defaults"])
widgetButton.tap()

Expand All @@ -144,18 +153,17 @@ class UserFeedbackUITests: BaseUITest {
messageTextView.tap()
messageTextView.typeText("UITest user feedback")

let cancelButton: XCUIElement = app.staticTexts["Cancel"]
cancelButton.tap()

// displaying the form again ensures the widget button still works afterwards; also assert that the fields are in their default state to ensure the entered data is not persisted between displays

widgetButton.tap()

// the placeholder text is returned for XCUIElement.value
XCTAssertEqual(try XCTUnwrap(nameField.value as? String), "Your Name")
XCTAssertEqual(try XCTUnwrap(emailField.value as? String), "[email protected]")

// the UITextView doesn't hav a placeholder, it's a label on top of it. so it is actually empty
XCTAssertEqual(try XCTUnwrap(messageTextView.value as? String), "")
XCTAssertEqual(try XCTUnwrap(messageTextView.value as? String), "", "The UITextView shouldn't have any initial text functioning as a placeholder; as UITextView has no placeholder property, the \"placeholder\" is a label on top of it.")
}

func testCancelFromFormBySwipeDown() {
Expand All @@ -174,24 +182,25 @@ class UserFeedbackUITests: BaseUITest {

// first swipe down dismisses the keyboard that's still visible from typing the above inputs
app.swipeDown(velocity: .fast)
// the cancel gesture

// the modal cancel gesture
app.swipeDown(velocity: .fast)

// the swipe dismiss animation takes an extra moment, so we need to wait for the widget to be visible again
XCTAssert(widgetButton.waitForExistence(timeout: 1))

// displaying the form again ensures the widget button still works afterwards; also assert that the fields are in their default state to ensure the entered data is not persisted between displays

widgetButton.tap()

// the placeholder text is returned for XCUIElement.value
XCTAssertEqual(try XCTUnwrap(nameField.value as? String), "Your Name")
XCTAssertEqual(try XCTUnwrap(emailField.value as? String), "[email protected]")

// the UITextView doesn't hav a placeholder, it's a label on top of it. so it is actually empty
XCTAssertEqual(try XCTUnwrap(messageTextView.value as? String), "")
XCTAssertEqual(try XCTUnwrap(messageTextView.value as? String), "", "The UITextView shouldn't have any initial text functioning as a placeholder; as UITextView has no placeholder property, the \"placeholder\" is a label on top of it.")
}

// MARK: Tests validating screenshot functionality

func testAddingAndRemovingScreenshots() {
launchApp(args: ["--io.sentry.feedback.all-defaults"])
widgetButton.tap()
Expand All @@ -203,6 +212,8 @@ class UserFeedbackUITests: BaseUITest {
XCTAssertFalse(removeScreenshotButton.isHittable)
}

// MARK: Tests validating error cases

func testSubmitWithNoFieldsFilledDefault() throws {
launchApp(args: ["--io.sentry.feedback.all-defaults"])

Expand Down Expand Up @@ -293,6 +304,24 @@ class UserFeedbackUITests: BaseUITest {
app.buttons["OK"].tap()
}

func testSubmissionErrorThenSuccessAfterFixingIssues() {
launchApp(args: ["--io.sentry.feedback.all-defaults"])
widgetButton.tap()

sendButton.tap()

XCTAssert(app.staticTexts["Error"].exists)

app.buttons["OK"].tap()

messageTextView.tap()
messageTextView.typeText("UITest user feedback")

sendButton.tap()

XCTAssert(widgetButton.waitForExistence(timeout: 1))
}

// MARK: Private

var cancelButton: XCUIElement {
Expand Down Expand Up @@ -327,3 +356,5 @@ class UserFeedbackUITests: BaseUITest {
app.buttons["io.sentry.feedback.form.remove-screenshot"]
}
}

//swiftlint:enable todo
2 changes: 2 additions & 0 deletions Sentry.podspec
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ Pod::Spec.new do |s|
'GCC_ENABLE_CPP_EXCEPTIONS' => 'YES',
'CLANG_CXX_LANGUAGE_STANDARD' => 'c++14',
'CLANG_CXX_LIBRARY' => 'libc++',
# APPLICATION_EXTENSION_API_ONLY has a side effect of exposing all `@objc` marked entities in `Sentry-Swift.h` (regardless of access level)
# This is currently needed for Sentry module to compile. Changing this to NO will break the build.
'APPLICATION_EXTENSION_API_ONLY' => 'YES',
'SWIFT_INCLUDE_PATHS' => '${PODS_TARGET_SRCROOT}/Sources/Sentry/include'
}
Expand Down

0 comments on commit f84c1c7

Please sign in to comment.