Created first iteration of "Recent Fits" view, in which a nav button is interacted with to show a list of the 100 most recently modified fits. Ship Broswer is littered with ToggleRecentShips() to reset the icon when not in "recent" mode. This should probably be fixed at some point.

Removed the FIT_CHANGED binding from FitItem - this was causing very odd issues when the object was destroyed (navigating to another "stage") such as the Fit Changed event for that fit no longer firing (or at least seemingly so)

To fix this, simply look at the active fit during FitItem.Refresh()

Also creates a new query to get a list of items from the DB, although it's not used (was gonna use it, decided against it, but didn't want to delete the code - could prove handy later)
This commit is contained in:
blitzmann
2017-04-23 20:20:04 -04:00
parent bb73065b43
commit 32f417ce5a
8 changed files with 149 additions and 36 deletions

View File

@@ -27,12 +27,11 @@ from eos.db.gamedata.group import groups_table
from eos.db.util import processEager, processWhere
from eos.gamedata import AlphaClone, Attribute, Category, Group, Item, MarketGroup, MetaGroup, AttributeInfo, MetaData
cache = {}
configVal = getattr(eos.config, "gamedataCache", None)
if configVal is True:
def cachedQuery(amount, *keywords):
def deco(function):
cache = {}
def checkAndReturn(*args, **kwargs):
useCache = kwargs.pop("useCache", True)
cacheKey = []
@@ -98,6 +97,34 @@ def getItem(lookfor, eager=None):
return item
@cachedQuery(1, "lookfor")
def getItems(lookfor, eager=None):
"""
Gets a list of items. Does a bit of cache hackery to get working properly -- cache
is usually based on function calls with the parameters, needed to extract data directly.
Works well enough. Not currently used, but it's here for possible future inclusion
"""
toGet = []
results = []
for id in lookfor:
if (id, None) in cache:
results.append(cache.get((id, None)))
else:
toGet.append(id)
if len(toGet) > 0:
# Get items that aren't currently cached, and store them in the cache
items = gamedata_session.query(Item).filter(Item.ID.in_(toGet)).all()
for item in items:
cache[(item.ID, None)] = item
results += items
# sort the results based on the original indexing
results.sort(key=lambda x: lookfor.index(x.ID))
return results
@cachedQuery(1, "lookfor")
def getAlphaClone(lookfor, eager=None):
if isinstance(lookfor, int):

View File

@@ -18,7 +18,6 @@
# ===============================================================================
import datetime
from sqlalchemy import inspect
from sqlalchemy.ext.associationproxy import association_proxy
from sqlalchemy.orm.collections import attribute_mapped_collection
from sqlalchemy.sql import and_
@@ -244,7 +243,7 @@ mapper(ProjectedFit, projectedFits_table,
properties={
"_ProjectedFit__amount": projectedFits_table.c.amount,
}
)
)
mapper(CommandFit, commandFits_table)
@@ -253,18 +252,22 @@ def rel_listener(target, value, initiator):
if not target or (isinstance(value, Module) and value.isEmpty):
return
print "{} has has has a relationship changes :(".format(target)
print "{} has had a relationship change :D".format(target)
target.modified = datetime.datetime.now()
def load_listener(target, context):
# We only want to se these events when the fit is first loaded (otherwise events will fire during the initial
# We only want to see these events when the fit is first loaded (otherwise events will fire during the initial
# population of data). This sets listeners for all the relationships on fits. This allows us to update the fit's
# modified date whenever something is added/removed from fit
# See http://docs.sqlalchemy.org/en/rel_1_0/orm/events.html#sqlalchemy.orm.events.InstanceEvents.load
for rel in inspect(es_Fit).relationships:
listen(rel, 'append', rel_listener)
listen(rel, 'remove', rel_listener)
# todo: when we can, move over to `inspect(es_Fit).relationships` (when mac binaries are updated)
manager = getattr(es_Fit, "_sa_class_manager", None)
if manager:
for rel in manager.mapper.relationships:
listen(rel, 'append', rel_listener)
listen(rel, 'remove', rel_listener)
listen(Module, 'load', load_listener)

View File

@@ -17,7 +17,6 @@
# along with eos. If not, see <http://www.gnu.org/licenses/>.
# ===============================================================================
from sqlalchemy import inspect
from sqlalchemy import Table, Column, Integer, ForeignKey, CheckConstraint, Boolean, DateTime, select
from sqlalchemy.orm import relation, mapper
from sqlalchemy.event import listen
@@ -55,16 +54,20 @@ def update_fit_modified(target, value, oldvalue, initiator):
target.owner.modified = datetime.datetime.now()
def my_load_listener(target, context):
def load_listener(target, context):
# We only want to se these events when the module is first loaded (otherwise events will fire during the initial
# population of data). This runs through all columns and sets up "set" events on each column. We do it with each
# column because the alternative would be to do a before/after_update for the Mapper itself, however we're only
# allowed to change the local attributes during those events as that's inter-flush.
# See http://docs.sqlalchemy.org/en/rel_1_0/orm/session_events.html#mapper-level-events
for col in inspect(Module).column_attrs:
listen(col, 'set', update_fit_modified)
# @todo replace with `inspect(Module).column_attrs` when mac binaries are updated
manager = getattr(Module, "_sa_class_manager", None)
if manager:
for col in manager.mapper.column_attrs:
listen(col, 'set', update_fit_modified)
listen(Module, 'load', my_load_listener)
listen(Module, 'load', load_listener)

View File

@@ -18,6 +18,7 @@
# ===============================================================================
from sqlalchemy.sql import and_
from sqlalchemy import desc, select
from eos.db import saveddata_session, sd_lock
from eos.db.saveddata.fit import projectedFits_table
@@ -242,6 +243,22 @@ def getFitsWithShip(shipID, ownerID=None, where=None, eager=None):
return fits
def getRecentFits(ownerID=None, where=None, eager=None):
eager = processEager(eager)
with sd_lock:
q = select((
Fit.ID,
Fit.shipID,
Fit.name,
Fit.modified,
Fit.created,
Fit.timestamp
)).order_by(desc(Fit.modified), desc(Fit.timestamp)).limit(50)
fits = eos.db.saveddata_session.execute(q).fetchall()
return fits
def getFitsWithModules(typeIDs, eager=None):
"""
Get all the fits that have typeIDs fitted to them