Zugriff auf einen Server (Socket) mit dem Emulator und/oder dem Gerät

D

didisoft

Neues Mitglied
0
Hallöle!

Ich möchte eine kleine Chat-App programmieren, die ich zunächst als "normales" Java-Programm geschrieben habe. Da hat auch alles funktioniert. Nun möchte ich das ganze auf Android übertragen, und, bevor ich einen Server miete, auf dem Emulator testen.
Nach einigen Google-Versuchen habe ich festgestellt, dass man als IP (bei new Socket("IP", Port)) 10.0.2.2 eingeben muss, um auf den localhost des "Entwicklungs-PCs" zuzugreifen. Den Server (oder eben den ServerSocket) habe ich als Java Konsolen-Programm geschrieben und auf meinem PC laufen.
So, nun spuckt unsere Log-Kitty ne schöne Exception aus, und ich kann nicht mit dem Server kommunizieren:

Code:
03-24 19:49:39.763: W/TextLayoutCache(1415): computeValuesWithHarfbuzz -- need to force to single run
03-24 19:49:39.771: W/TextLayoutCache(1415): computeValuesWithHarfbuzz -- need to force to single run
03-24 20:30:24.691: I/System.out(1415): Der client ist null!!!!!
03-24 20:30:24.691: W/System.err(1415): android.os.NetworkOnMainThreadException
03-24 20:30:24.701: W/System.err(1415): 	at android.os.StrictMode$AndroidBlockGuardPolicy.onNetwork(StrictMode.java:1084)
03-24 20:30:24.711: W/System.err(1415): 	at libcore.io.BlockGuardOs.connect(BlockGuardOs.java:74)
03-24 20:30:24.711: W/System.err(1415): 	at libcore.io.IoBridge.connectErrno(IoBridge.java:127)
03-24 20:30:24.711: W/System.err(1415): 	at libcore.io.IoBridge.connect(IoBridge.java:112)
03-24 20:30:24.711: W/System.err(1415): 	at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:192)
03-24 20:30:24.711: W/System.err(1415): 	at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:172)
03-24 20:30:24.711: W/System.err(1415): 	at java.net.Socket.startupSocket(Socket.java:566)
03-24 20:30:24.711: W/System.err(1415): 	at java.net.Socket.tryAllAddresses(Socket.java:127)
03-24 20:30:24.711: W/System.err(1415): 	at java.net.Socket.<init>(Socket.java:177)
03-24 20:30:24.721: W/System.err(1415): 	at java.net.Socket.<init>(Socket.java:149)
03-24 20:30:24.721: W/System.err(1415): 	at de.didisoft.hausaufgaben.ChatActivity.connectToServer(ChatActivity.java:51)
03-24 20:30:24.721: W/System.err(1415): 	at de.didisoft.hausaufgaben.ChatActivity.onCreate(ChatActivity.java:42)
03-24 20:30:24.731: W/System.err(1415): 	at android.app.Activity.performCreate(Activity.java:4465)
03-24 20:30:24.731: W/System.err(1415): 	at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1049)
03-24 20:30:24.731: W/System.err(1415): 	at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1919)
03-24 20:30:24.743: W/System.err(1415): 	at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1980)
03-24 20:30:24.751: W/System.err(1415): 	at android.app.ActivityThread.access$600(ActivityThread.java:122)
03-24 20:30:24.751: W/System.err(1415): 	at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1146)
03-24 20:30:24.761: W/System.err(1415): 	at android.os.Handler.dispatchMessage(Handler.java:99)
03-24 20:30:24.761: W/System.err(1415): 	at android.os.Looper.loop(Looper.java:137)
03-24 20:30:24.761: W/System.err(1415): 	at android.app.ActivityThread.main(ActivityThread.java:4340)
03-24 20:30:24.761: W/System.err(1415): 	at java.lang.reflect.Method.invokeNative(Native Method)
03-24 20:30:24.761: W/System.err(1415): 	at java.lang.reflect.Method.invoke(Method.java:511)
03-24 20:30:24.771: W/System.err(1415): 	at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:784)
03-24 20:30:24.771: W/System.err(1415): 	at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:551)
03-24 20:30:24.771: W/System.err(1415): 	at dalvik.system.NativeStart.main(Native Method)

Die Zeile "Der Client ist null!!" ist nur um zu sehen ob der Client, den ich erstelle, null ist.

Wenn ihr da durchseht würde ich mich freuen :thumbsup:

Und wie hoste ich den selbstprogrammierten "Server" dann eigentlich? Ich möchte ihn nur ungern auf dem eigenen Laptop als Homeserver laufen lassen :ohmy: vServer? Hat jemand schon Erfahrung damit?

Und als IP muss ich ja dann nur noch die IP des Servers eingeben, oder?

Ok, also, wenn ihr eine Idee habt, was falsch sein könnte, würde ich mich freuen.

Hier nochmal ein wenig code: (Kann man den auch besser/übersichtlicher posten?!) :eek:

die OnCreate() Methode und der Teil, bei dem ich den Socket erstelle:

Code:
@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);

		setContentView(R.layout.chat);

		messages = (TextView) findViewById(R.id.tvMessages);
		etMsg = (EditText) findViewById(R.id.etMessage);

		findViewById(R.id.bChatMenu).setOnClickListener(this);
		findViewById(R.id.bChatSend).setOnClickListener(this);
		
		if (connectToServer())
		
		new Thread(new MessagesFromServerListener()).start();

	}

	public boolean connectToServer() {
		try {
			client = new Socket("10.0.2.2", 6655);
			reader = new BufferedReader(new InputStreamReader(
					client.getInputStream()));
			writer = new PrintWriter(client.getOutputStream());
			addLine("Netzwerkverbindung hergestellt!");

			return true;
		} catch (Exception e) {
			addLine("Netzwerkverbindung konnte nicht hergestellt                    werden!");
			if (client == null) System.out.println("Der client ist null!!!!!");
			e.printStackTrace();
			return false;
		}
	}

Ach ja, und die Permission für das Internet habe ich.
Falls ihr mehr code braucht sagt bescheid :thumbup:

Vielen Dank im Vorraus!

LG, David
 
Zuletzt bearbeitet:
Code:
android.os.NetworkOnMainThreadException

Der Fehler wird geworfen, wenn eine Netzwerkverbindung im Hauptthread gestartet wird.

Lagere alles, was in der in der Methode connectToServer() steht, in einen Thread oder AsyncTask aus.
 
Oh... Vielen Dank, funktioniert jetzt!! :laugh::thumbup::thumbsup:

Allerdings hab ich noch einen Fehler:

Code:
03-25 14:50:21.676: E/AndroidRuntime(2945): FATAL EXCEPTION: Thread-110
03-25 14:50:21.676: E/AndroidRuntime(2945): android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.view.ViewRootImpl.checkThread(ViewRootImpl.java:3939)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.view.ViewRootImpl.invalidateChild(ViewRootImpl.java:714)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.view.ViewRootImpl.invalidateChildInParent(ViewRootImpl.java:763)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.view.ViewGroup.invalidateChild(ViewGroup.java:4012)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.view.View.invalidate(View.java:8515)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.view.View.invalidate(View.java:8466)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.widget.TextView.checkForRelayout(TextView.java:6695)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.widget.TextView.setText(TextView.java:3256)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.widget.TextView.setText(TextView.java:3110)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at android.widget.TextView.setText(TextView.java:3085)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at de.didisoft.hausaufgaben.ChatActivity.addLine(ChatActivity.java:103)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at de.didisoft.hausaufgaben.ChatActivity.access$0(ChatActivity.java:99)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at de.didisoft.hausaufgaben.ChatActivity$MessagesFromServerListener.run(ChatActivity.java:125)
03-25 14:50:21.676: E/AndroidRuntime(2945): 	at java.lang.Thread.run(Thread.java:856)

Weiß jemand, was das zu bedeuten hat?! An dieser Stelle versuche ich den Text in einem TextView zu bearbeiten...

Code:
private void addLine(String text) {
		if (messages.getText().toString() == null ||     messages.getText().toString() == "")
			messages.setText(" ");
		messages.setText(messages.getText().toString() + "\n" + text);
	}

messages ist ein TextView. Übrigends klappt alles wenn ich "Verbindung zum Server hergestellt" oder "Verbindung zum Server konnte nicht hergestellt werden!" bei der connect() Methode ausgebe.

Hier der Text...

Code:
public class MessagesFromServerListener implements Runnable {

		@Override
		public void run() {
			String message;

			try {
				if (reader == null)
					new Thread(new connect()).start();
				while ((message = reader.readLine()) != null) {
					addLine(message);
				}
			} catch (IOException e) {
				addLine("Nachricht konnte nicht empfangen werden!"); //Ob das sinnvoll ist ^^
				e.printStackTrace();
			}
		}

	}

diesen Thread starte ich in der onCreate() Methode.

Hab ich da was falsch gemacht?!

Ach und hat jemand zu meiner 2. Frage einen Plan? (Wie ich den Server hosten kann)

Vielen Dank schon mal! :thumbsup:
 
Ich würde vermuten, das der betreffende Thread direkt auf den UIThread zugreift, was nicht so ohne weiteres geht. Aus dem Code kann man nichts schließen. Die gängigste Weise von einem Thread auf den UIThread zu zugreifen, sind Handler.

Communicating with the UI Thread | Android Developers
 
oder die Methode Activity#runOnUiThread()...

lg. Dagobert
 
Vielen Dank!! Klappt alles!!
Wenn mir jetzt noch jemand sagen kann, wie ich den Server hoste, ist (fast) alles perfekt. :scared:

Freu mich auch auf weitere Tipps,

LG!
 
Du hast ein "stink normales Java Porgramm" oder?
Hab ich noch nie gemacht :D auser im lokalem Netz... ich würde jetzt mal sagen du brauchst nen root oder vserver... kannst da ganz normal java installieren... startest das programm iwie... öffnest die ports.. und bist fertig...

aber ich weiß nicht ob das wirklich so "einfach" ist und der richtige weg ist...

lg. Dagobert
 
ohhh Vielen Dank!
Nun, da werd ich Google mal ein wenig herausfordern und sehen was dabei raus kommt ^^ :tongue::tongue:

Also dann, vielen Dank an alle fleißigen Helfer!
(Weitere Tipps sind natürlich nicht unerwünscht:biggrin:)

LG, David
 

Ähnliche Themen

S
Antworten
4
Aufrufe
956
Sempervivum
S
D
Antworten
3
Aufrufe
438
jogimuc
J
B
Antworten
4
Aufrufe
432
bb321
B
Zurück
Oben Unten