How to maintain parse.com automatic user between application restarts? - android

Here is the scenario:
Automatic user is enabled via ParseUser.enableAutomaticUser()
I create an object, say a Todo from Offline Todo tutorial (https://github.com/ParsePlatform/OfflineTodos) and pin it:
Todo todo = new Todo();
todo.setUuidString();
todo.setTitle("test");
todo.pinInBackground();
It works fine for the first time
Now close the app (not just send it to background, close it using Recent Apps button and swipe it off the screen)
Run the app again. Here the exact same code above throws this exception:
cannot setReadAccess for a user with null id
Even though a workaround might be to sign-up the automatic user at some point before closing the app that's hardly the point of automatic users which are supposed to work offline plus there is no guarantee that the app won't be closed before our during sign-up process.
Saving the user to get an id is not an option too: not only its an online operation, you are not supposed to call save() on a user. According to documentations it should be signup() instead.
Even pinning the current user before creating other object didn't solve the problem.

Not sure if you found a solution on your own yet for this, but I think this should work: At app start-up, when you enable automatic user creation:
public class MyApplication extends Application {
#Override
public void onCreate() {
super.onCreate();
// ...
if (ParseUser.getCurrentUser()==null) {
ParseUser.enableAutomaticUser();
ParseUser.getCurrentUser().saveInBackground();
}
// ...
}
}
This will (a) ensure that you always have a current user, and (b) if it is an anonymous user that user will persist through application restarts.
Note 1: saveInBackground() won't actually save the user to the server because the user does not have a username/password, but will persist the user.
Note 2: I haven't tested this fully but it should fix your situation.

Related

The Parse current user is not deleted after app reinstalled

Users reported to us that they uninstalled the app, then reinstalled it and they were immediately transferred to the Home screen, instead of the Login screen. The thing is, since they don't login they don't have a Session token and hence, they can't call cloud functions!
Here's my check:
if (ParseUser.getCurrentUser()==null) {
// show login screen
}
else {
// show home screen
}
Here's an email we just got
I have managed to fix the problem. I had to clear all my temporary data for the application and reinstall it. After that it worked like it should. So the problem was with some temporary saved data in my device.
Any idea what's going on?
In AndroidManifest under the application tag, there is an android:allowBackup
flag that was responsible for this. as the documentation said:
android:allowBackup Whether to allow the application to participate in
the backup and restore infrastructure. If this attribute is set to
false, no backup or restore of the application will ever be performed,
even by a full-system backup that would otherwise cause all
application data to be saved via adb. The default value of this
attribute is true.
For your problem, you must make this false.

Device admin confirm before DEACTIVATE

I want to ask a confirmation before disabling/deactivating device admin for my application. I searched a lot about it but not fing any proper solution for this.
In short, I want to detect a callback when user click DEACTIVATE button from device admin and I want to ask a confirmation to use that whether are you sure you want to deactivate device admin ? If use press cancel then device admin should not be deactivated.
If you observer AppLock application by DoMobile Lab from google play store, you can find that this app is doing the same thing. So there must be some secret behind it.
You can do it by overriding onDisableRequested() method of DeviceAdminReceiver
public class AdminReceiver extends DeviceAdminReceiver {
#Override
public CharSequence onDisableRequested(Context context, Intent intent) {
return "Are you sure you want to disable the Device admin?";//OR whatever message you would like to display
}
}
As per documentation
Called when the user has asked to disable the administrator, as a result of receiving ACTION_DEVICE_ADMIN_DISABLE_REQUESTED, giving you a chance to present a warning message to them. The message is returned as the result; if null is returned (the default implementation), no message will be displayed.
This will show a popup with OK and cancel button, along with the text returned.

Android AccessibilityManager getEnabledAccessibilityServiceList returns empty list under certain circumstances

My app extends Android's AccessibilityService to monitor the currently active app. In order to detect changes in activities I have to register my service and get the user to consent to allow the permission. As a convenience to the user I detect whether my service is currently enabled when my app starts, if not enabled e.g. when the app is installed then I redirect the user to the Settings Accessibility page to allow them to enable the service. The following code checks whether my service is currently enabled, the id parameter is the id of my service e.g. com.foo.bar/.MyService syntax:
private boolean isAccessibilityEnabled(String id) {
AccessibilityManager am = (AccessibilityManager) getSystemService(Context.ACCESSIBILITY_SERVICE);
List<AccessibilityServiceInfo> enabledServices = am.getEnabledAccessibilityServiceList(AccessibilityEvent.TYPES_ALL_MASK);
for (AccessibilityServiceInfo service : enabledServices) {
if (id.equals(service.getId())) {
return true;
}
}
return false;
}
I've seen two scenarios where this check fails even though I know the service is enabled. Firstly if I debug my app from Android Studio this fails and enabledServices is empty, if I run (rather than debug) it works perfectly and returns a single entry in enabledServices. The second scenario I've noticed where it fails is when I run the adb backup command to backup my app, if my app is currently visible when the backup prompt comes up then when the backup completes my app's main activity onCreate is executed and the isAccessibilityEnabled method is checked and again fails to see my service is already enabled.
Is there a special case I need to take into account when calling getEnabledAccessibilityServiceList or is there a reason why my service isn't returned even though when I look in the Accessibility Settings page I can see the service is enabled.
There is an alternative way to query if an accessibility service is enabled, I've used the approach described here - Detect if my accessibility service is enabled and it seems to get around the issues I was encountering.

Screen pinning 3rd party apps programmatically

After achieving device ownership, I am trying to implement a method to instruct the device to lock any given app into kiosk mode (or screen pinning mode). Since I have device ownership, the user is not asked for the permission to do so.
From the developer website, brief description tells me that it is possible to do what I am trying:
http://developer.android.com/about/versions/android-5.0.html#ScreenPinning
Programmatically: To activate screen pinning programmatically, call
startLockTask() from your app. If the requesting app is not a device
owner, the user is prompted for confirmation. A device owner app can
call the setLockTaskPackages() method to enable apps to be pinnable
without the user confirmation step.
This indicates that as a device owner app, I can pin other apps without user confirmation... but I have no idea how to.
I have been able to put my own app into pinned mode.
Any help would be appreciated.
The setLockTaskPackages() is used the specify which applications (through their package names) will be able to programmatically be pinned without user confirmation.
The setLockTaskPackages() is called from your device owner app (most probably in your DeviceAdminReceiver's onEnabled() method).
So, in you owner device app, you'll have something like :
mDPM.setLockTaskPackages("com.foo.myapp");
and then, in your "com.foo.myapp" application, you will be autorized to call :
startLockTask();
Your application will immediately enter the Pinning mode, without any user confirmation.
If you don't first register your application with setLockTaskPackages, the application will be pinned but the user will have to confirm first.
Also notice that when an app is registered with setLockTaskPackages(), it has some different behaviours than the manual pin:
the user cannot unpin manually the application by long-pressing Back + Recent Apps. You'll have to programmatically unpin your app with stopLockTask();
The "Home" and "Recent Apps" buttons are invisible (not displayed)
When the app is unpinned (via stopLockTask()), the user will directly go back to Home : no Screen lock is displayed, even if a Keyguard is set (Pattern, code, or whatever Keyguard screen).
I've not enough reputation for a comment, just would point out that for devices with physical buttons (like the Samsung Galaxy Tab A mentioned by #chairman) one way for manage the forced unpinning of your application is to implement in your DeviceAdminReceiver class the following:
#Override public void onLockTaskModeExiting(Context context, Intent
intent)
So if your user want to for the unpin you can always re-pinning your app ;)
Here's a code snippet that should get you going:
DevicePolicyManager myDevicePolicyManager = (DevicePolicyManager) getSystemService(Context.DEVICE_POLICY_SERVICE);
mDeviceAdminSample = new ComponentName(this, DeviceAdminSample.class);
if (myDevicePolicyManager.isDeviceOwnerApp(this.getPackageName())) {
// Device owner
String[] packages = {this.getPackageName()};
myDevicePolicyManager.setLockTaskPackages(mDeviceAdminSample, packages);
} else {
// Not a device owner - prompt user or show error
}
if (myDevicePolicyManager.isLockTaskPermitted(this.getPackageName())) {
// Lock allowed
startLockTask();
} else {
// Lock not allowed - show error or something useful here
}

When to let server know user online or offline

I am designing an app which needs to know which users are online or offline. Each user can
notify the server if he is online or offline and then I can get that information from the server.
The issue is that is there a standard in android which marks the user as online or offline.
One solution is if the app is running then the user is online, if the app force stopped or not running then the user is offline. So in my app how will I know that the app is stopping?
If the above is not possible or not a good solution then when will my app tell the server that it is going offline.
Thanks in advance.
In Android, there is no hard solid concept of "leaving an application". Apps can be pushed on the stack by pressing home, still alive in the background or pushed away from top by another application. There is no real hook that you can use to say "ok, I am really going down now, I should notify the server".
So, you could take it the other way around : the server grants a bail to a user, for 5mn let's say, and the client app has to renew it. After 5 mn of inactivity, the server can know that a user is going offline.
Off course, the delay will be a trade off between the need of precision/responsiveness you want on the server side and battery usage as this will tend to decrease battery life by constantly notifying the server that the client is still online.
In Android When application is create onCreate() method of Application class is calls when application is force closed onTerminate() method is calls.
If you want to do something when application is create and terminate you need to create your custom application class by extending Application class.
1) Create your own application class like this
public class MyApplication extends Application {
#Override
public void onCreate() {
super.onCreate();
// When application creates
}
#Override
public void onTerminate() {
super.onTerminate();
// calls when application force closed.
}
}
2) In your manifest.xml
<application
android:name="com.yourpackagename.MyApplication"
android:allowTaskReparenting="true"
android:debuggable="true"
android:icon="#drawable/ijoomer_luncher_icon"
android:label="#string/app_name"
android:theme="#style/ijoomer_theme" >

Categories

Resources