Source

The Maggot / src / main.py

Full commit
#    This file is part of exquisite_code.
#    copyright 2010 Brendan Howell.
#
#    exquisite_code is free software: you can redistribute it and/or modify
#    it under the terms of the GNU General Public License as published by
#    the Free Software Foundation, either version 3 of the License, or
#    (at your option) any later version.
#
#    exquisite_code is distributed in the hope that it will be useful,
#    but WITHOUT ANY WARRANTY; without even the implied warranty of
#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
#    GNU General Public License for more details.
#
#    You should have received a copy of the GNU General Public License
#    along with exquisite_code.  If not, see <http://www.gnu.org/licenses/>.


import cherrypy
import os, random, glob
from Cheetah.Template import Template

from auth import AuthController, require, member_of, name_is
import auth

from model import *
import munger
import testchunks

from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
from sqlalchemy import and_
from sqlalchemy.orm.exc import NoResultFound


#session vars
USER_KEY = "_cp_username"
ROLE_KEY = "_excd_role"
CUR_EX_SESSION = "_excd_session"

class Index:
    _cp_config = {
        'tools.sessions.on': True,
        'tools.auth.on': True
    }
    
    auth = AuthController()
    sqlengine = create_engine('sqlite:///excode.db')
    SqlSession = sessionmaker()
    sqlmeta = Base.metadata
    sqlmeta.create_all(sqlengine)
    SqlSession.configure(bind=sqlengine)
    
    def __init__(self):
        auth.SqlSession = self.SqlSession

    @cherrypy.expose
    @require()
    def index(self):
        template = tmpldir + "/index.tmpl"
        page = Template(file=template)
        
        sqlsession = self.SqlSession()
        page.sessions = sqlsession.query(Corpus).all()
        page.old_sessions = []
        
        return unicode(page)
        
    @cherrypy.expose
    def newuser(self):
        template = tmpldir + "/adduser.tmpl"
        page = Template(file=template)
        
        return unicode(page)
        
    @cherrypy.expose
    def addnewuser(self, name, password):
        newuser = User(name, password)
        
        sqlsession = self.SqlSession()
        sqlsession.add(newuser)
        sqlsession.commit()
        raise cherrypy.HTTPRedirect("/")
        

    @cherrypy.expose
    @require()
    def newsession(self):
        template = tmpldir + "/newsession.tmpl"
        page = Template(file=template)
        page.creator = cherrypy.session.get(USER_KEY)
        
        return unicode(page)
  
        
    @cherrypy.expose
    @require()
    def addnewcorpus(self, name, creator, total_rounds):
        sqlsession = self.SqlSession()
        creator_user = sqlsession.query(User).filter(User.name==creator).first()
        
        newcorpus = Corpus(name, creator_user, total_rounds)
        
        sqlsession.add(newcorpus)
        sqlsession.commit()
        raise cherrypy.HTTPRedirect("/")   

    
    @cherrypy.expose
    @require()
    def corpus(self, cid):
        template = tmpldir + "/corpus.tmpl"
        sqlsession = self.SqlSession()
        corp = sqlsession.query(Corpus).filter(Corpus.id==cid).first()
        rnd = corp.current_round_index
        round = sqlsession.query(Round).filter(
            and_(Round.session==corp, Round.round_index==rnd)).first()
        prompt = None
        if sess.current_round_index < 2:
            lasttext = "no text written yet"
        else:
            lastround = sqlsession.query(Round).filter(
                and_(Round.session==sess, Round.round_index==(
                sess.current_round_index-1))).first()
            lastchunk = sqlsession.query(Chunk).filter(
                and_(Chunk.round==lastround, Chunk.selected==True)).first()
            if lastround:
                lasttext = lastround.text_out
            else:
                lasttext = None
            
        try:
            prompt = sqlsession.query(Prompt).filter(
                and_(Prompt.round==round, Prompt.selected==True)).first()
        except NoResultFound:
            prompt = None
        
        page = Template(file=template)
        page.corpus = corp
        page.lastchunk = lasttext
        page.prompt = prompt
        
        return unicode(page)


    @cherrypy.expose
    @require()
    def advanceround(self, cid, algorithm="roundrobin"):
        sqlsession = self.SqlSession()
        corp = sqlsession.query(Corpus).filter(Corpus.id==cid).first()
        rnd = corp.current_round_index
        round = sqlsession.query(Round).filter(
            and_(Round.session==corp, Round.round_index==rnd)).first()
        #TODO: use params for time
        #munge and update prompts
        chunks = sqlsession.query(Chunk).filter(Chunk.round==round).all()
        
        #this is very hacky but allows for dynamic creation of new munge functs
        mungefunction = eval("munger."+algorithm)
        munged_output = mungefunction(chunks)
        #chunk = random.choice(chunks)
        #chunk.selected = True
        round.text_out = munged_output
        txtout = open("out.txt", "a")
        txtout.write(munged_output)
        txtout.close()
        
        corp.current_round_index = corp.current_round_index + 1
        sqlsession.commit()
        raise cherrypy.HTTPRedirect("/session?cid="+cid)
    
            
    @cherrypy.expose
    @require()
    def addchunk(self, text, cid):
        sqlsession = self.SqlSession()
        corpus = sqlsession.query(Corpus).filter(Corpus.id==cid).first()
        rnd = corpus.current_round_index
        round = sqlsession.query(Round).filter(
            and_(Round.corpus==corpus, Round.round_index==rnd)).first()
        name = cherrypy.session.get(USER_KEY)
        author = sqlsession.query(User).filter(User.name==name).first()
        
        chunk = Chunk(text, author, corpus, round)
        
        sqlsession.add(chunk)
        sqlsession.commit()

        #TODO: if last commit, then advance the round

        raise cherrypy.HTTPRedirect("/wait?cid="+cid)
        
        
    @cherrypy.expose
    @require()
    def wait(self, cid):
        template = tmpldir + "/wait.tmpl"
        page = Template(file=template)
        page.cid = cid

        #TODO: check if user's lastround session var is != curr_corpus.current_round
        #      then redirect to corpus edit page

        #TODO: add js reload on 5 second interval to template
        
        return unicode(page)
        
    @cherrypy.expose
    def mungetest(self):
        pass
    
    @cherrypy.expose
    def domungetest(self, algorithm):
        sqlsession = self.SqlSession()
        round = sqlsession.query(Round).filter(Round.id==1).first()
        chunks = testchunks.testchunks
        #Achtung! hacky and insecure
        mungefunction = eval("munger."+algorithm)
        munged_output = mungefunction(chunks)
        return munged_output


current_dir = os.path.dirname(os.path.abspath(__file__))    
tmpldir = os.path.join(current_dir, "templates")
auth.tmpldir = tmpldir
datadir = os.path.join(current_dir, "data")

root = Index()

conf = { "/static" : { "tools.staticdir.on": True, 
                    "tools.staticdir.dir": os.path.join(current_dir, 'static')}}

cherrypy.config.update({ "server.socket_host": "127.0.0.1",
                        "server.socket_port": 8080 })

cherrypy.quickstart(root,config=conf)