mirror of
https://github.com/evennia/evennia.git
synced 2026-03-28 18:47:16 +01:00
Migrate. Added the "view" access restriction (to make objects invisible). Also changed the input of ObjectDB.objects.object_search() to not require a caller as an argument (this makes it consistent with other search methods). All default systems should have updated to the new call, but if you have custom calls, you need to change them to fit the new syntax (this is only important if explicitly use ObjectDB.objects.object_search; if you just use caller.search you should be fine)
This commit is contained in:
parent
28fe2ad3f4
commit
27809694d7
13 changed files with 267 additions and 34 deletions
|
|
@ -11,15 +11,30 @@ class ExitCommand(command.Command):
|
|||
is_exit = True
|
||||
locks = "cmd:all()" # should always be set to this.
|
||||
destination = None
|
||||
obj = None
|
||||
obj = None
|
||||
|
||||
def func(self):
|
||||
"Default exit traverse if no syscommand is defined."
|
||||
|
||||
if self.obj.access(self.caller, 'traverse'):
|
||||
self.caller.move_to(self.destination)
|
||||
# we may traverse the exit.
|
||||
|
||||
old_location = None
|
||||
if hasattr(self.caller, "location"):
|
||||
old_location = self.caller.location
|
||||
|
||||
# call pre/post hooks and move object.
|
||||
self.obj.at_before_traverse(self.caller)
|
||||
self.caller.move_to(self.destination)
|
||||
self.obj.at_after_traverse(self.caller, old_location)
|
||||
|
||||
else:
|
||||
self.caller.msg("You cannot enter.")
|
||||
if self.obj.db.err_traverse:
|
||||
# if exit has a better error message, let's use it.
|
||||
self.caller.msg(self.obj.db.err_traverse)
|
||||
else:
|
||||
# No shorthand error message. Call hook.
|
||||
self.obj.at_fail_traverse(self.caller)
|
||||
|
||||
class ExitHandler(object):
|
||||
"""
|
||||
|
|
|
|||
|
|
@ -165,18 +165,18 @@ class ObjectManager(TypedObjectManager):
|
|||
return eval("self.filter(db_location__id=location.id)%s" % estring)
|
||||
|
||||
@returns_typeclass_list
|
||||
def object_search(self, character, ostring,
|
||||
def object_search(self, ostring, caller=None,
|
||||
global_search=False,
|
||||
attribute_name=None, location=None):
|
||||
"""
|
||||
Search as an object and return results. The result is always an Object.
|
||||
If * is appended (player search, a Character controlled by this Player
|
||||
is looked for. The Character is returned, not the Player. Use player_search
|
||||
to find Player objects.
|
||||
to find Player objects. Always returns a list.
|
||||
|
||||
character: (Object) The object performing the search.
|
||||
ostring: (string) The string to compare names against.
|
||||
Can be a dbref. If name is appended by *, a player is searched for.
|
||||
caller: (Object) The object performing the search.
|
||||
global_search: Search all objects, not just the current location/inventory
|
||||
attribute_name: (string) Which attribute to search in each object.
|
||||
If None, the default 'key' attribute is used.
|
||||
|
|
@ -184,11 +184,8 @@ class ObjectManager(TypedObjectManager):
|
|||
"""
|
||||
#ostring = str(ostring).strip()
|
||||
|
||||
if not ostring or not character:
|
||||
return None
|
||||
|
||||
if not location and hasattr(character, "location"):
|
||||
location = character.location
|
||||
if not ostring:
|
||||
return []
|
||||
|
||||
# Easiest case - dbref matching (always exact)
|
||||
dbref = self.dbref(ostring)
|
||||
|
|
@ -197,14 +194,17 @@ class ObjectManager(TypedObjectManager):
|
|||
if dbref_match:
|
||||
return [dbref_match]
|
||||
|
||||
if not location and caller and hasattr(caller, "location"):
|
||||
location = caller.location
|
||||
|
||||
# Test some common self-references
|
||||
|
||||
if location and ostring == 'here':
|
||||
return [location]
|
||||
if character and ostring in ['me', 'self']:
|
||||
return [character]
|
||||
if character and ostring in ['*me', '*self']:
|
||||
return [character]
|
||||
if caller and ostring in ['me', 'self']:
|
||||
return [caller]
|
||||
if caller and ostring in ['*me', '*self']:
|
||||
return [caller]
|
||||
|
||||
# Test if we are looking for an object controlled by a
|
||||
# specific player
|
||||
|
|
@ -224,8 +224,10 @@ class ObjectManager(TypedObjectManager):
|
|||
or ostring.lower() in [alias.lower() for alias in location.aliases]):
|
||||
return [location]
|
||||
# otherwise, setup the locations to search in
|
||||
search_locations = [character, location]
|
||||
|
||||
search_locations = [location]
|
||||
if caller:
|
||||
search_locations.append(caller)
|
||||
|
||||
def local_and_global_search(ostring, exact=False):
|
||||
"Helper method for searching objects"
|
||||
matches = []
|
||||
|
|
|
|||
119
src/objects/migrations/0006_add_view_lock.py
Normal file
119
src/objects/migrations/0006_add_view_lock.py
Normal file
|
|
@ -0,0 +1,119 @@
|
|||
# encoding: utf-8
|
||||
import datetime
|
||||
from south.db import db
|
||||
from south.v2 import DataMigration
|
||||
from django.db import models
|
||||
|
||||
class Migration(DataMigration):
|
||||
|
||||
def forwards(self, orm):
|
||||
"Write your forwards methods here."
|
||||
|
||||
lockstring1 = 'control:id(1);get:all();edit:perm(Wizards);view:all();examine:perm(Builders);call:true();puppet:id(#4) or perm(Immortals) or pperm(Immortals);delete:id(1) or perm(Wizards)'
|
||||
lockstring2 = 'control:id(#3) or perm(Immortals);get:perm(Wizards);edit:perm(Wizards);view:all();examine:perm(Builders);call:false();puppet:id(%i) or pid(%i) or perm(Immortals) or pperm(Immortals);delete:perm(Wizards)'
|
||||
|
||||
try:
|
||||
for obj in orm.ObjectDB.objects.all().exclude(db_player__isnull=False):
|
||||
obj.db_lock_storage = lockstring1
|
||||
obj.save()
|
||||
for obj in orm.ObjectDB.objects.filter(db_player__isnull=False):
|
||||
obj.db_lock_storage = lockstring2 % (obj.id, obj.db_player.id)
|
||||
obj.save()
|
||||
|
||||
except utils.DatabaseError:
|
||||
# running from scatch. In this case we just ignore this.
|
||||
pass
|
||||
|
||||
def backwards(self, orm):
|
||||
"Write your backwards methods here."
|
||||
raise RuntimeError("You cannot reverse this migration.")
|
||||
|
||||
models = {
|
||||
'auth.group': {
|
||||
'Meta': {'object_name': 'Group'},
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
|
||||
'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '80'}),
|
||||
'permissions': ('django.db.models.fields.related.ManyToManyField', [], {'to': "orm['auth.Permission']", 'symmetrical': 'False', 'blank': 'True'})
|
||||
},
|
||||
'auth.permission': {
|
||||
'Meta': {'ordering': "('content_type__app_label', 'content_type__model', 'codename')", 'unique_together': "(('content_type', 'codename'),)", 'object_name': 'Permission'},
|
||||
'codename': ('django.db.models.fields.CharField', [], {'max_length': '100'}),
|
||||
'content_type': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['contenttypes.ContentType']"}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
|
||||
'name': ('django.db.models.fields.CharField', [], {'max_length': '50'})
|
||||
},
|
||||
'auth.user': {
|
||||
'Meta': {'object_name': 'User'},
|
||||
'date_joined': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}),
|
||||
'email': ('django.db.models.fields.EmailField', [], {'max_length': '75', 'blank': 'True'}),
|
||||
'first_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}),
|
||||
'groups': ('django.db.models.fields.related.ManyToManyField', [], {'to': "orm['auth.Group']", 'symmetrical': 'False', 'blank': 'True'}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
|
||||
'is_active': ('django.db.models.fields.BooleanField', [], {'default': 'True'}),
|
||||
'is_staff': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
|
||||
'is_superuser': ('django.db.models.fields.BooleanField', [], {'default': 'False'}),
|
||||
'last_login': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}),
|
||||
'last_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}),
|
||||
'password': ('django.db.models.fields.CharField', [], {'max_length': '128'}),
|
||||
'user_permissions': ('django.db.models.fields.related.ManyToManyField', [], {'to': "orm['auth.Permission']", 'symmetrical': 'False', 'blank': 'True'}),
|
||||
'username': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '30'})
|
||||
},
|
||||
'contenttypes.contenttype': {
|
||||
'Meta': {'ordering': "('name',)", 'unique_together': "(('app_label', 'model'),)", 'object_name': 'ContentType', 'db_table': "'django_content_type'"},
|
||||
'app_label': ('django.db.models.fields.CharField', [], {'max_length': '100'}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
|
||||
'model': ('django.db.models.fields.CharField', [], {'max_length': '100'}),
|
||||
'name': ('django.db.models.fields.CharField', [], {'max_length': '100'})
|
||||
},
|
||||
'objects.alias': {
|
||||
'Meta': {'object_name': 'Alias'},
|
||||
'db_key': ('django.db.models.fields.CharField', [], {'max_length': '255'}),
|
||||
'db_obj': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['objects.ObjectDB']"}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'})
|
||||
},
|
||||
'objects.objattribute': {
|
||||
'Meta': {'object_name': 'ObjAttribute'},
|
||||
'db_date_created': ('django.db.models.fields.DateTimeField', [], {'auto_now_add': 'True', 'blank': 'True'}),
|
||||
'db_key': ('django.db.models.fields.CharField', [], {'max_length': '255'}),
|
||||
'db_lock_storage': ('django.db.models.fields.TextField', [], {'blank': 'True'}),
|
||||
'db_obj': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['objects.ObjectDB']"}),
|
||||
'db_value': ('django.db.models.fields.TextField', [], {'null': 'True', 'blank': 'True'}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'})
|
||||
},
|
||||
'objects.objectdb': {
|
||||
'Meta': {'object_name': 'ObjectDB'},
|
||||
'db_cmdset_storage': ('django.db.models.fields.TextField', [], {'null': 'True'}),
|
||||
'db_date_created': ('django.db.models.fields.DateTimeField', [], {'auto_now_add': 'True', 'blank': 'True'}),
|
||||
'db_destination': ('django.db.models.fields.related.ForeignKey', [], {'blank': 'True', 'related_name': "'destinations_set'", 'null': 'True', 'to': "orm['objects.ObjectDB']"}),
|
||||
'db_home': ('django.db.models.fields.related.ForeignKey', [], {'blank': 'True', 'related_name': "'homes_set'", 'null': 'True', 'to': "orm['objects.ObjectDB']"}),
|
||||
'db_key': ('django.db.models.fields.CharField', [], {'max_length': '255'}),
|
||||
'db_location': ('django.db.models.fields.related.ForeignKey', [], {'blank': 'True', 'related_name': "'locations_set'", 'null': 'True', 'to': "orm['objects.ObjectDB']"}),
|
||||
'db_lock_storage': ('django.db.models.fields.TextField', [], {'blank': 'True'}),
|
||||
'db_permissions': ('django.db.models.fields.CharField', [], {'max_length': '512', 'blank': 'True'}),
|
||||
'db_player': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['players.PlayerDB']", 'null': 'True', 'blank': 'True'}),
|
||||
'db_typeclass_path': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True'}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'})
|
||||
},
|
||||
'objects.objectnick': {
|
||||
'Meta': {'unique_together': "(('db_nick', 'db_type', 'db_obj'),)", 'object_name': 'ObjectNick'},
|
||||
'db_nick': ('django.db.models.fields.CharField', [], {'max_length': '255', 'db_index': 'True'}),
|
||||
'db_obj': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['objects.ObjectDB']"}),
|
||||
'db_real': ('django.db.models.fields.TextField', [], {}),
|
||||
'db_type': ('django.db.models.fields.CharField', [], {'default': "'inputline'", 'max_length': '16', 'null': 'True', 'blank': 'True'}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'})
|
||||
},
|
||||
'players.playerdb': {
|
||||
'Meta': {'object_name': 'PlayerDB'},
|
||||
'db_cmdset_storage': ('django.db.models.fields.TextField', [], {'null': 'True'}),
|
||||
'db_date_created': ('django.db.models.fields.DateTimeField', [], {'auto_now_add': 'True', 'blank': 'True'}),
|
||||
'db_key': ('django.db.models.fields.CharField', [], {'max_length': '255'}),
|
||||
'db_lock_storage': ('django.db.models.fields.TextField', [], {'blank': 'True'}),
|
||||
'db_obj': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['objects.ObjectDB']", 'null': 'True'}),
|
||||
'db_permissions': ('django.db.models.fields.CharField', [], {'max_length': '512', 'blank': 'True'}),
|
||||
'db_typeclass_path': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True'}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
|
||||
'user': ('django.db.models.fields.related.ForeignKey', [], {'to': "orm['auth.User']", 'unique': 'True'})
|
||||
}
|
||||
}
|
||||
|
||||
complete_apps = ['objects']
|
||||
|
|
@ -527,7 +527,7 @@ class ObjectDB(TypedObject):
|
|||
else:
|
||||
results = PlayerDB.objects.player_search(ostring.lstrip('*'))
|
||||
else:
|
||||
results = ObjectDB.objects.object_search(self, ostring,
|
||||
results = ObjectDB.objects.object_search(ostring, caller=self,
|
||||
global_search=global_search,
|
||||
attribute_name=attribute_name,
|
||||
location=location)
|
||||
|
|
@ -658,8 +658,8 @@ class ObjectDB(TypedObject):
|
|||
except Exception:
|
||||
emit_to_obj.msg(errtxt % "at_announce_move()" )
|
||||
logger.log_trace()
|
||||
return False
|
||||
|
||||
return False
|
||||
|
||||
# Perform move
|
||||
try:
|
||||
self.location = destination
|
||||
|
|
|
|||
|
|
@ -62,6 +62,7 @@ class Object(TypeClass):
|
|||
|
||||
self.locks.add("control:id(%s) or perm(Immortals)" % dbref) # edit locks/permissions, delete
|
||||
self.locks.add("examine:perm(Builders)") # examine properties
|
||||
self.locks.add("view:all()") # look at object (visibility)
|
||||
self.locks.add("edit:perm(Wizards)") # edit properties/attributes
|
||||
self.locks.add("delete:perm(Wizards)") # delete object
|
||||
self.locks.add("get:all()") # pick up object
|
||||
|
|
@ -185,7 +186,33 @@ class Object(TypeClass):
|
|||
source_location - where moved_object came from.
|
||||
"""
|
||||
pass
|
||||
|
||||
|
||||
def at_before_traverse(self, traversing_object):
|
||||
"""
|
||||
Called just before an object uses this object to
|
||||
traverse to another object (i.e. this object is a type of Exit)
|
||||
|
||||
The target location should normally be available as self.destination.
|
||||
"""
|
||||
pass
|
||||
|
||||
def at_after_traverse(self, traversing_object, source_location):
|
||||
"""
|
||||
Called just after an object successfully used this object to
|
||||
traverse to another object (i.e. this object is a type of Exit)
|
||||
|
||||
The target location should normally be available as self.destination.
|
||||
"""
|
||||
pass
|
||||
|
||||
def at_failed_traverse(self, traversing_object):
|
||||
"""
|
||||
This is called if an object fails to traverse this object for some
|
||||
reason. It will not be called if the attribute err_traverse is defined,
|
||||
that attribute will then be echoed back instead.
|
||||
"""
|
||||
pass
|
||||
|
||||
# hooks called by the default cmdset.
|
||||
|
||||
|
|
@ -414,3 +441,12 @@ class Exit(Object):
|
|||
"""
|
||||
EXITHANDLER.clear(self.dbobj)
|
||||
return True
|
||||
|
||||
def at_failed_traverse(self, traversing_object):
|
||||
"""
|
||||
This is called if an object fails to traverse this object for some
|
||||
reason. It will not be called if the attribute "err_traverse" is defined,
|
||||
that attribute will then be echoed back instead as a convenient shortcut.
|
||||
"""
|
||||
traversing_object.msg("You cannot enter %s." % self.key)
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue