Token is showing expired when sending from android - java

When I'm sending a token(Bearer) from postman it is working fine. But when I'm sending the same token from the android app and it is showing token is expired but is it fresh and not expired and token is working fine with the postman.
I tried sending a get request without token and it is working fine. The server is running fine the class is working as excepted except authetication.
Node js code for checking the token:
const jwt = require('jsonwebtoken');
const JWT_KEY = require('../../config').getJwtSecrete();
module.exports = async (req, res, next) => {
try {
let token = req.headers.authorization;
token = getTokenFromHeader(token);
const decoded = jwt.verify(token, JWT_KEY);
req.email = decoded.email;
next();
} catch (error) {
return res.status(401).json({
message: 'Auth failed'
});
}
};
function getTokenFromHeader(token) {
return token.split(" ")[1];
}
Android: My get request method for sending the request
public class GET_Request extends AsyncTask<String, Void, Bundle> {
private static final String REQUEST_METHOD = "GET";
private static final int READ_TIMEOUT = 10000;
private static final int CONNECTION_TIMEOUT = 10000;
private GETAsyncResponse delegate;
public GET_Request(GETAsyncResponse delegate) {
this.delegate = delegate;
}
#Override
protected Bundle doInBackground(String... params) {
String Url = params[0];
Bundle bundle = new Bundle();
String result = null;
BufferedInputStream bufferedInputStream;
ByteArrayOutputStream byteArrayOutputStream;
try {
URL requestUrl = new URL(Url);
HttpURLConnection connection = (HttpURLConnection) requestUrl.openConnection();
connection.setRequestMethod(REQUEST_METHOD);
connection.setReadTimeout(READ_TIMEOUT);
connection.setConnectTimeout(CONNECTION_TIMEOUT);
connection.setDoInput(true);
connection.setUseCaches(false);
connection.setRequestProperty("Content-Type", "application/json; charset=UTF-8");
connection.setRequestProperty("Accept", "application/json");
connection.setRequestProperty("Authorization", "Bearer " + UserInfo.getToken());
connection.connect();
if (connection.getResponseCode() == HTTP_OK) {
bufferedInputStream = new BufferedInputStream(connection.getInputStream());
int bisReadResult = bufferedInputStream.read();
byteArrayOutputStream = new ByteArrayOutputStream();
while (bisReadResult != -1) {
byteArrayOutputStream.write((byte) bisReadResult);
bisReadResult = bufferedInputStream.read();
}
result = byteArrayOutputStream.toString();
} else { //reading error
Log.e("doInBackground: ", String.valueOf(connection.getResponseCode()));
String error;
bufferedInputStream = new BufferedInputStream(connection.getInputStream());
int bisRealError = bufferedInputStream.read();
byteArrayOutputStream = new ByteArrayOutputStream();
while (bisRealError != -1) {
byteArrayOutputStream.write((byte) bisRealError);
bisRealError = bufferedInputStream.read();
}
/*This error string is for debugging*/
error = byteArrayOutputStream.toString();
Log.e("Error Buffer: ", error);
}
bundle.putString(JSON, result);
bundle.putInt(RESPONSE_CODE, connection.getResponseCode());
connection.disconnect();
} catch (FileNotFoundException f) {
f.printStackTrace();
bundle.putInt(RESPONSE_CODE, 400);
}
/*Internet not connected*/ catch (SocketTimeoutException s) {
bundle.putInt(RESPONSE_CODE, 0);
}
/*Any other error*/ catch (IOException e) {
e.printStackTrace();
bundle.putInt(RESPONSE_CODE, 500);
}
return bundle;
}
protected void onPostExecute(Bundle result) {
super.onPostExecute(result);
delegate.AfterGetRequestFinish(result);
}
public interface GETAsyncResponse {
void AfterGetRequestFinish(Bundle bundle);
}
}
I want it to authenticate successfully. But I don't know why it is failing and showing code '401' and 'java.io.FileNotFoundException'.

One of the features of JWT is that they are essentially tamper-proof. That is, assuming your suspect JWT has a valid signature and checksum on the Node JS server side, then it means that your Android Java code could not possibly have altered the expiration date of that token.
That being said, the most likely explanation here is that the token you are passing in fact has already expired. This could come about for a number of reasons, most likely that you have cached an old token somewhere, perhaps in shared preferences.

Related

How to create library for GCM, library creation does not work

I'm trying to create a library for my apps, in all my apps have push notification.
I would like to take this package and create a library
In GCM do I have any limitations? Because it looks like it gets the package name to generate ID_TOKEN
I have an APP that has a package with the classes I use for PUSH notification, it works perfectly!
Now I've migrated this package and created a library, because so all other apps are just pointing the lib and it will be working.
Only that for some reason he does not call the lib, I've done everything and I can not.
The code to register the ID in GCM and start the service is this below:
Intent intent = new Intent(this, RegistrationIntentService.class);
startService(intent);
This code above is in my MainActivity
I thought that by doing so he would already call the library
EDIT:
I am using Eclipse and GCM
My class `RegistrationIntentService`
public class RegistrationIntentService extends IntentService {
private static final String TAG = "RegServicePush";
String newRegID = "";
String GetEmail = "";
public RegistrationIntentService() {
super(TAG);
}
#Override
protected void onHandleIntent(Intent intent) {
try {
InstanceID instanceID = InstanceID.getInstance(this);
String token = instanceID.getToken(Constants.GCM_SENDER_ID, GoogleCloudMessaging.INSTANCE_ID_SCOPE, null);
// TODO: Implement this method to send any registration to your
// app's servers.
sendRegistrationToServer(token, email);
} catch (Exception e) {
Log.d(TAG, "Failed to complete token refresh", e);
}
// Notify UI that registration has completed, so the progress indicator
// can be hidden.
}
private void sendRegistrationToServer(String token, String email) {
//MainActivity.newRegID = token;
WebServerRegistrationTask webServer = new WebServerRegistrationTask();
webServer.execute();
}
public class WebServerRegistrationTask extends AsyncTask<Void, Void, Void> {
#Override
protected Void doInBackground(Void... params) {
SharedPreferences sharedPreferences = PreferenceManager
.getDefaultSharedPreferences(RegistrationIntentService.this);
URL url = null;
try {
url = new URL(Constants.WEB_SERVER_URL);
} catch (MalformedURLException e) {
e.printStackTrace();
sharedPreferences.edit().putString(Constants.PREF_GCM_REG_ID, "").apply();
}
Map<String, String> dataMap = new HashMap<String, String>();
dataMap.put("regID", newRegID);
dataMap.put("appID", Constants.APP_ID);
StringBuilder postBody = new StringBuilder();
Iterator<Map.Entry<String, String>> iterator = dataMap.entrySet().iterator();
while (iterator.hasNext()) {
Entry<String, String> param = (Entry<String, String>) iterator.next();
postBody.append(param.getKey()).append('=').append(param.getValue());
if (iterator.hasNext()) {
postBody.append('&');
}
}
String body = postBody.toString();
byte[] bytes = body.getBytes();
HttpURLConnection conn = null;
try {
conn = (HttpURLConnection) url.openConnection();
conn.setDoOutput(true);
conn.setUseCaches(false);
conn.setFixedLengthStreamingMode(bytes.length);
conn.setRequestMethod("POST");
conn.setRequestProperty("Content-Type", "application/x-www-form-urlencoded;charset=UTF-8");
OutputStream out = conn.getOutputStream();
out.write(bytes);
out.close();
String response = "";
InputStream is = null;
try {
is = conn.getInputStream();
int ch;
StringBuffer sb = new StringBuffer();
while ((ch = is.read()) != -1) {
sb.append((char) ch);
}
response = sb.toString();
} catch (IOException e) {
throw e;
} finally {
if (is != null) {
is.close();
}
}
int status = conn.getResponseCode();
if (status == 200) {
if (response.equals("1")) {
sharedPreferences.edit().putString(Constants.PREF_GCM_REG_ID, newRegID).apply();
Intent registrationComplete = new Intent(Constants.SERVER_SUCCESS);
LocalBroadcastManager.getInstance(RegistrationIntentService.this)
.sendBroadcast(registrationComplete);
}
} else {
throw new IOException("Request failed with error code " + status);
}
} catch (ProtocolException pe) {
pe.printStackTrace();
sharedPreferences.edit().putString(Constants.PREF_GCM_REG_ID, "").apply();
} catch (IOException io) {
io.printStackTrace();
sharedPreferences.edit().putString(Constants.PREF_GCM_REG_ID, "").apply();
} finally {
if (conn != null) {
conn.disconnect();
}
}
return null;
}
}
}

My JSON looks different after sending through HTTP from android app to nodejs server

When I'm trying to send a json as a string through HTTP to a nodejs server, there when I'm trying to log request.body it looks different and I can't acces any field.
My class that send request to server:
public class SendData extends AsyncTask<String, Void, String> {
#Override
protected String doInBackground(String... strings) {
String data = "";
HttpURLConnection httpURLConnection = null;
try{
httpURLConnection = (HttpURLConnection)new URL(strings[0]).openConnection();
httpURLConnection.setRequestMethod("POST");
httpURLConnection.setDoOutput(true);
DataOutputStream wr = new DataOutputStream(httpURLConnection.getOutputStream());
wr.writeBytes(strings[1]);
wr.flush();
wr.close();
InputStreamReader inputStreamReader = new InputStreamReader(httpURLConnection.getInputStream());
int inputStreamData = inputStreamReader.read();
while (inputStreamData != -1){
char current = (char) inputStreamData;
inputStreamData = inputStreamReader.read();
data += current;
}
} catch (Exception e){
e.printStackTrace();
} finally {
if(httpURLConnection != null){
httpURLConnection.disconnect();
}
}
return data;
}
}
The server code:
app.post('/', function (req, res) {
var a = req.body;
console.log(a);
res.send(a);
})
And JSON there looks like this:
{ '{"name":"ffffc","email":"asdxx","password":"ffv","tel":"111"}': '' }
But should look like that:
{"name":"ffffc","email":"asdxx","password":"ffv","tel":"111"}
Your Java code needs to set it's Content-Type to application/json, like so:
httpURLConnection.setRequestProperty("Content-Type", "application/json");

java.net.ConnectException Connection timed out: connect

I'm working with a RESTFul api in Java EE7. I'm using a #Stateless EJB with a method that I can reach by a HTTP Post request. I am trying to validate a recaptcha code in the server side, so I need to make a HTTP Post request to https://www.google.com/recaptcha/api/siteverify/ with my secret key and the google captcha response that the client sent.
The problem occurs when I try to make the request from the server. The exception is a ConnectException with message "Connection timed out: connect". I think I cannot connect to the web, but I am not sure. I am using NetBeans IDE 8.1
Here is the code:
#Stateless
#Path("sign-in")
public class SignIn
{
#POST
#Produces(MediaType.APPLICATION_JSON)
public javax.ws.rs.core.Response registerUser(String data) throws IOException, JSONException
{
JSONObject JObj = new JSONObject(data);
String gCaptchaResponse = JObj.getString("$captchaResponse");
if (!VerifyGCaptchaResponse(gCaptchaResponse))
{
//Response with error
}
//Logic to "sign-in"
//...
}
private final String urlverificacion = "https://www.google.com/recaptcha/api/siteverify/";
private boolean VerifyGCaptchaResponse(String GCResponse) throws JSONException
{
boolean res = false;
String paramSecret = "secret="+appSettings.getCaptchaSecretKey();
String paramResponse = "response="+GCResponse;
String urlparameters = paramSecret + "&" + paramResponse;
byte[] postData = urlparameters.getBytes( StandardCharsets.UTF_8 );
int postDataLength = postData.length;
HttpURLConnection connection = null;
try
{
URL url = new URL(urlverificacion);
connection = (HttpURLConnection) url.openConnection();
connection.setDoOutput(true);
connection.setRequestMethod("POST");
connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
connection.setRequestProperty( "charset", "utf-8");
connection.setRequestProperty( "Content-Length", Integer.toString( postDataLength ));
connection.setConnectTimeout(30000);
connection.setReadTimeout(30000);
//Make request
OutputStream os = connection.getOutputStream(); // <<<<<<===== Here is when the problem occurs!!!
os.write(postData);
os.flush();
if (connection.getResponseCode() != HttpURLConnection.HTTP_OK)
{
throw new RuntimeException("Fallo conexion : codigo de error HTTP : " + connection.getResponseCode());
}
StringBuilder builder = new StringBuilder();
BufferedReader br = new BufferedReader(new InputStreamReader((connection.getInputStream())));
String output;
System.out.println("Respuesta del servicio .... \n");
while ((output = br.readLine()) != null) {
System.out.println(output);
builder.append(output);
}
String idSicom = "0";
Integer id = 0;
JSONObject jResponse = new JSONObject(builder.toString());
if (jResponse.has("success"))
{
String success = jResponse.getString("success");
res = true;
}
else
{
}
connection.disconnect();
}
catch (java.net.ConnectException e)
{
String error = e.getMessage();
String cause = Arrays.toString(e.getStackTrace());
}
catch (IOException | RuntimeException | JSONException e)
{
String error = e.getMessage();
String cause = Arrays.toString(e.getStackTrace());
}
finally
{
}
return res;
}
}

Posting multipart form data via Android AsyncTask

My issue is with the writeArgsToConn() function.....i think. I cant figure out how to implement it.
I am trying to post multipart-formdata from an Android device using AsyncTask class. Can anyone help with this? I want to stay away from the depreciated org.apache.http.legacy stuff and stick with up-to-date Android libraries.
I was able to use similar implementation for a class called DoPostJSON which used Content-Type: application/json and that class works fine.
Same question but on Reddit: https://redd.it/49qqyq
I had issues with getting nodejs express server to detect the parameters being sent in. My DoPostJSON class worked fine and my nodejs server was able to detect parameters...for some reason DoPostMultiPart doesnt work and nodejs server cant see paramters being passed in. I feel like I am using the library the wrong way.
public class DoPostMultiPart extends AsyncTask<JSONObject, Void, JSONObject> implements Post{
#Override
public HttpURLConnection createConn(String action) throws Exception{
URL url = new URL(Utils.host_api + action);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("POST");
conn.setDoInput(true);
conn.setDoOutput(true);
conn.setRequestProperty("Connection", "Keep-Alive");
conn.setRequestProperty("Cache-Control", "no-cache");
conn.setReadTimeout(35000);
conn.setConnectTimeout(35000);
return conn;
}
#Override
public JSONObject getResponse(HttpURLConnection conn) throws Exception {
int responseCode = conn.getResponseCode();
String response = "";
if (responseCode == HttpsURLConnection.HTTP_OK) {
InputStream in = new BufferedInputStream(conn.getInputStream());
BufferedReader responseStreamReader = new BufferedReader(new InputStreamReader(in));
String line = "";
StringBuilder stringBuilder = new StringBuilder();
while ((line = responseStreamReader.readLine()) != null)
stringBuilder.append(line).append("\n");
responseStreamReader.close();
response = stringBuilder.toString();
} else {
throw new Exception("response code: " + responseCode);
}
conn.disconnect();
return new JSONObject(response);
}
// TODO: fix this function
#Override
public void writeArgsToConn(JSONObject args, HttpURLConnection conn) throws Exception {
// define paramaters
String fullname = args.getString("fullname");
String email = args.getString("email");
String password = args.getString("password");
String confpassword = args.getString("confpassword");
Bitmap pic = (Bitmap) args.get("pic");
// plugin paramters into request
OutputStream os = conn.getOutputStream();
// how do I plugin the String paramters???
pic.compress(Bitmap.CompressFormat.JPEG, 100, os); // is this right???
os.flush();
os.close();
}
#Override
protected JSONObject doInBackground(JSONObject... params) {
JSONObject args = params[0];
try {
String action = args.getString("action");
HttpURLConnection conn = createConn(action);
writeArgsToConn(args, conn);
return getResponse(conn);
} catch (Exception e) {
Utils.logStackTrace(e);
return null;
}
}
}
I solved my issue by using OkHttpClient library.
JSONObject args = params[0];
try
{
final MediaType MEDIA_TYPE_PNG = MediaType.parse("image/png");
RequestBody requestBody = new MultipartBuilder()
.type(MultipartBuilder.FORM)
.addFormDataPart("fullname", args.getString("fullname"))
.addFormDataPart("email", args.getString("email"))
.addFormDataPart("password", args.getString("password"))
.addFormDataPart("confpassword", args.getString("confpassword"))
.addFormDataPart("pic", "profile.png", RequestBody.create(MEDIA_TYPE_PNG, (File) args.get("pic")))
.build();
Request request = new Request.Builder()
.url(Utils.host_api + args.getString("action"))
.post(requestBody)
.build();
OkHttpClient client = new OkHttpClient();
Response response = client.newCall(request).execute();
return new JSONObject(response.body().string());
}
catch (Exception e)
{
Utils.logStackTrace(e);
return null;
}

How to send request from android to servlet with parameters

I am trying to send a request from my android device to servlet with parameters and parameters are sending as part of the request.
I have a button on clicking on that I get the text from editText views modify my url to make a url with parameters and send that url to AsyncTask.
Here is my code.
buttonRegister.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String stringUrl = "http://192.168.11.4:8084/WebApplication1/DemoServlet?email=" + editTextEmail.getText() + "&password=" + editTextPassword.getText() + "&phone=" + editTextPhoneNumber.getText();
ConnectivityManager connMgr = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = connMgr.getActiveNetworkInfo();
if (networkInfo != null && networkInfo.isConnected()) {
new RegistrationTask().execute(stringUrl);
} else {
Toast.makeText(RegisterActivity.this, "Error!. Please check your internnet connection", Toast.LENGTH_SHORT).show();
}
}
});
}
And here is my RegistrationTask code.
class RegistrationTask extends AsyncTask<String, Void, String> {
#Override
protected String doInBackground(String... params) {
return getResponse(params[0]);
}
#Override
protected void onPostExecute(String result) {
editTextEmail.setText(result);
}
public String getResponse(String myurl) {
InputStream is = null;
String contentAsString = null;
int len = 500;
try {
URL url = new URL(myurl);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setReadTimeout(10000 /* milliseconds */);
conn.setConnectTimeout(15000 /* milliseconds */);
conn.setRequestMethod("GET");
conn.setDoInput(true);
conn.connect();
int response = conn.getResponseCode();
Log.d("Download", "The response is: " + response);
is = conn.getInputStream();
// Convert the InputStream into a string
contentAsString = readIt(is, len);
return contentAsString;
} catch (Exception e) {
} finally {
if (is != null) {
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return contentAsString;
}
// Reads an InputStream and converts it to a String.
public String readIt(InputStream stream, int len) throws IOException, UnsupportedEncodingException {
Reader reader = null;
reader = new InputStreamReader(stream, "UTF-8");
char[] buffer = new char[len];
reader.read(buffer);
return new String(buffer);
}
}
I tried to debug my servlet code but request coming as email=password=phone=
Please help me to sort it out.
Not an answer, but would help you.
First please share the servlet code too
Second, encode parameter using URLEncoder.encode(arg:String):String before sending the request, such as following
String stringUrl = "http://192.168.11.4:8084/WebApplication1/DemoServlet?email="
+URLEncoder.encode(editTextEmail.getText())
Also your method readIt(stream:InputStream,len:int):String is not reliable because of the way yo read the info.
Note that InputStream.read(buf::byte[]):int would not fill the whole buffer even if too much data is available, and the int response indicates the number of data was written to the buffer, so your code would get data inconsistency.
You may using DataInputStream.readFully(buff:byte[]):void which either fills the buffer completely or throws exception when there are not enough data.
Or better way read till EOS, where read() method returns -1.

Categories

Resources