Client Usage¶
UsageBroker
¶
Start¶
try {
UsageBroker.start(this, getApplicationContext(), "1.0", true);
} catch (Exception ex) {
sLogger.error(ex.getMessage());
}
try {
UsageBroker.start(this, getApplicationContext(), "1.0", true);
} catch (Exception ex) {
sLogger.error(ex.getMessage());
}
Upload¶
AppUsageUploader.addUploadListener(new AppUsageUploader.UploadListener() {
@Override
public void onSuccess() {
sLogger.debug("Usage upload complete, time taken (in nanos): " + (System.nanoTime() - startTime));
}
@Override
public void onError(Throwable error) {
Toast.makeText(getActivity(), "Upload Err:\n"+error.getMessage(), Toast.LENGTH_LONG).show();
if (error instanceof HttpException) {
sLogger.debug("Upload server error: {}, code = {}",
((HttpException) error).message(), ((HttpException) error).code());
} else {
sLogger.debug("Upload error: {}", error.getMessage());
}
}
@Override
public void onProgress(int i) {
sLogger.debug("Usage upload progress: " + i);
}
});
UsageBroker.upload(getApplicationContext(), false);
AppUsageUploader.addUploadListener(object : AppUsageUploader.UploadListener {
override fun onSuccess() {
sLogger.debug("Usage upload complete, time taken (in nanos): " + (System.nanoTime() - startTime))
}
override fun onError(error: Throwable) {
Toast.makeText(activity, "Upload Err:\n" + error.message, Toast.LENGTH_LONG).show()
if (error is HttpException) {
sLogger.debug("Upload server error: {}, code = {}",
error.message(), error.code())
} else {
sLogger.debug("Upload error: {}", error.message)
}
}
override fun onProgress(i: Int) {
sLogger.debug("Usage upload progress: $i")
}
})
UsageBroker.upload(getApplicationContext(), false)
Initialize AppUsage
and Its Upload Callback¶
// Init EncryptionUtil API for key generation using user-provided passcode
EncryptionUtil.initialize(context);
AppUsage.initialize(context, USAGE_STORE_NAME,
EncryptionUtil.getEncryptionKey(USAGE_KEY_ALIAS));
AppUsageUploader.addUploadListener(
new AppUsageUploader.UploadListener() {
// Executes on UI thread
@Override
public void onSuccess() {
logger.debug("AppUsage data uploaded successfully.");
}
// Executes on UI thread
@Override
public void onError(Throwable e) {
if (e instanceof HttpException) {
logger.error("AppUsage upload failed. Message: {}, http code: {}",
((HttpException) e).message(), ((HttpException) e).code());
} else {
logger.error("AppUsage upload failed: {}", e.getMessage());
}
}
// Executes on UI thread
@Override
public void onProgress(int percentUploaded) {
logger.debug("AppUsage {}% uploaded.", percentUploaded);
}
});
// Init EncryptionUtil API for key generation using user-provided passcode
EncryptionUtil.initialize(context!!)
AppUsage.initialize(context!!, USAGE_STORE_NAME, SettingsProvider.get(),
EncryptionUtil.getEncryptionKey(USAGE_KEY_ALIAS))
AppUsageUploader.addUploadListener(
object : AppUsageUploader.UploadListener {
// Executes on UI thread
override fun onSuccess() {
logger.debug("AppUsage data uploaded successfully.")
}
// Executes on UI thread
override fun onError(e: Throwable) {
if (e is HttpException) {
logger.error("AppUsage upload failed. Message: {}, http code: {}",
e.message(), e.code())
} else {
logger.error("AppUsage upload failed: {}", e.message)
}
}
// Executes on UI thread
override fun onProgress(percentUploaded: Int) {
logger.debug("AppUsage {}% uploaded.", percentUploaded)
}
})
Check if AppUsage
Upload Is Enabled on the Server¶
final Settings settings = new Settings();
// Invoke from UI thread
settings.load(Settings.SettingTarget.APPLICATION,
Settings.KeyPath.USAGEPOLICY,
new Settings.CallbackListener() {
// Executes on UI thread
@Override
public void onSuccess(@NonNull JSONObject settingsData) {
try {
boolean valueForDataCollectionEnabled = settingsData
.getBoolean("dataCollectionEnabled");
logger.debug("AppUsage Upload enabled: {}",
valueForDataCollectionEnabled);
} catch (JSONException ex) {
// Likely "No value for usagePolicy"
// which means Client Usage is not enabled for the appid
logger.error("Unexpected response: {}, error: {} ", settingsData, ex.getMessage());
}
}
// Executes on UI thread
@Override
public void onError(@NonNull Throwable e) {
// com.sap.cloud.mobile.foundation.networking.HttpException
if (e instanceof HttpException) {
logger.error("Settings load failed. Message: {}, http code: {}",
((HttpException) e).message(), ((HttpException) e).code());
} else {
logger.error("Settings load failed: ", e.getMessage());
}
}
});
val settings = Settings()
// Invoke from UI thread
settings.load(Settings.SettingTarget.APPLICATION,
Settings.KeyPath.USAGEPOLICY,
object : Settings.CallbackListener {
// Executes on UI thread
override fun onSuccess(settingsData: JSONObject) {
try {
val valueForDataCollectionEnabled = settingsData
.getBoolean("dataCollectionEnabled")
logger.debug("AppUsage Upload enabled: {}",
valueForDataCollectionEnabled)
} catch (ex: JSONException) {
// Likely "No value for usagePolicy"
// which means Client Usage is not enabled for the appid
logger.error("Unexpected response: {}, error: {} ", settingsData, ex.message)
}
}
// Executes on UI thread
override fun onError(e: Throwable) {
// com.sap.cloud.mobile.foundation.networking.HttpException
if (e is HttpException) {
logger.error("Settings load failed. Message: {}, http code: {}",
e.message(), e.code())
} else {
logger.error("Settings load failed: ", e.message)
}
}
})
Record AppUsage
Data and Upload to the Server¶
// Uses default targetID
AppUsage.sessionStart();//Session start is usually when app is launched or activity resumed
//Record an event with duration, unit is milliseconds (always, cannot be changed)
AppUsage.event("screens", "login", 10L,
new AppUsageInfo().screen("welcome").action("click_ok"));
AppUsage.event("screens", "orders", 30L,
new AppUsageInfo().screen("orders_list").action("get_orders"));
// Log an event with start and end markers, duration is calculated automatically
AppUsage.eventStart("operations", "orders",
new AppUsageInfo().screen("create_order"));
AppUsage.eventEnd("operations", "orders",
new AppUsageInfo().screen("create_order").value("submission_id:123"));
// Recording duration and count of an aggregate measure
AppUsage.event("views", "orders", 10L,
new AppUsageInfo().screen("orders_page").measurement("orders_created").value("1"));
//recording an event in a misc category
AppUsage.event("views", "settings", 2L,
new AppUsageInfo().screen("settings_page").others("settings_modified"));
// End session when app is put in background or closed
AppUsage.sessionEnd();
// Upload usage data at a later time depending on app requirements and end-user requests
// Must be invoked from UI thread
AppUsageUploader.upload(ClientProvider.get());
// Uses default targetID
AppUsage.sessionStart()//Session start is usually when app is launched or activity resumed
//Record an event with duration, unit is milliseconds (always, cannot be changed)
AppUsage.event("screens", "login", 10L,
AppUsageInfo().screen("welcome").action("click_ok"))
AppUsage.event("screens", "orders", 30L,
AppUsageInfo().screen("orders_list").action("get_orders"))
// Log an event with start and end markers, duration is calculated automatically
AppUsage.eventStart("operations", "orders",
AppUsageInfo().screen("create_order"))
AppUsage.eventEnd("operations", "orders",
AppUsageInfo().screen("create_order").value("submission_id:123"))
// Recording duration and count of an aggregate measure
AppUsage.event("views", "orders", 10L,
AppUsageInfo().screen("orders_page").measurement("orders_created").value("1"))
//recording an event in a misc category
AppUsage.event("views", "settings", 2L,
AppUsageInfo().screen("settings_page").others("settings_modified"))
// End session when app is put in background or closed
AppUsage.sessionEnd()
// Upload usage data at a later time depending on app requirements and end-user requests
// Must be invoked from UI thread
AppUsageUploader.upload()
Last update: April 14, 2021