Merge pull request #3197 from volundmush/fix_global_scripts

Alter Global Scripts handling
This commit is contained in:
Griatch 2023-10-31 20:36:33 +01:00 committed by GitHub
commit 4986888db9
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 48 additions and 48 deletions

View file

@ -106,6 +106,9 @@ MONITOR_HANDLER = None
GLOBAL_SCRIPTS = None GLOBAL_SCRIPTS = None
OPTION_CLASSES = None OPTION_CLASSES = None
# variables
PORTAL_MODE = False
def _create_version(): def _create_version():
""" """
@ -160,6 +163,8 @@ def _init(portal_mode=False):
global EvMenu, EvTable, EvForm, EvMore, EvEditor global EvMenu, EvTable, EvForm, EvMore, EvEditor
global ANSIString, FuncParser global ANSIString, FuncParser
global AttributeProperty, TagProperty, TagCategoryProperty global AttributeProperty, TagProperty, TagCategoryProperty
global PORTAL_MODE
PORTAL_MODE = portal_mode
# Parent typeclasses # Parent typeclasses
# utilities # utilities
@ -187,6 +192,7 @@ def _init(portal_mode=False):
from .utils import ansi, gametime, logger from .utils import ansi, gametime, logger
from .utils.ansi import ANSIString from .utils.ansi import ANSIString
if not PORTAL_MODE:
# containers # containers
from .utils.containers import GLOBAL_SCRIPTS, OPTION_CLASSES from .utils.containers import GLOBAL_SCRIPTS, OPTION_CLASSES
@ -218,7 +224,7 @@ def _init(portal_mode=False):
) )
from .utils.utils import class_from_module from .utils.utils import class_from_module
if portal_mode: if PORTAL_MODE:
# Set up the PortalSessionHandler # Set up the PortalSessionHandler
from evennia.server.portal import portalsessionhandler from evennia.server.portal import portalsessionhandler
@ -227,6 +233,7 @@ def _init(portal_mode=False):
else: else:
# Create the ServerSesssionHandler # Create the ServerSesssionHandler
from evennia.server import sessionhandler from evennia.server import sessionhandler
sess_handler_class = class_from_module(settings.SERVER_SESSION_HANDLER_CLASS) sess_handler_class = class_from_module(settings.SERVER_SESSION_HANDLER_CLASS)
sessionhandler.SESSIONS = sess_handler_class() sessionhandler.SESSIONS = sess_handler_class()
sessionhandler.SESSION_HANDLER = sessionhandler.SESSIONS sessionhandler.SESSION_HANDLER = sessionhandler.SESSIONS
@ -375,11 +382,6 @@ def _init(portal_mode=False):
del SystemCmds del SystemCmds
del _EvContainer del _EvContainer
# delayed starts - important so as to not back-access evennia before it has
# finished initializing
if not portal_mode:
GLOBAL_SCRIPTS.start()
def set_trace(term_size=(140, 80), debugger="auto"): def set_trace(term_size=(140, 80), debugger="auto"):
""" """

View file

@ -453,6 +453,10 @@ class Evennia:
# always call this regardless of start type # always call this regardless of start type
self.at_server_start() self.at_server_start()
# Moved here from evennia._init() to ensure it only runs after
# setup is complete and only in server mode.
evennia.GLOBAL_SCRIPTS.start()
@defer.inlineCallbacks @defer.inlineCallbacks
def shutdown(self, mode="reload", _reactor_stopping=False): def shutdown(self, mode="reload", _reactor_stopping=False):
""" """

View file

@ -114,26 +114,13 @@ class GlobalScriptContainer(Container):
initialized before Scripts are actually initialized. initialized before Scripts are actually initialized.
""" """
self.typeclass_storage = None self.typeclass_storage = dict()
self.loaded_data = { self.loaded_data = {
key: {} if data is None else data for key, data in settings.GLOBAL_SCRIPTS.items() key: {} if data is None else data for key, data in settings.GLOBAL_SCRIPTS.items()
} }
self.loaded = False
def _get_scripts(self, key=None, default=None):
global SCRIPTDB
if not SCRIPTDB:
from evennia.scripts.models import ScriptDB as SCRIPTDB
if key:
try:
return SCRIPTDB.objects.get(db_key__exact=key, db_obj__isnull=True)
except SCRIPTDB.DoesNotExist:
return default
else:
return SCRIPTDB.objects.filter(db_obj__isnull=True)
def _load_script(self, key): def _load_script(self, key):
self.load_data()
typeclass = self.typeclass_storage[key] typeclass = self.typeclass_storage[key]
script = typeclass.objects.filter( script = typeclass.objects.filter(
db_key=key, db_account__isnull=True, db_obj__isnull=True db_key=key, db_account__isnull=True, db_obj__isnull=True
@ -168,7 +155,7 @@ class GlobalScriptContainer(Container):
return None return None
# store a hash representation of the setup # store a hash representation of the setup
script.attributes.add("_global_script_settings", compare_hash, category="settings_hash") script.attributes.add("global_script_settings", compare_hash, category="settings_hash")
return script return script
@ -182,14 +169,18 @@ class GlobalScriptContainer(Container):
""" """
# populate self.typeclass_storage # populate self.typeclass_storage
if not self.loaded:
self.load_data() self.load_data()
# make sure settings-defined scripts are loaded # make sure settings-defined scripts are loaded
scripts_to_run = []
for key in self.loaded_data: for key in self.loaded_data:
self._load_script(key) script = self._load_script(key)
if script:
scripts_to_run.append(script)
# start all global scripts # start all global scripts
try: try:
for script in self._get_scripts(): for script in scripts_to_run:
script.start() script.start()
except (OperationalError, ProgrammingError): except (OperationalError, ProgrammingError):
# this can happen if db is not loaded yet (such as when building docs) # this can happen if db is not loaded yet (such as when building docs)
@ -201,13 +192,15 @@ class GlobalScriptContainer(Container):
initialized. initialized.
""" """
if self.typeclass_storage is None: if self.loaded:
self.typeclass_storage = {} return
if not self.typeclass_storage:
for key, data in list(self.loaded_data.items()): for key, data in list(self.loaded_data.items()):
typeclass = data.get("typeclass", settings.BASE_SCRIPT_TYPECLASS) typeclass = data.get("typeclass", settings.BASE_SCRIPT_TYPECLASS)
self.typeclass_storage[key] = class_from_module( self.typeclass_storage[key] = class_from_module(
typeclass, fallback=settings.BASE_SCRIPT_TYPECLASS typeclass, fallback=settings.BASE_SCRIPT_TYPECLASS
) )
self.loaded = True
def get(self, key, default=None): def get(self, key, default=None):
""" """
@ -223,8 +216,9 @@ class GlobalScriptContainer(Container):
Returns: Returns:
any (any): The data loaded on this container. any (any): The data loaded on this container.
""" """
res = self._get_scripts(key) if not self.loaded:
if not res: self.load_data()
out_value = default
if key in self.loaded_data: if key in self.loaded_data:
if key not in self.typeclass_storage: if key not in self.typeclass_storage:
# this means we are trying to load in a loop # this means we are trying to load in a loop
@ -234,9 +228,11 @@ class GlobalScriptContainer(Container):
"module the script is defined in." "module the script is defined in."
) )
# recreate if we have the info # recreate if we have the info
return self._load_script(key) or default script_found = self._load_script(key)
return default if script_found:
return res out_value = script_found
return out_value
def all(self): def all(self):
""" """
@ -247,11 +243,9 @@ class GlobalScriptContainer(Container):
scripts (list): All global script objects stored on the container. scripts (list): All global script objects stored on the container.
""" """
self.typeclass_storage = None if not self.loaded:
self.load_data() self.load_data()
for key in self.loaded_data: return self.scripts.values()
self._load_script(key)
return self._get_scripts(None)
# Create all singletons # Create all singletons