-
Notifications
You must be signed in to change notification settings - Fork 47
feat: add proactive bug reporting #559
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: dev
Are you sure you want to change the base?
Changes from 8 commits
03309e4
c2725a6
c3c3ddc
dffe0fb
fbdfe4b
0221b01
be71993
9bdf513
6082602
5c86b92
fe4786e
dbee490
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,7 @@ | ||
package com.instabug.flutter; | ||
|
||
import static org.mockito.ArgumentMatchers.any; | ||
import static org.mockito.ArgumentMatchers.argThat; | ||
import static org.mockito.ArgumentMatchers.eq; | ||
import static org.mockito.Mockito.mock; | ||
import static org.mockito.Mockito.mockStatic; | ||
|
@@ -194,4 +195,24 @@ public void testSetCommentMinimumCharacterCount() { | |
|
||
mBugReporting.verify(() -> BugReporting.setCommentMinimumCharacterCount(limit.intValue(), BugReporting.ReportType.BUG, BugReporting.ReportType.QUESTION)); | ||
} | ||
|
||
@Test | ||
public void testSetProactiveReportingConfigurations() { | ||
// given | ||
boolean enabled = true; | ||
long gapBetweekDialogs = 20; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I believe there's a small typo here. It should be |
||
long modeDelay = 30; | ||
|
||
// when | ||
api.setProactiveReportingConfigurations(enabled, gapBetweekDialogs, modeDelay); | ||
|
||
// then | ||
mBugReporting.verify(() -> BugReporting.setProactiveReportingConfigurations(argThat(config -> | ||
config.getModalsGap() == gapBetweekDialogs && | ||
config.getDetectionGap() == modeDelay && | ||
config.isEnabled() == enabled | ||
))); | ||
|
||
|
||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,66 @@ | ||
import 'package:flutter/foundation.dart'; | ||
|
||
class ProactiveReportingConfigs { | ||
final int gapBetweenModals; // Time in seconds | ||
final int modalDelayAfterDetection; // Time in seconds | ||
final bool enabled; | ||
|
||
// Private constructor to ensure it can only be created through the builder | ||
const ProactiveReportingConfigs._({ | ||
required this.gapBetweenModals, | ||
required this.modalDelayAfterDetection, | ||
required this.enabled, | ||
}); | ||
} | ||
|
||
// Builder class for ProactiveReportingConfigs | ||
class ProactiveReportingConfigsBuilder { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. would you please tell me why have we opted into Builder pattern here instead of named parameters with default value? |
||
int gapBetweenModals = 30; // Default: 30 seconds | ||
int modalDelayAfterDetection = 15; // Default: 15 seconds | ||
bool enabled = true; // Default: enabled | ||
|
||
// Logger method to handle logging | ||
void _logWarning(String message) { | ||
if (kDebugMode) { | ||
print('Warning: $message'); | ||
} | ||
} | ||
|
||
/// Controls the time gap between showing 2 proactive reporting dialogs in seconds | ||
ProactiveReportingConfigsBuilder setGapBetweenModals(int gap) { | ||
if (gap <= 0) { | ||
_logWarning( | ||
'gapBetweenModals must be a positive number. Using default value of 30 seconds.', | ||
); | ||
return this; | ||
} | ||
gapBetweenModals = gap; | ||
return this; | ||
} | ||
|
||
/// Controls the time gap between detecting a frustrating experience | ||
ProactiveReportingConfigsBuilder setModalDelayAfterDetection(int delay) { | ||
if (delay <= 0) { | ||
_logWarning( | ||
'modalDelayAfterDetection must be a positive number. Using default value of 15 seconds.', | ||
); | ||
return this; | ||
} | ||
modalDelayAfterDetection = delay; | ||
return this; | ||
} | ||
|
||
/// Controls the state of the feature | ||
ProactiveReportingConfigsBuilder isEnabled(bool value) { | ||
enabled = value; | ||
return this; | ||
} | ||
|
||
ProactiveReportingConfigs build() { | ||
return ProactiveReportingConfigs._( | ||
gapBetweenModals: gapBetweenModals, | ||
modalDelayAfterDetection: modalDelayAfterDetection, | ||
enabled: enabled, | ||
); | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could you please explain to me why are we explicitly running our logic using the
ThreadManager.runOnMainThread(...)
api?