I just scratched an itch to break out the App Engine Guestbook Tutorial into what satisfies me as a simple MVC framework (file/directory structure). The main benefit is to do data hiding on the model and controller (handler) classes to get them into different modules and so improve readability for me.
Small Changes
- Figuring out the imports was a bit tricky.
There may be a better way but this worked.
GuestbookM.py (the Guestbook Module) contains the class Guestbook, etc.. -
In class MainPage
NOW:
path = os.path.join(os.path.dirname(file), ‘../v/templates/MainPage.html’)
WAS:
path = os.path.join(os.path.dirname(file), ‘index.html’) -
I used the guestbook6_templates.py version available here. The index.html file is now in MainPage.html. The app name is jmvc. Here is the file structure:
jmvc/ c/ __init__.py GuestbookM.py MainPageM.py m/ __init__.py GreetingM.py v/ stylesheets/ main.css templates/ MainPage.html __init__.py app.yaml main.py
All init.py files are blank. As I said before MainPage.html is the same as index.html in the non MVC code. Here is the source for each of the remaining files :
# app.yaml application: jmvc version: 1 runtime: python api_version: 1 handlers: - url: /v/stylesheets static_dir: v/stylesheets - url: /.* script: main.py # main.py import cgi from google.appengine.ext import webapp from google.appengine.ext.webapp.util import run_wsgi_app from c import MainPageM MainPage = MainPageM.MainPage from c import Guestbook Guestbook = GuestbookM.Guestbook application = webapp.WSGIApplication( [('/', MainPage), ('/sign', Guestbook)], debug=True) def main(): run_wsgi_app(application) if __name__ == "__main__": main() # GuestbookM.py from google.appengine.ext import webapp from google.appengine.api import users from m import GreetingM Greeting = GreetingM.Greeting class Guestbook(webapp.RequestHandler): def post(self): greeting = Greeting() if users.get_current_user(): greeting.author = users.get_current_user() greeting.content = self.request.get('content') greeting.put() self.redirect('/') #MainPage.py from google.appengine.ext import webapp from google.appengine.api import users import os from google.appengine.ext.webapp import template from m import GreetingM Greeting = GreetingM.Greeting class MainPage(webapp.RequestHandler): def get(self): greetings_query = Greeting.all().order('-date') greetings = greetings_query.fetch(10) if users.get_current_user(): url = users.create_logout_url(self.request.uri) url_linktext = 'Logout' else: url = users.create_login_url(self.request.uri) url_linktext = 'Login' template_values = { 'greetings': greetings, 'url': url, 'url_linktext': url_linktext, } path = os.path.join(os.path.dirname(__file__), '../v/templates/MainPage.html') self.response.out.write(template.render(path, template_values)) # GuestbookM.py from google.appengine.ext import webapp from google.appengine.api import users from m import GreetingM Greeting = GreetingM.Greeting class Guestbook(webapp.RequestHandler): def post(self): greeting = Greeting() if users.get_current_user(): greeting.author = users.get_current_user() greeting.content = self.request.get('content') greeting.put() self.redirect('/') # MainPage.py from google.appengine.ext import webapp from google.appengine.api import users import os from google.appengine.ext.webapp import template from m import GreetingM Greeting = GreetingM.Greeting class MainPage(webapp.RequestHandler): def get(self): greetings_query = Greeting.all().order('-date') greetings = greetings_query.fetch(10) if users.get_current_user(): url = users.create_logout_url(self.request.uri) url_linktext = 'Logout' else: url = users.create_login_url(self.request.uri) url_linktext = 'Login' template_values = { 'greetings': greetings, 'url': url, 'url_linktext': url_linktext, } path = os.path.join(os.path.dirname(__file__), '../v/templates/MainPage.html') self.response.out.write(template.render(path, template_values)) # GreetingM.py from google.appengine.ext import db from google.appengine.api import users class Greeting(db.Model): author = db.UserProperty() content = db.StringProperty(multiline=True) date = db.DateTimeProperty(auto_now_add=True) # main.css body { font-family: Verdana, Helvetica, sans-serif; background-color: #DDDDDD; }
Please comment.
Thanks.
Love and peace,
Joe 🙂