diff --git a/Gemfile.lock b/Gemfile.lock index cb9b0d9c4f..833070354e 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,11 +1,12 @@ GIT remote: https://github.com/bugsnag/maze-runner - revision: 24f53756011b1247a166b70fe65ddf1c40b4fc89 + revision: 6f5af2c98c6fa1cfb07d6466a5cf3eaca5dcbc90 specs: bugsnag-maze-runner (1.0.0) cucumber (~> 3.1.0) cucumber-expressions (= 5.0.15) minitest (~> 5.0) + os (~> 1.0.0) rack (~> 2.0.0) rake (~> 12.3.0) test-unit (~> 3.2.0) @@ -34,17 +35,18 @@ GEM cucumber-wire (0.0.1) diff-lcs (1.3) gherkin (5.1.0) - method_source (0.9.0) + method_source (0.9.2) minitest (5.11.3) multi_json (1.13.1) multi_test (0.1.2) + os (1.0.0) power_assert (1.1.3) - pry (0.11.3) + pry (0.12.2) coderay (~> 1.1.0) method_source (~> 0.9.0) - rack (2.0.5) - rake (12.3.1) - test-unit (3.2.8) + rack (2.0.6) + rake (12.3.2) + test-unit (3.2.9) power_assert PLATFORMS @@ -55,4 +57,4 @@ DEPENDENCIES pry BUNDLED WITH - 1.16.2 + 1.16.1 diff --git a/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/NewSessionScenario.kt b/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/NewSessionScenario.kt new file mode 100644 index 0000000000..4f519bd3d2 --- /dev/null +++ b/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/NewSessionScenario.kt @@ -0,0 +1,37 @@ +package com.bugsnag.android.mazerunner.scenarios + +import android.content.Context +import com.bugsnag.android.Bugsnag +import com.bugsnag.android.Configuration +import android.os.Handler +import android.os.HandlerThread + +/** + * Sends an exception after stopping the session + */ +internal class NewSessionScenario(config: Configuration, + context: Context) : Scenario(config, context) { + init { + config.setAutoCaptureSessions(false) + } + + override fun run() { + super.run() + val client = Bugsnag.getClient() + val thread = HandlerThread("HandlerThread") + thread.start() + + Handler(thread.looper).post { + // send 1st exception which should include session info + client.startSession() + client.notifyBlocking(generateException()) + + // stop tracking the existing session + client.stopSession() + + // send 2nd exception which should contain new session info + client.startSession() + client.notifyBlocking(generateException()) + } + } +} diff --git a/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/ResumedSessionScenario.kt b/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/ResumedSessionScenario.kt new file mode 100644 index 0000000000..8ce6a97bc6 --- /dev/null +++ b/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/ResumedSessionScenario.kt @@ -0,0 +1,35 @@ +package com.bugsnag.android.mazerunner.scenarios + +import android.content.Context +import com.bugsnag.android.Bugsnag +import com.bugsnag.android.Configuration +import android.os.Handler +import android.os.HandlerThread + +/** + * Sends 2 exceptions, 1 before resuming a session, and 1 after resuming a session. + */ +internal class ResumedSessionScenario(config: Configuration, + context: Context) : Scenario(config, context) { + init { + config.setAutoCaptureSessions(false) + } + + override fun run() { + super.run() + val client = Bugsnag.getClient() + val thread = HandlerThread("HandlerThread") + thread.start() + + Handler(thread.looper).post { + // send 1st exception + client.startSession() + client.notifyBlocking(generateException()) + + // send 2nd exception after resuming a session + client.stopSession() + client.resumeSession() + client.notifyBlocking(generateException()) + } + } +} diff --git a/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/StoppedSessionScenario.kt b/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/StoppedSessionScenario.kt new file mode 100644 index 0000000000..c3450a0ba9 --- /dev/null +++ b/features/fixtures/mazerunner/src/main/java/com/bugsnag/android/mazerunner/scenarios/StoppedSessionScenario.kt @@ -0,0 +1,34 @@ +package com.bugsnag.android.mazerunner.scenarios + +import android.content.Context +import com.bugsnag.android.Bugsnag +import com.bugsnag.android.Configuration +import android.os.Handler +import android.os.HandlerThread + +/** + * Sends an exception after stopping the session + */ +internal class StoppedSessionScenario(config: Configuration, + context: Context) : Scenario(config, context) { + init { + config.setAutoCaptureSessions(false) + } + + override fun run() { + super.run() + val client = Bugsnag.getClient() + val thread = HandlerThread("HandlerThread") + thread.start() + + Handler(thread.looper).post { + // send 1st exception which should include session info + client.startSession() + client.notifyBlocking(generateException()) + + // send 2nd exception which should not include session info + client.stopSession() + client.notifyBlocking(generateException()) + } + } +} diff --git a/features/session_stopping.feature b/features/session_stopping.feature new file mode 100644 index 0000000000..35778329c7 --- /dev/null +++ b/features/session_stopping.feature @@ -0,0 +1,32 @@ +Feature: Stopping and resuming sessions + +Scenario: When a session is stopped the error has no session information + When I run "StoppedSessionScenario" + Then I should receive 3 requests + And the request 0 is valid for the session tracking API + And the request 1 is valid for the error reporting API + And the request 2 is valid for the error reporting API + And the payload field "events.0.session" is not null for request 1 + And the payload field "events.0.session" is null for request 2 + +Scenario: When a session is resumed the error uses the previous session information + When I run "ResumedSessionScenario" + Then I should receive 3 requests + And the request 0 is valid for the session tracking API + And the request 1 is valid for the error reporting API + And the request 2 is valid for the error reporting API + And the payload field "events.0.session.events.handled" equals 1 for request 1 + And the payload field "events.0.session.events.handled" equals 2 for request 2 + And the payload field "events.0.session.id" of request 1 equals the payload field "events.0.session.id" of request 2 + And the payload field "events.0.session.startedAt" of request 1 equals the payload field "events.0.session.startedAt" of request 2 + +Scenario: When a new session is started the error uses different session information + When I run "NewSessionScenario" + Then I should receive 4 requests + And the request 0 is valid for the session tracking API + And the request 1 is valid for the error reporting API + And the request 2 is valid for the session tracking API + And the request 3 is valid for the error reporting API + And the payload field "events.0.session.events.handled" equals 1 for request 1 + And the payload field "events.0.session.events.handled" equals 1 for request 3 + And the payload field "events.0.session.id" of request 1 does not equal the payload field "events.0.session.id" of request 3