
- Create project structure with FastAPI - Add database models for blocks, transactions, arbitrages, pools, and DEXes - Implement Solana RPC client for fetching blockchain data - Create arbitrage detection algorithm - Implement comprehensive API endpoints for analytics - Set up database migrations with Alembic - Add detailed project documentation generated with BackendIM... (backend.im) Co-Authored-By: Claude <noreply@anthropic.com>
63 lines
2.2 KiB
Python
63 lines
2.2 KiB
Python
from typing import List, Optional, Dict, Any, Union
|
|
|
|
from sqlalchemy import desc
|
|
from sqlalchemy.orm import Session
|
|
|
|
from app.crud.base import CRUDBase
|
|
from app.models.block import Block
|
|
from app.schemas.block import BlockCreate, BlockUpdate
|
|
|
|
|
|
class CRUDBlock(CRUDBase[Block, BlockCreate, BlockUpdate]):
|
|
"""CRUD operations for blocks."""
|
|
|
|
def get_by_height(self, db: Session, *, height: int) -> Optional[Block]:
|
|
"""Get a block by its height."""
|
|
return db.query(Block).filter(Block.block_height == height).first()
|
|
|
|
def get_by_hash(self, db: Session, *, block_hash: str) -> Optional[Block]:
|
|
"""Get a block by its hash."""
|
|
return db.query(Block).filter(Block.block_hash == block_hash).first()
|
|
|
|
def get_latest_blocks(
|
|
self, db: Session, *, limit: int = 20
|
|
) -> List[Block]:
|
|
"""Get the latest blocks ordered by height."""
|
|
return db.query(Block).order_by(desc(Block.block_height)).limit(limit).all()
|
|
|
|
def get_unprocessed_blocks(
|
|
self, db: Session, *, limit: int = 100
|
|
) -> List[Block]:
|
|
"""Get blocks that haven't been processed for arbitrage detection."""
|
|
return db.query(Block).filter(Block.processed == 0).limit(limit).all()
|
|
|
|
def mark_as_processed(
|
|
self, db: Session, *, block_id: int
|
|
) -> Optional[Block]:
|
|
"""Mark a block as processed."""
|
|
db_obj = db.query(Block).filter(Block.id == block_id).first()
|
|
if db_obj:
|
|
db_obj.processed = 1
|
|
db.add(db_obj)
|
|
db.commit()
|
|
db.refresh(db_obj)
|
|
return db_obj
|
|
|
|
def get_block_with_transactions(
|
|
self, db: Session, *, block_id: int
|
|
) -> Optional[Block]:
|
|
"""Get a block with all its transactions."""
|
|
return db.query(Block).filter(Block.id == block_id).first()
|
|
|
|
def get_block_count_by_time_range(
|
|
self, db: Session, *, start_time: Any, end_time: Any
|
|
) -> int:
|
|
"""Get count of blocks in a time range."""
|
|
return db.query(Block).filter(
|
|
Block.block_time >= start_time,
|
|
Block.block_time <= end_time
|
|
).count()
|
|
|
|
|
|
# Create a single instance for use in dependency injection
|
|
block = CRUDBlock(Block) |