How can I use setText instead of using append in android studio? - android

I'm trying to use RETROFIT to get an inform about COVID-19 data. And I want to show the latest data, so I tried
content1 = covid_post_data.getPositive() + "\n";
content2 = covid_post_data.getDeath() + "\n";
content3 = " (+" + covid_post_data.getPositiveIncrease() + ")\n";
content4 = " (+" + covid_post_data.getDeathIncrease() + ")\n";
content5 = " Updated : " + covid_post_data.getDate() + "\n";
textViewResult.setText(content1);
textViewResult2.setText(content2);
textViewResult3.setText(content3);
textViewResult4.setText(content4);
textViewResult5.setText(content5);
But it is not working.it didn't show any data. how can i show the latest data in JSON file with using retrofit? below is my whole code of main activity
1.MainActivity
public class COVIDActivity extends AppCompatActivity {
private TextView textViewResult;
private TextView textViewResult2;
private TextView textViewResult3;
private TextView textViewResult4;
private TextView textViewResult5;
private static final String TAG = "COVIDActivity";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.covid_menu);
//How go_back_button works
ImageButton bo_back_Button = (ImageButton) findViewById(R.id.covid_to_main);
bo_back_Button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Intent move_main_covid = new Intent(COVIDActivity.this,MainActivity.class);
startActivity(move_main_covid);
}
});
textViewResult = findViewById(R.id.text_view_result_positive);
textViewResult2 = findViewById(R.id.text_view_result_death);
textViewResult3 = findViewById(R.id.text_view_result_positive_increase);
textViewResult4 = findViewById(R.id.text_view_result_death_increase);
textViewResult5 = findViewById(R.id.today_date);
Retrofit retrofit = new Retrofit.Builder()
.baseUrl("https://covidtracking.com/api/v1/")
.addConverterFactory(GsonConverterFactory.create())
.build();
JsonPlaceHolderApi jsonPlaceHolderApi = retrofit.create(JsonPlaceHolderApi.class);
Call<List<COVID_Post_Data>> call = jsonPlaceHolderApi.get_covid_post();
call.enqueue(new Callback<List<COVID_Post_Data>>() {
#Override
public void onResponse(Call<List<COVID_Post_Data>> call, Response<List<COVID_Post_Data>> response) {
if (!response.isSuccessful()) {
textViewResult.setText(("Code: " + response.code()));
return;
}
List<COVID_Post_Data> posts = response.body();
//Give message if fail, TAG is COVIDActivity so that it will show log in this activity
if(posts == null) {
Log.w(TAG,"Did not receive any valid response body");
return;
}
for (COVID_Post_Data covid_post_data : posts) {
String content1,content2,content3,content4,content5 = "";
content1 = covid_post_data.getPositive() + "\n";
content2 = covid_post_data.getDeath() + "\n";
content3 = " (+" + covid_post_data.getPositiveIncrease() + ")\n";
content4 = " (+" + covid_post_data.getDeathIncrease() + ")\n";
content5 = " Updated : " + covid_post_data.getDate() + "\n";
textViewResult.append(content1);
textViewResult2.append(content2);
textViewResult3.append(content3);
textViewResult4.append(content4);
textViewResult5.append(content5);
}
}
2.get JSON file
public interface JsonPlaceHolderApi {
//get data from json about US infection
#GET("us/daily.json")
Call<List<COVID_Post_Data>> get_covid_post();
//get data from json about states infection
#GET("states/daily.json")
Call<List<COVID_Post_Data>> get_covid_post_state();
}
3.getter function
public class COVID_Post_Data {
private String dataChecked;
private int positiveIncrease;
private int negativeIncrease;
private int deathIncrease;
private String state;
private int positive;
private int death;
private int date;
//if the variable is matched with name in json file no need to put #SerializedName here
public String getDataChecked() {
return dataChecked;
}
public int getPositiveIncrease() {
return positiveIncrease;
}
public int getNegativeIncrease() {
return negativeIncrease;
}
public int getDeathIncrease() {
return deathIncrease;
}
public String getState() {
return state;
}
public int getPositive() {
return positive;
}
public int getDeath() { return death; }
public int getDate() {
return date;
}
}

Related

I want to save data in SecondActivity from FirstActivity using Room

I have three activities, I capture all data but one from DetailActivity upon button click and save in database using Room; My intention is to insert all these data into the database and start ReviewActivity so as to get the arraylist of reviews and also insert it in the database. Everything seems to work fine until when I want to view review offline because I believe it has been saved, reviews does not get loaded.
This is my DetailActivity,
TextView overview_tv; ImageView image_tv; TextView name_tv; TextView ratings; Context context; TextView release_date; ImageView backdrop_poster; private ExpandableHeightListView trailers; public static ArrayList<Youtube> youtube; public static ArrayList<Review> reviews; TrailerViewAdapter adapter; public static DataObject data; DataObject dataObject; ArrayList<Review> savedReview; private static final String IMAGE_URL = "http://image.tmdb.org/t/p/w185/"; private static final String THE_MOVIEDB_URL2 = "https://api.themoviedb.org/3/movie/"; private static final String MOVIE_QUERY2 = "api_key"; private static final String API_KEY2 = "6cc4f47bd4a64e0117e157b79072ae37"; private static String SEARCH_QUERY2 = "videos"; public static int movieId; Button viewReviews; Button favourite; String movieRating; private static final int YOUTUBE_SEARCH_LOADER = 23; private static final int REVIEW_SEARCH_LOADER = 24; File file; String name; String overview; String releaseDate; int switcher; public static ArrayList<Review> favouriteReviews; TextView trev; AppDatabase mDb; //Navigation arrow on the action bar #Override public boolean onOptionsItemSelected(MenuItem item) { int id = item.getItemId(); if (id == android.R.id.home) { NavUtils.navigateUpFromSameTask(this); } return super.onOptionsItemSelected(item); } #Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_detail); mDb = AppDatabase.getInstance(getApplicationContext()); youtube = new ArrayList<Youtube>(); reviews = new ArrayList<Review>(); adapter = new TrailerViewAdapter(this, youtube); //Credit to Paolorotolo #github trailers = findViewById(R.id.expandable_list); trailers.setAdapter(adapter); trailers.setExpanded(true); //Navigation arrow on the acton bar; check also override onOptionsItemSelected ActionBar actionBar = this.getSupportActionBar(); if (actionBar != null) { actionBar.setDisplayHomeAsUpEnabled(true); } context = getApplicationContext(); Intent intent = getIntent(); if (intent == null) { closeOnError(); } switcher = getIntent().getIntExtra("switch", 3); overview_tv = findViewById(R.id.overview); image_tv = findViewById(R.id.image); name_tv = findViewById(R.id.name); ratings = findViewById(R.id.ratings); release_date = findViewById(R.id.release_date); backdrop_poster = findViewById(R.id.backdrop_poster); trev = findViewById(R.id.review_show); viewReviews = findViewById(R.id.review_button); favourite = findViewById(R.id.favourite_button); addListenerOnRatingBar(ratings); if (switcher != 2) { favourite.setVisibility(View.INVISIBLE); dataObject = (DataObject) getIntent().getParcelableExtra("array"); final String favouriteName = dataObject.getName(); final String favouriteOverview = dataObject.getOverview(); final String favouriteReleaseDate = dataObject.getReleaseDate(); ArrayList<Youtube> savedTrailer = dataObject.getTrailers(); savedReview = dataObject.getMovieReviews(); movieRating = dataObject.getRating(); name_tv.setText(favouriteName); overview_tv.setText(favouriteOverview); ratings.setText("Rating: " + movieRating); release_date.setText("Release Date: " + favouriteReleaseDate);// Toast.makeText(this, "Testing Reviews " + savedReview.get(0).getAuthor(), Toast.LENGTH_SHORT).show(); String imagePath = name_tv.getText().toString() + "0i"; String backdropPath = name_tv.getText().toString() + "1b"; try { DataObjectAdapter.downloadImage(imagePath, image_tv, this); } catch (Exception e) { e.printStackTrace(); } try { DataObjectAdapter.downloadImage(backdropPath, backdrop_poster, context); } catch (Exception e) { e.printStackTrace(); } if (savedTrailer != null) { TrailerViewAdapter lv = new TrailerViewAdapter(DetailActivity.this, savedTrailer); trailers.setAdapter(lv); switcher = 3; } } else { name = getIntent().getStringExtra("Name"); overview = getIntent().getStringExtra("Overview"); final String image = getIntent().getStringExtra("Image"); movieId = getIntent().getIntExtra("movieId", 1); final String backdrop = getIntent().getStringExtra("backdrop"); releaseDate = getIntent().getStringExtra("releaseDate"); movieRating = getIntent().getStringExtra("rating"); Log.i("this", "switch " + switcher); name_tv.setText(name); overview_tv.setText(overview); ratings.setText("Rating: " + movieRating); release_date.setText("Release Date: " + releaseDate); //load backdrop poster Picasso.with(context) .load(IMAGE_URL + backdrop) .fit() .placeholder(R.drawable.placeholder_image) .error(R.drawable.placeholder_image) .into(backdrop_poster); Picasso.with(context) .load(IMAGE_URL + image) .fit() .placeholder(R.drawable.placeholder_image) .error(R.drawable.placeholder_image) .into(image_tv); getSupportLoaderManager().initLoader(YOUTUBE_SEARCH_LOADER, null, this); //getSupportLoaderManager().initLoader(REVIEW_SEARCH_LOADER, null, this); //loadTrailers(); //loadReviews(); //populateKeys(); } /** * Here manages the views(list) for reviews */ viewReviews.setOnClickListener(new View.OnClickListener() { #Override public void onClick(View v) { if (switcher == 3) { startActivity(new Intent(DetailActivity.this, ReviewActivity.class) .putExtra("switch", 3)); } else { Log.i("this", "I am from initial" + switcher); startActivity(new Intent(DetailActivity.this, ReviewActivity.class).putExtra("id", movieId)); } } } ); favourite.setOnClickListener(new View.OnClickListener() { #Override public void onClick(View v) { data = new DataObject(); data.setName(name); data.setOverview(overview); data.setRating(movieRating); data.setReleaseDate(releaseDate); data.setTrailers(youtube);// data.setMovieReviews(reviews); try { saveImage(name_tv.getText().toString() + "0i", image_tv); saveImage(name_tv.getText().toString() + "1b", backdrop_poster); } catch (IOException e) { e.printStackTrace(); } Toast.makeText(context, "The movie is saved as a favourite", Toast.LENGTH_LONG).show(); AppExecutors.getInstance().diskIO().execute(new Runnable() { #Override public void run() { mDb.dataDao().insertData(data); } }); startActivity(new Intent(DetailActivity.this, ReviewActivity.class).putExtra("id", movieId) .putExtra(ReviewActivity.EXTRA_DATA_ID, 20)); } } ); }
And my ReviewActivity
public class ReviewActivity extends AppCompatActivity implements LoaderManager.LoaderCallbacks<ArrayList<Review>>{ public static ArrayList<Review> reviews; public static List<DataObject> favouriteReviews; public static RecyclerView reviewList; ArrayList<Review> r; private static final int REVIEW_SEARCH_LOADER = 24; private static final String MOVIE_QUERY3 = "api_key"; private static final String API_KEY3 = "6cc4f47bd4a64e0117e157b79072ae37"; private static String SEARCH_QUERY3 = "reviews"; private static final String THE_MOVIEDB_URL3 = "https://api.themoviedb.org/3/movie/"; private static int movId; public static final String EXTRA_DATA_ID = "extraDataId"; private static final int DEFAULT_TASK_ID = -1; private int mTaskId = DEFAULT_TASK_ID; DataObject data1; AppDatabase mDb; ReviewAdapter revAdapter; int loaderSwitch; #Override protected void onResume() { super.onResume(); } #Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_review); mDb = AppDatabase.getInstance(getApplicationContext()); reviews = new ArrayList<Review>(); favouriteReviews = new ArrayList<DataObject>(); reviewList = findViewById(R.id.review_list); LinearLayoutManager layoutManager = new LinearLayoutManager(getApplicationContext()); reviewList.setLayoutManager(layoutManager); reviewList.setHasFixedSize(true); int switcher = getIntent().getIntExtra("switch", 1); Intent intent = getIntent(); if (intent == null) { finish(); } Log.i("this", "swithcer " + switcher); Log.i("this loader", "Loader " + loaderSwitch); if (switcher == 3){ DataObject dataObject = (DataObject) getIntent().getParcelableExtra("ArrayOfReviews"); if (dataObject != null){ ArrayList<Review> movieReviews = dataObject.getMovieReviews(); Toast.makeText(this, "There are reviews saved", Toast.LENGTH_LONG).show(); revAdapter = new ReviewAdapter(this, movieReviews ); reviewList.setAdapter(revAdapter); } } else { movId = getIntent().getIntExtra("id", 20); revAdapter = new ReviewAdapter(this, reviews); reviewList.setAdapter(revAdapter); loadReviews(); //populateReview(); } DividerItemDecoration decoration = new DividerItemDecoration(this, VERTICAL); reviewList.addItemDecoration(decoration); } #Override protected void onStart() { super.onStart(); //loadReviews(); } public static URL buildUrl3(String stringUrl) { Uri uri = Uri.parse(THE_MOVIEDB_URL3).buildUpon() .appendPath(stringUrl) .appendPath(SEARCH_QUERY3) .appendQueryParameter(MOVIE_QUERY3, API_KEY3) .build(); URL url = null; try { url = new URL(uri.toString()); } catch (MalformedURLException exception) { Log.e(TAG, "Error creating URL", exception); } return url; } public void loadReviews(){ // COMPLETED (19) Create a bundle called queryBundle Bundle queryBundle = new Bundle(); // COMPLETED (20) Use putString with SEARCH_QUERY_URL_EXTRA as the key and the String value of the URL as the value// queryBundle.putString(SEARCH_QUERY_URL_EXTRA, url.toString()); // COMPLETED (21) Call getSupportLoaderManager and store it in a LoaderManager variable LoaderManager loaderManager = getSupportLoaderManager(); // COMPLETED (22) Get our Loader by calling getLoader and passing the ID we specified Loader<ArrayList<Review>> movieReviews = loaderManager.getLoader(REVIEW_SEARCH_LOADER); // COMPLETED (23) If the Loader was null, initialize it. Else, restart it. if (movieReviews == null) { loaderManager.initLoader(REVIEW_SEARCH_LOADER, queryBundle, this); } else { loaderManager.restartLoader(REVIEW_SEARCH_LOADER, queryBundle, this); } } #Override public Loader<ArrayList<Review>> onCreateLoader(int id, Bundle args) { return new AsyncTaskLoader<ArrayList<Review>>(this) { #Override protected void onStartLoading() { super.onStartLoading(); forceLoad(); } #Override public ArrayList<Review> loadInBackground() { String g = String.valueOf(movId); // Create URL object URL url = buildUrl3(g); // Perform HTTP request on the URL and receive a JSON response back String jsonResponse = ""; try { jsonResponse = getResponseFromHttpUrl(url); } catch (Exception e) { e.printStackTrace(); } reviews = MovieJsonUtils.parseReview(jsonResponse); return reviews; } }; } #Override public void onLoadFinished(Loader<ArrayList<Review>> loader, ArrayList<Review> dat) { if (reviews != null) { Intent intent = getIntent(); if (intent != null && intent.hasExtra(EXTRA_DATA_ID)) { //mButton.setText(R.string.update_button); if (mTaskId == DEFAULT_TASK_ID) { mTaskId = intent.getIntExtra(EXTRA_DATA_ID, DEFAULT_TASK_ID); AppExecutors.getInstance().diskIO().execute(new Runnable() { #Override public void run() { data.setMovieReviews(reviews); mDb.dataDao().updateData(data); //mDb.dataDao().insertData(data); final List<DataObject> task = mDb.dataDao().loadById(mTaskId); runOnUiThread(new Runnable() { #Override public void run() { populateUI(task); } }); } }); } } else { ReviewAdapter lv = new ReviewAdapter(ReviewActivity.this, reviews); reviewList.setAdapter(lv); } } } #Override public void onLoaderReset(Loader<ArrayList<Review>> loader) { }
Data gets loaded from MainActivity, the saved data is passed on to other activities as a parcellable bundle via intent, the passed data is displayed in DetailActivity but not in ReviewActivity.
Alternatively, if I can load reviews alongside YouTube keys from DetailActivity, I believe I can handle the database issue from there, but two Loaders wouldn't just work together, the app crashes; I am aware two AsyncTasks concurrently run together solved this problem, but I prefer to use Loaders because of performance on configuration change

Method is not called from onCreate

I am making classified marketplace android app. So, I have to show ads or post done by people on my home page, all is working and I am getting all my post on postman but not on my recycleview.
public class SearchFragment extends Fragment {
private static final String TAG = "SearchFragment";
private static final String BASE_URL = "http://35.188.133.114//elasticsearch/posts/post/";
private static final int NUM_GRID_COLUMNS = 2;
private static final int GRID_ITEM_MARGIN = 5;
//widgets
private ImageView mFilters;
private EditText mSearchText;
private FrameLayout mFrameLayout;
//vars
private String mElasticSearchPassword;
private String mPrefCity;
private String mPrefStateProv;
//private String mPrefCountry;
private String mPrefCollege;
private ArrayList<Post> mPosts;
private RecyclerView mRecyclerView;
private PostListAdapter mAdapter;
private ListView listView;
private String currentuser;
private String user;
private ImageView filter;
ArrayList<Card> list = new ArrayList<>();
FloatingActionButton fab;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_search, container, false);
mFilters = (ImageView) view.findViewById(R.id.ic_search);
mSearchText = (EditText) view.findViewById(R.id.input_search);
mRecyclerView = (RecyclerView) view.findViewById(R.id.recyclerView);
mFrameLayout = (FrameLayout) view.findViewById(R.id.container);
filter = (ImageView) view.findViewById(R.id.filter);
currentuser = FirebaseAuth.getInstance().getUid();
filter.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Intent intent = new Intent(getActivity(),FiltersActivity.class);
startActivity(intent);
}
});
getElasticSearchPassword();
welcome();
init();
return view;
}
private void setupPostsList(){
RecyclerViewMargin itemDecorator = new RecyclerViewMargin(GRID_ITEM_MARGIN, NUM_GRID_COLUMNS);
mRecyclerView.addItemDecoration(itemDecorator);
GridLayoutManager gridLayoutManager = new GridLayoutManager(getActivity(), NUM_GRID_COLUMNS);
mRecyclerView.setLayoutManager(gridLayoutManager);
mAdapter = new PostListAdapter(getActivity(), mPosts);
mRecyclerView.setAdapter(mAdapter);
// CustomListAdapter adapter = new CustomListAdapter(getActivity(), R.layout.card_layout_main, list);
}
private void welcome() {
if (!currentuser.equals("")) {
mPosts = new ArrayList<Post>();
Retrofit retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.build();
ElasticSearchAPI searchAPI = retrofit.create(ElasticSearchAPI.class);
HashMap<String, String> headerMap = new HashMap<String, String>();
headerMap.put("Authorization", Credentials.basic("user", mElasticSearchPassword));
// String searchString = "*";
/* if(!mSearchText.equals("")){
searchString = searchString + mSearchText.getText().toString() + "*";
}*/
/* if(!mPrefCity.equals("")){
searchString = searchString + " city:" + mPrefCity;
}
if(!mPrefStateProv.equals("")){
searchString = searchString + " state_province:" + mPrefStateProv;
}*/
/* if(!mPrefCollege.equals("")){
searchString = searchString + " college:" + mPrefCollege;
}*/
/*if(!currentuser.equals("")){
searchString = searchString + " user_id:" + currentuser;
}*/
Call<HitsObject> call = searchAPI.search(headerMap, "AND", "*");
call.enqueue(new Callback<HitsObject>() {
#Override
public void onResponse(Call<HitsObject> call, Response<HitsObject> response) {
HitsList hitsList = new HitsList();
String jsonResponse = "";
try {
Log.d(TAG, "onResponse: server response: " + response.toString());
if (response.isSuccessful()) {
hitsList = response.body().getHits();
} else {
jsonResponse = response.errorBody().string();
}
Log.d(TAG, "onResponse: hits: " + hitsList);
for (int i = 0; i < hitsList.getPostIndex().size(); i++) {
Log.d(TAG, "onResponse: data: " + hitsList.getPostIndex().get(i).getPost().toString());
mPosts.add(hitsList.getPostIndex().get(i).getPost());
}
Log.d(TAG, "onResponse: size: " + mPosts.size());
//setup the list of posts
setupPostsList();
} catch (NullPointerException e) {
Log.e(TAG, "onResponse: NullPointerException: " + e.getMessage());
} catch (IndexOutOfBoundsException e) {
Log.e(TAG, "onResponse: IndexOutOfBoundsException: " + e.getMessage());
} catch (IOException e) {
Log.e(TAG, "onResponse: IOException: " + e.getMessage());
}
}
#Override
public void onFailure(Call<HitsObject> call, Throwable t) {
Log.e(TAG, "onFailure: " + t.getMessage());
Toast.makeText(getActivity(), "search failed", Toast.LENGTH_SHORT).show();
}
});
}
// return false;
}
private void init(){
mFilters.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
mPosts = new ArrayList<Post>();
Retrofit retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.build();
ElasticSearchAPI searchAPI = retrofit.create(ElasticSearchAPI.class);
HashMap<String, String> headerMap = new HashMap<String, String>();
headerMap.put("Authorization", Credentials.basic("user", mElasticSearchPassword));
String searchString = "";
if(!mSearchText.equals("")){
searchString = searchString + mSearchText.getText().toString() + "*";
}
/* if(!mPrefCity.equals("")){
searchString = searchString + " city:" + mPrefCity;
}
if(!mPrefStateProv.equals("")){
searchString = searchString + " state_province:" + mPrefStateProv;
}*/
if(!mPrefCollege.equals("")){
searchString = searchString + " college:" + mPrefCollege;
}
/*if(!currentuser.equals("")){
searchString = searchString + " user_id:" + currentuser;
}*/
Call<HitsObject> call = searchAPI.search(headerMap, "AND", searchString);
call.enqueue(new Callback<HitsObject>() {
#Override
public void onResponse(Call<HitsObject> call, Response<HitsObject> response) {
HitsList hitsList = new HitsList();
String jsonResponse = "";
try{
Log.d(TAG, "onResponse: server response: " + response.toString());
if(response.isSuccessful()){
hitsList = response.body().getHits();
}else{
jsonResponse = response.errorBody().string();
}
Log.d(TAG, "onResponse: hits: " + hitsList);
for(int i = 0; i < hitsList.getPostIndex().size(); i++){
Log.d(TAG, "onResponse: data: " + hitsList.getPostIndex().get(i).getPost().toString());
mPosts.add(hitsList.getPostIndex().get(i).getPost());
}
Log.d(TAG, "onResponse: size: " + mPosts.size());
//setup the list of posts
setupPostsList();
}catch (NullPointerException e){
Log.e(TAG, "onResponse: NullPointerException: " + e.getMessage() );
}
catch (IndexOutOfBoundsException e){
Log.e(TAG, "onResponse: IndexOutOfBoundsException: " + e.getMessage() );
}
catch (IOException e){
Log.e(TAG, "onResponse: IOException: " + e.getMessage() );
}
}
#Override
public void onFailure(Call<HitsObject> call, Throwable t) {
Log.e(TAG, "onFailure: " + t.getMessage() );
Toast.makeText(getActivity(), "search failed", Toast.LENGTH_SHORT).show();
}
});
}
// return false;
});
}
welcome() method is not called as i am not able to see any post but init() method is working and showing all the post when clicking on search button. And both methods are using same code, the only difference of the query that I am making, do not know why welcome() method is not showing any post.
Actually, Your method is called from onCreate() but your condition (!currentuser.equals("") is return false.
See the value of currentuser = FirebaseAuth.getInstance().getUid();
Only if you authenticate the user,then you will have this as not null else it will be empty or null.
This is issue with Firbase issue, Please check the firebase instance is configured and initialized properly in your application class. Then you should not able to get currentUser == "".
Firebase will return 401/410 error code incase of invalid user token / authentication with invalid user information.

Retrofit 2 Calls onFailure Method after Posting Parameters to API

I have an app that posts several variables to an API and returns responses from the API via Retrofit2. This is actually a payment model where the user's paymentAmount , paymentType ,userID ,billNumber is sent to the API for payment process and responses are received in an AlertDialog to tell whether payment process was successful or not.
The issue here is that the API successfully receives my variables to initialize a payment process however it doesn't return the onResponse method. Rather the onFailure method is called making it unable to receive responses from the API.
This is the log i recieve when i call Throwable t.getCause() from the onFailure method. Please Help.
04-23 20:20:32.368 25592-25592/com.example.gamor.rhema E/ContentValues: Unable to submit post to API.java.net.SocketException: Socket closed
API Response Format
{
"RespCode": "0",
"PaymentNumber": "PYMNT000000000375",
"PaymentAmount": 0.5,
"PaymentDate": "4/23/2018 6:55:09 PM",
"Respmessage": "Successful"
}
My API Interface - APIServicePayBill.java
public interface APIServicePayBill {
#POST("PayBills")
#FormUrlEncoded
Call<PostPayBill> savePostPayBill(#Field("AccountNumber") String AccountNumber,
#Field("Amount") float Amount,
#Field("Paytype") String Paytype,
#Field("BillNumber") String BillNumber);
}
JSON POJO Class - PostPayBill.java
public class PostPayBill {
#SerializedName("RespCode")
#Expose
private String respCode;
#SerializedName("PaymentNumber")
#Expose
private String paymentNumber;
#SerializedName("PaymentAmount")
#Expose
private float paymentAmount;
#SerializedName("PaymentDate")
#Expose
private String paymentDate;
#SerializedName("Respmessage")
#Expose
private String respmessage;
public String getRespCode() {
return respCode;
}
public void setRespCode(String respCode) {
this.respCode = respCode;
}
public String getPaymentNumber() {
return paymentNumber;
}
public void setPaymentNumber(String paymentNumber) {
this.paymentNumber = paymentNumber;
}
public float getPaymentAmount() {
return paymentAmount;
}
public void setPaymentAmount(float paymentAmount) {
this.paymentAmount = paymentAmount;
}
public String getPaymentDate() {
return paymentDate;
}
public void setPaymentDate(String paymentDate) {
this.paymentDate = paymentDate;
}
public String getRespmessage() {
return respmessage;
}
public void setRespmessage(String respmessage) {
this.respmessage = respmessage;
}
#Override
public String toString() {
return "PostPayBill{" +
"respCode='" + respCode + '\'' +
", paymentNumber='" + paymentNumber + '\'' +
", paymentAmount=" + paymentAmount +
", paymentDate='" + paymentDate + '\'' +
", respmessage='" + respmessage + '\'' +
'}';
}
}
ApiUtils Class - ApiUtils.java
public class ApiUtils {
private ApiUtils() {}
public static final String BASE_URL = "http://10.1.123.11/api/";
public static APIServicePayBill getUserServicePayBill(){
return RetrofitClient.getClient(BASE_URL).create(APIServicePayBill.class);
}
}
API Initialising
apiServicePayBill = ApiUtils.getUserServicePayBill();
Payment Method
private void sentPayBillsDetails(String AccountNumber, float Amount, String Paytype, String BillNumber ) {
apiServicePayBill.savePostPayBill(AccountNumber,Amount,Paytype,BillNumber).enqueue(new Callback<PostPayBill>() {
#Override
public void onResponse(Call<PostPayBill> call, Response<PostPayBill> response) {
if (response.isSuccessful()){
Log.i(TAG, "post submitted to API." + response.body().toString());
if ( progressDialog!=null && progressDialog.isShowing() ){
progressDialog.dismiss();
}
AlertDialog.Builder registrationAlert = new AlertDialog.Builder(MakePaymentActivity.this);
registrationAlert.setTitle(Html.fromHtml("<font color='#125688'>PAYMENT STATUS</font>"));
registrationAlert.setIcon(R.drawable.ic_check_box);
registrationAlert.setMessage("Payment Number: "+response.body().getPaymentNumber()+
"\nPayment Amount: "+response.body().getPaymentAmount()+
"\nPayment Date: "+response.body().getPaymentDate()+
"\nMessage: "+response.body().getRespmessage());
registrationAlert.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i) {
gotoRegistrationPage();
}
});
registrationAlert.setCancelable(false);
AlertDialog alertDialog = registrationAlert.create();
alertDialog.show();
}
}
#Override
public void onFailure(Call<PostPayBill> call, Throwable t) {
Log.e(TAG, "Unable to submit post to API."+t.getCause());
if ( progressDialog!=null && progressDialog.isShowing() ){
progressDialog.dismiss();
}
AlertDialog.Builder registrationAlert = new AlertDialog.Builder(MakePaymentActivity.this);
registrationAlert.setTitle(Html.fromHtml("<font color='#125688'>PAYMENT STATUS</font>"));
registrationAlert.setIcon(R.drawable.ic_check_box);
registrationAlert.setMessage("Unable to submit post to API");
registrationAlert.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i) {
gotoFaliedPage();
}
});
registrationAlert.setCancelable(false);
AlertDialog alertDialog = registrationAlert.create();
alertDialog.show();
}
});
}
Gradle File
// Retrofit
implementation 'com.squareup.retrofit2:retrofit:2.4.0'
// JSON Parsing
implementation 'com.google.code.gson:gson:2.6.1'
implementation 'com.squareup.retrofit2:converter-gson:2.4.0'

Google Play: update prices from IInAppBillingService

I created a class for working with subscriptions in the store.
In the beginning I receive from the server the list of subscriptions with the prices
The code is working and on most devices there is no problem.
But some users do not recive prices. It's like there's no response from the server. I've studied examples of implementation in Google documentation, but I can not understand where I can have problems in the code.
Part of my code:
public class BillingActivity extends AppCompatActivity {
RelativeLayout imageLayout;
View payButton;
// WebView payWebView;
// TextView useCodeButton;
ProgressBar progress1;
ProgressBar progress2;
ProgressBar progress3;
IInAppBillingService inAppBillingService;
#Override
public void onCreate(#Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_billing_subscription);
price_1monthTextView = (TextView) findViewById(R.id.price_1monthTextView);
relative_1month = (RelativeLayout) findViewById(R.id.relative_1month);
relative_1month.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (MainActivity.myAccount == null) return;
if (MainActivity.myAccount.getUniqid() == null) return;
if (subscription1m != null) {
try {
Log.d("my", "purchase..." + subscription1m.storeName);
purchaseProduct(subscription1m);
} catch (Exception e) {
e.printStackTrace();
Log.d("my", "purchase error = " + e.toString());
}
}
}
});
progress1 = (ProgressBar) findViewById(R.id.progress1);
startGoogleBilling();
}
private void startGoogleBilling() {
if (serviceConnection != null) {
unbindService(serviceConnection);
}
progress1.setVisibility(View.VISIBLE);
serviceConnection = new ServiceConnection() {
#Override
public void onServiceConnected(ComponentName name, IBinder service) {
inAppBillingService = IInAppBillingService.Stub.asInterface(service);
getSubscribtionsList();
}
#Override
public void onServiceDisconnected(ComponentName name) {
inAppBillingService = null;
}
};
Intent serviceIntent =
new Intent("com.android.vending.billing.InAppBillingService.BIND");
serviceIntent.setPackage("com.android.vending");
bindService(serviceIntent, serviceConnection, Context.BIND_AUTO_CREATE);
}
private static final int PR_CNT = 3;
List<InAppProduct> subscriptions = null;
InAppProduct subscription1m = null;
InAppProduct subscription3m = null;
InAppProduct subscription1y = null;
String[] productIds = {"eq.subscription.1m", "eq.subscription.3m.2", "eq.subscription.1y"};
private void getSubscribtionsList() {
mSwipeRefreshLayout.setRefreshing(false);
progress1.setVisibility(View.GONE);
try {
subscriptions =
getInAppPurchases("subs", productIds[0], productIds[1], productIds[2]);
if (subscriptions.size() == PR_CNT) {
for (InAppProduct inAppProduct : subscriptions) {
String productId = inAppProduct.productId;
Log.d("my", "productId= " + productId);
if (productId.contains(productIds[0])) subscription1m = inAppProduct;
if (productId.contains(productIds[1])) subscription3m = inAppProduct;
if (productId.contains(productIds[2])) subscription1y = inAppProduct;
}
Log.d("my", "1m= " + subscription1m.storeName + " pr=" + subscription1m.price + "\\n\\r " +
"3m= " + subscription3m.storeName + " pr=" + subscription3m.price + "\\n\\r " +
"1y= " + subscription1y.storeName + " pr=" + subscription1y.price + "\\n\\r ");
///----------------------!!!!
// purchaseProduct(inAppProduct);
}
updatePrices();
} catch (Exception e) {
Log.d("my", "exc = " + e.toString());
if (e.toString().contains("Attempt to invoke interface method 'android.os.Bundle com.android.vending.billing.IInAppBillingService.getSkuDetails")) {
if (attempt < 4) {
//getSubscribtionsList();
// startGoogleBilling();
} else {
}
}
// Toast.makeText(this, "Google inApp connection error", Toast.LENGTH_SHORT).show();
// refreshButton.setVisibility(View.VISIBLE);
startGoogleBilling();
}
}
private int attempt = 0;
#Override
public void onDestroy() {
super.onDestroy();
if (serviceConnection != null) {
unbindService(serviceConnection);
}
}
class InAppProduct {
public String productId;
public String storeName;
public String storeDescription;
public String price;
public boolean isSubscription;
public int priceAmountMicros;
public String currencyIsoCode;
public String getSku() {
return productId;
}
String getType() {
return isSubscription ? "subs" : "inapp";
}
}
List<InAppProduct> getInAppPurchases(String type, String... productIds) throws Exception {
ArrayList<String> skuList = new ArrayList<>(Arrays.asList(productIds));
Bundle query = new Bundle();
query.putStringArrayList("ITEM_ID_LIST", skuList);
Bundle skuDetails = inAppBillingService.getSkuDetails(
3, getPackageName(), type, query);
ArrayList<String> responseList = skuDetails.getStringArrayList("DETAILS_LIST");
List<InAppProduct> result = new ArrayList<>();
for (String responseItem : responseList) {
JSONObject jsonObject = new JSONObject(responseItem);
InAppProduct product = new InAppProduct();
// "com.example.myapp_testing_inapp1"
product.productId = jsonObject.getString("productId");
// Покупка
product.storeName = jsonObject.getString("title");
// Детали покупки
product.storeDescription = jsonObject.getString("description");
// "0.99USD"
product.price = jsonObject.getString("price");
// "true/false"
product.isSubscription = jsonObject.getString("type").equals("subs");
// "990000" = цена x 1000000
product.priceAmountMicros =
Integer.parseInt(jsonObject.getString("price_amount_micros"));
// USD
product.currencyIsoCode = jsonObject.getString("price_currency_code");
result.add(product);
}
return result;
}
private void updatePrices() {
if (subscriptions.size() == PR_CNT) {
price_1monthTextView.setText(subscription1m.price);
price_3monthTextView.setText(subscription3m.price);
price_1yearTextView.setText(subscription1y.price);
}
}
}
my problem was the bit depth of the X variable priceAmountMicros
The price from playmarket is multiplied by a 1000000 , and Kazakh tenge has exchange rate = 1 USD= 331,3 KZT.
And if i have price 18 000 KTZ and * 1000 000.
For price variable I must use long type

Update data of IntentService from activity

I have an IntentService to upload images to server (source below). While upload is in progress, user might select more images to upload. Right now it spawns another service. How can I add data to same running service or spawn new service if its not running
public class UploadService extends IntentService {
public static final String TAG = UploadService.class.getSimpleName();
public static final String ACTION_UPLOAD = UploadService.class.getName() + ".UPLOAD";
public static final String EXTRA_RESOURCE_ID = "resource_id";
public static final String EXTRA_RESOURCE_NAME = "resource_name";
public static final String EXTRA_IMAGES = "images";
private static final int CONCURRRENT_UPLOAD_COUNT = 3;
private static final int UPLOAD_STATUS_PENDING = 0;
private static final int UPLOAD_STATUS_UPLOADING = 1;
private static final int UPLOAD_STATUS_UPLOADED = 2;
private static final int UPLOAD_STATUS_FAILED = 3;
private static final int UPLOAD_STATUS_TERMINATED = 4;
private ArrayList<DiskImage> mImages = new ArrayList<>();
private ArrayMap<DiskImage, Integer> mStatusMap = new ArrayMap<>();
private OkHttpClient mOkHttpClient = new OkHttpClient();
public UploadService() {
super(TAG);
}
#Override
protected void onHandleIntent(Intent intent) {
if (intent.getAction().equals(ACTION_UPLOAD)) {
String resId = intent.getStringExtra(EXTRA_RESOURCE_ID);
String resName = intent.getStringExtra(EXTRA_RESOURCE_NAME);
ArrayList<DiskImage> images = intent.getParcelableArrayListExtra(EXTRA_IMAGES);
for (DiskImage image : images) {
image.mUploadId = resId;
image.mUploadResName = resName;
}
mImages.addAll(images);
upload(); // start the upload
updateNotification();
}
}
private int getUploadedImageCount() {
int count = 0;
for (int i = 0; i < mImages.size(); i++)
if (getStatus(mImages.get(i)) == UPLOAD_STATUS_UPLOADED)
count++;
return count;
}
private void updateNotification() {
UploadNotification.notify(UploadService.this, mImages.size(), getUploadedImageCount());
}
private void upload() {
final DiskImage image = getImageToUpload();
if (image != null) {
// show notification
MediaType mediaType = MediaType.parse(image.mimeType);
RequestBody requestBody = new MultipartBody.Builder()
.setType(MultipartBody.FORM)
.addFormDataPart("resource_id", image.mUploadId)
.addFormDataPart("resource_name", image.mUploadResName)
.addFormDataPart("image", getName(image.path),
RequestBody.create(mediaType, new File(image.path)))
.build();
Request request = new Request.Builder()
.url(getUploadUrl())
.post(requestBody)
.build();
mStatusMap.put(image, UPLOAD_STATUS_UPLOADING);
// Log.i(TAG, "Uploading image " + getName(image.path));
mOkHttpClient.newCall(request).enqueue(new Callback() {
#Override
public void onFailure(Call call, IOException e) {
mStatusMap.put(image, UPLOAD_STATUS_FAILED);
// add failed image in end
mImages.remove(image);
mImages.add(image);
// Log.i(TAG, "Upload failed " + getName(image.path));
upload();
e.printStackTrace();
}
#Override
public void onResponse(Call call, Response response) throws IOException {
// Log.i(TAG, "Uploaded image " + getName(image.path) + " Response: " + response.body().string());
mStatusMap.put(image, UPLOAD_STATUS_UPLOADED);
upload(); // upload next image
updateNotification();
}
});
}
}
private String getName(String path) {
return path.substring(path.lastIndexOf(File.separator) + 1, path.length());
}
private DiskImage getImageToUpload() {
for (int i = 0; i < mImages.size(); i++)
if (getStatus(mImages.get(i)) == UPLOAD_STATUS_PENDING)
return mImages.get(i);
return null;
}
private String getUploadUrl() {
return String.format(Constants.ALBUM_IMAGE_UPLOAD_URL, Preferences.getToken(this));
}
private int getStatus(DiskImage image) {
if (mStatusMap.get(image) == null)
return UPLOAD_STATUS_PENDING;
return mStatusMap.get(image);
}
}
Couldn't you just extend Service (not IntentService), bind your Activity to the Service and then call a method of this Service, that does the upload of the picture.
In this way, your service will run until you call stopSelf() in the service or stopService() in your bounded activity. Hence, you could use the same service to do multiple uploads.
Please let me know if this answer helped a bit...

Categories

Resources