Просмотр исходного кода

Add individual values to campaign item board.

master
Ben Kurtovic 8 лет назад
Родитель
Сommit
bb51e2ab1e
7 измененных файлов: 57 добавлений и 33 удалений
  1. +10
    -2
      calefaction/format.py
  2. +12
    -10
      calefaction/modules/campaigns/database.py
  3. +15
    -13
      calefaction/modules/campaigns/update.py
  4. +1
    -0
      config/modules/campaigns.yml.sample
  5. +1
    -0
      data/schema_campaigns.sql
  6. +5
    -2
      static/main.css
  7. +13
    -6
      templates/campaigns/renderers.mako

+ 10
- 2
calefaction/format.py Просмотреть файл

@@ -2,8 +2,16 @@ from datetime import datetime, timedelta

import humanize

__all__ = ["format_isk", "format_isk_compact", "format_utctime",
"format_utctime_compact", "format_security", "get_security_class"]
__all__ = [
"format_quantity", "format_isk", "format_isk_compact", "format_utctime",
"format_utctime_compact", "format_security", "get_security_class"
]

def format_quantity(value):
"""Nicely format an integer quantity."""
if value < 10**6:
return "{:,}".format(value)
return humanize.intword(value, "%.2f")

def format_isk(value):
"""Nicely format an ISK value."""


+ 12
- 10
calefaction/modules/campaigns/database.py Просмотреть файл

@@ -187,7 +187,7 @@ class CampaignDB:

The data should be a multi-layered dictionary. It maps operation names
to a dict that maps character IDs to a dict that maps type IDs to
integer counts.
tuples of integer counts and float values.
"""
with self._conn as conn:
cur = conn.execute("BEGIN TRANSACTION")
@@ -195,29 +195,31 @@ class CampaignDB:
cur.execute(query, (campaign,))

query = """INSERT INTO oper_item (
oi_campaign, oi_operation, oi_character, oi_type, oi_count)
VALUES (?, ?, ?, ?, ?)"""
oi_campaign, oi_operation, oi_character, oi_type, oi_count,
oi_value)
VALUES (?, ?, ?, ?, ?, ?)"""
cur.executemany(query, [
(campaign, operation, int(char_id), int(type_id), int(count))
(campaign, operation, int(char_id), int(type_id), int(count),
float(value))
for operation, chars in data.items()
for char_id, types in chars.items()
for type_id, count in types.items()])
for type_id, (count, value) in types.items()])

def get_associated_items(self, campaign, operation, limit=5, offset=0):
"""Return a list of items associated with a campaign/operation.

Items are returned as 2-tuples of (item_type, item_count), most recent
first, up to a limit. Use -1 for no limit.
Items are returned as 2-tuples of (item_type, item_count), most
valuable first, up to a limit. Use -1 for no limit.
"""
if not isinstance(limit, int):
raise ValueError(limit)
if not isinstance(offset, int):
raise ValueError(offset)

query = """SELECT oi_type, SUM(oi_count) as total_count
query = """SELECT oi_type, SUM(oi_count), TOTAL(oi_value) as total_val
FROM oper_item
WHERE oi_campaign = ? AND oi_operation = ?
GROUP BY oi_type ORDER BY total_count DESC LIMIT {} OFFSET {}"""
GROUP BY oi_type ORDER BY total_val DESC LIMIT {} OFFSET {}"""
qform = query.format(limit, offset)
res = self._conn.execute(qform, (campaign, operation)).fetchall()
return [(type_id, count or 0) for type_id, count in res]
return [(type_id, count or 0, value) for type_id, count, value in res]

+ 15
- 13
calefaction/modules/campaigns/update.py Просмотреть файл

@@ -81,23 +81,22 @@ def _update_killboard_operations(cname, opnames, min_kill_id):
secondary = None
_save_operation(cname, opname, primary, secondary, key=max_kill_id)

def _get_prices():
"""Return a dict mapping type IDs to ISK prices."""
pricelist = g.eve.esi().v1.markets.prices.get()
return {entry["type_id"]: entry["average_price"]
for entry in pricelist if "average_price" in entry}

def _save_collection_overview(cname, opnames, data):
"""Save collection overview data to the database."""
operations = config["campaigns"][cname]["operations"]
if any(operations[opname].get("isk", True) for opname in opnames):
pricelist = g.eve.esi().v1.markets.prices.get()
prices = {entry["type_id"]: entry["average_price"]
for entry in pricelist if "average_price" in entry}
else:
prices = {}

for opname in opnames:
primary = sum(sum(d.values()) for d in data[opname].values())
primary = sum(count for d in data[opname].values()
for (count, _) in d.values())
show_isk = operations[opname].get("isk", True)
if show_isk:
secondary = sum(prices.get(typeid, 0.0) * count
for d in data[opname].values()
for typeid, count in d.items())
secondary = sum(value for d in data[opname].values()
for (_, value) in d.values())
else:
secondary = None
_save_operation(cname, opname, primary, secondary)
@@ -110,6 +109,7 @@ def _update_collection_operations(cname, opnames):
qualif = operations[opname]["qualifiers"]
filters.append((_build_filter(qualif, "asset"), opname))

prices = _get_prices()
data = {opname: {} for opname in opnames}

for char_id, token in g.auth.get_valid_characters():
@@ -131,11 +131,13 @@ def _update_collection_operations(cname, opnames):
if filt(asset):
typeid = asset["type_id"]
count = 1 if asset["is_singleton"] else asset["quantity"]
value = prices.get(typeid, 0.0)
char = data[opname][char_id]
if typeid in char:
char[typeid] += count
char[typeid][0] += count
char[typeid][1] += count * value
else:
char[typeid] = count
char[typeid] = [count, count * value]

g.campaign_db.update_items(cname, data)
_save_collection_overview(cname, opnames, data)


+ 1
- 0
config/modules/campaigns.yml.sample Просмотреть файл

@@ -47,6 +47,7 @@ campaigns:
isk: false
# Report as "10 units" / "1 unit" of Tritanium
unit: unit|units
# Python function to filter items:
qualifiers: |-
type = g.eve.universe.type(asset["type_id"])
return type.name == "Tritanium"


+ 1
- 0
data/schema_campaigns.sql Просмотреть файл

@@ -60,6 +60,7 @@ CREATE TABLE oper_item (
oi_character INTEGER,
oi_type INTEGER,
oi_count INTEGER,
oi_value REAL,
UNIQUE (oi_campaign, oi_operation, oi_character, oi_type)
);



+ 5
- 2
static/main.css Просмотреть файл

@@ -519,13 +519,16 @@ h2 .disabled-info {
border-bottom: none;
}

.operation .itemboard .num {
.operation .itemboard td:last-child {
padding-left: 0.5em;
text-align: right;
}

.operation .itemboard .count {
font-weight: bold;
}

.operation .itemboard .num::before {
.operation .itemboard .count::before {
content: "×";
font-weight: normal;
color: #AAA;


+ 13
- 6
templates/campaigns/renderers.mako Просмотреть файл

@@ -1,7 +1,7 @@
<%!
from calefaction.format import (
format_isk_compact, format_utctime_compact, format_security,
get_security_class)
format_quantity, format_isk_compact, format_utctime_compact,
format_security, get_security_class)
%>
<%def name="_killboard_kill(kill)">
<%
@@ -56,13 +56,20 @@
</%def>
<%def name="_itemboard_item(item)">
<%
type_id, count = item
type_id, count, value = item
type = g.eve.universe.type(type_id)
%>
<tr>
<td class="icon"><img title="${type.name | h}" alt="" src="${g.eve.image.inventory(type_id, 64)}"/></td>
<td><a href="https://eve-central.com/home/quicklook.html?typeid=${type_id | u}">${type.name | h}</a></td>
<td class="num">${count | h}</td>
<td class="icon">
<img title="${type.name | h}" alt="" src="${g.eve.image.inventory(type_id, 64)}"/>
</td>
<td>
<a href="https://eve-central.com/home/quicklook.html?typeid=${type_id | u}">${type.name | h}</a>
</td>
<td>
<span class="count">${format_quantity(count) | h}</span><br/>
<abbr class="price" title="${"{:,.2f}".format(value)} ISK">${format_isk_compact(value) | h}</abbr>
</td>
</tr>
</%def>
<%def name="_killboard_recent(summary)">


Загрузка…
Отмена
Сохранить