Add exceptions to item triggers

This commit is contained in:
Tim Van Baak 2020-08-11 21:56:38 -07:00
parent 364480c08d
commit 814de5f094
3 changed files with 56 additions and 8 deletions

View File

@ -128,6 +128,14 @@ def new_item(source_name, item):
return WritethroughDict.create(item_path, item) return WritethroughDict.create(item_path, item)
def delete_item(source_name, item_id):
"""
Delete an item.
"""
item_path = os.path.join(DUNGEON_PATH, source_name, f'{item_id}.item')
os.remove(item_path)
def load_items(source_name): def load_items(source_name):
""" """
Returns a map of ids to items and a list of unreadable files. Returns a map of ids to items and a list of unreadable files.

View File

@ -135,7 +135,14 @@ def update_source(source_name, source):
item_source = item.get('source', source_name) item_source = item.get('source', source_name)
created_item = loader.new_item(item_source, item) created_item = loader.new_item(item_source, item)
if has_create_handler: if has_create_handler:
# Because some sources do not return items more than once,
# exceptions in the on-create handler must be squashed.
try:
source.on_create(state, created_item) source.on_create(state, created_item)
except:
error.as_item(
f'Exception in {source_name}.on_create',
traceback.format_exc())
# Update the other items using the fetched items' values. # Update the other items using the fetched items' values.
for new_item in updated_items: for new_item in updated_items:
@ -177,14 +184,16 @@ def update_source(source_name, source):
remove = True remove = True
# Items to be removed are deleted # Items to be removed are deleted
if remove: if remove:
if has_delete_handler:
source.on_delete(state, item)
del_count += 1
file_path = os.path.join(DUNGEON_PATH, item['source'], item['id'] + ".item")
try: try:
os.remove(file_path) if has_delete_handler:
# Run the delete handler so exceptions prevent deletions
source.on_delete(state, item)
loader.delete_item(source_name, item['id'])
del_count += 1
except: except:
error.as_item("Failed to delete {}".format(file_path)) error.as_item(
f'Failed to delete {source_name}/{item["id"]}',
traceback.format_exc())
# Note update timestamp in state # Note update timestamp in state
state['last_updated'] = timestamp.now() state['last_updated'] = timestamp.now()
@ -210,4 +219,6 @@ def item_callback(source_name, itemid):
item.flush() item.flush()
state.flush() state.flush()
except Exception: except Exception:
error.as_item(f"Error executing callback for {source_name}/{itemid}", traceback.format_exc()) error.as_item(
f"Error executing callback for {source_name}/{itemid}",
traceback.format_exc())

View File

@ -0,0 +1,29 @@
"""
Demonstrates the behavior of exceptions in create/delete triggers.
To allow for deletions, it alternates returning a single item and
returning nothing.
"""
# Standard library imports
from datetime import datetime
import json
import random
def fetch_new(state):
if state.get('return_item'):
state['return_item'] = False
return [{
'source': 'deletetriggerexdemo',
'id': 'deletetriggerexdemoitem',
'title': 'Delete trigger exception demo'
}]
else:
state['return_item'] = True
return []
def on_create(state, item):
raise Exception('on_create')
def on_delete(state, item):
raise Exception('on_delete')