Υπηρεσίες διαλειτουργικότητας (web services)

Εγχειρίδιο προγραμματιστή

Περιεχόμενα

  1. Εισαγωγή
  2. Επιστροφή όλων των δεδομένων (δράσεις/ομάδες/χρήστες/σχόλια)
  3. Επιστροφή μεμονωμένης δράσης
  4. Σύνδεση χρήστη
  5. Αποσύνδεση χρήστη
  6. Ανάρτηση δράσης
  7. Τροποποίηση δράσης
  8. Διαγραφή δράσης
  9. Λίστα εθελοντικών ομάδων
  10. Λίστα διαθέσιμων κατηγοριών
  11. Λίστα διαθέσιμων λέξεων-κλειδιά
  12. Λίστα διαθέσιμων Νομών-Δήμων
  13. Διαγνωστικά μηνύματα
  14. Μοντελοποίηση Οντοτήτων

1 Εισαγωγή

Το εγχειρίδιο προγραμματιστή περιγράφει τους διαδικτυακούς πόρους τους οποίους μπορεί να χρησιμοποιήσει κάποιος για να αξιοποιήσει τις υπηρεσίες διαλειτουργικότητας που προσφέρει η υπηρεσία υποστήριξης Εθελοντικών Δράσεων.

Παρέχεται διεπαφή XML, JSON και JSONp. Στις αιτήσεις, η δήλωση του τύπου περιεχομένου (Content-Type) είναι υποχρεωτική. Στις αποκρίσεις, το σώμα επιστρέφεται σε μορφή XML ή εκτός και αν έχει δηλωθεί διαφορετικά μέσω σχετικού πεδίου επικεφαλίδας. Στη δε περίπτωση που αιτηθεί JSONp (application/javascript ή text/javascript) θα πρέπει να δηλώνεται, επιπροσθέτως, η παράμετρος &callback= ακολοθούμενη από το όνομα της επιθυμητής συνάρτησης. Παράλειψη δήλωσής της οδηγεί σε σώμα απόκρισης μορφής JSON.

Όταν είναι επιθυμητή η αναφορά σε αναγνωριστικό (ID) κάποιου πόρου μέσα στο σώμα των αιτήσεων και των αποκρίσεων, χρησιμοποιείται η σύνταξη: τύπος_id, όπου τύπος: action, user, club, category… Σε διαφορετική περίπτωση (όπως σε URI), χρησιμοποιείται μόνο το αναγωνριστικό (ID), πχ: /webservice/action/1

2 Επιστροφή όλων των δεδομένων (δράσεις/ομάδες/χρήστες/σχόλια)

URI url/webservice/actions/
μέθοδος GET
request body OXI
παράμετροι NAI
αυθεντικοποίηση OXI

Σημειώσεις:

  • Όλες οι παράμετροι είναι προαιρετικές και χρησιμοποιούνται για τον περιορισμό των αποτελεσμάτων.
  • Οι δράσεις επιστρέφονται σελιδοποιημένες (μέγεθος σελίδας 10 εγγραφές).
  • Παράμετροι που δεν υποστηρίζονται, αγνοούνται.
Παράμετρος Έγκυρη Τιμή Περιγραφή
page ακέραιες τιμές

Αριθμός σελίδας αποτελεσμάτων.

Η αρίθμηση ξεκινάει από το 0, με 10 αποτελέσματα ανά σελίδα.

Προεπιλεγμένη τιμή: 0

name αλφαριθμητικά

Κάποια λέξη που περιέχεται στον τίτλο ή την περιγραφή της δράσης.

starts ημερομηνία

Ημερομηνία έναρξης τέλεσης δράσης.

Μορφή: YYYY-MM-DD

ends ημερομηνία

Ημερομηνία λήξης τέλεσης δράσης.

Μορφή: YYYY-MM-DD

keywords αλφαριθμητικά

Λέξεις-κλειδιά δράσης.

Για τις αποδεκτές τιμές, βλ. Λίστα διαθέσιμων λέξεων-κλειδιά

Τα κλειδιά χωρίζονται με κόμματα. Πχ:

&keywords=javascript,AJAX
category αλφαριθμητικά

Κατηγορία

Για τις αποδεκτές τιμές, βλ. Λίστα διαθέσιμων κατηγοριών

Για πολλαπλές κατηγορίες απαιτείται η χρήση array. Πχ:

&category[]=Εκπαίδευση&category[]=Υγεία
locality αλφαριθμητικά

Νομός / Δήμος

Προσοχή στην πτώση των ονομασιών. Για τις αποδεκτές τιμές, βλ. Λίστα διαθέσιμων Νομών-Δήμων

Για πολλαπλούς νομούς/δήμους απαιτείται η χρήση array. Πχ:

&locality[]=Αιγάλεω&locality[]=Κεφαλληνίας

3 Επιστροφή μεμονωμένης δράσης

URI url/webservice/action/id
μέθοδος GET
request body OXI
παράμετροι OXI
αυθεντικοποίηση OXI

Σημειώσεις:

  • Εκτός από της δράση, επιστρέφονται και οι σχετικές τις συσχετίσεις (ομάδες, χρήστες, σχόλια).

4 Σύνδεση χρήστη

URI url/webservice/user/login
μέθοδος POST
request body NAI
παράμετροι OXI
αυθεντικοποίηση OXI

Παράδειγμα αιτήματος σύνδεσης χρήστη με χρήση XML:

  • <login>
    • <username>όνομα χρήστη</username>
    • <password>συνθηματικό</password>
  • </login>

Παράδειγμα αιτήματος σύνδεσης χρήστη με χρήση JSON:

  • {
    • "username": "όνομα χρήστη",
    • "password": "συνθηματικό"
  • }

Σημειώσεις:

  • Η επιτυχής αυθεντικοποίηση του χρήστη επιστρέφει cookie στην επικεφαλίδα Set-Cookie της απόκρισης το οποίο (θα πρέπει να) χρησιμοποιείται στις αιτήσεις που απαιτούν αυθεντικοποίηση.

5 Αποσύνδεση χρήστη

Χρησιμοποιείται για τον τερματισμό της τρέχουσας συνεδρίας του χρήστη. Σε αυτήν την περίπτωση, και σε όλες που απαιτούν αυθεντικοποίηση, πρέπει να αποστέλλεται το cookie της αυθεντικοποίησης μέσα στην αίτηση.

URI url/webservice/user/logout
μέθοδος POST
request body ΟΧΙ
παράμετροι OXI
αυθεντικοποίηση ΝΑΙ

6 Ανάρτηση δράσης

URI url/webservice/action/
μέθοδος POST
request body NAI
παράμετροι OXI
αυθεντικοποίηση NAI

Παράδειγμα αιτήματος ανάρτηστης δράσης με χρήση XML:

  • <action>
    • <name><![CDATA[ ]]></name>
    • <description><![CDATA[<p>web service test description</p>]]></description>
    • <category>category_id</category>
    • <starts>2012-2-1T08:00:00</starts>
    • <ends>2012-3-10T17:00:00</ends>
    • <clubs>
      • <club>club_id</club>
    • </clubs>
    • <event_address>
      • <county></county>
      • <municipality></municipality>
      • <street><![CDATA[ ]]</street>
      • <postal_code></postal_code>
    • </event_address>
    •  
    • <!-- Τα υποχρεωτικά πεδία είναι τα ανωτέρω -->
    •  
    • <summary><![CDATA[]]></summary>
    • <meetup_address>
      • <county></county>
      • <municipality></municipality>
      • <street><![CDATA[ ]]</street>
      • <postal_code></postal_code>
    • </meetup_address>
    • <keywords>
      • <keyword><![CDATA[webservice]]</keyword>
      • <keyword><![CDATA[interoperability]]</keyword>
    • </keywords>
    • <image><![CDATA[ ]]</image>
    • <url><![CDATA[ ]]</url>
    • <allows_comments>false</allows_comments>
    • <desired_volunteers></desired_volunteers>
  • </action>

Παράδειγμα αιτήματος ανάρτηστης δράσης με χρήση JSON:

  • {
    • "name" : "",
    • "description" : "",
    • "category" : "",
    • "starts" : "2012-5-5T10:00:00",
    • "ends" : "2012-7-7T15:00:00",
    • "clubs" : [ "" ],
    • "event_address" : {
      • "county" : "",
      • "municipality" : "",
      • "street" : "",
      • "postal_code" : ""
    • },
    • "summary" : "<p><em>some summary</em></p>",
    • "meetup_address" : {
      • "county" : "",
      • "municipality" : "",
      • "street" : "",
      • "postal_code" : ""
    • },
    • "keywords" : [
      • "keyword_1",
      • "keyword_2"
    • ],
    • "image" : "",
    • "url" : "",
    • "allows_comments" : "true",
    • "desired_volunteers" : ""
  • }

Σημειώσεις:

  • Τα υποχρεωτικά προς συμπλήρωση πεδία είναι αυτά που εμφανίζονται μέχρι και τη διεύθυνση τέλεσης (event_address).
  • Η σειρά των πεδίων δεν επηρεάζουν το αποτέλεσμα.
  • Τα πεδία meetup_address και event_address προϋποθέτουν την συμπλήρωση όλων των εσωτερικών τους στοιχείων.
  • Η εικόνα είναι κωδικοποίησης Base64.
  • Για το σύνολο των αποδεκτών τιμών των πεδίων county και municipality, βλ. Λίστα διαθέσιμων Νομών-Δήμων.
  • Επιτυχής ολοκλήρωση επιστρέφει το αναγνωριστικό (ID) της νεάς δράση στην απόκριση.

7 Τροποποίηση δράσης

URI url/webservice/action/id
μέθοδος PUT
request body NAI
παράμετροι OXI
αυθεντικοποίηση NAI

Σημειώσεις:

  • Τα πεδία αιτημάτων τροποποίησης είναι τα ίδια με τα αιτήματα ανάρτησης δράσης.
  • Τα πεδία των οποίων η τιμή δεν είναι επιθυμητό να αλλάξει, πρέπει να παραληφθούν.
  • Για τη διαγραφή της εικόνας μία δράσης, αρκεί η συμπερίληψη ενός άδειου πεδίου image.

8 Διαγραφή δράσης

URI url/webservice/action/id
μέθοδος DELETE
request body OXI
παράμετροι OXI
αυθεντικοποίηση NAI

Σημειώσεις:

  • Δικαίωμα διαγραφής έχουν μόνο συγκεκριμένοι λογαριασμοί. Το δικαίωμα ανάρτησης δράσης δεν συνεπάγεται και δικαίωμα διαγραφής.

9 Λίστα εθελοντικών ομάδων

URI url/webservice/clubs
μέθοδος GET
request body OXI
παράμετροι OXI
αυθεντικοποίηση NAI

Παράδειγμα απόκρισης λίστας ομάδων σε μορφή XML:

  • <?xml version="1.0" encoding="UTF-8"?>
  • <result>
    • <clubs>
      • <club id="club_id">
        • <manager>user_id</manager>
        • <name><![CDATA[Ανάπτυξη Συστημάτων με ΕΛ/ΛΑΚ]]></name>
        • <description><![CDATA[Στόχος είναι …]]></description>
        • <phone>2104567893</phone>
        • <url></url>
        • <afm><![CDATA[011111111]]></afm>
        • <image></image>
      • </club>
      • <club id="club_id">
        • <manager>user_id</manager>
        • <name><![CDATA[Κοινωνική υπηρεσία]]></name>
        • <description><![CDATA[ ]]></description>
        • <phone>6900122111</phone>
        • <url></url>
        • <afm></afm>
        • <image></image>
      • </club>
    • </clubs>
  • </result>

Σημειώσεις:

  • Επιστρέφεται λίστα με τις εθελοντικές ομάδες για τις οποίες διαθέτει δικαίωμα ανάρτησης δράσεων ο αυθεντικοποιημένος χρήστης (είτε δικές του είτε ανατεθιμένες).
  • Μόνο οι επιστρεφόμενες ομάδες είναι δυνατό να χρησιμοποιηθούν στα αιτήματα δημιουργίας δράσης από τον αυθεντικοποιημένο χρήστη.

10 Λίστα διαθέσιμων κατηγοριών

Επιστρέφεται λίστα με όλες τις διαθέσιμες κατηγορίες δράσεων. Επιστρέφεται το όνομα κάθε κατηγορίας και το ID προκειμένου το τελευταίο να χρησιμοποιηθεί στην σύνταξη των αιτήσεων XML/JSON/JSONp, όπου αυτό απαιτείται.

URI url/webservice/categories
μέθοδος GET
request body OXI
παράμετροι OXI
αυθεντικοποίηση OXI

Παράδειγμα απόκρισης λίστας κατηγοριών σε μορφή XML:

  • <?xml version="1.0" encoding="UTF-8"?>
  • <result>
    • <categories>
      • <category id="category_1"><name>Περιβάλλον</name></category>
      • <category id="category_2"><name>Εκπαίδευση</name></category>
    • </categories>
  • </result>

Παράδειγμα απόκρισης λίστας κατηγοριών σε μορφή JSON:

  • {"categories" : [{
      • "@attributes" : {"id" : "category_1"},
      • "name" : "Περιβάλλον"
    • },
    • {
      • "@attributes" : {"id" : "category_2"},
      • "name" : "Εκπαίδευση"
    • }]
  • }

11 Λίστα διαθέσιμων λέξεων-κλειδιά

URI url/webservice/keywords
μέθοδος GET
request body OXI
παράμετροι OXI
αυθεντικοποίηση OXI

Επιστρέφεται λίστα με όλες τις διαθέσιμες λέξεις-κλειδιά των δράσεων. Χρησιμοποιούνται για την ευρετηρίαση και την καταχώρηση και ενημέρωση δράσεων.

Παράδειγμα απόκρισης λίστας λέξεων-κλειδιά σε μορφή XML:

  • <?xml version="1.0" encoding="UTF-8"?>
  • <result>
    •   <keywords>
      • <keyword>autotools</keyword>
      • <keyword>git</keyword>
      • <keyword>gnu</keyword>
    • </keywords>
  • </result>

12 Λίστα διαθέσιμων Νομών-Δήμων

URI url/webservice/localities
μέθοδος GET
request body OXI
παράμετροι OXI
αυθεντικοποίηση OXI

Επιστρέφεται λίστα των διαθέσιμων Νομών και Δήμων σε ιεραρχική μορφή. Χρησιμοποιείται για την ευρετηρίαση και την καταχώρηση και ενημέρωση δράσεων.

Παράδειγμα απόκρισης λίστας Νομών και Δήμων σε μορφή XML:

  • <?xml version="1.0" encoding="UTF-8"?>
  • <result>
    • <localities>
      • <county>
        • <name>Αττικής-Δυτικού Τομέα Αθηνών</name>
        • <municipalities>
          • <municipality><name>Αγίας Βαρβάρας</name></municipality>
          • <municipality><name>Αγίων Αναργύρων - Καματερού</name></municipality>
          • <municipality><name>Αιγάλεω</name></municipality>
          • <municipality><name>Ιλίου</name></municipality>
          • <municipality><name>Περιστερίου</name></municipality>
          • <municipality><name>Πετρούπολης</name></municipality>
          • <municipality><name>Χαϊδαρίου</name></municipality>
        • </municipalities>
      • </county>
      • <county>
        • <name>Αττικής-Κεντρικού Τομέα Αθηνών</name>
      • </county>
    • </localities>
  • </result>

13 Διαγνωστικά μηνύματα

Όταν δεν είναι δυνατή η επιστροφή κάποιου πόρου, επιστρέφονται διαγνωστικά μηνύματα τα οποία ενημερώνουν για την περάτωση ή μη της ενέργειας. Τα διαγνωστικά μηνύματα μπορούν να χρησιμοποιηθούν για την αντιμετώπιση διαφόρων καταστάσεων. Στις περισσότερες των περιπτώσεων, η κατανόηση και διόρθωσή τους είναι εύκολη. Για παράδειγμα, το ακόλουθο:

  • <?xml version="1.0" encoding="UTF-8"?>
  • <status code="400">
    • <messages>
      • <message>Το πεδίο Τίτλος είναι απαραίτητο.</message>
      • <message>Το πεδίο Περιγραφή είναι απαραίτητο.</message>
      • <message>Εντοπίστηκε εσφαλμένη τιμή σε πεδίο πολλαπλής επιλογής.</message>
      • <message>Η τιμή της ημερομηνίας δεν είναι έγκυρη για το πεδίο Ημερομηνίες και ώρες έναρξης.</message>
      • <message>Όλα τα στοιχεία της διεύθυνσης τέλεσης είναι απαραίτητα.</message>
    • </messages>
  • </status>

Ωστόσο, ορισμένα μηνύματα ίσως δεν παρέχουν αρκετές λεπτομέρειες. Στο παραπάνω παράδειγμα, το μήνυμα «Εντοπίστηκε εσφαλμένη τιμή σε πεδίο πολλαπλής επιλογής.» δύναται να αναφέρεται σε εσφαλμένη τιμής κατηγορίας ή και ομάδας. Επίσης, το παρακάτω μήνυμα μπορεί να οφείλεται σε εσφαλμένη σύνταξη του σώματος της αίτησης (πχ, ελλιπές closing-tag) ή κατά την παράλειψη δήλωσης του τύπου περιεχομένου (Content-Type) αυτού.

  • <?xml version="1.0" encoding="UTF-8"?>
  • <status code="400">
    •   <messages><message>Η δομή του αιτήματος δεν είναι η αναμενόμενη.</message></messages>
  • </status>

14 Μοντελοποίηση Οντοτήτων

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"

  xmlns:tns="http://openactions.teiath.gr/schemas/action"
  targetNamespace="http://openactions.teiath.gr/schemas/action">
  <!-- Email type -->
  <xs:simpleType name="email_type">
    <xs:restriction base="xs:string">
      <xs:pattern value="\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*"/>
    </xs:restriction>
  </xs:simpleType>

  <!-- AFM type -->
  <xs:simpleType name="afm_type">
    <xs:restriction base="xs:string">
      <xs:pattern value="\d{10}"/>
    </xs:restriction>
  </xs:simpleType>

  <!-- Postal Code type -->
  <xs:simpleType name="postal_code_type">
    <xs:restriction base="xs:string">
     <xs:pattern value="\d{5}"/>
    </xs:restriction>
  </xs:simpleType>

  <!-- Address type -->
  <xs:complexType name="address_type">
    <xs:sequence>
      <xs:element name="county" type="xs:string"/>
      <xs:element name="municipality" type="xs:string"/>
      <xs:element name="street" type="xs:string"/>
      <xs:element name="postal_code" type="tns:postal_code_type"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Municipality type -->
  <xs:complexType name="municipality_type">
    <xs:sequence>
      <xs:element name="name" type="xs:string"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of municipalities type -->
  <xs:complexType name="array_of_municipalities_type">
    <xs:sequence>
      <xs:element name="municipality" type="tns:municipality_type"/>
    </xs:sequence>
  </xs:complexType>

  <!-- County type -->
  <xs:complexType name="county_type">
    <xs:sequence>
      <xs:element name="name" type="xs:string"/>
      <xs:element name="municipalities" type="tns:array_of_municipalities_type"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of counties -->
  <xs:complexType name="array_of_counties_type">
    <xs:sequence>
      <xs:element name="county" type="tns:county_type" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of localities, ie counties -->
  <xs:complexType name="array_of_localities_type">
    <xs:sequence>
      <xs:element name="localities" type="tns:array_of_counties_type"/>
    </xs:sequence>
  </xs:complexType>

  <!-- User data -->
  <xs:complexType name="user_type">
    <xs:sequence>
      <xs:element name="first_name" type="xs:string" minOccurs="0"/>
      <xs:element name="last_name" type="xs:string" minOccurs="0"/>
      <xs:element name="url" type="xs:string" minOccurs="0"/>
      <xs:element name="email" type="tns:email_type"/>
    </xs:sequence>
    <xs:attribute name="id" type="xs:ID"/>
  </xs:complexType>

  <!-- Array of users -->
  <xs:complexType name="array_of_users_type">
    <xs:sequence>
      <xs:element name="user" type="tns:user_type" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of user references -->
  <xs:complexType name="array_of_users_ref_type">
    <xs:sequence>
      <xs:element name="user_id" type="xs:IDREF" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Club data -->
  <xs:complexType name="club_type">
    <xs:sequence>
      <xs:element name="manager" type="xs:IDREF" minOccurs="0"/>
      <xs:element name="name" type="xs:string"/>
      <xs:element name="description" type="xs:string"/>
      <xs:element name="phone" type="xs:string"/>
      <xs:element name="url" type="xs:string"/>
      <xs:element name="afm" type="tns:afm_type"/>
      <xs:element name="image" type="xs:string"/>
    </xs:sequence>
    <xs:attribute name="id" type="xs:ID"/>
  </xs:complexType>

  <!-- Array of clubs -->
  <xs:complexType name="array_of_clubs_type">
    <xs:sequence>
      <xs:element name="club" type="tns:club_type" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of club references -->
  <xs:complexType name="array_of_clubs_ref_type">
    <xs:sequence>
      <xs:element name="club_id" type="xs:IDREF" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Action category -->
  <xs:complexType name="action_category_type">
    <xs:sequence>
      <xs:element name="name" type="xs:string"/>
    </xs:sequence>
    <xs:attribute name="id" type="xs:ID"/>
 </xs:complexType>

  <!-- Array of categories -->
  <xs:complexType name="array_of_categories_type">
    <xs:sequence>
      <xs:element name="category" type="tns:action_category_type" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of actions -->
  <xs:complexType name="array_of_actions_type">
    <xs:sequence>
      <xs:element name="action" type="tns:action_type" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of action result -->
  <xs:complexType name="array_of_actions_type">
    <xs:sequence>
      <xs:element name="actions" type="tns:array_of_actions_type" minOccurs="0" maxOccurs="unbounded"/>
      <xs:element name="categories" type="tns:array_of_categories_type" minOccurs="0" maxOccurs="unbounded"/>
      <xs:element name="clubs" type="tns:array_of_clubs_type" minOccurs="0" maxOccurs="unbounded"/>
      <xs:element name="users" type="tns:array_of_users" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of keywords -->
  <xs:complexType name="array_of_keywords_type">
    <xs:sequence>
      <xs:element name="keyword" type="xs:string" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Action comments -->
  <xs:complexType name="comment_type">
    <xs:sequence>
      <xs:element name="author" type="xs:IDREF"/>
      <xs:element name="created" type="xs:dateTime"/>
      <xs:element name="subject" type="xs:string"/>
      <xs:element name="text" type="xs:string"/>
    </xs:sequence>
  </xs:complexType>

  <!-- Array of comments -->
  <xs:complexType name="array_of_comments_type">
    <xs:sequence>
      <xs:element name="comment" type="tns:comment_type" minOccurs="0" maxOccurs="unbounded"/>
    </xs:sequence>
  </xs:complexType>

  <!-- An action -->
  <xs:complexType name="action_type">
    <xs:sequence>
      <xs:element name="owner" type="xs:IDREF"/>
      <xs:element name="name" type="xs:string"/>
      <xs:element name="summary" type="xs:string" minOccurs="0"/>
      <xs:element name="description" type="xs:string"/>
      <xs:element name="clubs" type="tns:array_of_clubs_ref_type"/>
      <xs:element name="image" type="xs:string" minOccurs="0"/>
      <xs:element name="category" type="xs:IDREF"/>
      <xs:element name="keywords" type="tns:array_of_keywords_types" minOccurs="0"/>
      <xs:element name="url type="xs:string" minOccurs="0"/>
      <xs:element name="allows_comments" type="xs:boolean" minOccurs="0"/>
      <xs:element name="created" type="xs:dateTime"/>
      <xs:element name="starts" type="xs:dateTime"/>
      <xs:element name="ends" type="xs:dateTime"/>
      <xs:element name="desired_volunteers" type="xs:int" minOccurs="0"/>
      <xs:element name="meetup_address" type="tns:address_type"/>
      <xs:element name="event_address" type="tns:address_type" minOccurs="0"/>
      <xs:element name="comments" type="tns:array_of_comments_type" minOccurs="0"/>
      <xs:element name="volunteers" type="tns:array_of_users_ref_type" minOccurs="0"/>
    </xs:sequence>
    <xs:attribute name="id" type="xs:ID"/>
  </xs:complexType>
</xs:schema>