Gambas/Διάβασμα αρχείου XML

Από Βικιβιβλία

Ο ευκολότερος τρόπος για να διαβάσετε ένα έγγραφο XML με την GAMBAS είναι να χρησιμοποιήσετε την κλάση XmlReader που επιτρέπει την πλοήγηση μέσα στο έγγραφο με την κίνηση προς τα εμπρός. Θα χρησιμοποιείτε την reader.Read() η οποία διαβάζει διαδοχικά όλους τους κόμβους ενός αρχείου XML. Και θα πρέπει όταν δημιουργήσετε το project να επιλέξετε ότι θα κάνετε χρήση της XML για να φορτώσει το component.

Πρώτα βεβαιωθείτε ότι το αρχείο υπάρχει:

 'ορίζουμε τη μεταβλητή
 DIM prAnagnostis AS XmlReader
 'αρχικοποιούμε τη μεταβλητή
 prAnagnostis = NEW XmlReader
 'φυσικά θα βάλετε το όνομα και τη διαδρομή του αρχείου που θέλετε να διαβάσετε
 'εγώ εδώ έχω βάλει το όνομα του αρχείου Kapoio.xml που βρίσκεται στον προσωπικό μου φάκελο (User.home)
 TRY prAnagnostis.Open(User.home & "/Kapoio.xml")
 IF ERROR THEN 
   Message.Error("Error when trying to open the Kapoio.XML file!")
   'αυτό δεν σημαίνει ότι δεν βρέθηκε το αρχείο
   'μπορεί να βρέθηκε αλλά να μην είναι σωστό ή να μην έχετε δικαιώματα σε αυτό
   RETURN 
 ENDIF

Μετά αρχίζει το διάβασμα:

 DO WHILE TRUE
   TRY prAnagnostis.Read()
   IF prAnagnostis.Eof THEN BREAK
 'Εδώ θα βάλετε τον υπόλοιπο κώδικα
 LOOP
 'φυσικά κλείνουμε το αρχείο για να μην μείνει "ξεκρέμαστο"
 prAnagnostis.Close

Σε κάθε διάβασμα το πρόγραμμα διαβάζει και έναν κόμβο ή το περιεχόμενο του κόμβου. Εδώ βλέπετε τις πρώτες γραμμές (μόνο) από το αρχείο του Βικιλεξικού:

<mediawiki xmlns="http://www.mediawiki.org/xml/export-0.4/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.me
diawiki.org/xml/export-0.4/ http://www.mediawiki.org/xml/export-0.4.xsd" version="0.4" xml:lang="el">
  <siteinfo>
    <sitename>Βικιλεξικό</sitename>
    <base>http://el.wiktionary.org/wiki/%CE%92%CE%B9%CE%BA%CE%B9%CE%BB%CE%B5%CE%BE%CE%B9%CE%BA%CF%8C:%CE%9A%CF%8D%CF%81%CE%B9%CE%B1_%CE%A3%CE%B5%CE
%BB%CE%AF%CE%B4%CE%B1</base>
    <generator>MediaWiki 1.16wmf4</generator>
    <case>case-sensitive</case>
    <namespaces>
      <namespace key="-2" case="case-sensitive">Μέσο</namespace>
      <namespace key="-1" case="first-letter">Ειδικό</namespace>
      <namespace key="0" case="case-sensitive" />
      <namespace key="1" case="case-sensitive">Συζήτηση</namespace>
      <namespace key="2" case="first-letter">Χρήστης</namespace>
      <namespace key="3" case="first-letter">Συζήτηση χρήστη</namespace>
      <namespace key="4" case="case-sensitive">Βικιλεξικό</namespace>
      <namespace key="5" case="case-sensitive">Συζήτηση βικιλεξικού</namespace>
      <namespace key="6" case="case-sensitive">Αρχείο</namespace>
      <namespace key="7" case="case-sensitive">Συζήτηση αρχείου</namespace>
      <namespace key="8" case="first-letter">MediaWiki</namespace>
      <namespace key="9" case="first-letter">Συζήτηση MediaWiki</namespace>
      <namespace key="10" case="case-sensitive">Πρότυπο</namespace>
      <namespace key="11" case="case-sensitive">Συζήτηση προτύπου</namespace>
      <namespace key="12" case="case-sensitive">Βοήθεια</namespace>
      <namespace key="13" case="case-sensitive">Συζήτηση βοήθειας</namespace>
      <namespace key="14" case="case-sensitive">Κατηγορία</namespace>
      <namespace key="15" case="case-sensitive">Συζήτηση κατηγορίας</namespace>
      <namespace key="100" case="case-sensitive">Παράρτημα</namespace>
      <namespace key="101" case="case-sensitive">Συζήτηση παραρτήματος</namespace>
    </namespaces>
  </siteinfo>
  <page>
    <title>MediaWiki:Categories</title>
    <id>1</id>
    <revision>
      <id>2119</id>
      <timestamp>2004-01-29T21:39:30Z</timestamp>
      <contributor>
        <ip>Optim</ip>
      </contributor>
      <comment>greek</comment>
      <text xml:space="preserve">Κατηγορίες σελίδων</text>
    </revision>
  </page>

Ας πούμε ότι θέλουμε να "διαβάσουμε" το κείμενο που έχει η σελίδα που έχει τίτλο

MediaWiki:Categories

που είναι η πρώτη σελίδα από το αρχείο που έχω κατεβάσει εγώ.

Στο Loop που δείξαμε προηγουμένως προσθέτουμε τον κώδικα:

   'για όση ώρα το όνομα του κόμβου δεν είναι page διάβαζε συνέχεια
   DO WHILE prAnagnostis.Node.Name <> "page"
     TRY prAnagnostis.Read()
     'φυσικά αν για κάποιο λόγο φτάσεις στο τέλος βγες από το Loop. 
     '(για να είμαστε εξασφαλισμένοι και να μην σκάει το πρόγραμμα)
     IF prAnagnostis.Eof THEN BREAK  
   LOOP
   'Αφού έφτασες εδώ πάει να πει ότι βρήκες έναν κόμβο με το όνομα page.
   'Μέσα σε αυτόν τον κόμβο υπάρχουν άλλοι κόμβοι.
   'Ας ψάξουμε για τον κόμβο title για να έχουμε τον τίτλο (της wiki σελίδας).
   'Προφανώς είναι ο επόμενος κόμβος αλλά καλού κακού...
   DO WHILE prAnagnostis.Node.Name <> "title"
     TRY prAnagnostis.Read()
     IF prAnagnostis.Eof THEN BREAK  
   LOOP
   'Φτάσαμε στον κόμβο
   'Διαβάζουμε άλλη μια φορά για να διαβάσουμε την τιμή του κόμβου
    TRY prAnagnostis.Read()
    IF prAnagnostis.Eof THEN BREAK  
   'Βάλε το όνομα-τίτλο της σελίδας σε μια τοπική μεταβλητή για να το έχουμε    
   prTitle = prAnagnostis.Node.Value
   'και πάμε να βρούμε το κείμενο της σελίδας του wiki που βρίσκεται στον κόμβο text
   DO WHILE prAnagnostis.Node.Name <> "text"
     TRY prAnagnostis.Read()
     IF prAnagnostis.Eof THEN BREAK  
   LOOP
   'φτάσαμε στον κόμβο text αλλά το πραγματικό περιεχόμενο είναι στο επόμενο διάβασμα
   TRY prAnagnostis.Read()
   IF prAnagnostis.Eof THEN BREAK  
   'βάλε το κείμενο σε μια τοπική μεταβλητή
   prText = prAnagnostis.Node.Value
   ' και για λόγους αποσφαλμάτωσης δείξτο
   '(αργότερα σβήστε αυτή τη γραμμή με το Message για να μην εμφανίζεται κάθε φορά που βρίσκει κάτι) 
   Message.Info("Το κείμενο της σελίδας με τίτλο: " & prTitle  & Chr(13) & "είναι: " & prText)

Θα πρέπει να μας εμφανίσει ένα μήνυμα που να είναι τύπου info και να λέει:

 Το κείμενο της σελίδας με τίτλο: MediaWiki:Categories 
 είναι: Κατηγορίες σελίδων

Γιατί η πρώτη φορά που βρήκαμε κόμβο με το όνομα title ήταν στη γραμμή <title>MediaWiki:Categories</title>

Και μέσα στον κόμβο page ο κόμβος text περιείχε το κείμενο: Κατηγορίες σελίδων (Το κείμενο που υπάρχει στην ονομασία του κόμβου <text xml:space="preserve"> δεν είναι μέρος της τιμής)

Αν φυσικά συνεχίσει το πρόγραμμα και δεν το διακόψουμε και έχετε κατεβάσει όλο XML από το Βικιλεξικό, τότε κάθε λίγο θα σας εμφανίζεται ένα μύνημα με τον αντίστοιχο τίτλο και κείμενο για κάθε σελίδα του Βικιλεξικού.

Τελικά αν θέλαμε να δούμε το κείμενο που έχει η σελίδα καραβάκι στο Βικιλεξικό και είχαμε κατεβάσει το αρχείο και το σώσαμε με το όνομα wikt.xml (στον προσωπικό μας φάκελο) θα έπρεπε να χρησιμοποιήσουμε αυτόν τον κώδικα:

 DIM prAnagnostis AS XmlReader
 DIM prTitle AS String
 DIM prText AS String
 prAnagnostis = NEW XmlReader
 TRY prAnagnostis.Open(User.home & "/wikt.xml")
 IF ERROR THEN 
   Message.Error("Error when trying to open the wikt.XML file!")
   RETURN 
 ENDIF
 DO WHILE TRUE
   TRY prAnagnostis.Read()
   IF prAnagnostis.Eof THEN BREAK
   'για όση ώρα το όνομα του κόμβου δεν είναι page διάβαζε συνέχεια
   DO WHILE prAnagnostis.Node.Name <> "page"
     TRY prAnagnostis.Read()
     'φυσικά αν για κάποιο λόγο φτάσεις στο τέλος βγες από το Loop. 
     '(για να είμαστε εξασφαλισμένοι και να μην σκάει το πρόγραμμα)
     IF prAnagnostis.Eof THEN BREAK  
   LOOP
   'Αφού έφτασες εδώ πάει να πει ότι βρήκες έναν κόμβο με το όνομα page.
   'Μέσα σε αυτόν τον κόμβο υπάρχουν άλλοι κόμβοι.
   'Ας ψάξουμε για τον κόμβο title για να έχουμε τον τίτλο (της wiki σελίδας).
   'Προφανώς είναι ο επόμενος κόμβος αλλά καλού κακού...
   DO WHILE prAnagnostis.Node.Name <> "title"
     TRY prAnagnostis.Read()
     IF prAnagnostis.Eof THEN BREAK  
   LOOP
   'Φτάσαμε στον κόμβο
   'Διαβάζουμε άλλη μια φορά για να διαβάσουμε την τιμή του κόμβου
    TRY prAnagnostis.Read()
    IF prAnagnostis.Eof THEN BREAK  
   'Βάλε το όνομα-τίτλο της σελίδας σε μια τοπική μεταβλητή για να το έχουμε    
   IF prAnagnostis.Node.Value <> "καραβάκι" THEN
     'μην κάνεις τίποτε. προχώρα μέχρι να ξαναβρείς κόμβο με το όνομα title
      ' μέσα σε κόμβο με το όνομα page
   ELSE
     'φτάσαμε στον κόμβο που έχει τίτλο καραβάκι
      prTitle = prAnagnostis.Node.LocalName
     'πάμε να βρούμε το κείμενο της σελίδας του wiki που βρίσκεται στον κόμβο text
     DO WHILE prAnagnostis.Node.Name <> "text"
       TRY prAnagnostis.Read()
       IF prAnagnostis.Eof THEN BREAK  
     LOOP
     'φτάσαμε στον κόμβο text αλλά το πραγματικό περιεχόμενο είναι στο επόμενο διάβασμα
     TRY prAnagnostis.Read()
     IF prAnagnostis.Eof THEN BREAK  
     'βάλε το κείμενο σε μια τοπική μεταβλητή
     prText = prAnagnostis.Node.Value
     ' και για λόγους αποσφαλμάτωσης δείξτο
     '(αργότερα σβήστε αυτή τη γραμμή με το Message για να μην εμφανίζεται κάθε φορά που βρίσκει κάτι) 
     Message.Info("Το κείμενο της σελίδας με τίτλο: " & prTitle  & Chr(13) & "είναι: " & prText)
     'αν εδώ δεν του πούμε να σταματήσει (αφού βρήκαμε αυτό που ζητάγαμε)
     'θα συνεχίσει χωρίς λόγο να διαβάζει μέχρι να φτάσει στο τέλος του αρχείου
     'οπότε μπορείτε να βάλετε ένα
      BREAK
      ' για να βγει από το Loop και να πάει να κλείσει το αρχείο
   END IF
 'και εδώ ξαναγυρίζει στην αρχή του Loop δηλαδή στο DO WHILE TRUE
 '(για να συνεχίσει το διάβασμα)
 LOOP
 'φυσικά κλείνουμε το αρχείο για να μην μείνει "ξεκρέμαστο"
 prAnagnostis.Close