Skip to content

Commit

Permalink
OpenAPI metadata updates (#13)
Browse files Browse the repository at this point in the history
* v1.0.2

* fully switched to beanie

* update pyproject.toml

* versioning hatch scripts

* commit message with release bump

* OpenAPI metadata updates
  • Loading branch information
peterrauscher authored Feb 28, 2024
1 parent 6fa2ea9 commit 67d2038
Show file tree
Hide file tree
Showing 9 changed files with 114 additions and 126 deletions.
38 changes: 38 additions & 0 deletions bump-release.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
# updates the version number in the __about__.py file
import subprocess


def update_version(version_type):
with open("src/api/__about__.py", "r") as f:
version = f.read().split("=")[1].replace('"', "").strip()
patch_version = version.split(".")[2]
minor_version = version.split(".")[1]
major_version = version.split(".")[0]
if version_type == "major":
major_version = str(int(major_version) + 1)
minor_version = "0"
patch_version = "0"
elif version_type == "minor":
minor_version = str(int(minor_version) + 1)
patch_version = "0"
elif version_type == "patch":
patch_version = str(int(patch_version) + 1)
else:
raise ValueError("Invalid version type. Please use major, minor, or patch.")
with open("src/api/__about__.py", "w") as f:
new_version = f"{major_version}.{minor_version}.{patch_version}"
f.write(f'__version__ = "{new_version}"\n')
return f"v{new_version}"


# passes the command line argument to the function
if __name__ == "__main__":
import sys

new_version = update_version(sys.argv[1])
message = input(f"Version updated to {new_version}. Enter commit message: \n")
subprocess.run(["git", "add", "."])
subprocess.run(["git", "commit", "-m", message.strip()])
subprocess.run(["git", "push"])
subprocess.run(["git", "tag", "-a", new_version, "-m", message.strip()])
subprocess.run(["git", "push", "origin", new_version])
7 changes: 3 additions & 4 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,9 @@ allow-direct-references = true

[tool.hatch.envs.default.scripts]
start = "python -m src.api.main"

[tool.hatch.envs.dev]
pre-install-commands = ["pip install -e ../core"]
scripts.start = "python -m src.api.main"
patch = "python bump-release.py patch"
minor = "python bump-release.py minor"
major = "python bump-release.py major"

[tool.hatch.build.targets.wheel]
packages = ["src/api"]
Expand Down
2 changes: 1 addition & 1 deletion src/api/__about__.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
__version__ = "1.0.1"
__version__ = "1.0.4"
10 changes: 10 additions & 0 deletions src/api/data/models.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,15 @@
from enum import Enum

from beanie import Document


class Token(Document):
type: str
token: str

class Settings:
collection = "OAuth"


class SortKey(str, Enum):
BRAND = "brand"
Expand Down
99 changes: 0 additions & 99 deletions src/api/data/queries.py

This file was deleted.

20 changes: 18 additions & 2 deletions src/api/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,20 +6,36 @@
load_dotenv(os.path.join(os.getcwd(), ".env"))

from beanie import init_beanie
from core.models.shoes import Sneaker
from fastapi import FastAPI
from mangum import Mangum
from starlette.middleware.sessions import SessionMiddleware

from api.data.instance import DATABASE_NAME, client
from api.routes import auth, sneakers
from core.models.shoes import Sneaker

desc = """
# SoleSearch
## The sneaker reseller's Bloomberg Terminal
### 👟 Find product information, from every brand, fast.
### 📅 Never miss another release date.
### 💵 Never buy bricks. Stay ahead of the game with our comprehensive price history and trends.
"""

app = FastAPI(
redoc_url=None,
title="SoleSearch",
summary="The sneaker reseller's Bloomberg Terminal.",
version=api.__about__.__version__,
contact={
"name": "SoleSearch Developer Support",
"email": "[email protected]"
},
description=desc,
responses={404: {"description": "Not found"}},
)

app.add_middleware(SessionMiddleware, secret_key="some secret key here")
app.add_middleware(SessionMiddleware, secret_key="vT!y!r5s#bwcDxDG")


@app.on_event("startup")
Expand Down
9 changes: 7 additions & 2 deletions src/api/routes/auth.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
from fastapi import APIRouter, HTTPException, Request
from fastapi.responses import RedirectResponse

from api.data.queries import update_tokens
from api.data.models import Token

STOCKX_CLIENT_ID = os.environ.get("SOLESEARCH_STOCKX_CLIENT_ID", None)
STOCKX_CLIENT_SECRET = os.environ.get("SOLESEARCH_STOCKX_CLIENT_SECRET", None)
Expand Down Expand Up @@ -62,7 +62,12 @@ async def stockx_oauth_callback(state: str, code: str, request: Request):
headers=headers,
)
).json()
await update_tokens(tokens)
for token_type in ["id_token", "access_token", "refresh_token"]:
if token_type in tokens:
await Token.find_one(Token.type == token_type).set(
{"$set": {"token": tokens[token_type]}}
)
logging.info(f"Updated {token_type}")
return tokens
except Exception as e:
logging.error(e)
Expand Down
Empty file removed src/api/routes/pricing.py
Empty file.
55 changes: 37 additions & 18 deletions src/api/routes/sneakers.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
from datetime import UTC, datetime
from typing import Annotated

from core.models.details import Audience
from core.models.shoes import Sneaker
from fastapi import APIRouter, HTTPException, Query

from api.data.instance import DEFAULT_LIMIT, DEFAULT_OFFSET
from api.data.models import SortKey, SortOrder
from api.data.queries import find_sneakers
from core.models.details import Audience
from core.models.shoes import Sneaker

router = APIRouter(
prefix="/sneakers",
Expand All @@ -16,30 +16,49 @@
@router.get("/")
async def get_sneakers(
brand: str | None = None,
sku: str | None = None,
name: str | None = None,
colorway: str | None = None,
audience: Audience | None = None,
releaseDate: str | None = None,
released: bool | None = None,
sort: SortKey = SortKey.RELEASE_DATE,
sortOrder: SortOrder = SortOrder.DESCENDING,
order: SortOrder = SortOrder.DESCENDING,
offset: Annotated[int, Query(gte=DEFAULT_OFFSET)] = DEFAULT_OFFSET,
limit: Annotated[int, Query(gte=1, lte=100)] = DEFAULT_LIMIT,
):
return await find_sneakers(
brand=brand,
sku=sku,
name=name,
colorway=colorway,
audience=audience,
release_date=releaseDate,
released=released,
sort_by=sort,
sort_order=sortOrder,
offset=offset,
limit=limit,
query = Sneaker.find()
if brand:
query = query.find(Sneaker.brand == brand)
if name:
query = query.find(Sneaker.name == name)
if audience:
query = query.find(Sneaker.audience == audience)
if released is not None:
now = datetime.now(UTC)
if released:
query = query.find(Sneaker.releaseDate <= now)
else:
query = query.find(Sneaker.releaseDate > now)
elif releaseDate:
if ":" in releaseDate:
inequality_operator, date_str = releaseDate.split(":")
date_obj = datetime.strptime(date_str, "%Y-%m-%d")
if inequality_operator == "lt":
query = query.find(Sneaker.releaseDate < date_obj)
elif inequality_operator == "lte":
query = query.find(Sneaker.releaseDate <= date_obj)
elif inequality_operator == "gt":
query = query.find(Sneaker.releaseDate > date_obj)
elif inequality_operator == "gte":
query = query.find(Sneaker.releaseDate >= date_obj)
else:
date_obj = datetime.strptime(releaseDate, "%Y-%m-%d")
query = query.find(Sneaker.releaseDate == date_obj)

order = "+" if order == SortOrder.ASCENDING else "-"
sneakers_list = (
await query.sort(f"{order}{sort.value}").skip(offset).limit(limit).to_list()
)
return sneakers_list


@router.get("/{product_id}")
Expand Down

0 comments on commit 67d2038

Please sign in to comment.