Skip to content
This repository has been archived by the owner on Dec 24, 2023. It is now read-only.

Commit

Permalink
Move apps stats from postgresql view to spark job
Browse files Browse the repository at this point in the history
  • Loading branch information
Soniclev committed Jul 28, 2023
1 parent 5f2ab9d commit 5d1a76c
Show file tree
Hide file tree
Showing 20 changed files with 427 additions and 348 deletions.
26 changes: 26 additions & 0 deletions steam_trade_bot/api/models/market_item.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
from pydantic import BaseModel

from steam_trade_bot.domain.entities.market import EntireMarketDailyStats
from steam_trade_bot.domain.entities.game import Game
from steam_trade_bot.type import CurrencyValue


class MarketItemSellHistoryResponse(BaseModel):
Expand All @@ -24,3 +26,27 @@ class EntireMarketStatsResponse(BaseModel):
total_volume_steam_fee: float
total_quantity: int
items: list[EntireMarketDailyStats]


class MarketItemResponse(BaseModel):
app_id: int
market_hash_name: str
market_fee: str | None
market_marketable_restriction: int | None
market_tradable_restriction: int | None
commodity: bool

def is_tradable(self) -> bool:
return self.market_tradable_restriction != -1 # -1 means not tradable at all


class MarketItemsListResponse(BaseModel):
count: int
offset: int
items: list[MarketItemResponse]


class GamesListResponse(BaseModel):
count: int
offset: int
items: list[Game]
10 changes: 10 additions & 0 deletions steam_trade_bot/api/routes/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
from fastapi import APIRouter

from .entire_market import router as entire_market_router
from .market_item import router as market_item_router
from .game import router as game_router

router = APIRouter()
router.include_router(entire_market_router)
router.include_router(market_item_router)
router.include_router(game_router)
31 changes: 31 additions & 0 deletions steam_trade_bot/api/routes/entire_market.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
from typing import Literal

from dependency_injector.wiring import inject, Provide
from fastapi import Depends, APIRouter

from steam_trade_bot.api.models.market_item import EntireMarketStatsResponse
from steam_trade_bot.containers import Container
from steam_trade_bot.domain.interfaces.unit_of_work import IUnitOfWork


router = APIRouter()


@router.get("/get_entire_market_stats/", response_model=EntireMarketStatsResponse)
@inject
async def get_entire_market_stats(
mode: Literal["monthly", "weekly", "daily"] = "daily",
count: int | None = None,
offset: int | None = None,
uow: IUnitOfWork = Depends(Provide[Container.repositories.unit_of_work]),
):
async with uow:
stats = await uow.entire_market_daily_stats.get_all(mode=mode, count=count, offset=offset)
return EntireMarketStatsResponse(
total_volume=round(sum(x.volume for x in stats), 2),
total_volume_no_fee=round(sum(x.volume_no_fee for x in stats), 2),
total_volume_game_fee=round(sum(x.volume_game_fee for x in stats), 2),
total_volume_steam_fee=round(sum(x.volume_steam_fee for x in stats), 2),
total_quantity=round(sum(x.quantity for x in stats), 2),
items=stats
)
45 changes: 45 additions & 0 deletions steam_trade_bot/api/routes/game.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
from dependency_injector.wiring import inject, Provide
from fastapi import Depends, APIRouter

from steam_trade_bot.api.models.market_item import GamesListResponse
from steam_trade_bot.containers import Container
from steam_trade_bot.domain.entities.game import GameStatsResponse
from steam_trade_bot.domain.interfaces.unit_of_work import IUnitOfWork


router = APIRouter()


@router.get("/get_games/", response_model=GamesListResponse)
@inject
async def get_games(
count: int = 100,
offset: int = 0,
uow: IUnitOfWork = Depends(Provide[Container.repositories.unit_of_work]),
):
async with uow:
games = await uow.game.get_all(
count=count,
offset=offset,
)
return GamesListResponse(
count=len(games),
offset=offset,
items=games,
)


@router.get("/get_apps_stats/", response_model=list[GameStatsResponse])
@inject
async def get_apps_stats(
count: int | None = None,
offset: int | None = None,
uow: IUnitOfWork = Depends(Provide[Container.repositories.unit_of_work]),
):
async with uow:
stats = await uow.app_stats.get_all(
count=count,
offset=offset
)

return stats
93 changes: 93 additions & 0 deletions steam_trade_bot/api/routes/market_item.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
import dataclasses
import json

from dependency_injector.wiring import inject, Provide
from fastapi import Depends, APIRouter

from steam_trade_bot.api.models.market_item import MarketItemsListResponse, MarketItemResponse, MarketItemSellHistoryResponse
from steam_trade_bot.containers import Container
from steam_trade_bot.domain.entities.market import MarketItem, MarketItemOrders
from steam_trade_bot.domain.interfaces.unit_of_work import IUnitOfWork

router = APIRouter()


@router.get("/get_market_items/", response_model=MarketItemsListResponse)
@inject
async def get_market_items(
app_id: int = 730,
count: int = 100,
offset: int = 0,
uow: IUnitOfWork = Depends(Provide[Container.repositories.unit_of_work]),
):
async with uow:
items = await uow.market_item.get_all(
app_id=app_id,
count=count,
offset=offset,
)
return MarketItemsListResponse(
count=len(items),
offset=offset,
items=[MarketItemResponse(**item.dict()) for item in items],
)


@router.get("/get_market_item/", response_model=MarketItem)
@inject
async def get_market_item(
app_id: int = 730,
market_hash_name: str = "Sticker | Skull Lil Boney",
uow: IUnitOfWork = Depends(Provide[Container.repositories.unit_of_work]),
):
async with uow:
item = await uow.market_item.get(
app_id=app_id,
market_hash_name=market_hash_name,
)
return item


@router.get("/get_market_item_orders/", response_model=MarketItemOrders)
@inject
async def get_market_item_orders(
app_id: int = 730,
market_hash_name: str = "Sticker | Skull Lil Boney",
uow: IUnitOfWork = Depends(Provide[Container.repositories.unit_of_work]),
):
async with uow:
item = await uow.market_item_orders.get(
app_id=app_id,
market_hash_name=market_hash_name,
)
return item


@router.get("/get_item_sell_history/", response_model=MarketItemSellHistoryResponse)
@inject
async def get_item_sell_history(
app_id: int = 730,
market_hash_name: str = "Sticker | Skull Lil Boney",
uow: IUnitOfWork = Depends(Provide[Container.repositories.unit_of_work]),
):
async with uow:
history = await uow.sell_history.get(
app_id=app_id,
market_hash_name=market_hash_name,
)
stats = await uow.sell_history_stats.get(
app_id=app_id,
market_hash_name=market_hash_name
)

return MarketItemSellHistoryResponse(
app_id=history.app_id,
market_hash_name=history.market_hash_name,
timestamp=history.timestamp,
total_sold=stats.total_sold,
total_volume=stats.total_volume,
total_volume_approx_fee=round(float(stats.total_volume) * 0.13, 2),
first_sale_datetime=stats.first_sale_timestamp,
last_sale_datetime=stats.last_sale_timestamp,
history=json.loads(history.history),
)
Loading

0 comments on commit 5d1a76c

Please sign in to comment.