Home | History | Annotate | Download | only in samplesyncadapter_server
      1 #!/usr/bin/python2.5
      2 
      3 # Copyright (C) 2010 The Android Open Source Project
      4 #
      5 # Licensed under the Apache License, Version 2.0 (the "License"); you may not
      6 # use this file except in compliance with the License. You may obtain a copy of
      7 # the License at
      8 #
      9 # http://www.apache.org/licenses/LICENSE-2.0
     10 #
     11 # Unless required by applicable law or agreed to in writing, software
     12 # distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
     13 # WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
     14 # License for the specific language governing permissions and limitations under
     15 # the License.
     16 
     17 """
     18 Defines Django forms for inserting/updating/viewing contact data
     19 to/from SampleSyncAdapter datastore.
     20 """
     21 
     22 import cgi
     23 import datetime
     24 import os
     25 
     26 from google.appengine.ext import db
     27 from google.appengine.ext import webapp
     28 from google.appengine.ext.webapp import template
     29 from google.appengine.ext.db import djangoforms
     30 from model import datastore
     31 from google.appengine.api import images
     32 
     33 import wsgiref.handlers
     34 
     35 class BaseRequestHandler(webapp.RequestHandler):
     36     """
     37     Base class for our page-based request handlers that contains
     38     some helper functions we use in most pages.
     39     """
     40 
     41     """
     42     Return a form (potentially partially filled-in) to
     43     the user.
     44     """
     45     def send_form(self, title, action, contactId, handle, content_obj):
     46         if (contactId >= 0):
     47             idInfo = '<input type="hidden" name="_id" value="%s">'
     48         else:
     49             idInfo = ''
     50 
     51         template_values = {
     52                 'title': title,
     53                 'header': title,
     54                 'action': action,
     55                 'contactId': contactId,
     56                 'handle': handle,
     57                 'has_contactId': (contactId >= 0),
     58                 'has_handle': (handle != None),
     59                 'form_data_rows': str(content_obj)
     60                 }
     61 
     62         path = os.path.join(os.path.dirname(__file__), 'templates', 'simple_form.html')
     63         self.response.out.write(template.render(path, template_values))
     64 
     65 class ContactForm(djangoforms.ModelForm):
     66     """Represents django form for entering contact info."""
     67 
     68     class Meta:
     69         model = datastore.Contact
     70 
     71 
     72 class ContactInsertPage(BaseRequestHandler):
     73     """
     74     Processes requests to add a new contact. GET presents an empty
     75     contact form for the user to fill in.  POST saves the new contact
     76     with the POSTed information.
     77     """
     78 
     79     def get(self):
     80         self.send_form('Add Contact', '/add_contact', -1, None, ContactForm())
     81 
     82     def post(self):
     83         data = ContactForm(data=self.request.POST)
     84         if data.is_valid():
     85             # Save the data, and redirect to the view page
     86             entity = data.save(commit=False)
     87             entity.put()
     88             self.redirect('/')
     89         else:
     90             # Reprint the form
     91             self.send_form('Add Contact', '/add_contact', -1, None, data)
     92 
     93 
     94 class ContactEditPage(BaseRequestHandler):
     95     """
     96     Process requests to edit a contact's information.  GET presents a form
     97     with the current contact information filled in. POST saves new information
     98     into the contact record.
     99     """
    100 
    101     def get(self):
    102         id = int(self.request.get('id'))
    103         contact = datastore.Contact.get(db.Key.from_path('Contact', id))
    104         self.send_form('Edit Contact', '/edit_contact', id, contact.handle, 
    105                        ContactForm(instance=contact))
    106 
    107     def post(self):
    108         id = int(self.request.get('id'))
    109         contact = datastore.Contact.get(db.Key.from_path('Contact', id))
    110         data = ContactForm(data=self.request.POST, instance=contact)
    111         if data.is_valid():
    112             # Save the data, and redirect to the view page
    113             entity = data.save(commit=False)
    114             entity.updated = datetime.datetime.utcnow()
    115             entity.put()
    116             self.redirect('/')
    117         else:
    118             # Reprint the form
    119             self.send_form('Edit Contact', '/edit_contact', id, contact.handle, data)
    120 
    121 class ContactDeletePage(BaseRequestHandler):
    122     """Processes delete contact request."""
    123 
    124     def get(self):
    125         id = int(self.request.get('id'))
    126         contact = datastore.Contact.get(db.Key.from_path('Contact', id))
    127         contact.deleted = True
    128         contact.updated = datetime.datetime.utcnow()
    129         contact.put()
    130 
    131         self.redirect('/')
    132 
    133 class AvatarEditPage(webapp.RequestHandler):
    134     """
    135     Processes requests to edit contact's avatar. GET is used to fetch
    136     a page that displays the contact's current avatar and allows the user 
    137     to specify a file containing a new avatar image.  POST is used to
    138     submit the form which will change the contact's avatar.
    139     """
    140 
    141     def get(self):
    142         id = int(self.request.get('id'))
    143         contact = datastore.Contact.get(db.Key.from_path('Contact', id))
    144         template_values = {
    145                 'avatar': contact.avatar,
    146                 'contactId': id
    147                 }
    148         
    149         path = os.path.join(os.path.dirname(__file__), 'templates', 'edit_avatar.html')
    150         self.response.out.write(template.render(path, template_values))
    151 
    152     def post(self):
    153         id = int(self.request.get('id'))
    154         contact = datastore.Contact.get(db.Key.from_path('Contact', id))
    155         #avatar = images.resize(self.request.get("avatar"), 128, 128)
    156         avatar = self.request.get("avatar")
    157         contact.avatar = db.Blob(avatar)
    158         contact.updated = datetime.datetime.utcnow()
    159         contact.put()
    160         self.redirect('/')
    161 
    162 class AvatarViewPage(BaseRequestHandler):
    163     """
    164     Processes request to view contact's avatar. This is different from
    165     the GET AvatarEditPage request in that this doesn't return a page -
    166     it just returns the raw image itself.
    167     """
    168 
    169     def get(self):
    170         id = int(self.request.get('id'))
    171         contact = datastore.Contact.get(db.Key.from_path('Contact', id))
    172         if (contact.avatar):
    173             self.response.headers['Content-Type'] = "image/png"
    174             self.response.out.write(contact.avatar)
    175         else:
    176             self.redirect(self.request.host_url + '/static/img/default_avatar.gif')
    177 
    178 class ContactsListPage(webapp.RequestHandler):
    179     """
    180     Display a page that lists all the contacts associated with
    181     the specifies user account.
    182     """
    183 
    184     def get(self):
    185         contacts = datastore.Contact.all()
    186         template_values = {
    187                 'contacts': contacts,
    188                 'username': 'user'
    189                 }
    190 
    191         path = os.path.join(os.path.dirname(__file__), 'templates', 'contacts.html')
    192         self.response.out.write(template.render(path, template_values))
    193 
    194 
    195 def main():
    196     application = webapp.WSGIApplication(
    197         [('/', ContactsListPage),
    198          ('/add_contact', ContactInsertPage),
    199          ('/edit_contact', ContactEditPage),
    200          ('/delete_contact', ContactDeletePage),
    201          ('/avatar', AvatarViewPage),
    202          ('/edit_avatar', AvatarEditPage)
    203         ],
    204         debug=True)
    205     wsgiref.handlers.CGIHandler().run(application)
    206 
    207 if __name__ == '__main__':
    208   main()