2013-01-13 8 views
23

Ich versuche, NanoHTTP zu verwenden, um eine HTML-Datei zu erstellen. Allerdings ist NanoHTTP relativ un-dokumentiert, und ich bin neu in Android. Meine Frage ist, wo ich die HTML-Datei speichern kann, und wie kann ich es mit NanoHTTP spezifisch bedienen.Verwenden von NanoHTTPD in Android

+1

Sofern dies einige bestehende Android-Port von NanoHTTPD ist, Sie einige Arbeit vor sich haben, nicht etwas, würde ich für jemanden „neue empfehlen zu Android ". Wenn es * ein * vorhandener Android-Port von NanoHTTPD ist, haben die Autoren dieses Ports hoffentlich einige Mittel zur Verfügung gestellt, um das Dokumentenstammverzeichnis über eine 'Datei' zu spezifizieren. – CommonsWare

+2

nun, ich bin neu in Android, aber ich bin nicht neu in Java oder Networking. Alles, was ich brauche, ist ein kleiner Stoß in die richtige Richtung. – Zwade

Antwort

33

Eine späte Antwort, kann aber für andere nützlich sein.

Hier ist ein einfacher Hallo Web Server, nicht genau das, was Sie fragen, aber Sie können von hier fortfahren. Das folgende Programm setzt voraus, dass Sie ein Verzeichnis www im Stammverzeichnis der SD-Karte und eine Datei index.html im Inneren haben.

Haupttätigkeit Httpd.java:

package com.inforscience.web; 

import android.app.Activity; 
import android.os.Bundle; 
import android.os.Environment; 
import android.util.Log; 
import java.io.*; 
import java.util.*; 


public class Httpd extends Activity 
{ 
    private WebServer server; 
    /** Called when the activity is first created. */ 
    @Override 
    public void onCreate(Bundle savedInstanceState) 
    { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.main); 
     server = new WebServer(); 
     try { 
      server.start(); 
     } catch(IOException ioe) { 
      Log.w("Httpd", "The server could not start."); 
     } 
     Log.w("Httpd", "Web server initialized."); 
    } 


    // DON'T FORGET to stop the server 
    @Override 
    public void onDestroy() 
    { 
     super.onDestroy(); 
     if (server != null) 
      server.stop(); 
    } 

    private class WebServer extends NanoHTTPD { 

     public WebServer() 
     { 
      super(8080); 
     } 

     @Override 
     public Response serve(String uri, Method method, 
           Map<String, String> header, 
           Map<String, String> parameters, 
           Map<String, String> files) { 
      String answer = ""; 
      try { 
       // Open file from SD Card 
       File root = Environment.getExternalStorageDirectory(); 
       FileReader index = new FileReader(root.getAbsolutePath() + 
         "/www/index.html"); 
       BufferedReader reader = new BufferedReader(index); 
       String line = ""; 
       while ((line = reader.readLine()) != null) { 
        answer += line; 
       } 
       reader.close(); 

      } catch(IOException ioe) { 
       Log.w("Httpd", ioe.toString()); 
      } 


      return new NanoHTTPD.Response(answer); 
     } 
    } 

} 

Offensichtlich ist die NanoHTTPD Klasse im selben Paket sein muss.

Sie müssen Internet-Erlaubnis in AndroidManifest.xml gewähren.

<uses-permission android:name="android.permission.INTERNET" /> 

und lesen Sie externe Speicherberechtigung.

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> 

EDIT: Für den Zugriff auf den Server, den Sie Web-Browser mit der IP-Adresse Ihres Geräts öffnen, z.B. 192.168.1.20:8080.

NOTES:

+1

Danke für das Posten, ich sollte meinen eigenen Code hinzugefügt haben, sobald ich es herausgefunden habe (was eine Weile dauerte). – Zwade

+2

Hinzufügen meines Dankes. Ernsthaft, sehr hilfreich. Dies ist das erste nanohttpd-Beispiel, das ich gefunden habe, das tatsächlich mit dem aktuellen nanohttpd funktioniert. Mein Prozess: Erstellen Sie ein neues Android-Anwendungsprojekt, fügen Sie Ihre Hauptaktivität ein (Ändern des Paketnamens und des Aktivitätsnamens, um sie an mein Projekt anzupassen), kopieren Sie in die NanoHTTPD.java-Datei (aus nanohttpd-master/core/src/main/java/fi/iki/elonen/im aktuellen https://github.com/NanoHttpd/nanohttpd download), fügen Sie die INTERNET-Berechtigung hinzu, erstellen Sie die Datei www/index.html, und das war es. Boom. Lief die App auf meinem Hinweis II und sah die Webseite von meinem PC aus. Funktioniert! –

+1

Gern geschehen. Ich benutzte einen Server für ein College-Projekt (https://bitbucket.org/rendon/smsserver) und NanoHTTPD hat die Arbeit so gut gemacht. – rendon

8

Ziemlich gut Quellcode kann hier gefunden werden: https://github.com/Teaonly/android-eye

Chceck Vermögenswerte Ordner, in dem HTML und JavaScript-Dateien https://github.com/Teaonly/android-eye/tree/master/assets

TeaServer gespeichert sind - Server-Implementierung https://github.com/Teaonly/android-eye/blob/master/src/teaonly/droideye/TeaServer.java

MainActivity - Server-Initialisierung https://github.com/Teaonly/android-eye/blob/master/src/teaonly/droideye/MainActivity.java

+0

Dies funktioniert nicht mit Android 3 und höher, da Sie kein Netzwerk von einem UI-Thread aus tun können. – Paulus

+0

Dies funktioniert unter Android 3+ und dient zur Bereitstellung von Images/Skripts/etc. Ich war auf der Suche nach etwas, das für ein paar Tage funktionierte. Ihre Implementierung behandelt MIME-Typen, ohne sie auch manuell angeben zu müssen. Vielen Dank für diese Info :) – suomi35

4

Aktualisiert WebServer Klasse (siehe rendon Antwort), die mit aktueller NanoHTTPD Version funktioniert:

private class WebServer extends NanoHTTPD { 

    public WebServer() { 
     super(8080); 
    } 

    @Override 
    public Response serve(IHTTPSession session) { 
     String answer = ""; 
     try { 
      // Open file from SD Card 
      File root = Environment.getExternalStorageDirectory(); 
      FileReader index = new FileReader(root.getAbsolutePath() + 
        "/www/index.html"); 
      BufferedReader reader = new BufferedReader(index); 
      String line = ""; 
      while ((line = reader.readLine()) != null) { 
       answer += line; 
      } 
      reader.close(); 

     } catch(IOException ioe) { 
      Log.w("Httpd", ioe.toString()); 
     } 

     return newFixedLengthResponse(answer); 
    } 

} 
+0

leider funktioniert es nicht für mich .... – GvSharma

1

Try this ... erstellen 2 Pakete (Aktivität, util), erstellen Sie nur für die Organisation In Tätigkeit AndroidWebServer.java

package awserverfatepi.com.activity; 
import android.content.BroadcastReceiver; 
import android.content.Context; 
import android.content.DialogInterface; 
import android.content.Intent; 
import android.content.IntentFilter; 
import android.net.ConnectivityManager; 
import android.net.NetworkInfo; 
import android.net.wifi.WifiManager; 
import android.support.design.widget.CoordinatorLayout; 
import android.support.design.widget.FloatingActionButton; 
import android.support.design.widget.Snackbar; 
import android.support.v4.content.ContextCompat; 
import android.support.v7.app.AlertDialog; 
import android.support.v7.app.AppCompatActivity; 
import android.os.Bundle; 
import android.view.KeyEvent; 
import android.view.View; 
import android.widget.EditText; 
import android.widget.TextView; 

import awserverfatepi.com.R; 
import awserverfatepi.com.util.AndroidWebServer; 

public class MainActivity extends AppCompatActivity { 

    private static final int DEFAULT_PORT = 8080; 

    private AndroidWebServer androidWebServer; 
    private BroadcastReceiver broadcastReceiverNetworkState; 
    private static boolean isStarted = false; 

    private CoordinatorLayout coordinatorLayout; 
    private EditText editTextPort; 
    private FloatingActionButton floatingActionButtonOnOff; 
    private View textViewMessage; 
    private TextView textViewIpAccess; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 

     initGui(); 
     setIpAccess(); 
     floatingActionButtonOnOff = (FloatingActionButton) findViewById(R.id.floatingActionButtonOnOff); 
     floatingActionButtonOnOff.setOnClickListener(new View.OnClickListener() { 
      @Override 
      public void onClick(View v) { 
       if (isConnectedInWifi()) { 
        if (!isStarted && startAndroidWebServer()) { 
         isStarted = true; 
         textViewMessage.setVisibility(View.VISIBLE); 
         floatingActionButtonOnOff.setBackgroundTintList(ContextCompat.getColorStateList(MainActivity.this, 
           R.color.colorGreen)); 
         editTextPort.setEnabled(false); 
        } else if (stopAndroidWebServer()) { 
         isStarted = false; 
         textViewMessage.setVisibility(View.INVISIBLE); 
         floatingActionButtonOnOff.setBackgroundTintList(ContextCompat.getColorStateList(MainActivity.this, 
           R.color.colorRed)); 
         editTextPort.setEnabled(true); 
        } 
       } else { 
        Snackbar.make(coordinatorLayout, getString(R.string.wifi_message), Snackbar.LENGTH_LONG).show(); 
       } 
      } 
     }); 

     initBroadcastReceiverNetworkStateChanged(); 
    } 

    private void initGui() { 
     coordinatorLayout = (CoordinatorLayout) findViewById(R.id.coordinatorLayout); 
     editTextPort = (EditText) findViewById(R.id.editTextPort); 
     textViewMessage = findViewById(R.id.textViewMessage); 
     textViewIpAccess = (TextView) findViewById(R.id.textViewIpAccess); 
    } 

    private boolean startAndroidWebServer() { 
     if (!isStarted) { 
      int port = getPortFromEditText(); 
      try { 
       if (port == 0) { 
        throw new Exception(); 
       } 
       androidWebServer = new AndroidWebServer(port); 
       androidWebServer.start(); 
       return true; 
      } catch (Exception e) { 
       e.printStackTrace(); 
       Snackbar.make(coordinatorLayout, "A porta " + port + " não está funcionando, por favor altere para outra no intervalo" + 
         " entre 1000 e 9999.", Snackbar.LENGTH_LONG).show(); 
      } 
     } 
     return false; 
    } 

    private boolean stopAndroidWebServer() { 
     if (isStarted && androidWebServer != null) { 
      androidWebServer.stop(); 
      return true; 
     } 
     return false; 
    } 

    private void setIpAccess() { 
     textViewIpAccess.setText(getIpAccess()); 
    } 

    private void initBroadcastReceiverNetworkStateChanged() { 
     final IntentFilter filters = new IntentFilter(); 
     filters.addAction("android.net.wifi.WIFI_STATE_CHANGED"); 
     filters.addAction("android.net.wifi.STATE_CHANGE"); 
     broadcastReceiverNetworkState = new BroadcastReceiver() { 
      @Override 
      public void onReceive(Context context, Intent intent) { 
       setIpAccess(); 
      } 
     }; 
     super.registerReceiver(broadcastReceiverNetworkState, filters); 
    } 

    private String getIpAccess() { 
     WifiManager wifiManager = (WifiManager) getSystemService(WIFI_SERVICE); 
     int ipAddress = wifiManager.getConnectionInfo().getIpAddress(); 
     final String formatedIpAddress = String.format("%d.%d.%d.%d", (ipAddress & 0xff), (ipAddress >> 8 & 0xff), 
       (ipAddress >> 16 & 0xff), (ipAddress >> 24 & 0xff)); 
     return "http://" + formatedIpAddress + ":"; 
    } 

    private int getPortFromEditText() { 
     String valueEditText = editTextPort.getText().toString(); 
     return (valueEditText.length() > 0) ? Integer.parseInt(valueEditText) : DEFAULT_PORT; 
    } 

    public boolean isConnectedInWifi() { 
     WifiManager wifiManager = (WifiManager) getSystemService(Context.WIFI_SERVICE); 
     NetworkInfo networkInfo = ((ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE)).getActiveNetworkInfo(); 
     if (networkInfo != null && networkInfo.isAvailable() && networkInfo.isConnected() 
       && wifiManager.isWifiEnabled() && networkInfo.getTypeName().equals("WIFI")) { 
      return true; 
     } 
     return false; 
    } 

    public boolean onKeyDown(int keyCode, KeyEvent evt) { 
     if (keyCode == KeyEvent.KEYCODE_BACK) { 
      if (isStarted) { 
       new AlertDialog.Builder(this) 
         .setTitle(R.string.warning) 
         .setMessage(R.string.dialog_exit_message) 
         .setPositiveButton(getResources().getString(android.R.string.ok), new DialogInterface.OnClickListener() { 
          public void onClick(DialogInterface dialog, int id) { 
           finish(); 
          } 
         }) 
         .setNegativeButton(getResources().getString(android.R.string.cancel), null) 
         .show(); 
      } else { 
       finish(); 
      } 
      return true; 
     } 
     return false; 
    } 

    @Override 
    protected void onDestroy() { 
     super.onDestroy(); 
     stopAndroidWebServer(); 
     isStarted = false; 
     if (broadcastReceiverNetworkState != null) { 
      unregisterReceiver(broadcastReceiverNetworkState); 
     } 
    } 

} 

im AndroidWebserver.java die Klasse MainActivity.java in util die Klasse erstellen

package awserverfatepi.com.util; 
import java.util.Map; 
import fi.iki.elonen.NanoHTTPD; 

public class AndroidWebServer extends NanoHTTPD { 

    public AndroidWebServer(int port) { 
     super(port); 
    } 

    public AndroidWebServer(String hostname, int port) { 
     super(hostname, port); 
    } 

    @Override 
    public Response serve(IHTTPSession session) { 
     String msg = "<html><body><h1>Hello World</h1>\n"; 
     Map<String, String> parms = session.getParms(); 
     if (parms.get("username") == null) { 
      msg += "<form action='?' method='get'>\n <p>Seu nome: <input type='text' name='username'></p>\n" + "</form>\n"; 
     } else { 
      msg += "<p>Hello, " + parms.get("username") + "!</p>"; 
     } 
     return newFixedLengthResponse(msg + "</body></html>\n"); 
    } 
} 

Manifest nicht vergessen.xml

<uses-permission android:name="android.permission.INTERNET" /> 
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" /> 
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> 
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> 

Und last

activity_main.xml

<?xml version="1.0" encoding="utf-8"?> 
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    xmlns:app="http://schemas.android.com/apk/res-auto" 
    android:id="@+id/coordinatorLayout" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent"> 

    <LinearLayout 
     android:layout_width="match_parent" 
     android:layout_height="match_parent" 
     android:orientation="vertical"> 

     <ImageView 
      android:layout_width="match_parent" 
      android:layout_height="150dp" 
      android:scaleType="centerCrop" 
      android:src="@drawable/header" /> 

     <LinearLayout 
      android:layout_width="match_parent" 
      android:layout_height="0dp" 
      android:layout_weight="1" 
      android:background="@color/colorPrimaryLight" 
      android:gravity="center" 
      android:orientation="vertical"> 

      <LinearLayout 
       android:layout_width="wrap_content" 
       android:layout_height="wrap_content" 
       android:orientation="horizontal"> 

       <TextView 
        android:id="@+id/textViewIpAccess" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="http://000.000.000.000:" 
        android:textColor="@android:color/white" 
        android:textSize="20sp" 
        android:textStyle="bold" /> 

       <EditText 
        android:id="@+id/editTextPort" 
        android:layout_width="60dp" 
        android:layout_height="wrap_content" 
        android:gravity="center" 
        android:hint="8080" 
        android:inputType="numberDecimal" 
        android:maxLength="4" 
        android:text="8080" 
        android:textColor="@android:color/white" 
        android:textSize="20sp" 
        android:textStyle="bold" /> 

      </LinearLayout> 

      <TextView 
       android:id="@+id/textViewMessage" 
       android:layout_width="wrap_content" 
       android:layout_height="wrap_content" 
       android:layout_marginLeft="50dp" 
       android:layout_marginRight="50dp" 
       android:layout_marginTop="50dp" 
       android:gravity="center" 
       android:text="@string/message" 
       android:textColor="@android:color/white" 
       android:textSize="18sp" 
       android:visibility="invisible" /> 

     </LinearLayout> 

    </LinearLayout> 

    <android.support.design.widget.FloatingActionButton 
     android:id="@+id/floatingActionButtonOnOff" 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content" 
     android:layout_gravity="end|bottom" 
     android:layout_margin="16dp" 
     android:elevation="4dp" 
     android:src="@drawable/on_btn" 
     app:backgroundTint="@color/colorRed" /> 

</android.support.design.widget.CoordinatorLayout> 
Verwandte Themen