Using Retrofit API With Android 2.2 - retrofit

I have to build an android application that accesses a php script that echoes json.
I migrated to android studio,targeted andoid sdk 22 (5.0),had a minimum
sdk of 8(Froyo) and built the project.
The snag occurred where my past code that i used on eclipse
to launch "httppost" requests where not working.
The logcat showed an "unknown host exception" for the urls that where
passed as strings.
When i changed from "defaulthttpclient" to "httpurlconnection"
it worked,but the connection was too slow. (On android 2.2)
I read about the "Retrofit" api as a good library for fast http requests,
but i read two conflicting reports:
The minimum sdk for retrofit is android 2.3
And then
Retrofit uses httpurlconnection on android 2.3+ and httpclient on androd 2.2
This has me a bit confused. So the real question is
Can retrofit handle my http requests on an android 2.2 phone?

Yes, but you have to run retrofit with pre2.0 okhttp, urlconnection or apache client.
Latest versions of the okhttp require Java7 or android 2.3+
https://square.github.io/retrofit/#download
https://github.com/square/retrofit/issues/826
https://github.com/square/okhttp/issues/528#issuecomment-96622594

Related

xamarin.forms: ios cannot create async on firestore. failing with with "bad gRPC response"

I created an empty xamarin forms project and followed the path to connect to the database. I am able to connect with the right key store file but as soon as I try to create data on the server I am getting a bad grpc response.
It look like ios is calling with http 1.1, but google requiers 2.0.
This is the line that fails:
await docRef.SetAsync(user);
This is the error I am getting:
e {Grpc.Core.RpcException: Status(StatusCode="Internal", Detail="Bad gRPC response. Response protocol downgraded to HTTP/1.1.") at Google.Api.Gax.Grpc.ApiCallRetryExtensions+<>c__DisplayClass0_0`2[TRequest,TResponse].<WithRetry>b__0 (TRequest request, Google.Ap…}
I am stuck here for days now, please help.
The same code works fine on android devices, its just iOS problem in xamarin.forms.
EDIT:
I have noticed, that this issue does not exist on the firebase nuget package 3.2.1 and below. Just the higher ones throw this error.

Web Service Call Stopped Processing

I have a bunch of Xamarin iOS applications running on our Corporate iPhones and iPads. I recently upgraded my Visual Studio and Mac Book Pro to latest release version and my applications are no longer PROCESSING data from my web service correctly. I did not change version of Xamarin.Forms
VS 2017 Version 15.9.13
Xamarin.Forms.2.4.0.282
The web services are http. I have my NSAppTransportSecurityNSAllowsArbitraryLoads
set to allow http.
I am using the flag true to generate the Task.Factory.FromAsync methods in the Web Service Reference.cs file.
I could go on with describing how everything works if anyone needs more info.
Luckily, my Mac Book Pro Simulator has old and new versions of my apps installed in different iPhone/iPad devices for me to test. I installed fiddler to make sure all the requests/responses were the same. My old App in one device works and my new App in a different device fails. Same thing for ALL of my Applications. Old one works and new one fails.
When I review fiddler, the requests and responses are all working the same:
Request is made
App gets an authentication prompt
Authentication happens
Request returns code 200 with the data requested
The only difference in Fiddler is that two of the headers are in a different order: Working one has SOAPAction first and Content-Type next, the one failing has Content-Type and then SOAPAction. I am grasping at straws here because the order of these headers should not matter.
This is for all the applications. The only problem is that my new applications are ignoring the response. It is almost like the endMethod function from the parameter passed to FromAsync is never called.
This is the function call:
public async Task<ProcessLogon> ExecuteSaveLogon(DeviceItem DeviceItem)
{
ResultLogin = new ProcessLogon();
try
{
var ProcessLogon = await Task<WebServiceTrading.ProcessLogon>.Factory.FromAsync(serviceTrading.BeginSaveLogon, serviceTrading.EndSaveLogon, ToServiceTrading(DeviceItem), TaskCreationOptions.None);
ResultLogin = FromServiceTrading(ProcessLogon);
}
catch (Exception ex)
{
System.Diagnostics.Debug.WriteLine(#"ExecuteSaveLogon ERROR {0}", ex.Message);
}
return ResultLogin;
}
Does anyone know of any DEBUG or LOGGING tools that I could use to find out why my successful response is lost?

Asp.Net Core SignalR + Angular 6 issue

I have a WebApi that was made using Asp.net Core 2.0 and consuming this API an Angular 5 App. Now I'm making a new version of this App using Angular 6.
In this Web API I use SignalR 1.0.0-alpha-final and in the Angular 5 app I use this as client "#aspnet/signalr-client": "^1.0.0-alpha2-final".
In the old Angular App everything works fine as intended. My problem is that I can use this package on the new version of my app:
npm ERR! code ELIFECYCLE
npm ERR! errno 1
npm ERR! #aspnet/signalr-client#1.0.0-alpha2-update1 install: `echo "This package has been deprecated. Use '#aspnet/signalr' instead." && exit 1`
npm ERR! Exit status 1
npm ERR!
npm ERR! Failed at the #aspnet/signalr-client#1.0.0-alpha2-update1 install script.
npm ERR! This is probably not a problem with npm. There is likely additional logging output above.
Then I try to use the recommended version, I follow this article and everything runs OK on the Angular 6 App side, but it never actually connects to the Hub. this is the message I get when running my local Angular APP:
Access to XMLHttpRequest at 'http://localhost:27081/hub/notification/negotiate?jwttoken=the_token_here' from origin 'http://localhost:4200' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: The value of the 'Access-Control-Allow-Origin' header in the response must not be the wildcard '*' when the request's credentials mode is 'include'. The credentials mode of requests initiated by the XMLHttpRequest is controlled by the withCredentials attribute.
It's not a real CORS problem, I made the WebAPI and and Angular APP run in the same domain and I never had CORS problem in my old App. I have the right Cors policies to allow localhost to use the api.
It's weird that the client added negotiate to the connection URL and even If I make my hub answer in this address I get error 400 with this message: Connection ID required
I do believe that this Client Library was made to another version than the one I have on the server, since the client and server has to follow the same version.
I tried using the node_modules from the older Angular App but I cannot get it to compile.. I don't know what to do. Has anyone experienced this issue and managed to solve? Any tips? I can't update the version on the WebAPI or I'll make the current App stop working.
Thanks for any help
I just got to make it work without changing the version of the webapi. This is how I make the connection:
this._hubConnection = new signalR.HubConnectionBuilder()
.withUrl('http://localhost:27081/hub/notification/?jwttoken='+ this.jwt,
{
accessTokenFactory: ()=> this.jwt ,
skipNegotiation: true,
transport: signalR.HttpTransportType.WebSockets
})
.build();
That's all. Yes, in the version I have in the API i have to send the token in the querysting. This documentation helped me achieve that.
You should update to the latest .Net core SignalR if you can
This include the client script #aspnet/signalR (currently 1.0.4)
With the latest Nuget Package Microsoft.AspNetCore.SignalRCore (currently 1.0.4)
Also note that initialising the hub in javascript changed from the preview version, looks something like this:
var connection = new signalR.HubConnectionBuilder().withUrl("/yourhub/").build();

SparkPost SMTP relay with StartTLS suddenly gives error "Authentication failed because the remote party has closed the transport stream."

I have a (long) running webapplication written in VB on the ASP.NET 4.0 framework.
We have been using SparkPost to send e-mails for a while, but since a few days (not sure about the exact date), the e-mail functionality has stopped working and started giving the following error message
Authentication failed because the remote party has closed the transport stream.
We use MailKit version 1.22 (latest to support ASP.NET 4.0) to make the connection and send the e-mails like so:
Using objMessage As New MailMessage(from, to, title, message)
objMessage.IsBodyHtml = True
'https://github.com/jstedfast/MailKit
Using client As New MailKit.Net.Smtp.SmtpClient()
''accept all SSL certificates (in case the server supports STARTTLS)
client.ServerCertificateValidationCallback = Function(sender, certificate, chain, errors)
Return True
End Function
''Note: since we don't have an OAuth2 token, disable the XOAUTH2 authentication mechanism.
client.AuthenticationMechanisms.Remove("XOAUTH2")
client.AuthenticationMechanisms.Add("AUTH LOGIN")
client.Connect("smtp.sparkpostmail.com", 587, SecureSocketOptions.StartTls)
''Note: only needed if the SMTP server requires authentication
client.Authenticate("SMTP_Injection", "**********************")//the asterixes are the API key
client.Send(objMessage)
client.Disconnect(True)
End Using
End Using
this setup with StartTLS is what SparkPost documentation wants me to use.
I read that SparkPost has recently stopped supporting TSL 1.0. Could this be the culprit?
The .NET Framework 4.0 use SSL3.0 or TLS1.0 as default protocol. The easiest way to fix the problem is to upgrade your existing application to .NET Framework 4.6.2. After the upgrade your app will use the TLS1.2 protocol as default. You can read more about it here

Do I need a new PayPal API to support TLS 1.2 on .Net server?

I am running ASP.Net 4.5, but using a very old version of the PayPal SOAP api. The reference is to paypal_base.dll with a reported version of 4.3.1.0. The code that calls the API has "using" statements that reference:
com.paypal.sdk.services
com.paypal.soap.api.
I have verified at the point where the call to the PayPal api is made, that this value
System.Net.ServicePointManager.SecurityProtocol
includes both ssl3 and tls1.2.
I am pointing at the "sandbox" mode.
But when the setExpressCheckout call is made, I get a runtime exception that says:
The request was aborted: Could not create SSL/TLS secure channel.
I have downloaded the PayPal API Samples project and using the same sandbox credentials, it works. Looking in Fiddler, the calls are nearly identical except the samples API call goes to api-3t.sandbox.paypal.com, while my code goes to api-aa.sandbox.paypal.com, but according to the documentation on TLS 1.2 readyness, both apis should work. I don't see anywhere in either API to set the endpoint other than switching between "live" and "sandbox".
In the fiddler response, both show:
"A SSLv3-compatible ServerHello handshake was found. Fiddler extracted the parameters below.
Version: 3.3 (TLS/1.2)"
And the responses are identical except for the "random" parameter. So the old API call is using TLS 1.2
My code and the Samples API code are only slightly different, the sample uses:
SetExpressCheckoutRequestType request = new SetExpressCheckoutRequestType();
populateRequestObject(request); //populate request data
SetExpressCheckoutReq wrapper = new SetExpressCheckoutReq();
wrapper.SetExpressCheckoutRequest = request;
Dictionary<string, string> configurationMap = Configuration.GetAcctAndConfig(); //set merchant config
PayPalAPIInterfaceServiceService service = new PayPalAPIInterfaceServiceService(configurationMap);
SetExpressCheckoutResponseType setECResponse = service.SetExpressCheckout(wrapper); //make the call
Where my (again, very old code looks like this):
CallerServices caller = new CallerServices();
caller.APIProfile = SetProfile.ApplicationProfile; //set merchant config
SetExpressCheckoutRequestType pp_request = new SetExpressCheckoutRequestType();
// Create the request details object
pp_request.SetExpressCheckoutRequestDetails = new SetExpressCheckoutRequestDetailsType();
pp_request.SetExpressCheckoutRequestDetails.PaymentAction = paymentAction;
pp_request.SetExpressCheckoutRequestDetails.PaymentActionSpecified = true;
pp_request.SetExpressCheckoutRequestDetails.OrderTotal = new BasicAmountType();
pp_request.SetExpressCheckoutRequestDetails.OrderTotal.currencyID = currencyCodeType;
pp_request.SetExpressCheckoutRequestDetails.OrderTotal.Value = paymentAmount;
pp_request.SetExpressCheckoutRequestDetails.CancelURL = cancelURL;
pp_request.SetExpressCheckoutRequestDetails.ReturnURL = returnURL;
return (SetExpressCheckoutResponseType) caller.Call("SetExpressCheckout", pp_request); //do the call
The sample code works, my code throws the SSL/TLS error. I tried upgrading to the latest SDK, but so much has changed, it will be quite a large effort to migrate all that code.
From fiddler, it seems to be using TLS 1.2 even with the old API, but I get a runtime exception about the SSL/TLS connection. Is it because of the different endpoint? Is the old API just too old?
Thanks in advance for any help - I would love to avoid migrating all that ancient code!.
EDIT: I should mention I am using the UserName/Password/Signature credentials, not certificate based credentials.
As TLS1.2 is supported in .Net4.5 but it is not a default protocol. you need to opt-in to use it. The following code will make TLS 1.2 default, make sure to execute it before making a connection to secured resource:
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12
I was having a similar issue, with a PP Sandbox credentialing "HttpWebRequest" in C# Web Application 4.5, receiving the following error: "You must write ContentLength bytes to the request stream before calling [Begin]GetResponse".
I read this Q/A and applied the ServicePointManager reference from above answer - as the first line in my HttpWebRequest call method, and it worked. Thanks to all.
FYI, the example code I am building is from //learn.microsoft.com, "Getting Started with ASP.NET 4.5 Web Forms and Visual Studio 2017".

Resources