Meine Anwendung scheint eine Race Condition zu erleben und ich bin mir nicht sicher warum. Es passiert nur, wenn ich die Anwendung zum ersten Mal öffne. Entsprechend dem Fehler ist die statische Variableninstanz in MainActivity gleich null, aber ich setze die Variable vor dem Start des Dienstes. Es scheint fast so, als ob der Dienst gestartet wird, bevor der onCreate innerhalb der Aktivität beendet wird, aber ich glaube nicht, dass dies möglich ist. Irgendwelche Ideen was passiert?Context Service Race Condition
Fehlermeldung
E/AndroidRuntime: FATAL EXCEPTION: Timer-
java.lang.NullPointerException
at NetworkCalls.getRequestQueue(NetworkCalls.java:42)
at NetworkCalls.addToRequestQueue(NetworkCalls.java:48)
at NetworkCalls.createLocationPost(NetworkCalls.java:72)
at StaticMethods.handleWarnings(StaticMethods.java:84)
at LocationService.checkInPost(LocationService.java:73)
at LocationService$1.run(LocationService.java:66)
at java.util.Timer$TimerImpl.run(Timer.java:284)
Networks Klasse
public class NetworkCalls {
private static NetworkCalls singleton;
private RequestQueue mRequestQueue;
private static Context warningCtx = WarningActivity.instance;
private static Context mCtx = MainActivity.instance;
private NetworkCalls() {
}
public static synchronized NetworkCalls getInstance() {
if (singleton == null) {
singleton = new NetworkCalls();
}
return singleton;
}
private RequestQueue getRequestQueue() {
if (mRequestQueue == null) {
//Problem here is that mCtx is null
if(mCtx == null){
Log.e("Error", "It's FUBAR");
}else {
Log.e("Error", "It's Okay");
}
mRequestQueue = Volley.newRequestQueue(mCtx.getApplicationContext());
}
return mRequestQueue;
}
private <T> void addToRequestQueue(Request<T> req) {
getRequestQueue().add(req);
}
public void createLocationPost(LocationData locationData) {
String url = "http://httpbin.org/post";
HashMap<String, String> params = new HashMap<>();
params.put("Token", "key");
JsonObjectRequest jsObj = new JsonObjectRequest(url, new JSONObject(params), new Response.Listener<JSONObject>() {
@Override
public void onResponse(JSONObject response) {
try {
Log.i("NetworkCalls Successful", response.getJSONObject("json").toString());
} catch (JSONException ex) {
Log.i("Parsing response", "Unable to get json string");
}
// On Response recieved
}
}, new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError error) {
Log.i("NetworkCalls Error", error.toString());
}
});
addToRequestQueue(jsObj);
}
Haupt Akivität
public class MainActivity extends AppCompatActivity {
public static MainActivity instance = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ColorDrawable colorDrawable = new ColorDrawable(Color.parseColor("#000000"));
getSupportActionBar().setBackgroundDrawable(colorDrawable);
this.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LOCKED);
instance = MainActivity.this;
startService(new Intent(getBaseContext(), QueuePostService.class));
}
}
}
Das hat perfekt funktioniert, danke. Ich würde nicht darüber nachdenken, wie der Klassenlader funktionierte und es war nahezu unmöglich, das Problem zu verfolgen. Erspart mir stundenlanges Kopfschlagen! – Ubarjohade
Denken Sie nicht darüber nach, wie der Klassenlader geladen wird: Denken Sie daran, dass Java-Variablen Werte und keine Referenzen sind. Nachfolgende Änderungen der Variablen "referenziert" werden daher nicht in der Variablen "referenzieren" wiedergegeben. –