Skip to content
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

Bug/sdk 3671 #577

Merged
merged 7 commits into from
Mar 19, 2024
Merged
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -2767,13 +2767,13 @@ void deviceIDCreated(String deviceId) {
StoreProvider storeProvider = StoreProvider.getInstance();

if (storeRegistry.getInAppStore() == null) {
InAppStore inAppStore = storeProvider.provideInAppStore(context, cryptHandler, deviceInfo,
InAppStore inAppStore = storeProvider.provideInAppStore(context, cryptHandler, deviceId,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@CTLalit passing deviceId instead of deviceInfo will not solve null pointer exception. I believe deviceId will also be null here.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

generated the device id and passed it as function return type, can you elaborate some null cases?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

as discussed on call this can be resolved

accountId);
storeRegistry.setInAppStore(inAppStore);
coreState.getCallbackManager().addChangeUserCallback(inAppStore);
}
if (storeRegistry.getImpressionStore() == null) {
ImpressionStore impStore = storeProvider.provideImpressionStore(context, deviceInfo,
ImpressionStore impStore = storeProvider.provideImpressionStore(context, deviceId,
accountId);
storeRegistry.setImpressionStore(impStore);
coreState.getCallbackManager().addChangeUserCallback(impStore);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,7 @@ static CoreState getCoreState(Context context, CleverTapInstanceConfig cleverTap

DeviceInfo deviceInfo = new DeviceInfo(context, config, cleverTapID, coreMetaData);
coreState.setDeviceInfo(deviceInfo);
deviceInfo.onInitDeviceInfo(cleverTapID);

CTPreferenceCache.getInstance(context, config);

Expand Down Expand Up @@ -124,14 +125,14 @@ static CoreState getCoreState(Context context, CleverTapInstanceConfig cleverTap
}
if (coreState.getDeviceInfo() != null && coreState.getDeviceInfo().getDeviceID() != null) {
if (storeRegistry.getInAppStore() == null) {
InAppStore inAppStore = storeProvider.provideInAppStore(context, cryptHandler, deviceInfo,
InAppStore inAppStore = storeProvider.provideInAppStore(context, cryptHandler, deviceInfo.getDeviceID(),
config.getAccountId());
storeRegistry.setInAppStore(inAppStore);
evaluationManager.loadSuppressedCSAndEvaluatedSSInAppsIds();
callbackManager.addChangeUserCallback(inAppStore);
}
if (storeRegistry.getImpressionStore() == null) {
ImpressionStore impStore = storeProvider.provideImpressionStore(context, deviceInfo,
ImpressionStore impStore = storeProvider.provideImpressionStore(context, deviceInfo.getDeviceID(),
config.getAccountId());
storeRegistry.setImpressionStore(impStore);
callbackManager.addChangeUserCallback(impStore);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -503,25 +503,26 @@ public static int getDeviceType(final Context context) {
this.library = null;
this.customLocale = null;
mCoreMetaData = coreMetaData;
onInitDeviceInfo(cleverTapID);
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "DeviceInfo() called");
}

public void forceNewDeviceID() {
String deviceID = generateGUID();
forceUpdateDeviceId(deviceID);
}

public void forceUpdateCustomCleverTapID(String cleverTapID) {
public String forceUpdateCustomCleverTapID(String cleverTapID) {
if (Utils.validateCTID(cleverTapID)) {
getConfigLogger()
.info(config.getAccountId(), "Setting CleverTap ID to custom CleverTap ID : " + cleverTapID);
forceUpdateDeviceId(Constants.CUSTOM_CLEVERTAP_ID_PREFIX + cleverTapID);
String id = Constants.CUSTOM_CLEVERTAP_ID_PREFIX + cleverTapID;
forceUpdateDeviceId(id);
return id;
} else {
setOrGenerateFallbackDeviceID();
String fallbackId = generateFallbackDeviceID();
removeDeviceID();
String error = recordDeviceError(Constants.INVALID_CT_CUSTOM_ID, cleverTapID, getFallBackDeviceID());
getConfigLogger().info(config.getAccountId(), error);
return fallbackId;
}
}

Expand Down Expand Up @@ -758,6 +759,7 @@ private int getLocalInAppCountFromPreference() {
}

void onInitDeviceInfo(final String cleverTapID) {
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "DeviceInfo() called");
Task<Void> taskDeviceCachedInfo = CTExecutorFactory.executors(config).ioTask();
taskDeviceCachedInfo.execute("getDeviceCachedInfo", new Callable<Void>() {
@Override
Expand All @@ -767,22 +769,21 @@ public Void call() throws Exception {
}
});

Task<Void> task = CTExecutorFactory.executors(config).ioTask();
task.addOnSuccessListener(new OnSuccessListener<Void>() {
Task<String> task = CTExecutorFactory.executors(config).ioTask();
task.addOnSuccessListener(new OnSuccessListener<String>() {
// callback on main thread
@Override
public void onSuccess(final Void aVoid) {
public void onSuccess(final String deviceId) {
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID",
"DeviceID initialized successfully!" + Thread.currentThread());
// No need to put getDeviceID() on background thread because prefs already loaded
CleverTapAPI.instanceWithConfig(context, config).deviceIDCreated(getDeviceID());
CleverTapAPI.instanceWithConfig(context, config).deviceIDCreated(deviceId);
}
});
task.execute("initDeviceID", new Callable<Void>() {
task.execute("initDeviceID", new Callable<String>() {
@Override
public Void call() throws Exception {
initDeviceID(cleverTapID);
return null;
public String call() throws Exception {
return initDeviceID(cleverTapID);
}
});

Expand All @@ -806,12 +807,7 @@ void setDeviceNetworkInfoReportingFromStorage() {

private String _getDeviceID() {
synchronized (deviceIDLock) {
if (this.config.isDefaultInstance()) {
String _new = StorageHelper.getString(this.context, getDeviceIdStorageKey(), null);
return _new != null ? _new : StorageHelper.getString(this.context, Constants.DEVICE_ID_TAG, null);
} else {
return StorageHelper.getString(this.context, getDeviceIdStorageKey(), null);
}
return StorageHelper.getString(this.context, getDeviceIdStorageKey(), null);
}
}

Expand Down Expand Up @@ -863,7 +859,7 @@ private synchronized void fetchGoogleAdID() {
}
}

private synchronized void generateDeviceID() {
private synchronized String generateDeviceID() {
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "generateDeviceID() called!");
String generatedDeviceID;
String adId = getGoogleAdID();
Expand All @@ -876,6 +872,7 @@ private synchronized void generateDeviceID() {
}
forceUpdateDeviceId(generatedDeviceID);
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "generateDeviceID() done executing!");
return generatedDeviceID;
}

private String generateGUID() {
Expand Down Expand Up @@ -905,7 +902,7 @@ private String getFallbackIdStorageKey() {
return Constants.FALLBACK_ID_TAG + ":" + this.config.getAccountId();
}

private void initDeviceID(String cleverTapID) {
private String initDeviceID(String cleverTapID) {
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "Called initDeviceID()");
//Show logging as per Manifest flag
if (config.getEnableCustomCleverTapId()) {
Expand All @@ -929,27 +926,27 @@ private void initDeviceID(String cleverTapID) {
String error = recordDeviceError(Constants.UNABLE_TO_SET_CT_CUSTOM_ID, deviceID, cleverTapID);
getConfigLogger().info(config.getAccountId(), error);
}
return;
return deviceID;
}

if (this.config.getEnableCustomCleverTapId()) {
forceUpdateCustomCleverTapID(cleverTapID);
return;
return forceUpdateCustomCleverTapID(cleverTapID);
}

if (!this.config.isUseGoogleAdId()) {
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "Calling generateDeviceID()");
generateDeviceID();
String genId = generateDeviceID();
getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "Called generateDeviceID()");
return;
return genId;
}

// fetch the googleAdID to generate GUID
//has to be called on background thread
fetchGoogleAdID();
generateDeviceID();
String genId = generateDeviceID();

getConfigLogger().verbose(config.getAccountId() + ":async_deviceID", "initDeviceID() done executing!");
return genId;
}

private String recordDeviceError(int messageCode, String... varargs) {
Expand All @@ -962,18 +959,18 @@ private void removeDeviceID() {
StorageHelper.remove(this.context, getDeviceIdStorageKey());
}

private synchronized void setOrGenerateFallbackDeviceID() {
if (getFallBackDeviceID() == null) {
synchronized (deviceIDLock) {
String fallbackDeviceID = Constants.ERROR_PROFILE_PREFIX + UUID.randomUUID().toString()
.replace("-", "");
if (fallbackDeviceID.trim().length() > 2) {
updateFallbackID(fallbackDeviceID);
} else {
getConfigLogger()
.verbose(this.config.getAccountId(), "Unable to generate fallback error device ID");
}
}
private synchronized String generateFallbackDeviceID() {
String existingId = getFallBackDeviceID();

if (existingId != null) {
return existingId;
}

synchronized (deviceIDLock) {
String fallbackDeviceID = Constants.ERROR_PROFILE_PREFIX + UUID.randomUUID().toString()
.replace("-", "");
updateFallbackID(fallbackDeviceID);
return fallbackDeviceID;
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -70,34 +70,34 @@ class StoreProvider {
*
* @param context The Android application context.
* @param cryptHandler The handler used for encryption and decryption of In-App messages.
* @param deviceInfo The information about the device.
* @param deviceId The device id for user.
* @param accountId The unique account identifier.
* @return An instance of [InAppStore].
*/
fun provideInAppStore(
context: Context,
cryptHandler: CryptHandler,
deviceInfo: DeviceInfo,
deviceId: String,
accountId: String
): InAppStore {
val prefName = constructStorePreferenceName(STORE_TYPE_INAPP, deviceInfo.deviceID, accountId)
val prefName = constructStorePreferenceName(STORE_TYPE_INAPP, deviceId, accountId)
return InAppStore(getCTPreference(context, prefName), cryptHandler)
}

/**
* Provides an instance of [ImpressionStore] using the given parameters.
*
* @param context The Android application context.
* @param deviceInfo The information about the device.
* @param deviceId The device id for user.
* @param accountId The unique account identifier.
* @return An instance of [ImpressionStore].
*/
fun provideImpressionStore(
context: Context,
deviceInfo: DeviceInfo,
deviceId: String,
accountId: String
): ImpressionStore {
val prefName = constructStorePreferenceName(STORE_TYPE_IMPRESSION, deviceInfo.deviceID, accountId)
val prefName = constructStorePreferenceName(STORE_TYPE_IMPRESSION, deviceId, accountId)
return ImpressionStore(getCTPreference(context, prefName))
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ class ImpressionManagerTest : BaseTestCase() {
`when`(deviceInfo.deviceID).thenReturn("device_id")

impressionStore = StoreProvider.getInstance().provideImpressionStore(
appCtx, deviceInfo, "account_id"
appCtx, deviceInfo.deviceID, "account_id"
)

storeRegistry.impressionStore = impressionStore
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ class StoreProviderTest {
every { storeProvider.constructStorePreferenceName(STORE_TYPE_INAPP, mockDeviceInfo.deviceID, accountId) } returns prefName

// Act
val inAppStore = storeProvider.provideInAppStore(mockContext, mockCryptHandler, mockDeviceInfo, accountId)
val inAppStore = storeProvider.provideInAppStore(mockContext, mockCryptHandler, mockDeviceInfo.deviceID, accountId)

// Assert
verify { storeProvider.getCTPreference(mockContext, prefName) }
Expand All @@ -54,7 +54,7 @@ class StoreProviderTest {
every { storeProvider.constructStorePreferenceName(STORE_TYPE_IMPRESSION, mockDeviceInfo.deviceID, accountId) } returns prefName

// Act
val impressionStore = storeProvider.provideImpressionStore(mockContext, mockDeviceInfo, accountId)
val impressionStore = storeProvider.provideImpressionStore(mockContext, mockDeviceInfo.deviceID, accountId)

// Assert
verify { storeProvider.getCTPreference(mockContext, prefName) }
Expand Down
Loading