diff --git a/app/src/main/java/fr/free/nrw/commons/achievements/AchievementsActivity.java b/app/src/main/java/fr/free/nrw/commons/achievements/AchievementsActivity.java
index d04d2b7b1..b2b14f3c9 100644
--- a/app/src/main/java/fr/free/nrw/commons/achievements/AchievementsActivity.java
+++ b/app/src/main/java/fr/free/nrw/commons/achievements/AchievementsActivity.java
@@ -185,6 +185,7 @@ public class AchievementsActivity extends NavigationBaseActivity {
* which then calls parseJson when results are fetched
*/
private void setAchievements() {
+ progressBar.setVisibility(View.VISIBLE);
if (checkAccount()) {
compositeDisposable.add(mediaWikiApi
.getAchievements(Objects.requireNonNull(sessionManager.getCurrentAccount()).name)
@@ -195,17 +196,23 @@ public class AchievementsActivity extends NavigationBaseActivity {
if (response != null) {
setUploadCount(Achievements.from(response));
} else {
- onError();
+ showSnackBarWithRetry();
}
},
t -> {
Timber.e(t, "Fetching achievements statistics failed");
- onError();
+ showSnackBarWithRetry();
}
));
}
}
+ private void showSnackBarWithRetry() {
+ progressBar.setVisibility(View.GONE);
+ ViewUtil.showDismissibleSnackBar(findViewById(android.R.id.content),
+ R.string.achievements_fetch_failed, R.string.retry, view -> setAchievements());
+ }
+
/**
* Shows a generic error toast when error occurs while loading achievements or uploads
*/
diff --git a/app/src/main/java/fr/free/nrw/commons/di/NetworkingModule.java b/app/src/main/java/fr/free/nrw/commons/di/NetworkingModule.java
index 953b7ecee..92469202d 100644
--- a/app/src/main/java/fr/free/nrw/commons/di/NetworkingModule.java
+++ b/app/src/main/java/fr/free/nrw/commons/di/NetworkingModule.java
@@ -9,6 +9,7 @@ import com.google.gson.GsonBuilder;
import java.io.File;
+import java.util.concurrent.TimeUnit;
import javax.inject.Named;
import javax.inject.Singleton;
@@ -30,9 +31,11 @@ public class NetworkingModule {
@Singleton
public OkHttpClient provideOkHttpClient(Context context) {
File dir = new File(context.getCacheDir(), "okHttpCache");
- return new OkHttpClient.Builder()
- .cache(new Cache(dir, OK_HTTP_CACHE_SIZE))
- .build();
+ return new OkHttpClient.Builder().connectTimeout(30, TimeUnit.SECONDS)
+ .writeTimeout(30, TimeUnit.SECONDS)
+ .readTimeout(30, TimeUnit.SECONDS)
+ .cache(new Cache(dir, OK_HTTP_CACHE_SIZE))
+ .build();
}
@Provides
diff --git a/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java b/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java
index aef3dddb0..2f9107190 100644
--- a/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java
+++ b/app/src/main/java/fr/free/nrw/commons/utils/ViewUtil.java
@@ -87,4 +87,24 @@ public class ViewUtil {
popup.showAsDropDown(anchorView);
}
+ /**
+ * A snack bar which has an action button which on click dismisses the snackbar and invokes the
+ * listener passed
+ */
+ public static void showDismissibleSnackBar(View view, int messageResourceId,
+ int actionButtonResourceId, View.OnClickListener onClickListener) {
+ if (view.getContext() == null) {
+ return;
+ }
+ ExecutorUtils.uiExecutor().execute(() -> {
+ Snackbar snackbar = Snackbar.make(view, view.getContext().getString(messageResourceId),
+ Snackbar.LENGTH_INDEFINITE);
+ snackbar.setAction(view.getContext().getString(actionButtonResourceId), v -> {
+ snackbar.dismiss();
+ onClickListener.onClick(v);
+ });
+ snackbar.show();
+ });
+ }
+
}
diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml
index 4224f231f..22feaa82a 100644
--- a/app/src/main/res/values/strings.xml
+++ b/app/src/main/res/values/strings.xml
@@ -420,5 +420,6 @@ Upload your first media by touching the camera or gallery icon above.
Never ask this again
Display location permission
Ask for location permission when needed for nearby notification card view feature.
+ Something went wrong, We could not fetch your achievements