Accessing application.conf in GlobalSettings onStart (Play Framework) - java

I am using Java / Play Framework 2.1.0.
I have found other questions asking how to access application.conf, and I tried two methods:
Play.application().configuration().getString("my.thing");
and
ConfigFactory.load().getString("my.thing");
In both cases I dont get anything back. I am trying to do this in onStart of my Global class. Maybe onStart happens before configuration is loaded?
How can I access values in application.conf from within onStart? (Or, to be more precise, how do I access values in myapp.conf which is included in application.conf)

Can you verify that your onStart is getting called at all?
The configuration values are loaded and accessible at that point. In fact, you are getting the play.Application instance passed as an argument, so you can just do this:
public void onStart(Application app)
{
super.onStart(app);
String value = app.configuration().getString("my.thing");
// do something with value
}

Related

How to populate default values of fields while creating issues in JIRA using jira-plugin?

I am working on jira-plugin to create issues in JIRA. I am using the method - create(user,createValidationResult) to create issue.
I need to give values of mandatory fields while creating.
I want to give the default values of fields while creating. (The default values are the ones which are configured during the creation of these in JIRA)
I have found the below methods
method populateDefaults
method getDefaultValue
But both the methods require Issue- parameter which is not yet created as I need to create the issue after setting default values
Please let me know how to set the values for these fields. These fields are added using method addCustomFieldValue in the class IssueInputParameters
I found the solution myself : (This works perfectly)
Use the below method :
IssueInputParameters issueInputParameters =
issueService.newIssueInputParameters();
issueInputParameters.setApplyDefaultValuesWhenParameterNotProvided(true);
IssueService.CreateValidationResult createValidationResult =
issueService.validateCreate(user, issueInputParameters);
issueService.create(user,createValidationResult);
Note : In the above code 'issueService' is an object of IssueService.

Apache Spark - passing configuration to nodes

I have an application where I am using Apache Spark 1.4.1 - Standalone cluster. Code from this application has evolved and it's quite complicated (more than a few lines of code as we see in most Apache Spark examples), with lots of method calls from one class to another.
I am trying to add code that when encounters a problem with data (while processing it on the cluster nodes) it notifies an external application. For contacting the external application we have connection details setup in a config file. I want to pass somehow the connection details to the cluster nodes but passing them as parameters to each method that runs on nodes (as parameters or broadcast variable) is not ok for my application because it means that each and every method has to pass them and we've got lots of "chained method calls" (method A calls B, B calls C.....Y calls Z) which is different from most Apache Spark example where we see only one or two method calls.
I am trying to workaround this problem - is there a way to pass data to nodes besides method parameters and broadcast variables ? For example I was looking to setup a env property that would point to the config file (using System.setProperty) and to set it on all nodes, so that I can read connection details on the fly and the code would isolated in one block of code only, but I've got no luck so far.
Actually after some hours of investigation I found a way that really suits my needs. There are two spark properties (one for driver, one for executors) that can be used for passing parameters that can be then read using System.getProperty() :
spark.executor.extraJavaOptions
spark.driver.extraJavaOptions
Using them is more simpler than the approach suggested in above post and you could easily make your application to switch configuration from one environment to another (e.g QA/DEV vs PROD) when you've got all environment setup in your project.
They can be set in the SparkConf object when you're initializing the SparkContext.
The post that helped me a lot in figuring the solution is : http://progexc.blogspot.co.uk/2014/12/spark-configuration-mess-solved.html
The properties you provide as part of --properties-file will be loaded at runtime and will be available only as part of driver but not on any of the executors. But you can always make it available to the executors.
Simple hack:
private static String getPropertyString(String key, Boolean mandatory){
String value=sparkConf.get(key,null);
if(mandatory && value == null ){
value = sparkConf.getenv(key);
if(value == null)
shutDown(key); // Or whatever action you would like to take
}
if(value !=null && sparkConf.getenv(key)==null )
sparkConf.setExecutorEnv(key,value);
return value;
}
First time when your driver kicks, it will find all the properties provided from properties file from sparkconf. As soon as it finds, check whether that key already present in environment if not set those values to executors using setExecutorEnv in your program.
Its tough to distinguish whether your program is in driver or in executor so check whether the property exists in sparkconf if not then check it against environment using getenv(key).
I suggest the following solution:
Put the configuration in a database.
Put the database connection details in a JOCL (Java Object configuration Language) file and have this file available on the class path of each executors.
Make a singleton class that reads the DB connection details from the JOCL, connects to the database, extracts the configuration info and exposes it as getter methods.
Import the class into the context where you have your Spark calls and use it to access the configuration from within them.

SqlCipher attempt to write a readonly database

I am attempting to implement Sqlcipher for android. I am using this for multiple activities and as such am extending SQLiteOpenHelper {}.
However I am
I am aware that the OnCreate override method is not called until the database is accessed for the first time.
My oncreate method looks like
#Override
public void onCreate(SQLiteDatabase db) {
SQLiteDatabase.loadLibs(context);
File databaseFile = context.getDatabasePath("SyncableDiabetesDatabase.db");
databaseFile.mkdirs();
databaseFile.delete();
mDataBase = SQLiteDatabase.openOrCreateDatabase(databaseFile,SuperKey, null);
I am attempting to get the OnCreate Method to call this method by calling this.getWritableDatabase(SuperKey); However when I run this command i receive the error
net.sqlcipher.database.SQLiteException: attempt to write a readonly database: PRAGMA user_version = 1
I'm not exactly sure how this is possible since the command is for a writeable DB
I know sqlcipher is correctly installed, as I can put the DB creation code above outside of OnCreate and the data is stored correctly. However the file is overridden each time the activity is called than, hence why I am moving it to OnCreate which is only called once when I create the tables.
Any insight here would be more than welcome.
I can provide any additional code snippits if needed.
Thank you
You do not need to call SQLiteDatabase.openOrCreateDatabase within the onCreate method of the SQLiteOpenHelper, the database instance is already provided as a parameter to the function. An example of using the SQLiteOpenHelper can be found here.

Dynamically set the authority of a ContentProvider

Perhaps the title is a bit misleading. My problem is that I have an Android library project which is shared between two standard Android projects: one for a free version of the app and the other for a paid version. The library currently has the code for a ContentProvider, including a contract class with several static String variables for things such as the URI and column names. Now I want the "authority" for the URI to change depending on which app is using the library. One solution that comes to mind is storing the authority as a string resource and loading that string at run-time into the static final String variable. However, I'm not sure how to do this as the contract class has a private constructor and no Context object in order to load the string resource. What other options are available to solve my problem?
Here's a better solution for those using newer versions of the build tools: make the authority relative to your application ID. You can do this automatically using ${applicationId}, which is expanded into your app's application ID during the build process.
<provider
android:name=".MyContentProvider"
android:authorities="${applicationId}.provider"/>
Let's say your application IDs are com.example.app.paid and com.example.app.free. When you build your app, the authority will become com.example.app.paid.provider and com.example.app.free.provider, correspondingly.
To reference the provider authority in your code, use BuildConfig.APPLICATION_ID + ".provider".
Using different authorities for the free and the paid version makes sense in case the user tries to install both versions.
I'm defining a different authority for the two versions in the manifest like so:
<provider
android:name="MyApp.MyProvider"
android:authorities="MyApp.MyProvider.free"
android:grantUriPermissions="true"/>
Then I configure the provider in an xml file (I use a special config.xml file because I have more configuration data like the provider authority, but you can use strings.xml of course):
<string name="my_provider_authority">MyApp.MyProvider.free</string>
The code retrieves the provider authority as any other string resource. To access string resources without a context use the application context. I'm using an application class to have access to the application context from anywhere in my app (there are two exceptions though):
public class MyApplication extends Application {
private static Context sContext;
#Override
public void onCreate() {
super.onCreate();
sContext = this;
}
public static Context getContext() {
return sContext;
}
}
Of course you need to define MyApplication in your manifest.
This allows you to access string and other resources from anywhere in your app.
There are two exception though:
ContentProviders. ContentProviders can be started before Application starts and so you won't have an Application context available. That's no problem though because ContentProviders get their own context through getContext().
Static code: the context might not be available outside the life cycle of Android components (Activities, Fragments, BroadcastReceivers, Services etc.). Static initializers that are relying on the application context are therefore not a good idea. But that's also not a real issue because using a context outside the life cycle of Android components isn't allowed anyway and static methods accessing a context would always be called from within that life cycle. E.g. if an Activity needs to know a ContentProvider's authority it would call a static method in your contract class and that call would be from one of the activity's onXYZ() methods like onCreate() or onStart() which would make sure that the context is initialized. So all you need to do is lazy initialize the variables in your contract class and make sure the caller does retrieve the variables only when it's clear that Application.onCreate() has been called before. Of course from within an activity you could retrieve the string resources directly. The real advantage of my method will become obvious when you need the resources in other classes/objects. These objects would still be tied to the life cycle of some Android component but you wouldn't have to pass around the context to all these objects, which is 1) very cumbersome and 2) very error prone when it comes to leaking the context which could lead to memory usage issues (one of the most common problems with Android apps).
Why change the authority at all? You're not required to export the provider, which means that nobody could even see the authority name except by deconstructing the app. Even then, they wouldn't be able to access the provider.
If it's for your own internal convenience, then I'd use the same authority but put different security on the URIs.
In short, your idea is interesting, but I wouldn't do it that way. Too much of a mess.

Register in android a session like value shared by all activity

How can I register data (like integer or poco objects) shared by all activity like the id of the user ? Have I to use a simple singleton or is there a special Android way ?
Note : I don't need to make that data persistant (no need of SharedPreferences or sqlite)
Thank you
You can create your own class that implements Application and specify this in your manifest file. In that case, every time you call getApplicationContext you will get a reference of your application that can hold any kind of information.
How to declare global variables in Android?
Sample code:
class MyApplication extends Application {
public void setMethod() {
//
}
}
((MyApplication)getApplicationContext()).setMethod()
The android way is to create a custom Application for your project. Then in onCreate of that application you initialize whatever you need, and for example from an Activity do something like:
((MyApplication) getApplication()).getMyData()
If using roboguice you can use a #Singleton injection which basically does the boilerplate of a singleton for you - that's much nicer.

Categories