How can I map a string and compare with another string? - android

This question might be silly but I'm not able to achieve this. I have a payment device that I'm connected via bluetooth to my app. For the device to display currency code, I need to pass a string, like this :
String codeForPaymendDevice = "978";
This "978" basically sends "EUR" currency code and displays on the screen of the payment device. (The device's library maps and handles this). In my app, when the user makes a purchase in EUR currency, it should compare with "978(EUR)" and if both matches, it should parse codeForPaymentDevice. I'm not able to do this because I cannot compare "EUR" with 978 (as my code doesn't know 978 is EUR, only the payment device knows 978 is EUR).
What I need to do is, map "978" to "EUR" code and then compare transaction.getCurrencyCode() with the mapped variable and then parse it.
private SaleRequest buildTransactionRequest(Transaction transaction) {
final SaleRequest tr = new SaleRequest();
BigDecimal amount = getAmountPaid();
String codeForPaymentDevice = "978";
String formattedAmount;
try {
if (!transaction.getCurrencyCode().equalsIgnoreCase(CREW_CURRENCY)) {
formattedAmount = AirFiApplication
.getPriceFormatter(AirFiApplication.getCurrency(transaction.getCurrencyCode())).format(amount);
// transaction.getCurrencyCode = EUR
tr.setCurrency(codeForPaymentDevice); // TODO remove hardcoding
}
} catch (MPosValueException e) {
LOG.error("Error while building transaction request due to {}", e.getLocalizedMessage());
}
return tr;
}

You can create a Map with some key (for now I have used currency code) with the value you need to pass as the value.
Map<String, String> map = new HashMap<>();
map.put("EUR", "978");
map.put("INR", "979");
map.put("USD", "980");
map.put("AED", "981");
...
In your code,
tr.setCurrency(map.get(transaction.getCurrencyCode()));

Related

Show hourly price on Stripe payment instead of deposit price

For a rental company, we need to set up deferred payment.
When a user rents an item we must lock $25 on his credit card (a deposit).
He will be charged $1 per hour. If he returns his item within 5 hours, he will be charged $5. After 25 hours we consider the item lost and it is charged the full price $25.
At the time of the customer payment validation we should show a $1 bill (not a $25 bill).
We managed to implement this on Apple Pay with pkdeferredpaymentsummaryitem.
Do you have any idea how to implement this with Stripe Pay?
For the moment here is our code:
public PaymentIntent createCapturePaymentIntent(String amount, String currency, String customerId,
String paymentMethodId, String description) throws Exception {
Map < String, Object > params = new HashMap < > ();
params.put("amount", amount);
params.put("currency", currency);
params.put("customer", customerId);
if (null != paymentMethodId) {
params.put("payment_method", paymentMethodId);
}
params.put("description", description);
// params.put("confirm", "true");
params.put("capture_method", "manual");
LoggerHelper.mdc("stripe", "createCapturePaymentIntent body ==> {}", JacksonUtils.toJson(params));
PaymentIntent paymentIntent = null;
try {
paymentIntent = PaymentIntent.create(params, requestOptions);
} catch (CardException e) {
LoggerHelper.mdc("stripe", "createCapturePaymentIntent error ==> {}: {}", e.getCode(), e.getMessage());
String paymentIntentId = e.getStripeError().getPaymentIntent().getId();
paymentIntent = PaymentIntent.retrieve(paymentIntentId, requestOptions);
}
LoggerHelper.mdc("stripe", "createCapturePaymentIntent result ==> {}", JSON.toJson(paymentIntent));
return paymentIntent;
}
But the user is shown a $25 bill instead of a $1 one:
Apple Pay Documentation: pkdeferredpaymentsummaryitem
Edit: Do you think creating a $1 payment with the option setup_future_usage set to off_session is a good idea to achieve our goal?
Since your customers agree to your certain terms and condition, your app UI can display $1 on the frontend and while in the background, you'll deduct the full $25. This should solve it if stripe doesn't have the API method to do that

Retrofit - Send request body as array or number

I'm using Retrofit 2 and I need to send request body. The problem is somehow the value is converted to string. On the example below, you can see that items and totalPrice which should be array and number respectively are converted to string.
{ cashierId: 'fff7079c-3fc2-453e-99eb-287521feee63',
items: '[{"amount":3,"id":"602a79e3-b4c1-4161-a082-92202f92d1d6","name":"Play Station Portable","price":1500000.0}]',
paymentMethod: 'Debt',
totalPrice: '4500000.0' }
The desired request body is
{ cashierId: 'fff7079c-3fc2-453e-99eb-287521feee63',
items: [{"amount":3,"id":"602a79e3-b4c1-4161-a082-92202f92d1d6","name":"Play Station Portable","price":1500000.0}],
paymentMethod: 'Debt',
totalPrice: 4500000.0 }
Here's the service
#POST("api/sales")
#FormUrlEncoded
Call<Sale> createSale(
#FieldMap Map<String, Object> fields
);
And this is how I call createSale
Map<String, Object> fields = new HashMap<>();
fields.put("cashierId", UUID.fromString("fff7079c-3fc2-453e-99eb-287521feeaaa"));
fields.put("totalPrice", totalPrice);
fields.put("paymentMethod", paymentMethod);
fields.put("items", jsonArray);
Call<Sale> call = retailService.createSale(fields);
Is it possible to send those values as number and array, not as string?
The conversion most certainly happens because you are using #FormUrlEncoded.
According to the documentation:
Field names and values will be UTF-8 encoded before being URI-encoded in accordance to RFC-3986.
A solution would be to use a model class instead of a Map. I see you already have a Sale class. If it looks like something like this:
public class Sale {
String cashierId;
int totalPrice;
String paymentMethod;
ArrayList<SomeObject> items;
}
you can simply do like this:
// in service
#POST("api/sales")
Call<Sale> createSale(#Body Sale sale);
// when doing the call
Sale sale = new Sale();
// set everything in your object
// then
Call<Sale> call = retailService.createSale(sale);

JSoup web-scraping: How to select each value

I'm currently trying to get some values from a website with Jsoup for my android application.
Basically, I wanted to extract these values:
so that in the code, the model name should go to gpuModel variable, prices goes to gpuPrice and so on for every single Graphic card. and then I would store them in firebase using this code:
public void addToDatabase(String model, int price, int rating, double value,
double bench) {
Map<String, Object> docData = new HashMap<>();
docData.put("model", model);
docData.put("rating", rating);
docData.put("bench", bench);
docData.put("value", value);
docData.put("price", price);
db.collection("gpu").document(model).set(docData);
}
This is the HTML code for each GPU:
i am currently trying to extract only the gpu model name to keep it simple (in the end i want to extract all the other values too), this is my current web scraping code:
public void webScrape(){
new Thread(new Runnable() {
#Override
public void run() {
final StringBuilder builder = new StringBuilder();
try {
Document doc = Jsoup.connect("https://www.videocardbenchmark.net/GPU_mega_page.html").get();
Elements gpus = doc.select("[id^=gpu]");
for (Element i : gpus) {
Elements gpuModel = i.select("tr td:nth-child(2)");
String gpuName = gpuModel.text().replace("/", "");
addToDatabase(gpuName, 12,12,12,12);
}
} catch (IOException e){
e.printStackTrace();
}
runOnUiThread(new Runnable() {
#Override
public void run() {
}
});
}
}).start();
going by my logic, this should select all the GPU, and then in the for loop, it would extract only the card's name. set the gpuName to whatever was extracted and push it to the database.
But instead, I got this in my database:
It extracted the GPU name, but also all the other unwanted fields (including the prices, value, test date, etc).
so my question is, how do i select each value separately? all the examples i found on the internet was done with a very simple website where each value has their own ID so I can't really learn from them.
If there's anything i should provide, please do tell me.
simple code representation of what i want:
Document doc = Jsoup.connect(the url).get();
Elements gpus = doc.select(all gpu);
for (each gpu in all gpus) {
gpuName = gpu.select(name);
gpuPrice = gpu.select(price);
gpuValue = gpu.select(value);
gpuPower = gpu.select(power);
addToDatabase(gpuName, gpuPrice, gpuPower, gpuValue);
}
You should use a:nth-child(2) as the model name selector inside your run method:
Elements gpuModel = i.select("a:nth-child(2)");

Iterate through MySql to ListView in Android

I wrote an Android App that pulls data from a MySql Database on a remote web server. The information is parsed and displayed in a listview. The listview also displays images which could slow down the activity. I was wondering how I could only display items 0-9, then when you click a button it will display 10-19, and so on. I can do it in VB using "do until" but as far as android/java, I am kind of lost. Any help would be appreciated.
Below is the class where I need to implement it. I believe I would need to add an Integer to keep count and implement a form of "DO UNTIL" before I loop through the array and add a count to the "Integer" but I am not sure how to go about it here.
class ProductQuery extends AsyncTask<String, String, String>{
#Override
protected String doInBackground(String... file_url) {
// TODO Auto-generated method stub
try{
//Settings to send to PHP
List<NameValuePair> settings = new ArrayList<NameValuePair>();
//Adding Search Criteria(Keyword) to settings
settings.add(new BasicNameValuePair("product", product));
//Getting JSON result from request
JSONObject jObject = jParser.makeHttpRequest(url_to_php, "GET", settings);
//Display JSON in LogCat
Log.d("Product Search", jObject.toString());
//Get Result
int result = jObject.getInt(KEY_RESULT);
//If Result Equals 1 then
if(result==1){
//Getting the KEY_PRODUCTS
products = jObject.getJSONArray(KEY_PRODUCTS);
//Loop through Array
for(int i = 0; i < products.length();i++){
JSONObject x = products.getJSONObject(i);
String proPid = x.getString(KEY_PRODID);
String name = x.getString(KEY_NAME);
String price = x.getString(KEY_PRICE);
String desc = x.getString(KEY_DESCRIPTION);
String img = x.getString(KEY_IMAGE);
// creating new HashMap
HashMap<String, String> hmap = new HashMap<String, String>();
hmap.put(KEY_PRODID, proPid);
hmap.put(KEY_NAME, name);
hmap.put(KEY_PRICE, price);
hmap.put(KEY_DESCRIPTION, desc);
hmap.put(KEY_IMAGE, img);
//Hash to ArrayList
myproducts.add(hmap);
}
} else {
}
} catch (JSONException e) {
e.printStackTrace();
}
return null;
}
Instead of making pagination in the app, you should leave this to the server.
On your server, you should change the way you receive requests, so that when you call your server, you post a start index to fetch rows from and how many rows you want fetched for each request.
So the url to the server could look like this:
http://example.com/myjsonrequest.php?startindex=10&numofrows=10
In your PHP select statement on your server, you change it so it selects only the rows you need, like so:
SELECT * FROM my_table LIMIT $startindex, $numofrows;
Remember to check for SQL injections of course.
This way, you only fetch the data you actually want instead of fetching all the data in one go. Remember, your app is on a mobile OS, with a somewhat volatile internet connection sometimes, so if the data you're returning is growing, it wouldn't be nice from a user-perspective to sit and wait for all the data to load, especially when some of it, isn't needed yet.
For instance if you get let's say 1000 rows of data returned, that would take a while to fetch over a mobile internet connection.
After you receive the JSonObject with only a limited amount of entries, you can now parse it without keeping track of how many entries are returned.
Inside your Android app, all you need to keep track of is what index in the database, the user has seen so far and then increment this counter every time the user fetches a new page.

How to know whether liked the post or not without doing searching in the list

I tried to use the fql query to get json response,I used this code for doing this
String postid=jsonObject.getString("id");
String query = "SELECT likes.user_likes FROM stream WHERE post_id = \'" + postid + "'";
Bundle params = new Bundle();
params.putString("method", "fql.query");
params.putString("query", query);
String fqlResponse = Utility.mFacebook.request(params);
System.out.println(fqlResponse);
But I am getting null pointer exception at Utility.mFacebook.request(params);
I am using the default class in Github
I personally find the Facebook Graph API a little inadequate at times. For example, in your current requirement, if you need to use just the Graph API, you will need to first, get a list of all Users who have liked a particular post. After you have a list, you will then have to check if the User ID matches that of the logged in User and then, based on the result, run a function or something.
Instead, FQL offers a simpler function. In my app, for the exact same function, I exclusively make use of FQL.
You can fire a simple query. For example:
SELECT likes.user_likes FROM stream WHERE post_id ='XXXXXXXXXXXXX_XXXXXXXXX'
Replace the X's with the Post's ID. Make sure you surround the Post ID with 'YOUR_POST_ID'
Try it like this in the Graph API Explorer: fql?q=SELECT likes.user_likes FROM stream WHERE post_id = 'ENTER_YOUR_POST_ID'
After running the query, you should get a result that looks this this:
{
"data": [
{
"likes": {
"user_likes": true
}
}
]
}
If the User likes the Post, the field user_likes will be true and false if the User has not liked the Post.
You can parse the result like this (pseudo code):
if (JOLikeStatus.has("likes")) {
JSONObject optLikes = JOLikeStatus.optJSONObject("likes");
if (optLikes.has("user_likes")) {
String getUserLikes = optLikes.getString("user_likes");
if (getUserLikes.equals("true")) {
String getLikeStatus = "true";
} else if (getUserLikes.equals("false")) {
String getLikeStatus = "false";
}
} else {
String getLikeStatus = null;
}
} else {
String getLikeStatus = null;
}
EDIT 2: To get the number (count) of total likes, modify the earlier query like this:
fql?q=SELECT likes.user_likes, likes.count FROM stream WHERE post_id = 'ENTER_YOUR_POST_ID'

Categories

Resources