Skip to content

Commit

Permalink
feat: add option to disable screen view usage (#190)
Browse files Browse the repository at this point in the history
  • Loading branch information
mrehan27 authored Jan 6, 2025
1 parent 4b905cd commit b4a4fed
Show file tree
Hide file tree
Showing 15 changed files with 176 additions and 40 deletions.
2 changes: 1 addition & 1 deletion android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ android {
dependencies {
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
// Customer.io SDK
def cioVersion = "4.4.1"
def cioVersion = "4.5.0"
implementation "io.customer.android:datapipelines:$cioVersion"
implementation "io.customer.android:messaging-push-fcm:$cioVersion"
implementation "io.customer.android:messaging-in-app:$cioVersion"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import io.customer.customer_io.bridge.nativeNoArgs
import io.customer.customer_io.messaginginapp.CustomerIOInAppMessaging
import io.customer.customer_io.messagingpush.CustomerIOPushMessaging
import io.customer.customer_io.utils.getAs
import io.customer.datapipelines.config.ScreenView
import io.customer.sdk.CustomerIO
import io.customer.sdk.CustomerIOBuilder
import io.customer.sdk.core.di.SDKComponent
Expand Down Expand Up @@ -182,13 +183,15 @@ class CustomerIOPlugin : FlutterPlugin, MethodCallHandler, ActivityAware {
val logLevelRawValue = args.getAs<String>("logLevel")
val regionRawValue = args.getAs<String>("region")
val givenRegion = regionRawValue.let { Region.getRegion(it) }
val screenViewRawValue = args.getAs<String>("screenViewUse")

CustomerIOBuilder(
applicationContext = application,
cdpApiKey = cdpApiKey
).apply {
logLevelRawValue?.let { logLevel(CioLogLevel.getLogLevel(it)) }
regionRawValue?.let { region(givenRegion) }
screenViewRawValue?.let { screenViewUse(ScreenView.getScreenView(it)) }

args.getAs<String>("migrationSiteId")?.let(::migrationSiteId)
args.getAs<Boolean>("autoTrackDeviceAttributes")?.let(::autoTrackDeviceAttributes)
Expand Down
2 changes: 2 additions & 0 deletions apps/amiapp_flutter/.gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,11 @@
*.swp
.DS_Store
.atom/
.build/
.buildlog/
.history
.svn/
.swiftpm/
migrate_working_dir/
fastlane/report.xml

Expand Down
2 changes: 1 addition & 1 deletion apps/amiapp_flutter/ios/Podfile
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# -------------
# This code only used internally for Customer.io testing
require 'open-uri'
IO.copy_stream(URI.open('https://raw.githubusercontent.com/customerio/customerio-ios/v2/scripts/cocoapods_override_sdk.rb'), "/tmp/override_cio_sdk.rb")
IO.copy_stream(URI.open('https://raw.githubusercontent.com/customerio/customerio-ios/main/scripts/cocoapods_override_sdk.rb'), "/tmp/override_cio_sdk.rb")
load "/tmp/override_cio_sdk.rb"
# end of internal Customer.io testing code
# -------------
Expand Down
1 change: 1 addition & 0 deletions apps/amiapp_flutter/lib/src/customer_io.dart
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@ class CustomerIOSDK extends ChangeNotifier {
cdnHost: _sdkConfig?.cdnHost,
flushAt: _sdkConfig?.flushAt,
flushInterval: _sdkConfig?.flushInterval?.toInt(),
screenViewUse: _sdkConfig?.screenViewUse,
inAppConfig: inAppConfig,
),
);
Expand Down
40 changes: 19 additions & 21 deletions apps/amiapp_flutter/lib/src/data/config.dart
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ class CustomerIOSDKConfig {
final String? cdnHost;
final int? flushAt;
final int? flushInterval;
final ScreenView? screenViewUse;
final InAppConfig? inAppConfig;
final PushConfig pushConfig;

Expand All @@ -29,6 +30,7 @@ class CustomerIOSDKConfig {
this.cdnHost,
this.flushAt,
this.flushInterval,
this.screenViewUse,
this.inAppConfig,
PushConfig? pushConfig,
}) : pushConfig = pushConfig ?? PushConfig();
Expand All @@ -45,10 +47,11 @@ class CustomerIOSDKConfig {
throw ArgumentError('cdpApiKey cannot be null');
}

final region = prefs.getString(_PreferencesKey.region) != null
? Region.values.firstWhere(
(e) => e.name == prefs.getString(_PreferencesKey.region))
: null;
final region =
prefs.getEnumValueFromPrefs(_PreferencesKey.region, Region.values);
final screenViewUse = prefs.getEnumValueFromPrefs(
_PreferencesKey.screenViewUse, ScreenView.values);

return CustomerIOSDKConfig(
cdpApiKey: cdpApiKey,
migrationSiteId: prefs.getString(_PreferencesKey.migrationSiteId),
Expand All @@ -63,27 +66,11 @@ class CustomerIOSDKConfig {
cdnHost: prefs.getString(_PreferencesKey.cdnHost),
flushAt: prefs.getInt(_PreferencesKey.flushAt),
flushInterval: prefs.getInt(_PreferencesKey.flushInterval),
screenViewUse: screenViewUse,
inAppConfig: InAppConfig(
siteId: prefs.getString(_PreferencesKey.migrationSiteId) ?? ""),
);
}

Map<String, dynamic> toMap() {
return {
'cdpApiKey': cdpApiKey,
'migrationSiteId': migrationSiteId,
'region': region?.name,
'logLevel': debugModeEnabled,
'screenTrackingEnabled': screenTrackingEnabled,
'autoTrackDeviceAttributes': autoTrackDeviceAttributes,
'apiHost': apiHost,
'cdnHost': cdnHost,
'flushAt': flushAt,
'flushInterval': flushInterval,
'inAppConfig': inAppConfig?.toMap(),
'pushConfig': pushConfig.toMap(),
};
}
}

extension ConfigurationPreferencesExtensions on SharedPreferences {
Expand Down Expand Up @@ -128,8 +115,18 @@ extension ConfigurationPreferencesExtensions on SharedPreferences {
result = result &&
await setOrRemoveInt(
_PreferencesKey.flushInterval, config.flushInterval);
result = result &&
await setOrRemoveString(
_PreferencesKey.screenViewUse, config.screenViewUse?.name);
return result;
}

T? getEnumValueFromPrefs<T extends Enum>(String key, List<T> values) {
final storedValue = getString(key);
if (storedValue == null) return null;

return values.firstWhere((e) => e.name == storedValue);
}
}

class _PreferencesKey {
Expand All @@ -143,4 +140,5 @@ class _PreferencesKey {
static const cdnHost = 'CDN_HOST';
static const flushAt = 'FLUSH_AT';
static const flushInterval = 'FLUSH_INTERVAL';
static const screenViewUse = 'SCREEN_VIEW_USE';
}
17 changes: 17 additions & 0 deletions apps/amiapp_flutter/lib/src/screens/settings.dart
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import 'package:customer_io/config/in_app_config.dart';
import 'package:customer_io/customer_io.dart';
import 'package:customer_io/customer_io_enums.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:go_router/go_router.dart';
Expand Down Expand Up @@ -44,6 +45,7 @@ class _SettingsScreenState extends State<SettingsScreen> {
late final TextEditingController _flushAtValueController;
late final TextEditingController _flushIntervalValueController;

late ScreenView _screenViewUse;
late bool _featureTrackScreens;
late bool _featureTrackDeviceAttributes;
late bool _featureDebugMode;
Expand All @@ -65,6 +67,7 @@ class _SettingsScreenState extends State<SettingsScreen> {
TextEditingController(text: cioConfig?.flushAt?.toString());
_flushIntervalValueController =
TextEditingController(text: cioConfig?.flushInterval?.toString());
_screenViewUse = cioConfig?.screenViewUse ?? ScreenView.all;
_featureTrackScreens = cioConfig?.screenTrackingEnabled ?? true;
_featureTrackDeviceAttributes =
cioConfig?.autoTrackDeviceAttributes ?? true;
Expand All @@ -85,6 +88,7 @@ class _SettingsScreenState extends State<SettingsScreen> {
cdnHost: _cdnHostValueController.text.trim().nullIfEmpty(),
flushAt: _flushAtValueController.text.trim().toIntOrNull(),
flushInterval: _flushIntervalValueController.text.trim().toIntOrNull(),
screenViewUse: _screenViewUse,
screenTrackingEnabled: _featureTrackScreens,
autoTrackDeviceAttributes: _featureTrackDeviceAttributes,
debugModeEnabled: _featureDebugMode,
Expand Down Expand Up @@ -119,6 +123,7 @@ class _SettingsScreenState extends State<SettingsScreen> {
_flushAtValueController.text = defaultConfig.flushAt?.toString() ?? '';
_flushIntervalValueController.text =
defaultConfig.flushInterval?.toString() ?? '';
_screenViewUse = defaultConfig.screenViewUse ?? ScreenView.all;
_featureTrackScreens = defaultConfig.screenTrackingEnabled;
_featureTrackDeviceAttributes =
defaultConfig.autoTrackDeviceAttributes ?? true;
Expand Down Expand Up @@ -287,6 +292,18 @@ class _SettingsScreenState extends State<SettingsScreen> {
updateState: ((value) =>
setState(() => _featureDebugMode = value)),
),
const SizedBox(height: 8),
ChoiceSettingsFormField<ScreenView>(
labelText: 'ScreenView Use',
semanticsLabel: 'ScreenView options',
value: _screenViewUse,
options: ScreenView.values,
updateState: (ScreenView selected) {
setState(() {
_screenViewUse = selected;
});
},
),
],
),
),
Expand Down
4 changes: 4 additions & 0 deletions apps/amiapp_flutter/lib/src/utils/extensions.dart
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,10 @@ extension AmiAppStringExtensions on String {
(min == null || value >= min) &&
(max == null || value <= max);
}

String capitalize() {
return '${this[0].toUpperCase()}${substring(1)}';
}
}

extension LocationExtensions on GoRouter {
Expand Down
96 changes: 96 additions & 0 deletions apps/amiapp_flutter/lib/src/widgets/settings_form_field.dart
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import 'package:flutter/material.dart';

import '../components/text_field_label.dart';
import '../utils/extensions.dart';

class TextSettingsFormField extends StatelessWidget {
const TextSettingsFormField({
Expand Down Expand Up @@ -121,3 +122,98 @@ class SwitchSettingsFormField extends StatelessWidget {
);
}
}

class ChoiceSettingsFormField<T> extends StatelessWidget {
const ChoiceSettingsFormField({
super.key,
required this.labelText,
required this.semanticsLabel,
required this.value,
required this.updateState,
required this.options,
this.enabled = true,
});

final String labelText;
final String semanticsLabel;
final T value;
final List<T> options;
final void Function(T) updateState;
final bool enabled;

@override
Widget build(BuildContext context) {
const double defaultBorderRadius = 8.0;

return UnmanagedRestorationScope(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
labelText,
style: Theme.of(context).textTheme.bodyMedium,
),
const SizedBox(height: 12),
Container(
decoration: BoxDecoration(
color: enabled
? Theme.of(context).colorScheme.surface
: Theme.of(context)
.colorScheme
.onSurface
.withValues(alpha: 0.12),
borderRadius: BorderRadius.circular(defaultBorderRadius),
),
child: Row(
children: options.map((option) {
final bool isSelected = option == value;
return Expanded(
child: GestureDetector(
onTap: enabled
? () {
updateState(option);
}
: null,
child: Container(
padding: const EdgeInsets.symmetric(vertical: 12.0),
decoration: BoxDecoration(
color: isSelected
? Theme.of(context).colorScheme.primary
: Theme.of(context)
.colorScheme
.surfaceContainerHighest,
borderRadius: BorderRadius.only(
topLeft: option == options.first
? const Radius.circular(defaultBorderRadius)
: Radius.zero,
bottomLeft: option == options.first
? const Radius.circular(defaultBorderRadius)
: Radius.zero,
topRight: option == options.last
? const Radius.circular(defaultBorderRadius)
: Radius.zero,
bottomRight: option == options.last
? const Radius.circular(defaultBorderRadius)
: Radius.zero,
),
),
child: Text(
option.toString().split('.').last.capitalize(),
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.bodyMedium?.copyWith(
color: isSelected
? Theme.of(context).colorScheme.onPrimary
: Theme.of(context).colorScheme.onSurface,
),
),
),
),
);
}).toList(),
),
),
],
),
);
}
}
Loading

0 comments on commit b4a4fed

Please sign in to comment.