Merge pull request 'postgres-migration' (#1) from postgres-migration into main
All checks were successful
Build Docker Image / build (push) Successful in 3m21s
All checks were successful
Build Docker Image / build (push) Successful in 3m21s
Reviewed-on: #1
This commit is contained in:
commit
65c00800d2
375
.gitea/workflows/build.yml
Normal file
375
.gitea/workflows/build.yml
Normal file
@ -0,0 +1,375 @@
|
|||||||
|
# Gitea Actions: Docker Build, Push, and Notify
|
||||||
|
#
|
||||||
|
# This workflow provides a complete CI/CD pipeline for Paper Dynasty Database:
|
||||||
|
# - Validates semantic versioning on PRs
|
||||||
|
# - Builds Docker images on every push/PR
|
||||||
|
# - Pushes to Docker Hub on main branch merges
|
||||||
|
# - Sends Discord notifications on success/failure
|
||||||
|
#
|
||||||
|
# Created: 2026-02-05
|
||||||
|
# For: Paper Dynasty Database API
|
||||||
|
|
||||||
|
name: Build Docker Image
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
branches:
|
||||||
|
- main
|
||||||
|
pull_request:
|
||||||
|
branches:
|
||||||
|
- main
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
|
||||||
|
steps:
|
||||||
|
# ==============================================
|
||||||
|
# 1. CHECKOUT CODE
|
||||||
|
# ==============================================
|
||||||
|
- name: Checkout code
|
||||||
|
uses: actions/checkout@v4
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 2. SEMANTIC VERSION VALIDATION (PRs only)
|
||||||
|
# ==============================================
|
||||||
|
# Enforces proper semantic versioning:
|
||||||
|
# - Blocks PRs that don't bump VERSION file
|
||||||
|
# - Validates version changes follow semver rules
|
||||||
|
# - Prevents skipping versions or going backwards
|
||||||
|
#
|
||||||
|
# Valid bumps:
|
||||||
|
# - Patch: 1.2.3 → 1.2.4 (bug fixes)
|
||||||
|
# - Minor: 1.2.3 → 1.3.0 (new features)
|
||||||
|
# - Major: 1.2.3 → 2.0.0 (breaking changes)
|
||||||
|
#
|
||||||
|
# Invalid bumps:
|
||||||
|
# - 1.2.3 → 1.4.0 (skipped minor version)
|
||||||
|
# - 1.2.3 → 1.2.0 (went backwards)
|
||||||
|
# - 1.2.3 → 1.3.1 (didn't reset patch)
|
||||||
|
#
|
||||||
|
- name: Check VERSION was bumped (semantic versioning)
|
||||||
|
if: github.event_name == 'pull_request'
|
||||||
|
run: |
|
||||||
|
# Get VERSION from this PR branch
|
||||||
|
PR_VERSION=$(cat VERSION 2>/dev/null || echo "0.0.0")
|
||||||
|
|
||||||
|
# Get VERSION from main branch
|
||||||
|
git fetch origin main:main
|
||||||
|
MAIN_VERSION=$(git show main:VERSION 2>/dev/null || echo "0.0.0")
|
||||||
|
|
||||||
|
echo "📋 Semantic Version Check"
|
||||||
|
echo "Main branch version: $MAIN_VERSION"
|
||||||
|
echo "PR branch version: $PR_VERSION"
|
||||||
|
echo ""
|
||||||
|
|
||||||
|
# Parse versions into components
|
||||||
|
IFS='.' read -r MAIN_MAJOR MAIN_MINOR MAIN_PATCH <<< "$MAIN_VERSION"
|
||||||
|
IFS='.' read -r PR_MAJOR PR_MINOR PR_PATCH <<< "$PR_VERSION"
|
||||||
|
|
||||||
|
# Remove any non-numeric characters
|
||||||
|
MAIN_MAJOR=${MAIN_MAJOR//[!0-9]/}
|
||||||
|
MAIN_MINOR=${MAIN_MINOR//[!0-9]/}
|
||||||
|
MAIN_PATCH=${MAIN_PATCH//[!0-9]/}
|
||||||
|
PR_MAJOR=${PR_MAJOR//[!0-9]/}
|
||||||
|
PR_MINOR=${PR_MINOR//[!0-9]/}
|
||||||
|
PR_PATCH=${PR_PATCH//[!0-9]/}
|
||||||
|
|
||||||
|
# Check if VERSION unchanged
|
||||||
|
if [ "$PR_VERSION" = "$MAIN_VERSION" ]; then
|
||||||
|
echo "❌ ERROR: VERSION file has not been updated!"
|
||||||
|
echo ""
|
||||||
|
echo "Please update the VERSION file in your PR."
|
||||||
|
echo "Current version: $MAIN_VERSION"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Validate semantic version bump
|
||||||
|
VALID=false
|
||||||
|
BUMP_TYPE=""
|
||||||
|
|
||||||
|
# Check for major version bump (X.0.0)
|
||||||
|
if [ "$PR_MAJOR" -eq $((MAIN_MAJOR + 1)) ] && [ "$PR_MINOR" -eq 0 ] && [ "$PR_PATCH" -eq 0 ]; then
|
||||||
|
VALID=true
|
||||||
|
BUMP_TYPE="major"
|
||||||
|
# Check for minor version bump (x.X.0)
|
||||||
|
elif [ "$PR_MAJOR" -eq "$MAIN_MAJOR" ] && [ "$PR_MINOR" -eq $((MAIN_MINOR + 1)) ] && [ "$PR_PATCH" -eq 0 ]; then
|
||||||
|
VALID=true
|
||||||
|
BUMP_TYPE="minor"
|
||||||
|
# Check for patch version bump (x.x.X)
|
||||||
|
elif [ "$PR_MAJOR" -eq "$MAIN_MAJOR" ] && [ "$PR_MINOR" -eq "$MAIN_MINOR" ] && [ "$PR_PATCH" -eq $((MAIN_PATCH + 1)) ]; then
|
||||||
|
VALID=true
|
||||||
|
BUMP_TYPE="patch"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$VALID" = true ]; then
|
||||||
|
echo "✅ Valid $BUMP_TYPE version bump: $MAIN_VERSION → $PR_VERSION"
|
||||||
|
else
|
||||||
|
echo "❌ ERROR: Invalid semantic version change!"
|
||||||
|
echo ""
|
||||||
|
echo "Current version: $MAIN_VERSION"
|
||||||
|
echo "PR version: $PR_VERSION"
|
||||||
|
echo ""
|
||||||
|
echo "Valid version bumps:"
|
||||||
|
echo " - Patch: $MAIN_MAJOR.$MAIN_MINOR.$((MAIN_PATCH + 1))"
|
||||||
|
echo " - Minor: $MAIN_MAJOR.$((MAIN_MINOR + 1)).0"
|
||||||
|
echo " - Major: $((MAIN_MAJOR + 1)).0.0"
|
||||||
|
echo ""
|
||||||
|
echo "Common issues:"
|
||||||
|
echo " ❌ Skipping versions (e.g., 2.5.0 → 2.7.0)"
|
||||||
|
echo " ❌ Going backwards (e.g., 2.5.0 → 2.4.0)"
|
||||||
|
echo " ❌ Not resetting lower components (e.g., 2.5.0 → 2.6.1)"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 3. DOCKER BUILDX SETUP
|
||||||
|
# ==============================================
|
||||||
|
- name: Set up Docker Buildx
|
||||||
|
uses: docker/setup-buildx-action@v3
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 4. DOCKER HUB LOGIN (main branch only)
|
||||||
|
# ==============================================
|
||||||
|
# Requires secrets in Gitea:
|
||||||
|
# - DOCKERHUB_USERNAME: Your Docker Hub username
|
||||||
|
# - DOCKERHUB_TOKEN: Docker Hub access token (not password!)
|
||||||
|
#
|
||||||
|
# To create token:
|
||||||
|
# 1. Go to hub.docker.com
|
||||||
|
# 2. Account Settings → Security → New Access Token
|
||||||
|
# 3. Copy token to Gitea repo → Settings → Secrets → Actions
|
||||||
|
#
|
||||||
|
- name: Login to Docker Hub
|
||||||
|
if: github.ref == 'refs/heads/main'
|
||||||
|
uses: docker/login-action@v3
|
||||||
|
with:
|
||||||
|
username: ${{ secrets.DOCKERHUB_USERNAME }}
|
||||||
|
password: ${{ secrets.DOCKERHUB_TOKEN }}
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 5. EXTRACT METADATA
|
||||||
|
# ==============================================
|
||||||
|
# Reads VERSION file and generates image tags:
|
||||||
|
# - version: From VERSION file (e.g., "1.2.3")
|
||||||
|
# - sha_short: First 7 chars of commit SHA
|
||||||
|
# - version_sha: Combined version+commit (e.g., "v1.2.3-a1b2c3d")
|
||||||
|
# - branch: Current branch name
|
||||||
|
# - timestamp: ISO 8601 format for Discord
|
||||||
|
#
|
||||||
|
- name: Extract metadata
|
||||||
|
id: meta
|
||||||
|
run: |
|
||||||
|
VERSION=$(cat VERSION 2>/dev/null || echo "0.0.0")
|
||||||
|
SHA_SHORT=$(echo ${{ github.sha }} | cut -c1-7)
|
||||||
|
echo "version=${VERSION}" >> $GITHUB_OUTPUT
|
||||||
|
echo "sha_short=${SHA_SHORT}" >> $GITHUB_OUTPUT
|
||||||
|
echo "version_sha=v${VERSION}-${SHA_SHORT}" >> $GITHUB_OUTPUT
|
||||||
|
echo "branch=${{ github.ref_name }}" >> $GITHUB_OUTPUT
|
||||||
|
echo "timestamp=$(date -u +'%Y-%m-%dT%H:%M:%SZ')" >> $GITHUB_OUTPUT
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 6. BUILD AND PUSH DOCKER IMAGE
|
||||||
|
# ==============================================
|
||||||
|
# Creates 3 tags for each build:
|
||||||
|
# - latest: Always points to newest build
|
||||||
|
# - v{VERSION}: Semantic version from VERSION file
|
||||||
|
# - v{VERSION}-{COMMIT}: Version + commit hash for traceability
|
||||||
|
#
|
||||||
|
# Example tags:
|
||||||
|
# - manticorum67/paper-dynasty-database:latest
|
||||||
|
# - manticorum67/paper-dynasty-database:v1.5.5
|
||||||
|
# - manticorum67/paper-dynasty-database:v1.5.5-a1b2c3d
|
||||||
|
#
|
||||||
|
# Push behavior:
|
||||||
|
# - PRs: Build only (test), don't push
|
||||||
|
# - Main: Build and push to Docker Hub
|
||||||
|
#
|
||||||
|
- name: Build Docker image
|
||||||
|
uses: docker/build-push-action@v5
|
||||||
|
with:
|
||||||
|
context: .
|
||||||
|
push: ${{ github.ref == 'refs/heads/main' }}
|
||||||
|
tags: |
|
||||||
|
manticorum67/paper-dynasty-database:latest
|
||||||
|
manticorum67/paper-dynasty-database:v${{ steps.meta.outputs.version }}
|
||||||
|
manticorum67/paper-dynasty-database:${{ steps.meta.outputs.version_sha }}
|
||||||
|
cache-from: type=gha
|
||||||
|
cache-to: type=gha,mode=max
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 7. BUILD SUMMARY
|
||||||
|
# ==============================================
|
||||||
|
# Creates a formatted summary visible in Actions UI
|
||||||
|
# Shows: image tags, build details, push status
|
||||||
|
#
|
||||||
|
- name: Build Summary
|
||||||
|
run: |
|
||||||
|
echo "## 🐳 Docker Build Successful! ✅" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "**Image Tags:**" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "- \`manticorum67/paper-dynasty-database:latest\`" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "- \`manticorum67/paper-dynasty-database:v${{ steps.meta.outputs.version }}\`" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "- \`manticorum67/paper-dynasty-database:${{ steps.meta.outputs.version_sha }}\`" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "**Build Details:**" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "- Branch: \`${{ steps.meta.outputs.branch }}\`" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "- Commit: \`${{ github.sha }}\`" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "- Timestamp: \`${{ steps.meta.outputs.timestamp }}\`" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "" >> $GITHUB_STEP_SUMMARY
|
||||||
|
if [ "${{ github.ref }}" == "refs/heads/main" ]; then
|
||||||
|
echo "🚀 **Pushed to Docker Hub!**" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "" >> $GITHUB_STEP_SUMMARY
|
||||||
|
echo "Pull with: \`docker pull manticorum67/paper-dynasty-database:latest\`" >> $GITHUB_STEP_SUMMARY
|
||||||
|
else
|
||||||
|
echo "_PR build - image not pushed to Docker Hub_" >> $GITHUB_STEP_SUMMARY
|
||||||
|
fi
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 8. DISCORD NOTIFICATION - SUCCESS
|
||||||
|
# ==============================================
|
||||||
|
# Sends green embed to Discord on successful builds
|
||||||
|
#
|
||||||
|
# Only fires on main branch pushes (not PRs)
|
||||||
|
#
|
||||||
|
# Setup:
|
||||||
|
# 1. Create webhook in Discord channel:
|
||||||
|
# Right-click channel → Edit → Integrations → Webhooks → New
|
||||||
|
# 2. Copy webhook URL
|
||||||
|
# 3. Add to Gitea: Settings → Secrets → Actions → DISCORD_WEBHOOK
|
||||||
|
#
|
||||||
|
- name: Discord Notification - Success
|
||||||
|
if: success() && github.ref == 'refs/heads/main'
|
||||||
|
run: |
|
||||||
|
curl -H "Content-Type: application/json" \
|
||||||
|
-d '{
|
||||||
|
"embeds": [{
|
||||||
|
"title": "✅ Paper Dynasty Database Build Successful",
|
||||||
|
"description": "Docker image built and pushed to Docker Hub!",
|
||||||
|
"color": 3066993,
|
||||||
|
"fields": [
|
||||||
|
{
|
||||||
|
"name": "Version",
|
||||||
|
"value": "`v${{ steps.meta.outputs.version }}`",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Image Tag",
|
||||||
|
"value": "`${{ steps.meta.outputs.version_sha }}`",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Branch",
|
||||||
|
"value": "`${{ steps.meta.outputs.branch }}`",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Commit",
|
||||||
|
"value": "`${{ steps.meta.outputs.sha_short }}`",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Author",
|
||||||
|
"value": "${{ github.actor }}",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Docker Hub",
|
||||||
|
"value": "[manticorum67/paper-dynasty-database](https://hub.docker.com/r/manticorum67/paper-dynasty-database)",
|
||||||
|
"inline": false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "View Run",
|
||||||
|
"value": "[Click here](${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }})",
|
||||||
|
"inline": false
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"timestamp": "${{ steps.meta.outputs.timestamp }}"
|
||||||
|
}]
|
||||||
|
}' \
|
||||||
|
${{ secrets.DISCORD_WEBHOOK }}
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# 9. DISCORD NOTIFICATION - FAILURE
|
||||||
|
# ==============================================
|
||||||
|
# Sends red embed to Discord on build failures
|
||||||
|
#
|
||||||
|
# Only fires on main branch pushes (not PRs)
|
||||||
|
#
|
||||||
|
- name: Discord Notification - Failure
|
||||||
|
if: failure() && github.ref == 'refs/heads/main'
|
||||||
|
run: |
|
||||||
|
TIMESTAMP=$(date -u +%Y-%m-%dT%H:%M:%SZ)
|
||||||
|
curl -H "Content-Type: application/json" \
|
||||||
|
-d '{
|
||||||
|
"embeds": [{
|
||||||
|
"title": "❌ Paper Dynasty Database Build Failed",
|
||||||
|
"description": "Docker build encountered an error.",
|
||||||
|
"color": 15158332,
|
||||||
|
"fields": [
|
||||||
|
{
|
||||||
|
"name": "Branch",
|
||||||
|
"value": "`${{ github.ref_name }}`",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Commit",
|
||||||
|
"value": "`${{ github.sha }}`",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Author",
|
||||||
|
"value": "${{ github.actor }}",
|
||||||
|
"inline": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "View Logs",
|
||||||
|
"value": "[Click here](${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }})",
|
||||||
|
"inline": false
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"timestamp": "'"$TIMESTAMP"'"
|
||||||
|
}]
|
||||||
|
}' \
|
||||||
|
${{ secrets.DISCORD_WEBHOOK }}
|
||||||
|
|
||||||
|
# ==============================================
|
||||||
|
# SETUP CHECKLIST
|
||||||
|
# ==============================================
|
||||||
|
# Before this workflow will work:
|
||||||
|
#
|
||||||
|
# ✅ Add secrets to Gitea repo (Settings → Secrets → Actions):
|
||||||
|
# - DOCKERHUB_USERNAME: Your Docker Hub username (manticorum67)
|
||||||
|
# - DOCKERHUB_TOKEN: Docker Hub access token
|
||||||
|
# - DISCORD_WEBHOOK: Discord webhook URL for notifications
|
||||||
|
#
|
||||||
|
# ✅ Ensure VERSION file exists in repo root (currently at 1.5.5)
|
||||||
|
#
|
||||||
|
# ✅ Update branch name if not using "main"
|
||||||
|
#
|
||||||
|
# ==============================================
|
||||||
|
# TROUBLESHOOTING
|
||||||
|
# ==============================================
|
||||||
|
# Common issues and solutions:
|
||||||
|
#
|
||||||
|
# 1. VERSION validation failing unexpectedly
|
||||||
|
# - Ensure VERSION file exists in repo root
|
||||||
|
# - Check file contains only version number (no 'v' prefix or extra text)
|
||||||
|
# - Verify version follows semver: MAJOR.MINOR.PATCH
|
||||||
|
#
|
||||||
|
# 2. Docker Hub push failing
|
||||||
|
# - Verify DOCKERHUB_USERNAME and DOCKERHUB_TOKEN secrets are set
|
||||||
|
# - Check Docker Hub token has push permissions
|
||||||
|
# - Ensure repository name matches your Docker Hub repo exactly
|
||||||
|
#
|
||||||
|
# 3. Discord notifications not appearing
|
||||||
|
# - Verify DISCORD_WEBHOOK secret is set in Gitea
|
||||||
|
# - Test webhook URL manually with curl
|
||||||
|
# - Check webhook still exists in Discord channel settings
|
||||||
|
#
|
||||||
|
# 4. Build cache not working
|
||||||
|
# - GitHub Actions cache is stored per repository
|
||||||
|
# - Cache is shared across branches
|
||||||
|
# - May need to clear cache if corrupted
|
||||||
|
#
|
||||||
|
# ==============================================
|
||||||
File diff suppressed because it is too large
Load Diff
@ -116,6 +116,7 @@ CARDSETS = {
|
|||||||
"gauntlet-9": {
|
"gauntlet-9": {
|
||||||
"primary": [27], # 2005
|
"primary": [27], # 2005
|
||||||
"secondary": [24], # 2025
|
"secondary": [24], # 2025
|
||||||
|
"human": [x for x in range(1, 30)],
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
898
db_engine.py
898
db_engine.py
@ -1,898 +0,0 @@
|
|||||||
import math
|
|
||||||
|
|
||||||
"""
|
|
||||||
DEPRECATED: This file is a legacy implementation from before the deployment
|
|
||||||
of /database/app/. The active codebase is now in /database/app/db_engine.py.
|
|
||||||
This file is kept for reference only and should not be used.
|
|
||||||
"""
|
|
||||||
|
|
||||||
from datetime import datetime
|
|
||||||
from typing import List
|
|
||||||
import logging
|
|
||||||
import os
|
|
||||||
|
|
||||||
from pandas import DataFrame
|
|
||||||
from peewee import *
|
|
||||||
from peewee import ModelSelect
|
|
||||||
from playhouse.shortcuts import model_to_dict
|
|
||||||
|
|
||||||
db = SqliteDatabase(
|
|
||||||
"storage/pd_master.db",
|
|
||||||
pragmas={"journal_mode": "wal", "cache_size": -1 * 64000, "synchronous": 0},
|
|
||||||
)
|
|
||||||
|
|
||||||
date = f"{datetime.now().year}-{datetime.now().month}-{datetime.now().day}"
|
|
||||||
log_level = logging.INFO if os.environ.get("LOG_LEVEL") == "INFO" else "WARN"
|
|
||||||
logging.basicConfig(
|
|
||||||
filename=f"logs/database/{date}.log",
|
|
||||||
format="%(asctime)s - database - %(levelname)s - %(message)s",
|
|
||||||
level=log_level,
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def model_csv_headers(this_obj, exclude=None) -> List:
|
|
||||||
data = model_to_dict(this_obj, recurse=False, exclude=exclude)
|
|
||||||
return [x for x in data.keys()]
|
|
||||||
|
|
||||||
|
|
||||||
def model_to_csv(this_obj, exclude=None) -> List:
|
|
||||||
data = model_to_dict(this_obj, recurse=False, exclude=exclude)
|
|
||||||
return [x for x in data.values()]
|
|
||||||
|
|
||||||
|
|
||||||
def query_to_csv(all_items: ModelSelect, exclude=None):
|
|
||||||
if all_items.count() == 0:
|
|
||||||
data_list = [["No data found"]]
|
|
||||||
else:
|
|
||||||
data_list = [model_csv_headers(all_items[0], exclude=exclude)]
|
|
||||||
for x in all_items:
|
|
||||||
data_list.append(model_to_csv(x, exclude=exclude))
|
|
||||||
|
|
||||||
return DataFrame(data_list).to_csv(header=False, index=False)
|
|
||||||
|
|
||||||
|
|
||||||
def complex_data_to_csv(complex_data: List):
|
|
||||||
if len(complex_data) == 0:
|
|
||||||
data_list = [["No data found"]]
|
|
||||||
else:
|
|
||||||
data_list = [[x for x in complex_data[0].keys()]]
|
|
||||||
for line in complex_data:
|
|
||||||
logging.debug(f"line: {line}")
|
|
||||||
this_row = []
|
|
||||||
for key in line:
|
|
||||||
logging.debug(f"key: {key}")
|
|
||||||
if line[key] is None:
|
|
||||||
this_row.append("")
|
|
||||||
|
|
||||||
elif isinstance(line[key], dict):
|
|
||||||
if "name" in line[key]:
|
|
||||||
this_row.append(line[key]["name"])
|
|
||||||
elif "abbrev" in line[key]:
|
|
||||||
this_row.append(line[key]["abbrev"])
|
|
||||||
else:
|
|
||||||
this_row.append(line[key]["id"])
|
|
||||||
|
|
||||||
elif isinstance(line[key], int) and line[key] > 100000000:
|
|
||||||
this_row.append(f"'{line[key]}")
|
|
||||||
|
|
||||||
elif isinstance(line[key], str) and "," in line[key]:
|
|
||||||
this_row.append(line[key].replace(",", "-_-"))
|
|
||||||
|
|
||||||
else:
|
|
||||||
this_row.append(line[key])
|
|
||||||
|
|
||||||
data_list.append(this_row)
|
|
||||||
|
|
||||||
return DataFrame(data_list).to_csv(header=False, index=False)
|
|
||||||
|
|
||||||
|
|
||||||
class BaseModel(Model):
|
|
||||||
class Meta:
|
|
||||||
database = db
|
|
||||||
|
|
||||||
|
|
||||||
class Current(BaseModel):
|
|
||||||
season = IntegerField()
|
|
||||||
week = IntegerField(default=0)
|
|
||||||
gsheet_template = CharField()
|
|
||||||
gsheet_version = CharField()
|
|
||||||
live_scoreboard = IntegerField()
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def latest():
|
|
||||||
latest_current = Current.select().order_by(-Current.id).get()
|
|
||||||
return latest_current
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Current])
|
|
||||||
|
|
||||||
|
|
||||||
class Rarity(BaseModel):
|
|
||||||
value = IntegerField()
|
|
||||||
name = CharField(unique=True)
|
|
||||||
color = CharField()
|
|
||||||
|
|
||||||
def __str__(self):
|
|
||||||
return self.name
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Rarity])
|
|
||||||
|
|
||||||
|
|
||||||
class Event(BaseModel):
|
|
||||||
name = CharField()
|
|
||||||
short_desc = CharField(null=True)
|
|
||||||
url = CharField(null=True)
|
|
||||||
long_desc = CharField(null=True)
|
|
||||||
thumbnail = CharField(null=True)
|
|
||||||
active = BooleanField(default=False)
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Event])
|
|
||||||
|
|
||||||
|
|
||||||
class Cardset(BaseModel):
|
|
||||||
name = CharField()
|
|
||||||
description = CharField()
|
|
||||||
event = ForeignKeyField(Event, null=True)
|
|
||||||
for_purchase = BooleanField(default=True) # for_purchase
|
|
||||||
total_cards = IntegerField()
|
|
||||||
in_packs = BooleanField(default=True)
|
|
||||||
ranked_legal = BooleanField(default=True)
|
|
||||||
|
|
||||||
def __str__(self):
|
|
||||||
return self.name
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Cardset])
|
|
||||||
|
|
||||||
|
|
||||||
class MlbPlayer(BaseModel):
|
|
||||||
first_name = CharField()
|
|
||||||
last_name = CharField()
|
|
||||||
key_fangraphs = IntegerField(null=True)
|
|
||||||
key_bbref = CharField(null=True)
|
|
||||||
key_retro = CharField(null=True)
|
|
||||||
key_mlbam = IntegerField(null=True)
|
|
||||||
offense_col = IntegerField(default=1)
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([MlbPlayer])
|
|
||||||
|
|
||||||
|
|
||||||
class Player(BaseModel):
|
|
||||||
player_id = IntegerField(primary_key=True)
|
|
||||||
p_name = CharField()
|
|
||||||
cost = IntegerField(default=0)
|
|
||||||
image = CharField()
|
|
||||||
image2 = CharField(null=True)
|
|
||||||
mlbclub = CharField()
|
|
||||||
franchise = CharField()
|
|
||||||
cardset = ForeignKeyField(Cardset)
|
|
||||||
set_num = IntegerField()
|
|
||||||
rarity = ForeignKeyField(Rarity)
|
|
||||||
pos_1 = CharField()
|
|
||||||
pos_2 = CharField(null=True)
|
|
||||||
pos_3 = CharField(null=True)
|
|
||||||
pos_4 = CharField(null=True)
|
|
||||||
pos_5 = CharField(null=True)
|
|
||||||
pos_6 = CharField(null=True)
|
|
||||||
pos_7 = CharField(null=True)
|
|
||||||
pos_8 = CharField(null=True)
|
|
||||||
headshot = CharField(null=True)
|
|
||||||
vanity_card = CharField(null=True)
|
|
||||||
strat_code = CharField(null=True)
|
|
||||||
bbref_id = CharField(null=True)
|
|
||||||
fangr_id = CharField(null=True)
|
|
||||||
description = CharField()
|
|
||||||
quantity = IntegerField(default=999)
|
|
||||||
mlbplayer = ForeignKeyField(MlbPlayer, null=True)
|
|
||||||
|
|
||||||
def __str__(self):
|
|
||||||
return f"{self.cardset} {self.p_name} ({self.rarity.name})"
|
|
||||||
|
|
||||||
# def __eq__(self, other):
|
|
||||||
# if self.cardset.id == other.cardset.id and self.name == other.name:
|
|
||||||
# return True
|
|
||||||
# else:
|
|
||||||
# return False
|
|
||||||
|
|
||||||
def __lt__(self, other):
|
|
||||||
if self.wara < other.wara:
|
|
||||||
return True
|
|
||||||
elif self.wara > other.wara:
|
|
||||||
return False
|
|
||||||
elif self.name < other.name:
|
|
||||||
return True
|
|
||||||
else:
|
|
||||||
return False
|
|
||||||
|
|
||||||
def get_all_pos(self):
|
|
||||||
all_pos = []
|
|
||||||
|
|
||||||
if self.pos_1 and self.pos_1 != "CP":
|
|
||||||
all_pos.append(self.pos_1)
|
|
||||||
if self.pos_2 and self.pos_2 != "CP":
|
|
||||||
all_pos.append(self.pos_2)
|
|
||||||
if self.pos_3 and self.pos_3 != "CP":
|
|
||||||
all_pos.append(self.pos_3)
|
|
||||||
if self.pos_4 and self.pos_4 != "CP":
|
|
||||||
all_pos.append(self.pos_4)
|
|
||||||
if self.pos_5 and self.pos_5 != "CP":
|
|
||||||
all_pos.append(self.pos_5)
|
|
||||||
if self.pos_6 and self.pos_6 != "CP":
|
|
||||||
all_pos.append(self.pos_6)
|
|
||||||
if self.pos_7 and self.pos_7 != "CP":
|
|
||||||
all_pos.append(self.pos_7)
|
|
||||||
if self.pos_8 and self.pos_8 != "CP":
|
|
||||||
all_pos.append(self.pos_8)
|
|
||||||
|
|
||||||
return all_pos
|
|
||||||
|
|
||||||
def change_on_sell(self):
|
|
||||||
# caps = {
|
|
||||||
# 'replacement': 15,
|
|
||||||
# 'reserve': 50,
|
|
||||||
# 'starter': 200,
|
|
||||||
# 'all-star': 750,
|
|
||||||
# 'mvp': 2500,
|
|
||||||
# 'hof': 999999999
|
|
||||||
# }
|
|
||||||
logging.info(f"{self.p_name} cost changing from: {self.cost}")
|
|
||||||
self.cost = max(math.floor(self.cost * 0.95), 1)
|
|
||||||
# if self.quantity != 999:
|
|
||||||
# self.quantity += 1
|
|
||||||
logging.info(f"{self.p_name} cost now: {self.cost}")
|
|
||||||
self.save()
|
|
||||||
|
|
||||||
def change_on_buy(self):
|
|
||||||
logging.info(f"{self.p_name} cost changing from: {self.cost}")
|
|
||||||
self.cost = math.ceil(self.cost * 1.1)
|
|
||||||
# if self.quantity != 999:
|
|
||||||
# self.quantity -= 1
|
|
||||||
logging.info(f"{self.p_name} cost now: {self.cost}")
|
|
||||||
self.save()
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Player])
|
|
||||||
|
|
||||||
|
|
||||||
class Team(BaseModel):
|
|
||||||
abbrev = CharField()
|
|
||||||
sname = CharField()
|
|
||||||
lname = CharField()
|
|
||||||
gmid = IntegerField()
|
|
||||||
gmname = CharField()
|
|
||||||
gsheet = CharField()
|
|
||||||
wallet = IntegerField()
|
|
||||||
team_value = IntegerField()
|
|
||||||
collection_value = IntegerField()
|
|
||||||
logo = CharField(null=True)
|
|
||||||
color = CharField(null=True)
|
|
||||||
season = IntegerField()
|
|
||||||
event = ForeignKeyField(Event, null=True)
|
|
||||||
career = IntegerField(default=0)
|
|
||||||
ranking = IntegerField(default=1000)
|
|
||||||
has_guide = BooleanField(default=False)
|
|
||||||
is_ai = IntegerField(null=True)
|
|
||||||
|
|
||||||
def __str__(self):
|
|
||||||
return f"S{self.season} {self.lname}"
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def get_by_owner(gmid, season=None):
|
|
||||||
if not season:
|
|
||||||
season = Current.get().season
|
|
||||||
team = Team.get_or_none((Team.gmid == gmid) & (Team.season == season))
|
|
||||||
|
|
||||||
if not team:
|
|
||||||
return None
|
|
||||||
|
|
||||||
return team
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def select_season(season=None):
|
|
||||||
if not season:
|
|
||||||
season = Current.get().season
|
|
||||||
return Team.select().where(Team.season == season)
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def get_season(abbrev, season=None):
|
|
||||||
if not season:
|
|
||||||
season = Current.get().season
|
|
||||||
return Team.get_or_none(Team.season == season, Team.abbrev == abbrev.upper())
|
|
||||||
|
|
||||||
def team_hash(self):
|
|
||||||
hash_string = f"{self.sname[-1]}{self.gmid / 6950123:.0f}{self.sname[-2]}{self.gmid / 42069123:.0f}"
|
|
||||||
logging.info(f"string: {hash_string}")
|
|
||||||
return hash_string
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Team])
|
|
||||||
|
|
||||||
|
|
||||||
class PackType(BaseModel):
|
|
||||||
name = CharField()
|
|
||||||
card_count = IntegerField()
|
|
||||||
description = CharField()
|
|
||||||
cost = IntegerField()
|
|
||||||
available = BooleanField(default=True)
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([PackType])
|
|
||||||
|
|
||||||
|
|
||||||
class Pack(BaseModel):
|
|
||||||
team = ForeignKeyField(Team)
|
|
||||||
pack_type = ForeignKeyField(PackType)
|
|
||||||
pack_team = ForeignKeyField(Team, null=True)
|
|
||||||
pack_cardset = ForeignKeyField(Cardset, null=True)
|
|
||||||
open_time = DateTimeField(null=True)
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Pack])
|
|
||||||
|
|
||||||
|
|
||||||
class Card(BaseModel):
|
|
||||||
player = ForeignKeyField(Player, null=True)
|
|
||||||
team = ForeignKeyField(Team, null=True)
|
|
||||||
pack = ForeignKeyField(Pack, null=True)
|
|
||||||
value = IntegerField(default=0)
|
|
||||||
|
|
||||||
def __str__(self):
|
|
||||||
if self.player:
|
|
||||||
return f"{self.player} - {self.team.sname}"
|
|
||||||
else:
|
|
||||||
return f"Blank - {self.team.sname}"
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def select_season(season):
|
|
||||||
return Card.select().join(Team).where(Card.team.season == season)
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables([Card])
|
|
||||||
|
|
||||||
|
|
||||||
class Roster(BaseModel):
|
|
||||||
team = ForeignKeyField(Team)
|
|
||||||
name = CharField()
|
|
||||||
roster_num = IntegerField()
|
|
||||||
card_1 = ForeignKeyField(Card)
|
|
||||||
card_2 = ForeignKeyField(Card)
|
|
||||||
card_3 = ForeignKeyField(Card)
|
|
||||||
card_4 = ForeignKeyField(Card)
|
|
||||||
card_5 = ForeignKeyField(Card)
|
|
||||||
card_6 = ForeignKeyField(Card)
|
|
||||||
card_7 = ForeignKeyField(Card)
|
|
||||||
card_8 = ForeignKeyField(Card)
|
|
||||||
card_9 = ForeignKeyField(Card)
|
|
||||||
card_10 = ForeignKeyField(Card)
|
|
||||||
card_11 = ForeignKeyField(Card)
|
|
||||||
card_12 = ForeignKeyField(Card)
|
|
||||||
card_13 = ForeignKeyField(Card)
|
|
||||||
card_14 = ForeignKeyField(Card)
|
|
||||||
card_15 = ForeignKeyField(Card)
|
|
||||||
card_16 = ForeignKeyField(Card)
|
|
||||||
card_17 = ForeignKeyField(Card)
|
|
||||||
card_18 = ForeignKeyField(Card)
|
|
||||||
card_19 = ForeignKeyField(Card)
|
|
||||||
card_20 = ForeignKeyField(Card)
|
|
||||||
card_21 = ForeignKeyField(Card)
|
|
||||||
card_22 = ForeignKeyField(Card)
|
|
||||||
card_23 = ForeignKeyField(Card)
|
|
||||||
card_24 = ForeignKeyField(Card)
|
|
||||||
card_25 = ForeignKeyField(Card)
|
|
||||||
card_26 = ForeignKeyField(Card)
|
|
||||||
|
|
||||||
def __str__(self):
|
|
||||||
return f"{self.team} Roster"
|
|
||||||
|
|
||||||
# def get_cards(self, team):
|
|
||||||
# all_cards = Card.select().where(Card.roster == self)
|
|
||||||
# this_roster = []
|
|
||||||
# return [this_roster.card1, this_roster.card2, this_roster.card3, this_roster.card4, this_roster.card5,
|
|
||||||
# this_roster.card6, this_roster.card7, this_roster.card8, this_roster.card9, this_roster.card10,
|
|
||||||
# this_roster.card11, this_roster.card12, this_roster.card13, this_roster.card14, this_roster.card15,
|
|
||||||
# this_roster.card16, this_roster.card17, this_roster.card18, this_roster.card19, this_roster.card20,
|
|
||||||
# this_roster.card21, this_roster.card22, this_roster.card23, this_roster.card24, this_roster.card25,
|
|
||||||
# this_roster.card26]
|
|
||||||
|
|
||||||
|
|
||||||
class Result(BaseModel):
|
|
||||||
away_team = ForeignKeyField(Team)
|
|
||||||
home_team = ForeignKeyField(Team)
|
|
||||||
away_score = IntegerField()
|
|
||||||
home_score = IntegerField()
|
|
||||||
away_team_value = IntegerField(null=True)
|
|
||||||
home_team_value = IntegerField(null=True)
|
|
||||||
away_team_ranking = IntegerField(null=True)
|
|
||||||
home_team_ranking = IntegerField(null=True)
|
|
||||||
scorecard = CharField()
|
|
||||||
week = IntegerField()
|
|
||||||
season = IntegerField()
|
|
||||||
ranked = BooleanField()
|
|
||||||
short_game = BooleanField()
|
|
||||||
game_type = CharField(null=True)
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def select_season(season=None):
|
|
||||||
if not season:
|
|
||||||
season = Current.get().season
|
|
||||||
return Result.select().where(Result.season == season)
|
|
||||||
|
|
||||||
|
|
||||||
class BattingStat(BaseModel):
|
|
||||||
card = ForeignKeyField(Card)
|
|
||||||
team = ForeignKeyField(Team)
|
|
||||||
roster_num = IntegerField()
|
|
||||||
vs_team = ForeignKeyField(Team)
|
|
||||||
result = ForeignKeyField(Result, null=True)
|
|
||||||
pos = CharField()
|
|
||||||
pa = IntegerField()
|
|
||||||
ab = IntegerField()
|
|
||||||
run = IntegerField()
|
|
||||||
hit = IntegerField()
|
|
||||||
rbi = IntegerField()
|
|
||||||
double = IntegerField()
|
|
||||||
triple = IntegerField()
|
|
||||||
hr = IntegerField()
|
|
||||||
bb = IntegerField()
|
|
||||||
so = IntegerField()
|
|
||||||
hbp = IntegerField()
|
|
||||||
sac = IntegerField()
|
|
||||||
ibb = IntegerField()
|
|
||||||
gidp = IntegerField()
|
|
||||||
sb = IntegerField()
|
|
||||||
cs = IntegerField()
|
|
||||||
bphr = IntegerField()
|
|
||||||
bpfo = IntegerField()
|
|
||||||
bp1b = IntegerField()
|
|
||||||
bplo = IntegerField()
|
|
||||||
xch = IntegerField()
|
|
||||||
xhit = IntegerField()
|
|
||||||
error = IntegerField()
|
|
||||||
pb = IntegerField()
|
|
||||||
sbc = IntegerField()
|
|
||||||
csc = IntegerField()
|
|
||||||
week = IntegerField()
|
|
||||||
season = IntegerField()
|
|
||||||
created = DateTimeField()
|
|
||||||
game_id = IntegerField()
|
|
||||||
|
|
||||||
|
|
||||||
class PitchingStat(BaseModel):
|
|
||||||
card = ForeignKeyField(Card)
|
|
||||||
team = ForeignKeyField(Team)
|
|
||||||
roster_num = IntegerField()
|
|
||||||
vs_team = ForeignKeyField(Team)
|
|
||||||
result = ForeignKeyField(Result, null=True)
|
|
||||||
ip = FloatField()
|
|
||||||
hit = IntegerField()
|
|
||||||
run = IntegerField()
|
|
||||||
erun = IntegerField()
|
|
||||||
so = IntegerField()
|
|
||||||
bb = IntegerField()
|
|
||||||
hbp = IntegerField()
|
|
||||||
wp = IntegerField()
|
|
||||||
balk = IntegerField()
|
|
||||||
hr = IntegerField()
|
|
||||||
ir = IntegerField()
|
|
||||||
irs = IntegerField()
|
|
||||||
gs = IntegerField()
|
|
||||||
win = IntegerField()
|
|
||||||
loss = IntegerField()
|
|
||||||
hold = IntegerField()
|
|
||||||
sv = IntegerField()
|
|
||||||
bsv = IntegerField()
|
|
||||||
week = IntegerField()
|
|
||||||
season = IntegerField()
|
|
||||||
created = DateTimeField()
|
|
||||||
game_id = IntegerField()
|
|
||||||
|
|
||||||
|
|
||||||
class Award(BaseModel):
|
|
||||||
name = CharField()
|
|
||||||
season = IntegerField()
|
|
||||||
timing = CharField(default="In-Season")
|
|
||||||
card = ForeignKeyField(Card, null=True)
|
|
||||||
team = ForeignKeyField(Team, null=True)
|
|
||||||
image = CharField(null=True)
|
|
||||||
|
|
||||||
|
|
||||||
class Paperdex(BaseModel):
|
|
||||||
team = ForeignKeyField(Team)
|
|
||||||
player = ForeignKeyField(Player)
|
|
||||||
created = DateTimeField(default=datetime.now)
|
|
||||||
|
|
||||||
# def add_to_paperdex(self, team, cards: list):
|
|
||||||
# for x in players:
|
|
||||||
# if not isinstance(x, Card):
|
|
||||||
# raise TypeError(f'The Pokedex can only take a list of Player or Card objects')
|
|
||||||
#
|
|
||||||
# Paperdex.get_or_create(team=team, player=player)
|
|
||||||
|
|
||||||
|
|
||||||
class Reward(BaseModel):
|
|
||||||
name = CharField(null=True)
|
|
||||||
season = IntegerField()
|
|
||||||
week = IntegerField()
|
|
||||||
team = ForeignKeyField(Team)
|
|
||||||
created = DateTimeField()
|
|
||||||
|
|
||||||
|
|
||||||
class GameRewards(BaseModel):
|
|
||||||
name = CharField()
|
|
||||||
pack_type = ForeignKeyField(PackType, null=True)
|
|
||||||
player = ForeignKeyField(Player, null=True)
|
|
||||||
money = IntegerField(null=True)
|
|
||||||
|
|
||||||
|
|
||||||
class Notification(BaseModel):
|
|
||||||
created = DateTimeField()
|
|
||||||
title = CharField()
|
|
||||||
desc = CharField(null=True)
|
|
||||||
field_name = CharField()
|
|
||||||
message = CharField()
|
|
||||||
about = CharField() # f'{Topic}-{Object ID}'
|
|
||||||
ack = BooleanField(default=False)
|
|
||||||
|
|
||||||
|
|
||||||
class GauntletReward(BaseModel):
|
|
||||||
name = CharField()
|
|
||||||
gauntlet = ForeignKeyField(Event)
|
|
||||||
reward = ForeignKeyField(GameRewards)
|
|
||||||
win_num = IntegerField()
|
|
||||||
loss_max = IntegerField(default=1)
|
|
||||||
|
|
||||||
|
|
||||||
class GauntletRun(BaseModel):
|
|
||||||
team = ForeignKeyField(Team)
|
|
||||||
gauntlet = ForeignKeyField(Event)
|
|
||||||
wins = IntegerField(default=0)
|
|
||||||
losses = IntegerField(default=0)
|
|
||||||
gsheet = CharField(null=True)
|
|
||||||
created = DateTimeField(default=datetime.now)
|
|
||||||
ended = DateTimeField(null=True)
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables(
|
|
||||||
[
|
|
||||||
Roster,
|
|
||||||
BattingStat,
|
|
||||||
PitchingStat,
|
|
||||||
Result,
|
|
||||||
Award,
|
|
||||||
Paperdex,
|
|
||||||
Reward,
|
|
||||||
GameRewards,
|
|
||||||
Notification,
|
|
||||||
GauntletReward,
|
|
||||||
GauntletRun,
|
|
||||||
]
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
class BattingCard(BaseModel):
|
|
||||||
player = ForeignKeyField(Player)
|
|
||||||
variant = IntegerField()
|
|
||||||
steal_low = IntegerField()
|
|
||||||
steal_high = IntegerField()
|
|
||||||
steal_auto = BooleanField()
|
|
||||||
steal_jump = FloatField()
|
|
||||||
bunting = CharField()
|
|
||||||
hit_and_run = CharField()
|
|
||||||
running = IntegerField()
|
|
||||||
offense_col = IntegerField()
|
|
||||||
hand = CharField(default="R")
|
|
||||||
|
|
||||||
|
|
||||||
bc_index = ModelIndex(
|
|
||||||
BattingCard, (BattingCard.player, BattingCard.variant), unique=True
|
|
||||||
)
|
|
||||||
BattingCard.add_index(bc_index)
|
|
||||||
|
|
||||||
|
|
||||||
class BattingCardRatings(BaseModel):
|
|
||||||
battingcard = ForeignKeyField(BattingCard)
|
|
||||||
vs_hand = CharField(default="R")
|
|
||||||
pull_rate = FloatField()
|
|
||||||
center_rate = FloatField()
|
|
||||||
slap_rate = FloatField()
|
|
||||||
homerun = FloatField()
|
|
||||||
bp_homerun = FloatField()
|
|
||||||
triple = FloatField()
|
|
||||||
double_three = FloatField()
|
|
||||||
double_two = FloatField()
|
|
||||||
double_pull = FloatField()
|
|
||||||
single_two = FloatField()
|
|
||||||
single_one = FloatField()
|
|
||||||
single_center = FloatField()
|
|
||||||
bp_single = FloatField()
|
|
||||||
hbp = FloatField()
|
|
||||||
walk = FloatField()
|
|
||||||
strikeout = FloatField()
|
|
||||||
lineout = FloatField()
|
|
||||||
popout = FloatField()
|
|
||||||
flyout_a = FloatField()
|
|
||||||
flyout_bq = FloatField()
|
|
||||||
flyout_lf_b = FloatField()
|
|
||||||
flyout_rf_b = FloatField()
|
|
||||||
groundout_a = FloatField()
|
|
||||||
groundout_b = FloatField()
|
|
||||||
groundout_c = FloatField()
|
|
||||||
avg = FloatField(null=True)
|
|
||||||
obp = FloatField(null=True)
|
|
||||||
slg = FloatField(null=True)
|
|
||||||
|
|
||||||
|
|
||||||
bcr_index = ModelIndex(
|
|
||||||
BattingCardRatings,
|
|
||||||
(BattingCardRatings.battingcard, BattingCardRatings.vs_hand),
|
|
||||||
unique=True,
|
|
||||||
)
|
|
||||||
BattingCardRatings.add_index(bcr_index)
|
|
||||||
|
|
||||||
|
|
||||||
class PitchingCard(BaseModel):
|
|
||||||
player = ForeignKeyField(Player)
|
|
||||||
variant = IntegerField()
|
|
||||||
balk = IntegerField()
|
|
||||||
wild_pitch = IntegerField()
|
|
||||||
hold = IntegerField()
|
|
||||||
starter_rating = IntegerField()
|
|
||||||
relief_rating = IntegerField()
|
|
||||||
closer_rating = IntegerField(null=True)
|
|
||||||
batting = CharField(null=True)
|
|
||||||
offense_col = IntegerField()
|
|
||||||
hand = CharField(default="R")
|
|
||||||
|
|
||||||
|
|
||||||
pc_index = ModelIndex(
|
|
||||||
PitchingCard, (PitchingCard.player, PitchingCard.variant), unique=True
|
|
||||||
)
|
|
||||||
PitchingCard.add_index(pc_index)
|
|
||||||
|
|
||||||
|
|
||||||
class PitchingCardRatings(BaseModel):
|
|
||||||
pitchingcard = ForeignKeyField(PitchingCard)
|
|
||||||
vs_hand = CharField(default="R")
|
|
||||||
homerun = FloatField()
|
|
||||||
bp_homerun = FloatField()
|
|
||||||
triple = FloatField()
|
|
||||||
double_three = FloatField()
|
|
||||||
double_two = FloatField()
|
|
||||||
double_cf = FloatField()
|
|
||||||
single_two = FloatField()
|
|
||||||
single_one = FloatField()
|
|
||||||
single_center = FloatField()
|
|
||||||
bp_single = FloatField()
|
|
||||||
hbp = FloatField()
|
|
||||||
walk = FloatField()
|
|
||||||
strikeout = FloatField()
|
|
||||||
flyout_lf_b = FloatField()
|
|
||||||
flyout_cf_b = FloatField()
|
|
||||||
flyout_rf_b = FloatField()
|
|
||||||
groundout_a = FloatField()
|
|
||||||
groundout_b = FloatField()
|
|
||||||
xcheck_p = FloatField()
|
|
||||||
xcheck_c = FloatField()
|
|
||||||
xcheck_1b = FloatField()
|
|
||||||
xcheck_2b = FloatField()
|
|
||||||
xcheck_3b = FloatField()
|
|
||||||
xcheck_ss = FloatField()
|
|
||||||
xcheck_lf = FloatField()
|
|
||||||
xcheck_cf = FloatField()
|
|
||||||
xcheck_rf = FloatField()
|
|
||||||
avg = FloatField(null=True)
|
|
||||||
obp = FloatField(null=True)
|
|
||||||
slg = FloatField(null=True)
|
|
||||||
|
|
||||||
|
|
||||||
pcr_index = ModelIndex(
|
|
||||||
PitchingCardRatings,
|
|
||||||
(PitchingCardRatings.pitchingcard, PitchingCardRatings.vs_hand),
|
|
||||||
unique=True,
|
|
||||||
)
|
|
||||||
PitchingCardRatings.add_index(pcr_index)
|
|
||||||
|
|
||||||
|
|
||||||
class CardPosition(BaseModel):
|
|
||||||
player = ForeignKeyField(Player)
|
|
||||||
variant = IntegerField()
|
|
||||||
position = CharField()
|
|
||||||
innings = IntegerField()
|
|
||||||
range = IntegerField()
|
|
||||||
error = IntegerField()
|
|
||||||
arm = IntegerField(null=True)
|
|
||||||
pb = IntegerField(null=True)
|
|
||||||
overthrow = IntegerField(null=True)
|
|
||||||
|
|
||||||
|
|
||||||
pos_index = ModelIndex(
|
|
||||||
CardPosition,
|
|
||||||
(CardPosition.player, CardPosition.variant, CardPosition.position),
|
|
||||||
unique=True,
|
|
||||||
)
|
|
||||||
CardPosition.add_index(pos_index)
|
|
||||||
|
|
||||||
|
|
||||||
db.create_tables(
|
|
||||||
[BattingCard, BattingCardRatings, PitchingCard, PitchingCardRatings, CardPosition]
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
db.close()
|
|
||||||
|
|
||||||
# scout_db = SqliteDatabase(
|
|
||||||
# 'storage/card_creation.db',
|
|
||||||
# pragmas={
|
|
||||||
# 'journal_mode': 'wal',
|
|
||||||
# 'cache_size': -1 * 64000,
|
|
||||||
# 'synchronous': 0
|
|
||||||
# }
|
|
||||||
# )
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class BaseModelScout(Model):
|
|
||||||
# class Meta:
|
|
||||||
# database = scout_db
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class ScoutCardset(BaseModelScout):
|
|
||||||
# set_title = CharField()
|
|
||||||
# set_subtitle = CharField(null=True)
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class ScoutPlayer(BaseModelScout):
|
|
||||||
# sba_id = IntegerField(primary_key=True)
|
|
||||||
# name = CharField()
|
|
||||||
# fg_id = IntegerField()
|
|
||||||
# br_id = CharField()
|
|
||||||
# offense_col = IntegerField()
|
|
||||||
# hand = CharField(default='R')
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# scout_db.create_tables([ScoutCardset, ScoutPlayer])
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class BatterRatings(BaseModelScout):
|
|
||||||
# id = CharField(unique=True, primary_key=True)
|
|
||||||
# player = ForeignKeyField(ScoutPlayer)
|
|
||||||
# cardset = ForeignKeyField(ScoutCardset)
|
|
||||||
# vs_hand = FloatField()
|
|
||||||
# is_prep = BooleanField()
|
|
||||||
# homerun = FloatField()
|
|
||||||
# bp_homerun = FloatField()
|
|
||||||
# triple = FloatField()
|
|
||||||
# double_three = FloatField()
|
|
||||||
# double_two = FloatField()
|
|
||||||
# double_pull = FloatField()
|
|
||||||
# single_two = FloatField()
|
|
||||||
# single_one = FloatField()
|
|
||||||
# single_center = FloatField()
|
|
||||||
# bp_single = FloatField()
|
|
||||||
# hbp = FloatField()
|
|
||||||
# walk = FloatField()
|
|
||||||
# strikeout = FloatField()
|
|
||||||
# lineout = FloatField()
|
|
||||||
# popout = FloatField()
|
|
||||||
# flyout_a = FloatField()
|
|
||||||
# flyout_bq = FloatField()
|
|
||||||
# flyout_lf_b = FloatField()
|
|
||||||
# flyout_rf_b = FloatField()
|
|
||||||
# groundout_a = FloatField()
|
|
||||||
# groundout_b = FloatField()
|
|
||||||
# groundout_c = FloatField()
|
|
||||||
# avg = FloatField(null=True)
|
|
||||||
# obp = FloatField(null=True)
|
|
||||||
# slg = FloatField(null=True)
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class PitcherRatings(BaseModelScout):
|
|
||||||
# id = CharField(unique=True, primary_key=True)
|
|
||||||
# player = ForeignKeyField(ScoutPlayer)
|
|
||||||
# cardset = ForeignKeyField(ScoutCardset)
|
|
||||||
# vs_hand = CharField()
|
|
||||||
# is_prep = BooleanField()
|
|
||||||
# homerun = FloatField()
|
|
||||||
# bp_homerun = FloatField()
|
|
||||||
# triple = FloatField()
|
|
||||||
# double_three = FloatField()
|
|
||||||
# double_two = FloatField()
|
|
||||||
# double_cf = FloatField()
|
|
||||||
# single_two = FloatField()
|
|
||||||
# single_one = FloatField()
|
|
||||||
# single_center = FloatField()
|
|
||||||
# bp_single = FloatField()
|
|
||||||
# hbp = FloatField()
|
|
||||||
# walk = FloatField()
|
|
||||||
# strikeout = FloatField()
|
|
||||||
# fo_slap = FloatField()
|
|
||||||
# fo_center = FloatField()
|
|
||||||
# groundout_a = FloatField()
|
|
||||||
# groundout_b = FloatField()
|
|
||||||
# xcheck_p = FloatField()
|
|
||||||
# xcheck_c = FloatField()
|
|
||||||
# xcheck_1b = FloatField()
|
|
||||||
# xcheck_2b = FloatField()
|
|
||||||
# xcheck_3b = FloatField()
|
|
||||||
# xcheck_ss = FloatField()
|
|
||||||
# xcheck_lf = FloatField()
|
|
||||||
# xcheck_cf = FloatField()
|
|
||||||
# xcheck_rf = FloatField()
|
|
||||||
# avg = FloatField(null=True)
|
|
||||||
# obp = FloatField(null=True)
|
|
||||||
# slg = FloatField(null=True)
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# # scout_db.create_tables([BatterRatings, PitcherRatings])
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class CardColumns(BaseModelScout):
|
|
||||||
# id = CharField(unique=True, primary_key=True)
|
|
||||||
# player = ForeignKeyField(ScoutPlayer)
|
|
||||||
# hand = CharField()
|
|
||||||
# b_ratings = ForeignKeyField(BatterRatings, null=True)
|
|
||||||
# p_ratings = ForeignKeyField(PitcherRatings, null=True)
|
|
||||||
# one_dice = CharField()
|
|
||||||
# one_results = CharField()
|
|
||||||
# one_splits = CharField()
|
|
||||||
# two_dice = CharField()
|
|
||||||
# two_results = CharField()
|
|
||||||
# two_splits = CharField()
|
|
||||||
# three_dice = CharField()
|
|
||||||
# three_results = CharField()
|
|
||||||
# three_splits = CharField()
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class Position(BaseModelScout):
|
|
||||||
# player = ForeignKeyField(ScoutPlayer)
|
|
||||||
# cardset = ForeignKeyField(ScoutCardset)
|
|
||||||
# position = CharField()
|
|
||||||
# innings = IntegerField()
|
|
||||||
# range = IntegerField()
|
|
||||||
# error = IntegerField()
|
|
||||||
# arm = CharField(null=True)
|
|
||||||
# pb = IntegerField(null=True)
|
|
||||||
# overthrow = IntegerField(null=True)
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class BatterData(BaseModelScout):
|
|
||||||
# player = ForeignKeyField(ScoutPlayer)
|
|
||||||
# cardset = ForeignKeyField(ScoutCardset)
|
|
||||||
# stealing = CharField()
|
|
||||||
# st_low = IntegerField()
|
|
||||||
# st_high = IntegerField()
|
|
||||||
# st_auto = BooleanField()
|
|
||||||
# st_jump = FloatField()
|
|
||||||
# bunting = CharField(null=True)
|
|
||||||
# hit_and_run = CharField(null=True)
|
|
||||||
# running = CharField()
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class PitcherData(BaseModelScout):
|
|
||||||
# player = ForeignKeyField(ScoutPlayer)
|
|
||||||
# cardset = ForeignKeyField(ScoutCardset)
|
|
||||||
# balk = IntegerField(null=True)
|
|
||||||
# wild_pitch = IntegerField(null=True)
|
|
||||||
# hold = CharField()
|
|
||||||
# starter_rating = IntegerField()
|
|
||||||
# relief_rating = IntegerField()
|
|
||||||
# closer_rating = IntegerField(null=True)
|
|
||||||
# batting = CharField(null=True)
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# scout_db.create_tables([CardColumns, Position, BatterData, PitcherData])
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# class CardOutput(BaseModelScout):
|
|
||||||
# name = CharField()
|
|
||||||
# hand = CharField()
|
|
||||||
# positions = CharField()
|
|
||||||
# stealing = CharField()
|
|
||||||
# bunting = CharField()
|
|
||||||
# hitandrun = CharField()
|
|
||||||
# running = CharField()
|
|
||||||
#
|
|
||||||
#
|
|
||||||
# scout_db.close()
|
|
||||||
@ -1,50 +0,0 @@
|
|||||||
from playhouse.migrate import *
|
|
||||||
import db_engine
|
|
||||||
|
|
||||||
# Automatically select correct migrator based on database type
|
|
||||||
if hasattr(db_engine.db, '__class__') and 'Postgres' in db_engine.db.__class__.__name__:
|
|
||||||
migrator = PostgresqlMigrator(db_engine.db)
|
|
||||||
else:
|
|
||||||
migrator = SqliteMigrator(db_engine.db)
|
|
||||||
|
|
||||||
# db_engine.db.create_tables([db_engine.PackTheme])
|
|
||||||
|
|
||||||
# pubdate_field = DateTimeField(null=True)
|
|
||||||
# comment_field = TextField(default='')
|
|
||||||
|
|
||||||
|
|
||||||
# pitcher_injury = IntegerField(null=True)
|
|
||||||
# offense_col = IntegerField(null=True)
|
|
||||||
# pos_2 = CharField(null=True)
|
|
||||||
# last_game = CharField(null=True)
|
|
||||||
# game_type = CharField(null=True)
|
|
||||||
mlb_player = ForeignKeyField(db_engine.MlbPlayer, field=db_engine.MlbPlayer.id, null=True)
|
|
||||||
result = ForeignKeyField(db_engine.Result, field=db_engine.Result.id, null=True)
|
|
||||||
# active_theme = ForeignKeyField(PackTheme, to_field='id', field_type=int, null=True)
|
|
||||||
# active_theme = ForeignKeyField(db_engine.PackTheme, field=db_engine.PackTheme.id, null=True) # for careers
|
|
||||||
# game_type = CharField(null=True)
|
|
||||||
# pack_team = ForeignKeyField(db_engine.Team, field=db_engine.Team.id, null=True)
|
|
||||||
# pack_cardset = ForeignKeyField(db_engine.Cardset, field=db_engine.Cardset.id, null=True)
|
|
||||||
pull_rate = FloatField(default=0.333)
|
|
||||||
|
|
||||||
migrate(
|
|
||||||
# migrator.add_column('current', 'active_theme_id', active_theme),
|
|
||||||
# migrator.add_column('pack', 'pack_team_id', pack_team),
|
|
||||||
# migrator.add_column('player', 'mlbplayer_id', mlb_player),
|
|
||||||
migrator.add_column('battingstat', 'result_id', result),
|
|
||||||
migrator.add_column('pitchingstat', 'result_id', result),
|
|
||||||
# migrator.add_column('battingcardratings', 'pull_rate', pull_rate),
|
|
||||||
# migrator.rename_column('cardset', 'available', 'for_purchase')
|
|
||||||
# migrator.add_column('player', 'offense_col', offense_col),
|
|
||||||
# migrator.add_column('comment_tbl', 'comment', comment_field),
|
|
||||||
# migrator.rename_column('story', 'pub_date', 'publish_date'),
|
|
||||||
# migrator.drop_column('story', 'some_old_field'),
|
|
||||||
# migrator.drop_not_null('team', 'abbrev'),
|
|
||||||
# migrator.add_not_null('story', 'modified_date'),
|
|
||||||
# migrator.rename_table('story', 'stories_tbl'),
|
|
||||||
# migrator.drop_index('team', 'team_abbrev'),
|
|
||||||
# migrator.drop_index('player', 'player_name')
|
|
||||||
# migrator.add_column('pack', 'pack_type', pack_type),
|
|
||||||
)
|
|
||||||
|
|
||||||
db_engine.db.close()
|
|
||||||
@ -1,104 +0,0 @@
|
|||||||
-- Migration: Normalize Player.franchise to city-agnostic values
|
|
||||||
-- Date: 2026-01-07
|
|
||||||
-- Purpose: Enable cross-era player matching for AI rosters by normalizing
|
|
||||||
-- franchise values to match Team.sname (e.g., 'Oakland Athletics' -> 'Athletics')
|
|
||||||
--
|
|
||||||
-- IMPORTANT: Backup database before running!
|
|
||||||
-- Run on dev first, verify with: SELECT DISTINCT franchise FROM player ORDER BY franchise;
|
|
||||||
-- Then run on prod.
|
|
||||||
--
|
|
||||||
-- Rollback: See inverse statements at bottom of file
|
|
||||||
|
|
||||||
-- ============================================
|
|
||||||
-- FORWARD MIGRATION: Normalize franchise values
|
|
||||||
-- ============================================
|
|
||||||
|
|
||||||
-- National League West
|
|
||||||
UPDATE player SET franchise = 'Diamondbacks' WHERE franchise = 'Arizona Diamondbacks';
|
|
||||||
UPDATE player SET franchise = 'Rockies' WHERE franchise = 'Colorado Rockies';
|
|
||||||
UPDATE player SET franchise = 'Dodgers' WHERE franchise = 'Los Angeles Dodgers';
|
|
||||||
UPDATE player SET franchise = 'Padres' WHERE franchise = 'San Diego Padres';
|
|
||||||
UPDATE player SET franchise = 'Giants' WHERE franchise = 'San Francisco Giants';
|
|
||||||
|
|
||||||
-- National League Central
|
|
||||||
UPDATE player SET franchise = 'Cubs' WHERE franchise = 'Chicago Cubs';
|
|
||||||
UPDATE player SET franchise = 'Reds' WHERE franchise = 'Cincinnati Reds';
|
|
||||||
UPDATE player SET franchise = 'Brewers' WHERE franchise = 'Milwaukee Brewers';
|
|
||||||
UPDATE player SET franchise = 'Pirates' WHERE franchise = 'Pittsburgh Pirates';
|
|
||||||
UPDATE player SET franchise = 'Cardinals' WHERE franchise IN ('St Louis Cardinals', 'St. Louis Cardinals');
|
|
||||||
|
|
||||||
-- National League East
|
|
||||||
UPDATE player SET franchise = 'Braves' WHERE franchise = 'Atlanta Braves';
|
|
||||||
UPDATE player SET franchise = 'Marlins' WHERE franchise = 'Miami Marlins';
|
|
||||||
UPDATE player SET franchise = 'Mets' WHERE franchise = 'New York Mets';
|
|
||||||
UPDATE player SET franchise = 'Phillies' WHERE franchise = 'Philadelphia Phillies';
|
|
||||||
UPDATE player SET franchise = 'Nationals' WHERE franchise = 'Washington Nationals';
|
|
||||||
|
|
||||||
-- American League West
|
|
||||||
UPDATE player SET franchise = 'Astros' WHERE franchise = 'Houston Astros';
|
|
||||||
UPDATE player SET franchise = 'Angels' WHERE franchise = 'Los Angeles Angels';
|
|
||||||
UPDATE player SET franchise = 'Athletics' WHERE franchise = 'Oakland Athletics';
|
|
||||||
UPDATE player SET franchise = 'Mariners' WHERE franchise = 'Seattle Mariners';
|
|
||||||
UPDATE player SET franchise = 'Rangers' WHERE franchise = 'Texas Rangers';
|
|
||||||
|
|
||||||
-- American League Central
|
|
||||||
UPDATE player SET franchise = 'White Sox' WHERE franchise = 'Chicago White Sox';
|
|
||||||
UPDATE player SET franchise = 'Guardians' WHERE franchise = 'Cleveland Guardians';
|
|
||||||
UPDATE player SET franchise = 'Tigers' WHERE franchise = 'Detroit Tigers';
|
|
||||||
UPDATE player SET franchise = 'Royals' WHERE franchise = 'Kansas City Royals';
|
|
||||||
UPDATE player SET franchise = 'Twins' WHERE franchise = 'Minnesota Twins';
|
|
||||||
|
|
||||||
-- American League East
|
|
||||||
UPDATE player SET franchise = 'Orioles' WHERE franchise = 'Baltimore Orioles';
|
|
||||||
UPDATE player SET franchise = 'Red Sox' WHERE franchise = 'Boston Red Sox';
|
|
||||||
UPDATE player SET franchise = 'Yankees' WHERE franchise = 'New York Yankees';
|
|
||||||
UPDATE player SET franchise = 'Rays' WHERE franchise = 'Tampa Bay Rays';
|
|
||||||
UPDATE player SET franchise = 'Blue Jays' WHERE franchise = 'Toronto Blue Jays';
|
|
||||||
|
|
||||||
-- ============================================
|
|
||||||
-- VERIFICATION QUERY
|
|
||||||
-- ============================================
|
|
||||||
-- Run after migration to verify all 30 teams have correct values:
|
|
||||||
-- SELECT DISTINCT franchise FROM player ORDER BY franchise;
|
|
||||||
--
|
|
||||||
-- Expected output (30 city-agnostic franchise names):
|
|
||||||
-- Angels, Athletics, Blue Jays, Braves, Brewers, Cardinals, Cubs,
|
|
||||||
-- Diamondbacks, Dodgers, Giants, Guardians, Mariners, Marlins, Mets,
|
|
||||||
-- Nationals, Orioles, Padres, Phillies, Pirates, Rangers, Rays,
|
|
||||||
-- Red Sox, Reds, Rockies, Royals, Tigers, Twins, White Sox, Yankees
|
|
||||||
|
|
||||||
-- ============================================
|
|
||||||
-- ROLLBACK MIGRATION (if needed)
|
|
||||||
-- ============================================
|
|
||||||
-- Use these statements to revert to original values:
|
|
||||||
--
|
|
||||||
-- UPDATE player SET franchise = 'Arizona Diamondbacks' WHERE franchise = 'Diamondbacks' AND mlbclub LIKE '%Arizona%';
|
|
||||||
-- UPDATE player SET franchise = 'Atlanta Braves' WHERE franchise = 'Braves' AND mlbclub LIKE '%Atlanta%';
|
|
||||||
-- UPDATE player SET franchise = 'Baltimore Orioles' WHERE franchise = 'Orioles' AND mlbclub LIKE '%Baltimore%';
|
|
||||||
-- UPDATE player SET franchise = 'Boston Red Sox' WHERE franchise = 'Red Sox' AND mlbclub LIKE '%Boston%';
|
|
||||||
-- UPDATE player SET franchise = 'Chicago Cubs' WHERE franchise = 'Cubs' AND mlbclub LIKE '%Chicago%';
|
|
||||||
-- UPDATE player SET franchise = 'Chicago White Sox' WHERE franchise = 'White Sox' AND mlbclub LIKE '%Chicago%';
|
|
||||||
-- UPDATE player SET franchise = 'Cincinnati Reds' WHERE franchise = 'Reds' AND mlbclub LIKE '%Cincinnati%';
|
|
||||||
-- UPDATE player SET franchise = 'Cleveland Guardians' WHERE franchise = 'Guardians' AND mlbclub LIKE '%Cleveland%';
|
|
||||||
-- UPDATE player SET franchise = 'Colorado Rockies' WHERE franchise = 'Rockies' AND mlbclub LIKE '%Colorado%';
|
|
||||||
-- UPDATE player SET franchise = 'Detroit Tigers' WHERE franchise = 'Tigers' AND mlbclub LIKE '%Detroit%';
|
|
||||||
-- UPDATE player SET franchise = 'Houston Astros' WHERE franchise = 'Astros' AND mlbclub LIKE '%Houston%';
|
|
||||||
-- UPDATE player SET franchise = 'Kansas City Royals' WHERE franchise = 'Royals' AND mlbclub LIKE '%Kansas%';
|
|
||||||
-- UPDATE player SET franchise = 'Los Angeles Angels' WHERE franchise = 'Angels' AND mlbclub LIKE '%Los Angeles%' AND mlbclub NOT LIKE '%Dodgers%';
|
|
||||||
-- UPDATE player SET franchise = 'Los Angeles Dodgers' WHERE franchise = 'Dodgers' AND mlbclub LIKE '%Los Angeles%';
|
|
||||||
-- UPDATE player SET franchise = 'Miami Marlins' WHERE franchise = 'Marlins' AND mlbclub LIKE '%Miami%';
|
|
||||||
-- UPDATE player SET franchise = 'Milwaukee Brewers' WHERE franchise = 'Brewers' AND mlbclub LIKE '%Milwaukee%';
|
|
||||||
-- UPDATE player SET franchise = 'Minnesota Twins' WHERE franchise = 'Twins' AND mlbclub LIKE '%Minnesota%';
|
|
||||||
-- UPDATE player SET franchise = 'New York Mets' WHERE franchise = 'Mets' AND mlbclub LIKE '%New York%';
|
|
||||||
-- UPDATE player SET franchise = 'New York Yankees' WHERE franchise = 'Yankees' AND mlbclub LIKE '%New York%';
|
|
||||||
-- UPDATE player SET franchise = 'Oakland Athletics' WHERE franchise = 'Athletics' AND mlbclub LIKE '%Oakland%';
|
|
||||||
-- UPDATE player SET franchise = 'Philadelphia Phillies' WHERE franchise = 'Phillies' AND mlbclub LIKE '%Philadelphia%';
|
|
||||||
-- UPDATE player SET franchise = 'Pittsburgh Pirates' WHERE franchise = 'Pirates' AND mlbclub LIKE '%Pittsburgh%';
|
|
||||||
-- UPDATE player SET franchise = 'San Diego Padres' WHERE franchise = 'Padres' AND mlbclub LIKE '%San Diego%';
|
|
||||||
-- UPDATE player SET franchise = 'San Francisco Giants' WHERE franchise = 'Giants' AND mlbclub LIKE '%San Francisco%';
|
|
||||||
-- UPDATE player SET franchise = 'Seattle Mariners' WHERE franchise = 'Mariners' AND mlbclub LIKE '%Seattle%';
|
|
||||||
-- UPDATE player SET franchise = 'St Louis Cardinals' WHERE franchise = 'Cardinals' AND mlbclub LIKE '%St%Louis%';
|
|
||||||
-- UPDATE player SET franchise = 'Tampa Bay Rays' WHERE franchise = 'Rays' AND mlbclub LIKE '%Tampa%';
|
|
||||||
-- UPDATE player SET franchise = 'Texas Rangers' WHERE franchise = 'Rangers' AND mlbclub LIKE '%Texas%';
|
|
||||||
-- UPDATE player SET franchise = 'Toronto Blue Jays' WHERE franchise = 'Blue Jays' AND mlbclub LIKE '%Toronto%';
|
|
||||||
-- UPDATE player SET franchise = 'Washington Nationals' WHERE franchise = 'Nationals' AND mlbclub LIKE '%Washington%';
|
|
||||||
156
sheets.py
156
sheets.py
@ -1,156 +0,0 @@
|
|||||||
import logging
|
|
||||||
from db_engine import Player, Card, Team, Cardset
|
|
||||||
|
|
||||||
|
|
||||||
PD_SHEET_KEY = '1xqPOrJIjdUWfDSFNnUiecRgo8DDKFKk2Pf1iQ4pTREM'
|
|
||||||
|
|
||||||
|
|
||||||
def send_to_sheets(sheets, sheet_key: str, worksheet_title: str, data_list: list, data_range: str):
|
|
||||||
this_sheet = sheets.open_by_key(sheet_key)
|
|
||||||
this_ws = this_sheet.worksheet_by_title(worksheet_title)
|
|
||||||
this_ws.update_values(
|
|
||||||
crange=data_range,
|
|
||||||
values=data_list
|
|
||||||
)
|
|
||||||
return this_sheet
|
|
||||||
|
|
||||||
|
|
||||||
def update_all_players(sheets):
|
|
||||||
player_list = Player.select()
|
|
||||||
logging.debug(f'send to sheets player_list: {player_list}')
|
|
||||||
player_data = []
|
|
||||||
for x in player_list:
|
|
||||||
player_data.append(
|
|
||||||
[
|
|
||||||
x.player_id, x.p_name, x.cost, x.image,
|
|
||||||
x.image2, x.mlbclub, x.franchise,
|
|
||||||
x.cardset.name, x.rarity.name, x.pos_1, x.pos_2,
|
|
||||||
x.pos_3, x.pos_4, x.pos_5, x.pos_6,
|
|
||||||
x.pos_7, x.pos_8, x.headshot, x.vanity_card,
|
|
||||||
x.strat_code, x.bbref_id,
|
|
||||||
x.description, x.cardset.for_purchase, x.cardset.in_packs
|
|
||||||
]
|
|
||||||
)
|
|
||||||
|
|
||||||
return send_to_sheets(
|
|
||||||
sheets,
|
|
||||||
sheet_key=PD_SHEET_KEY,
|
|
||||||
worksheet_title='All Players',
|
|
||||||
data_list=player_data,
|
|
||||||
data_range='A2'
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def send_ai_cards(sheets):
|
|
||||||
card_list = Card.select().join(Team).where(Card.team.is_ai)
|
|
||||||
logging.debug(f'send to sheets card_list: {card_list}')
|
|
||||||
card_data = []
|
|
||||||
|
|
||||||
for x in card_list:
|
|
||||||
card_data.append([
|
|
||||||
x.player.cardset.name, x.player.p_name, x.player.rarity.name, x.player.image, x.player.image2,
|
|
||||||
x.player.pos_1,
|
|
||||||
x.player.pos_2, x.player.pos_3, x.player.pos_4, x.player.pos_5, x.player.pos_6, x.player.pos_7,
|
|
||||||
x.player.pos_8, x.player.cost, x.player.mlbclub, x.player.franchise, x.player.set_num, x.player.bbref_id,
|
|
||||||
x.player_id, x.id, x.team.id
|
|
||||||
])
|
|
||||||
|
|
||||||
return send_to_sheets(
|
|
||||||
sheets,
|
|
||||||
sheet_key=PD_SHEET_KEY,
|
|
||||||
worksheet_title='AI Cards',
|
|
||||||
data_list=card_data,
|
|
||||||
data_range='A2'
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def post_new_cards(sheets, starting_id: int):
|
|
||||||
card_list = Card.select().where(Card.id >= starting_id)
|
|
||||||
logging.debug(f'post_new_cards to sheets card_list: {card_list}')
|
|
||||||
card_data = []
|
|
||||||
|
|
||||||
count = starting_id
|
|
||||||
for x in card_list:
|
|
||||||
while count < x.id:
|
|
||||||
card_data.append(['', '', '', '', ''])
|
|
||||||
count += 1
|
|
||||||
|
|
||||||
card_data.append([
|
|
||||||
x.player.cardset.name, x.player.p_name, x.player.rarity.name, x.player.image, x.player.image2,
|
|
||||||
x.player.pos_1,
|
|
||||||
x.player.pos_2, x.player.pos_3, x.player.pos_4, x.player.pos_5, x.player.pos_6, x.player.pos_7,
|
|
||||||
x.player.pos_8, x.player.cost, x.player.mlbclub, x.player.franchise, x.player.set_num, x.player.bbref_id,
|
|
||||||
x.player_id, x.id, x.team.id
|
|
||||||
])
|
|
||||||
count += 1
|
|
||||||
|
|
||||||
return send_to_sheets(
|
|
||||||
sheets,
|
|
||||||
sheet_key=PD_SHEET_KEY,
|
|
||||||
worksheet_title='All Cards',
|
|
||||||
data_list=card_data,
|
|
||||||
data_range=f'A{starting_id + 1}'
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def post_deletion(sheets, del_ids: list):
|
|
||||||
del_data = []
|
|
||||||
deletion_ids = [int(x) for x in del_ids]
|
|
||||||
deletion_ids.sort()
|
|
||||||
logging.info(f'sorted: {deletion_ids}')
|
|
||||||
|
|
||||||
x = deletion_ids[0]
|
|
||||||
while x <= deletion_ids[-1]:
|
|
||||||
if x in deletion_ids:
|
|
||||||
del_data.append(['TRUE'])
|
|
||||||
else:
|
|
||||||
del_data.append([''])
|
|
||||||
x += 1
|
|
||||||
|
|
||||||
return send_to_sheets(
|
|
||||||
sheets,
|
|
||||||
sheet_key=PD_SHEET_KEY,
|
|
||||||
worksheet_title='All Cards',
|
|
||||||
data_list=del_data,
|
|
||||||
data_range=f'V{deletion_ids[0] + 1}'
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
# def update_one_player(sheets, this_player):
|
|
||||||
# logging.debug(f'send to sheets this_player: {this_player}')
|
|
||||||
# player_data = [[
|
|
||||||
# this_player['player_id'], this_player['p_name'], this_player['cost'], this_player['image'],
|
|
||||||
# this_player['image2'], this_player['mlbclub'], this_player['franchise'],
|
|
||||||
# this_player['cardset']['name'], this_player['rarity']['name'], this_player['pos_1'], this_player['pos_2'],
|
|
||||||
# this_player['pos_3'], this_player['pos_4'], this_player['pos_5'], this_player['pos_6'],
|
|
||||||
# this_player['pos_7'], this_player['pos_8'], this_player['headshot'], this_player['vanity_card'],
|
|
||||||
# this_player['strat_code'], this_player['bbref_id'],
|
|
||||||
# this_player['description'], this_player['cardset']['for_purchase'], this_player['cardset']['in_packs']
|
|
||||||
# ]]
|
|
||||||
#
|
|
||||||
# return send_to_sheets(
|
|
||||||
# sheets,
|
|
||||||
# sheet_key=PD_SHEET_KEY,
|
|
||||||
# worksheet_title='All Cards',
|
|
||||||
# data_list=player_data,
|
|
||||||
# data_range=f'A{this_player["player_id"] + 1}'
|
|
||||||
# )
|
|
||||||
|
|
||||||
|
|
||||||
# def update_many_players(sheets, player_list):
|
|
||||||
# logging.debug(f'send to sheets player_list: {player_list}')
|
|
||||||
# player_data = []
|
|
||||||
# for x in player_list:
|
|
||||||
# player_data.append(
|
|
||||||
# [
|
|
||||||
# x['player_id'], x['p_name'], x['cost'], x['image'],
|
|
||||||
# x['image2'], x['mlbclub'], x['franchise'],
|
|
||||||
# x['cardset']['name'], x['rarity']['name'], x['pos_1'], x['pos_2'],
|
|
||||||
# x['pos_3'], x['pos_4'], x['pos_5'], x['pos_6'],
|
|
||||||
# x['pos_7'], x['pos_8'], x['headshot'], x['vanity_card'],
|
|
||||||
# x['strat_code'], x['bbref_id'],
|
|
||||||
# x['description'], x['cardset']['for_purchase'], x['cardset']['in_packs']
|
|
||||||
# ]
|
|
||||||
# )
|
|
||||||
#
|
|
||||||
#
|
|
||||||
Loading…
Reference in New Issue
Block a user