Lots of goodies in this one. More work on the default web front page, a few extra utility functions for functions_db as well. Some cleanup in the session code to use some of the new abstraction I added a while back. Player's last login time is now also set on the User object. Issue 28: Forward slashes causing crashes, found by Kuros, fixed by me.

This commit is contained in:
Greg Taylor 2007-06-06 13:38:13 +00:00
parent 270db06820
commit e2cc754441
7 changed files with 57 additions and 25 deletions

View file

@ -8,6 +8,7 @@ from django.contrib.auth.models import User
from django.utils import simplejson from django.utils import simplejson
from apps.news.models import NewsEntry from apps.news.models import NewsEntry
import functions_db
""" """
This file contains the generic, assorted views that don't fall under one of This file contains the generic, assorted views that don't fall under one of
@ -23,6 +24,9 @@ def page_index(request):
pagevars = { pagevars = {
"page_title": "Front Page", "page_title": "Front Page",
"news_entries": news_entries, "news_entries": news_entries,
"players_connected": functions_db.num_connected_players(),
"players_registered": functions_db.num_total_players(),
"players_connected_recent": functions_db.num_recently_connected_players(),
} }
context_instance = RequestContext(request) context_instance = RequestContext(request)

View file

@ -75,6 +75,10 @@ def handle(cdat):
# Player-visible idle time, not used in idle timeout calcs. # Player-visible idle time, not used in idle timeout calcs.
session.cmd_last_visible = time.time() session.cmd_last_visible = time.time()
# Just in case. Prevents some really funky-case crashes.
if len(parsed_input['root_cmd']) == 0:
raise UnknownCommand
# Shortened say alias. # Shortened say alias.
if parsed_input['root_cmd'][0] == '"': if parsed_input['root_cmd'][0] == '"':
parsed_input['splitted'].insert(0, "say") parsed_input['splitted'].insert(0, "say")

View file

@ -89,9 +89,9 @@ def cmd_inventory(cdat):
money = int(pobject.get_attribute_value("MONEY", default=0)) money = int(pobject.get_attribute_value("MONEY", default=0))
if money == 1: if money == 1:
money_name = functions_db.get_server_config("MONEY_NAME_SINGULAR") money_name = gameconf.get_configvalue("MONEY_NAME_SINGULAR")
else: else:
money_name = functions_db.get_server_config("MONEY_NAME_PLURAL") money_name = gameconf.get_configvalue("MONEY_NAME_PLURAL")
session.msg("You have %d %s." % (money,money_name)) session.msg("You have %d %s." % (money,money_name))

View file

@ -22,7 +22,7 @@ def cmd_connect(cdat):
password = cdat['uinput']['splitted'][2] password = cdat['uinput']['splitted'][2]
# Match an email address to an account. # Match an email address to an account.
email_matches = functions_db.get_dbref_from_email(uemail) email_matches = functions_db.get_user_from_email(uemail)
autherror = "Specified email does not match any accounts!" autherror = "Specified email does not match any accounts!"
# No username match # No username match
@ -36,7 +36,6 @@ def cmd_connect(cdat):
if not user.check_password(password): if not user.check_password(password):
session.msg(autherror) session.msg(autherror)
else: else:
user = email_matches[0]
uname = user.username uname = user.username
session.login(user) session.login(user)
@ -70,7 +69,7 @@ def cmd_create(cdat):
# Search for a user object with the specified username. # Search for a user object with the specified username.
account = User.objects.filter(username=uname) account = User.objects.filter(username=uname)
# Match an email address to an account. # Match an email address to an account.
email_matches = functions_db.get_dbref_from_email(email) email_matches = functions_db.get_user_from_email(email)
if not account.count() == 0: if not account.count() == 0:
session.msg("There is already a player with that name!") session.msg("There is already a player with that name!")

View file

@ -1,20 +1,42 @@
import sets import sets
from datetime import datetime, timedelta
from django.db import connection from django.db import connection
from django.contrib.auth.models import User from django.contrib.auth.models import User
from apps.objects.models import Object, Attribute from apps.objects.models import Object, Attribute
from apps.config.models import ConfigValue
import defines_global as defines_global import defines_global as defines_global
import gameconf import gameconf
""" """
Common database functions. Common database functions.
""" """
def get_server_config(configname): def num_total_players():
""" """
Returns a server config value. Returns the total number of registered players.
""" """
return ConfigValue.objects.get(conf_key__iexact=configname).conf_value return User.objects.count()
def get_connected_players():
"""
Returns the a QuerySet containing the currently connected players.
"""
return Object.objects.filter(nosave_flags__contains="CONNECTED")
def num_connected_players():
"""
Returns the number of connected players.
"""
return get_connected_players().count()
def num_recently_connected_players(days=7):
"""
Returns a QuerySet containing the player User accounts that have been
connected within the last <days> days.
"""
end_date = datetime.now()
tdelta = timedelta(days)
start_date = end_date - tdelta
return User.objects.filter(last_login__range=(start_date, end_date)).count()
def is_unsavable_flag(flagname): def is_unsavable_flag(flagname):
""" """
@ -211,9 +233,9 @@ def is_dbref(dbstring):
else: else:
return True return True
def get_dbref_from_email(uemail): def get_user_from_email(uemail):
""" """
Returns a player's dbref when given an email address. Returns a player's User object when given an email address.
""" """
return User.objects.filter(email__iexact=uemail) return User.objects.filter(email__iexact=uemail)

View file

@ -1,4 +1,5 @@
import time, sys import time, sys
from datetime import datetime
import cPickle as pickle import cPickle as pickle
from twisted.conch.telnet import StatefulTelnetProtocol from twisted.conch.telnet import StatefulTelnetProtocol
@ -147,11 +148,16 @@ class SessionProtocol(StatefulTelnetProtocol):
session_mgr.disconnect_duplicate_session(self) session_mgr.disconnect_duplicate_session(self)
self.msg("You are now logged in as %s." % (self.name,)) self.msg("You are now logged in as %s." % (self.name,))
pobject.get_location().emit_to_contents("%s has connected." % (pobject.get_name(),), exclude=pobject) pobject.get_location().emit_to_contents("%s has connected." % (pobject.get_name(),), exclude=pobject)
cdat = {"session": self, "uinput":'look', "server": self.factory.server} self.execute_cmd("look")
cmdhandler.handle(cdat)
functions_general.log_infomsg("Login: %s" % (self,)) functions_general.log_infomsg("Login: %s" % (self,))
# Update their account's last login time.
user.last_login = datetime.now()
user.save
pobject.set_attribute("Last", "%s" % (time.strftime("%a %b %d %H:%M:%S %Y", time.localtime()),)) pobject.set_attribute("Last", "%s" % (time.strftime("%a %b %d %H:%M:%S %Y", time.localtime()),))
pobject.set_attribute("Lastsite", "%s" % (self.address[0],)) pobject.set_attribute("Lastsite", "%s" % (self.address[0],))
# Load their channel selection from a pickled attribute.
self.load_user_channels() self.load_user_channels()
def msg(self, message): def msg(self, message):

View file

@ -77,15 +77,12 @@
<div class="rowOfBoxes dividingBorderAbove"> <div class="rowOfBoxes dividingBorderAbove">
<div class="quarter noBorderOnLeft"> <div class="quarter noBorderOnLeft">
<h1>Standards</h1>
<p><span lang="la">Prosimii</span> is 100% compliant with
<acronym title="eXtensible HyperText Markup Language">XHTML</acronym> 1.0 Strict and
uses <acronym title="Cascading Style Sheets">CSS</acronym>.
<span class="doNotPrint">[Validate
<a href="http://validator.w3.org/check/referer">XHTML</a>]</span></p>
<p>Unlike this design&rsquo;s inspiration, no tables have been used to layout elements <h1>Players</h1>
and text.</p> <p>
There are currently <strong>{{players_connected}}</strong> connected,
and a total of <strong>{{players_registered}}</strong> registered. Of these, {{players_recent}} were created this week, and <strong>{{players_connected_recent}}</strong> have connected within the last seven days.
</p>
</div> </div>
<div class="quarter"> <div class="quarter">