PHP Dashboard für HmIP Smartmeter
09.10.2024
Elektronik | Funk | Software
Der Technik-Blog
Dieses Beispiel zeigt, wie man mit Android ein Image an den Server sendet. Dazu wird als Erstes das Foto über einen ImagePicker ausgewählt. Wenn das Bild in der Galerie ausgewählt wurde, zeigt die App den absoluten Pfad vom Foto an. Jetzt leuchtet der Upload-Button grün. Durch Drücken des Upload-Buttons beginnt die App mit dem Upload. Es erscheint ein "Loading Spinner" bis der Upload abgeschlossen wurde oder ein Fehler auftretet. Anschließend wird das Ergebnis vom Server oder eine Fehlermeldung in der TextView angezeigt. Die Datenübertragung wird mittels HTTP-POST an den Server gesendet. Der Code unterstützt auch die Verwendung von HTTPs. Vor der ersten Verwendung sollte man prüfen, ob der Zugriff auf die Daten in den Einstellungen aktiviert ist.
Serverseitig läuft ein PHP-Script, der das POST-File entgegen nimmt und auf das Filesystem in den Ordner IMG speichert. Außerdem wird am Server ein Logfile (log.txt) erstellt, der die Uhrzeit und den Dateinamen speichert. Damit die PHP-Anwendung einwandfrei funktioniert, muss das PHP-Script Schreibrechte haben. Außerdem kann es vorkommen, dass Bilddateien, die größer als 2 Megabyte sind, nicht hochgeladen werden können. Um dies zu ändern, muss "upload_max_filesize" & "post_max_size" in der PHP-Konfiguration geändert werden. Der PHP-Script prüft auch, ob es sich bei der gesendeten Datei um ein Foto (JPG, PNG) handelt. Sollte es sich um einen anderen Dateityp handeln, so wird die Datei nicht gespeichert. Für den ersten Test können Sie auch gerne unseren Testserver verwenden. Den Link zum Foto zeigt die App, wenn man diese mit der URL zu unseren Testserver betreibt.
MainActivity.java: Dieser Code befindet sich in der MainActivity.
package com.aeqweb.imagesend;
import ...
public class MainActivity extends Activity {
Button selectButton, uploadButton;
TextView view_status;
ProgressDialog progress;
String response;
String realPath;
String UPLOAD_SERVER = "http://testserver.aeq-web.com/android_send_image/";
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
view_status = (TextView) findViewById(R.id.view_status);
view_status.setText("Select your Image");
selectButton = (Button) findViewById(R.id.button);
selectButton.getBackground().setColorFilter(0xFF00FF00, PorterDuff.Mode.MULTIPLY);
selectButton.setOnClickListener( new View.OnClickListener() {
@Override
public void onClick(View v) {
//Open image selector
Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
intent.setType("image/*");
startActivityForResult(intent, 0);
selectButton.getBackground().setColorFilter(0xffd6d7d7, PorterDuff.Mode.MULTIPLY);
}
});
uploadButton = (Button) findViewById(R.id.button2);
uploadButton.setOnClickListener( new View.OnClickListener() {
@Override
public void onClick(View v) {
//Open image selector
SendImage start_task = new SendImage();
start_task.execute();
view_status.setText("Try to upload Image");
view_status.setTextColor(Color.GRAY);
}
});
}
@Override
protected void onActivityResult(int reqCode, int resCode, Intent data) {
if(resCode == Activity.RESULT_OK && data != null){
// Check the SDK Version
if (Build.VERSION.SDK_INT < 11)
realPath = PathOfImage.PathAPI11(this, data.getData());
else if (Build.VERSION.SDK_INT < 19)
realPath = PathOfImage.Path_API18(this, data.getData());
else
realPath = PathOfImage.Path_API19(this, data.getData());
view_status.setText("Image path: " + realPath + "\n\nYou can start the upload now");
uploadButton.getBackground().setColorFilter(0xFF00FF00, PorterDuff.Mode.MULTIPLY);
}
}
public class SendImage extends AsyncTask<Void, Void, Void> {
@Override
protected void onPreExecute() {
progress = new ProgressDialog(MainActivity.this);
progress.setTitle("Uploading....");
progress.setMessage("Please wait until the process is finished");
progress.setCancelable(false); // disable dismiss by tapping outside of the dialog
progress.show();
}
@Override
protected Void doInBackground(Void... params) {
try {
response = POST_Data(realPath);
progress.dismiss();
} catch (Exception e) {
response = "Image was not uploaded!";
progress.dismiss();
}
return null;
}
@Override
protected void onPostExecute(Void result) {
if(response.contains("success"))
{
view_status.setTextColor(Color.parseColor("#21c627"));
}
view_status.setText(response);
uploadButton.getBackground().setColorFilter(0xffd6d7d7, PorterDuff.Mode.MULTIPLY);
}
}
public String POST_Data(String filepath) throws Exception {
HttpURLConnection connection = null;
DataOutputStream outputStream = null;
InputStream inputStream = null;
String boundary = "*****"+Long.toString(System.currentTimeMillis())+"*****";
int bytesRead, bytesAvailable, bufferSize;
byte[] buffer;
String[] q = filepath.split("/");
int idx = q.length - 1;
File file = new File(filepath);
FileInputStream fileInputStream = new FileInputStream(file);
URL url = new URL(UPLOAD_SERVER);
connection = (HttpURLConnection) url.openConnection();
connection.setDoInput(true);
connection.setDoOutput(true);
connection.setUseCaches(false);
connection.setRequestMethod("POST");
connection.setRequestProperty("Connection", "Keep-Alive");
connection.setRequestProperty("User-Agent", "Android Multipart HTTP Client 1.0");
connection.setRequestProperty("Content-Type", "multipart/form-data; boundary="+boundary);
outputStream = new DataOutputStream(connection.getOutputStream());
outputStream.writeBytes("--" + boundary + "\r\n");
outputStream.writeBytes("Content-Disposition: form-data; name=\"" + "img_upload" + "\"; filename=\"" + q[idx] +"\"" + "\r\n");
outputStream.writeBytes("Content-Type: image/jpeg" + "\r\n");
outputStream.writeBytes("Content-Transfer-Encoding: binary" + "\r\n");
outputStream.writeBytes("\r\n");
bytesAvailable = fileInputStream.available();
bufferSize = Math.min(bytesAvailable, 1048576);
buffer = new byte[bufferSize];
bytesRead = fileInputStream.read(buffer, 0, bufferSize);
while(bytesRead > 0) {
outputStream.write(buffer, 0, bufferSize);
bytesAvailable = fileInputStream.available();
bufferSize = Math.min(bytesAvailable, 1048576);
bytesRead = fileInputStream.read(buffer, 0, bufferSize);
}
outputStream.writeBytes("\r\n");
outputStream.writeBytes("--" + boundary + "--" + "\r\n");
inputStream = connection.getInputStream();
int status = connection.getResponseCode();
if (status == HttpURLConnection.HTTP_OK) {
BufferedReader in = new BufferedReader(new InputStreamReader(connection.getInputStream()));
String inputLine;
StringBuffer response = new StringBuffer();
while ((inputLine = in.readLine()) != null) {
response.append(inputLine);
}
inputStream.close();
connection.disconnect();
fileInputStream.close();
outputStream.flush();
outputStream.close();
return response.toString();
} else {
throw new Exception("Non ok response returned");
}
}
}
PathOfImage.java: Diese Datei ermittelt den richtigen Pfad für das Bild.
package com.aeqweb.imagesend; import ... public class PathOfImage { @SuppressLint("NewApi") public static String Path_API19(Context context, Uri uri) { String filePath = ""; String wholeID = DocumentsContract.getDocumentId(uri); String id = wholeID.split(":")[1]; String[] column = {MediaStore.Images.Media.DATA}; String sel = MediaStore.Images.Media._ID + "=?"; Cursor cursor = context.getContentResolver().query(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, column, sel, new String[]{id}, null); int columnIndex = cursor.getColumnIndex(column[0]); if (cursor.moveToFirst()) { filePath = cursor.getString(columnIndex); } cursor.close(); return filePath; } @SuppressLint("NewApi") public static String Path_API18(Context context, Uri contentUri) { String[] proj = {MediaStore.Images.Media.DATA}; String result = null; CursorLoader cursorLoader = new CursorLoader( context, contentUri, proj, null, null, null); Cursor cursor = cursorLoader.loadInBackground(); if (cursor != null) { int column_index = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA); cursor.moveToFirst(); result = cursor.getString(column_index); } return result; } public static String PathAPI11(Context context, Uri contentUri) { String[] proj = {MediaStore.Images.Media.DATA}; Cursor cursor = context.getContentResolver().query(contentUri, proj, null, null, null); int column_index = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA); cursor.moveToFirst(); return cursor.getString(column_index); } }
In der Manifest muss der Zugriff auf das Dateisystem und Internet aktiviert werden.
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.INTERNET" />
Auf dieser Seite zeigen wir, wie unter Android ein asynchroner HTTP/HTTPS Request gestartet wird und mittels Task verarbeitet wird.
WeiterlesenAuf dieser Seite zeigen wir, wie mit Android die GPS-Position, Geschwindigkeit & Seehöhe sowie der Name der Ortschaft ermittelt werden kann.
WeiterlesenAEQ-WEB © 2015-2024 All Right Reserved