Idee notwendig - Aktualität einer XML feststellen

  • 9 Antworten
  • Letztes Antwortdatum
Max1809

Max1809

Fortgeschrittenes Mitglied
6
Guten Abend zusammen,

stehe gerade vor einem Problem. :sad:

In meiner App möchte ich eine bestimmte XML-Datei genau ein mal vom Webserver herunterladen. Besser gesagt: die aktuellste Version der XML-Datei möchte ich genau einmal herunterladen. Dieses "herunterladen" geschieht bei mir aktuell beim Start der App.

Das ist einfach ein übles Performanceproblem, wenn ich die XML Datei jedes mal erneut herunterladen muss.

Jedoch kann sich der Inhalt der XML-Datei auf dem Server ändern - aber unbestimmt, durch den Kunden.

Wie kriege ich das in der App hin, dass eben die XML-Datei vom Server nur dann heruntergeladen wird, wenn diese tatsächlich aktueller ist, als die bereits heruntergeladene? :confused:

Ich habe das aktuell mit einem "Hashcode" versucht.

Sprich - beim Start lass ich mir den Hashcode der lokalen XML-Datei geben und ebenfalls den Hashcode der Datei vom Server - diese vergleiche ich und wenn ungleich, lade ich die vom Webserver herunter.

Leider sind die Hashcodes immer unterschiedlich. :mad2:

Kann es sein das:
Code:
int java.lang.[URL="https://www.android-hilfe.de/eclipse-javadoc:%E2%98%82=MobileKommune_Abschlussarbeit/D:%5C/Installierte%20Programme%5C/adt-bundle-windows-x86_64-20130219%5C/sdk%5C/platforms%5C/android-17%5C/android.jar%3Cjava.lang(Object.class%E2%98%83Object"]Object[/URL].hashCode()
anders vorgeht als:
Code:
int java.io.[URL="https://www.android-hilfe.de/eclipse-javadoc:%E2%98%82=MobileKommune_Abschlussarbeit/D:%5C/Installierte%20Programme%5C/adt-bundle-windows-x86_64-20130219%5C/sdk%5C/platforms%5C/android-17%5C/android.jar%3Cjava.io(File.class%E2%98%83File"]File[/URL].hashCode()
?

Hier gehe ich die Configdateien auf dem Webserver durch und bei der richtigen, bilde ich den Hashcode und überprüfe diesen mit dem mitgegebenen der lokalen XML-Datei.

Code:
for (int i = 0; i < length; i++) {
                String name = ftpFiles[i].getName();

                if (name.equals("config_level_1.xml")) {
                    
                    Integer temp= ftpFiles[i].hashCode();     //temporär zur Anzeige im Debugger       
                    
                    if (temp== hashCodeAlteDatei) {
                        lErfolg = false; // nicht erneut herunterladen
                    } else {
                        lErfolg = true;
                    }
                }            
            }
 
Der Hashcode kann ja nicht funktionieren, da du um den hashcode einer Datei zu berechnen diese erst mal komplett kennen musst.

zum Hashcode selber:
"As much as is reasonably practical, the hashCode method defined by class Object does return distinct integers for distinct objects."

Heißt verschiedene Objecte ergeben verschiedene Hashcodes (standartmäßig).
Wenn die also 2 Objekte der gleichen Klasse die gleich sind (equals() implentiert) aber bei denen hashcode nicht überschrieben ist, haben verschiedene Hashcodes.

Wie viel Einfluss hast du denn auf den Server?
Kannst du evtl dort einen kleinen Webservice implentieren, der dir den Änderungszeitpunkt der Datei geben kann?
Eigentlich ist dafür der HTTP Header "Last modified" zuständig.
Du kannst ja mal gucken ob der Server das schon mitschickt

Gerade mal nachgeguckt:
File generiert den hashCode aus dem abstrakten Dateinamen
http://www.tutorialspoint.com/java/io/file_hashcode.htm
 
Zuletzt bearbeitet:
Mir würden spontan auch erst mal ein zeit Stempel einfallen oder einen Prüfsumme wie md5 oder wie das teil mit s nochmal heißt.

Mfg Dagobert

Gesendet von meinem GT-I9300 mit der Android-Hilfe.de App
 
Hashfunktionen sind für sowas keine gute Idee - es ist nicht sichergestellt, dass zwei VM instanzen den selben Wert liefern (schönes Beispiel für Überraschungen: Collections Framework Enhancements in Java SE 7)

Man nimmt besser die md5 summe.
 
Also wie schon erwähnt ich würde den HTTP header nutzen, der ist ja genau dafür gedacht. Damit der Client entscheiden kann ob er die Datei neu laden muss oder nicht.
 
Sorry amfa,

habe erst gerade gesehen, dass du das auch schon geschrieben hattest.
Ist durch meinen "wichtig" Scan irgendwie durchgerutscht.

Habe am Anfang deines Beitrages MD5 gelesen und am Ende deines Beitrages MD5 und dann nicht mehr die Mitte beachtet :)
 
;)
Wobei ich nix von MD5 geschrieben hab sonder nur von der Java hashCode() methode.
 
Puh ....

Ich habe es geschafft. :)

Zunächst gehe ich nun tatsächlich auf einen gewissen TimeStamp. Kein Hash, kein MD5.

Den TimeStamp der Datei auf dem Server kann ich mir geben lassen, ohne diese extra herunterzuladen. Ich schätze intern läuft das über ein HTTP-Request (wie von "Kardroid" beschrieben).

Nun ein Codeausschnitt:

Code:
    for (int i = 0; i < length; i++) {
                String name = ftpFiles[i].getName();

                if (name.equals("config_level_1.xml")) {

                    Long datum_Server = ftpFiles[i].getTimestamp()
                            .getTimeInMillis();

                    // Irgendwie fehlen hier zwei Stunden ...
                    datum_Server = datum_Server + (3600000 * 2);

                    Log.d("test", "Lokal:" + datum_lokal.toString());
                    Log.d("test", "Server: " + datum_Server.toString());

                    Date date_server = new Date();
                    date_server.setTime(datum_Server);

                    Log.d("test",
                            "Server: " + String.valueOf(date_server.getHours())
                                    + ":"
                                    + String.valueOf(date_server.getMinutes()));

                    Date date_lokal = new Date();
                    date_lokal.setTime(datum_lokal);

                    Log.d("test",
                            "Lokal: " + String.valueOf(date_lokal.getHours())
                                    + ":"
                                    + String.valueOf(date_lokal.getMinutes()));

                    if (date_server.after(date_lokal)) {
                        lErfolg = true;
                        Log.d("test", "erneut herunterladen.");
                    } else {
                        lErfolg = false; // nicht erneut herunterladen
                        Log.d("test", "nicht erneut herunterladen.");
                    }
        
                    break;
                }
            }
Was wirklich, wirklich doof war:

Folgender Codeteil lieferte mir einen Zeitpunkt, bei dem zwei Stunden fehlten:
Code:
 Long datum_Server = ftpFiles[i].getTimestamp()
                            .getTimeInMillis();
Liegt das am Standort des FTP-Servers? :O

Nun ja ...

Jedenfalls funktioniert das nun. :D

Danke an alle! :thumbup:
 
Liegt vermutlich an der Zeitzone des Servers ja.
Wenn der in einer anderen zeitone ist gibt der natürlich auch ein anders Datum zurück.

Sollest du vielleicht in eine Variable auslagern, lässt sich etwas einfacher ändern, wenn sich die Zeit auf dem Server mal ändern sollte.
 
Zurück
Oben Unten