I have a websocket hosted on a server which has been tested and works. I cant identify any error messages in the logs.
The connect to the servers websocket fails with no error
Btw I am new with android.
Here is the code from android. The WebListener class in empty.
package kean.pathfinder;
import android.Manifest;
import android.content.Context;
import android.content.pm.PackageManager;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.os.PersistableBundle;
import android.widget.Button;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.app.ActivityCompat;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.MapView;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.Polyline;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.IOException;
import java.util.concurrent.atomic.AtomicReference;
import kean.pathfinder.websocket.WebListener;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.WebSocket;
public class MainActivity extends AppCompatActivity implements OnMapReadyCallback, LocationListener {
private MapView map;
private final Path path = new Path();
private GoogleMap googleMap;
private LocationManager locationManager;
private WebSocket ws;
private OkHttpClient client;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
map = findViewById(R.id.map);
Button start = findViewById(R.id.start);
Button undo = findViewById(R.id.undo);
Button clear = findViewById(R.id.clear);
client = new OkHttpClient();
Request request = new Request.Builder().url("ws://myServer.ip").build();
WebListener listener = new WebListener();
ws = client.newWebSocket(request,listener);
ws.send("Hi from android");
ws.close(1000,"Session end");
start.setOnClickListener(l -> {
try {
JSONObject object = new JSONObject();
JSONArray array = new JSONArray();
for (LatLng latLng : path.getPoints()){
JSONObject point = new JSONObject();
point.put("lat",latLng.latitude);
point.put("lng",latLng.longitude);
array.put(point);
}
object.put("points",array);
ws.send(object.toString());
} catch (JSONException e){
e.printStackTrace();
}
});
undo.setOnClickListener(l -> {
path.undo();
updatePoly();
});
clear.setOnClickListener(l -> {
path.clear();
updatePoly();
});
map.getMapAsync(this);
map.onCreate(savedInstanceState);
locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
requestLocation();
}
public void onMapReady(@NonNull GoogleMap googleMap) {
googleMap.setMapType(GoogleMap.MAP_TYPE_SATELLITE);
this.googleMap = googleMap;
googleMap.setOnMapClickListener(l -> {
path.add(l);
updatePoly();
});
}
private final AtomicReference<Polyline> polyline = new AtomicReference<>();
private void updatePoly(){
Polyline p = polyline.get();
if (p != null) p.remove();
polyline.set(googleMap.addPolyline(path.getPoly()));
}
public void onLocationChanged(@NonNull Location location) {
LatLng latLng = new LatLng(location.getLatitude(),location.getLongitude());
googleMap.moveCamera(CameraUpdateFactory.newLatLngZoom(latLng,50));
locationManager.removeUpdates(this);
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
if (requestCode == 1){
requestLocation();
}
}
private void requestLocation()
{
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(this,new String[]{Manifest.permission.ACCESS_FINE_LOCATION},1);
return;
}
locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 400L, 1000f, this);
}
@Override
protected void onStart() {
super.onStart();
map.onStart();
}
@Override
protected void onResume() {
super.onResume();
map.onResume();
}
@Override
protected void onPause() {
super.onPause();
map.onPause();
}
@Override
protected void onStop() {
super.onStop();
map.onStop();
ws.close(1000,"Session ended");
client.dispatcher().executorService().shutdown();
}
@Override
protected void onDestroy() {
super.onDestroy();
map.onDestroy();
}
@Override
public void onSaveInstanceState(@NonNull Bundle outState, @NonNull PersistableBundle outPersistentState) {
super.onSaveInstanceState(outState, outPersistentState);
map.onSaveInstanceState(outState);
}
@Override
public void onLowMemory() {
super.onLowMemory();
map.onLowMemory();
}
}
Here is the manifest file
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools">
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<application
android:allowBackup="true"
android:dataExtractionRules="@xml/data_extraction_rules"
android:fullBackupContent="@xml/backup_rules"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/Theme.PathFinder"
tools:targetApi="31">
<activity
android:name=".MainActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<meta-data
android:name="android.app.lib_name"
android:value="" />
</activity>
<meta-data
android:name="com.google.android.maps.v2.API_KEY"
android:value="token" />
</application>
</manifest>
I have also tested the code in a normal java project and it worked. Here is the code
package org.example;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.WebSocket;
public class Main {
public static void main(String[] args) {
OkHttpClient client = new OkHttpClient();
Request request = new Request.Builder().url("ws://myServer.ip").build();
// Empty class
WebListener listener = new WebListener();
WebSocket ws = client.newWebSocket(request,listener);
ws.send("Hello World");
ws.close(1000,"End");
client.dispatcher().executorService().shutdown();
}
}
CodePudding user response:
Verify you manifest has Internet permission
<uses-permission android:name="android.permission.INTERNET"/>
Verify that you have clear traffic for unsecure ws connection
<application
android:usesCleartextTraffic="true">
</application>
Implement the WebSocketListener and override onFailure to see errors.
@Override
public void onFailure(@NotNull WebSocket webSocket, @NotNull Throwable t, @Nullable Response response) {
Log.v(LOG_TAG, "OnFailure: " response ", " t);
super.onFailure(webSocket, t, response);
}