This commit is contained in:
Waylon Walker 2023-06-27 16:19:32 -05:00
parent 3490305e39
commit d747299c95
No known key found for this signature in database
GPG key ID: 66E2BF2B4190EFE4
8 changed files with 64 additions and 49 deletions

View file

@ -4,9 +4,9 @@ WORKDIR /app
Copy pyproject.toml /app Copy pyproject.toml /app
COPY learn_sql_model/__about__.py /app/learn_sql_model/__about__.py COPY learn_sql_model/__about__.py /app/learn_sql_model/__about__.py
COPY README.md /app COPY README.md /app
RUN pip3 install '.[api]' RUN pip3 install '.[all]'
COPY . /app COPY . /app
RUN pip3 install '.[api]' RUN pip3 install '.[all]'
EXPOSE 5000 EXPOSE 5000

View file

@ -8,13 +8,13 @@ hero_router = APIRouter()
@hero_router.on_event("startup") @hero_router.on_event("startup")
def on_startup() -> None: async def on_startup() -> None:
# SQLModel.metadata.create_all(get_config().database.engine) # SQLModel.metadata.create_all(get_config().database.engine)
... ...
@hero_router.get("/hero/{hero_id}") @hero_router.get("/hero/{hero_id}")
def get_hero( async def get_hero(
*, *,
session: Session = Depends(get_session), session: Session = Depends(get_session),
hero_id: int, hero_id: int,
@ -27,7 +27,7 @@ def get_hero(
@hero_router.post("/hero/") @hero_router.post("/hero/")
def post_hero( async def post_hero(
*, *,
session: Session = Depends(get_session), session: Session = Depends(get_session),
hero: HeroCreate, hero: HeroCreate,
@ -42,7 +42,7 @@ def post_hero(
@hero_router.patch("/hero/") @hero_router.patch("/hero/")
def patch_hero( async def patch_hero(
*, *,
session: Session = Depends(get_session), session: Session = Depends(get_session),
hero: HeroUpdate, hero: HeroUpdate,
@ -61,7 +61,7 @@ def patch_hero(
@hero_router.delete("/hero/{hero_id}") @hero_router.delete("/hero/{hero_id}")
def delete_hero( async def delete_hero(
*, *,
session: Session = Depends(get_session), session: Session = Depends(get_session),
hero_id: int, hero_id: int,
@ -77,11 +77,11 @@ def delete_hero(
@hero_router.get("/heros/") @hero_router.get("/heros/")
def get_heros( async def get_heros(
*, *,
session: Session = Depends(get_session), session: Session = Depends(get_session),
) -> Heros: ) -> Heros:
"get all heros" "get all heros"
statement = select(Hero) statement = select(Hero)
heros = session.exec(statement).all() heros = session.execute(statement).all()
return Heros(__root__=heros) return Heros(__root__=heros)

View file

@ -29,6 +29,8 @@ def run(
help="show the log messages", help="show the log messages",
), ),
): ):
import uvicorn
uvicorn.run(**get_config().api_server.dict()) uvicorn.run(**get_config().api_server.dict())

View file

@ -54,7 +54,7 @@ def list() -> Union[Hero, List[Hero]]:
def clear() -> Union[Hero, List[Hero]]: def clear() -> Union[Hero, List[Hero]]:
"list many heros" "list many heros"
heros = Heros.list() heros = Heros.list()
for hero in heros.heros: for hero in heros.__root__:
HeroDelete.delete(id=hero.id) HeroDelete.delete(id=hero.id)
return hero return hero

View file

@ -4,6 +4,7 @@ from typing import TYPE_CHECKING
from fastapi import Depends from fastapi import Depends
from pydantic import BaseModel, BaseSettings, validator from pydantic import BaseModel, BaseSettings, validator
from sqlalchemy import create_engine from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
from sqlmodel import Session from sqlmodel import Session
from learn_sql_model.standard_config import load from learn_sql_model.standard_config import load
@ -18,6 +19,7 @@ class ApiServer(BaseModel):
reload: bool = True reload: bool = True
log_level: str = "info" log_level: str = "info"
host: str = "0.0.0.0" host: str = "0.0.0.0"
workers: int = 1
class ApiClient(BaseModel): class ApiClient(BaseModel):
@ -42,7 +44,16 @@ class Database:
@property @property
def engine(self) -> "Engine": def engine(self) -> "Engine":
return create_engine(self.config.database_url) try:
return self._engine
except AttributeError:
self._engine = create_engine(
self.config.database_url,
connect_args={"check_same_thread": False},
pool_recycle=3600,
pool_pre_ping=True,
)
return self._engine
@property @property
def session(self) -> "Session": def session(self) -> "Session":
@ -87,11 +98,20 @@ def get_config(overrides: dict = {}) -> Config:
return config return config
config = get_config()
engine = create_engine(
config.database_url,
connect_args={"check_same_thread": False},
pool_recycle=3600,
pool_pre_ping=True,
)
SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
def get_session() -> "Session": def get_session() -> "Session":
config = get_config()
engine = create_engine(config.database_url)
with Session(engine) as session: with Session(engine) as session:
yield session yield SessionLocal()
async def reset_db_state(config: Config = None) -> None: async def reset_db_state(config: Config = None) -> None:

View file

@ -1,13 +1,11 @@
from typing import Dict, Optional from typing import Dict
import httpx import httpx
from pydantic import BaseModel from pydantic import BaseModel
from sqlmodel import Field, SQLModel from sqlmodel import Field, SQLModel
from learn_sql_model.config import config from learn_sql_model.config import config
from learn_sql_model.optional import optional from learn_sql_model.optional import optional
from learn_sql_model.models.pet import Pet
class HeroBase(SQLModel, table=False): class HeroBase(SQLModel, table=False):
@ -75,7 +73,7 @@ class HeroUpdate(HeroBase):
def update(self) -> Hero: def update(self) -> Hero:
r = httpx.patch( r = httpx.patch(
f"{config.api_client.url}/hero/", f"{config.api_client.url}/hero/",
json=self.dict(), json=self.dict(exclude_none=True),
) )
if r.status_code != 200: if r.status_code != 200:
raise RuntimeError(f"{r.status_code}:\n {r.text}") raise RuntimeError(f"{r.status_code}:\n {r.text}")

View file

@ -7,30 +7,26 @@ Create Date: 2023-06-22 15:03:27.338959
""" """
from alembic import op from alembic import op
import sqlalchemy as sa import sqlalchemy as sa
import sqlmodel
from learn_sql_model.er_diagram import generate_er_diagram, generate_er_markdown
from learn_sql_model.config import get_config
# revision identifiers, used by Alembic. # revision identifiers, used by Alembic.
revision = '3555f61aaa79' revision = "3555f61aaa79"
down_revision = '79972ec5f79d' down_revision = "79972ec5f79d"
branch_labels = None branch_labels = None
depends_on = None depends_on = None
def upgrade() -> None: def upgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ### # ### commands auto generated by Alembic - please adjust! ###
op.add_column('hero', sa.Column('x', sa.Integer(), nullable=False)) op.add_column("hero", sa.Column("x", sa.Integer(), nullable=False))
op.add_column('hero', sa.Column('y', sa.Integer(), nullable=False)) op.add_column("hero", sa.Column("y", sa.Integer(), nullable=False))
# ### end Alembic commands ### # ### end Alembic commands ###
generate_er_diagram(f'migrations/versions/{revision}_er_diagram.png') # generate_er_diagram(f'migrations/versions/{revision}_er_diagram.png')
generate_er_markdown(f'migrations/versions/{revision}_er_diagram.md', f'migrations/versions/er_diagram_{revision}.png') # generate_er_markdown(f'migrations/versions/{revision}_er_diagram.md', f'migrations/versions/er_diagram_{revision}.png')
def downgrade() -> None: def downgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ### # ### commands auto generated by Alembic - please adjust! ###
op.drop_column('hero', 'y') op.drop_column("hero", "y")
op.drop_column('hero', 'x') op.drop_column("hero", "x")
# ### end Alembic commands ### # ### end Alembic commands ###

View file

@ -1,20 +1,17 @@
"""int """int
Revision ID: 79972ec5f79d Revision ID: 79972ec5f79d
Revises: Revises:
Create Date: 2023-06-22 15:02:20.292322 Create Date: 2023-06-22 15:02:20.292322
""" """
from alembic import op from alembic import op
import sqlalchemy as sa import sqlalchemy as sa
import sqlmodel import sqlmodel
from learn_sql_model.er_diagram import generate_er_diagram, generate_er_markdown
from learn_sql_model.config import get_config
# revision identifiers, used by Alembic. # revision identifiers, used by Alembic.
revision = '79972ec5f79d' revision = "79972ec5f79d"
down_revision = None down_revision = None
branch_labels = None branch_labels = None
depends_on = None depends_on = None
@ -22,25 +19,27 @@ depends_on = None
def upgrade() -> None: def upgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ### # ### commands auto generated by Alembic - please adjust! ###
op.create_table('hero', op.create_table(
sa.Column('name', sqlmodel.sql.sqltypes.AutoString(), nullable=False), "hero",
sa.Column('secret_name', sqlmodel.sql.sqltypes.AutoString(), nullable=False), sa.Column("name", sqlmodel.sql.sqltypes.AutoString(), nullable=False),
sa.Column('id', sa.Integer(), nullable=False), sa.Column("secret_name", sqlmodel.sql.sqltypes.AutoString(), nullable=False),
sa.PrimaryKeyConstraint('id') sa.Column("id", sa.Integer(), nullable=False),
sa.PrimaryKeyConstraint("id"),
) )
op.create_table('pet', op.create_table(
sa.Column('name', sqlmodel.sql.sqltypes.AutoString(), nullable=False), "pet",
sa.Column('birthday', sa.DateTime(), nullable=True), sa.Column("name", sqlmodel.sql.sqltypes.AutoString(), nullable=False),
sa.Column('id', sa.Integer(), nullable=False), sa.Column("birthday", sa.DateTime(), nullable=True),
sa.PrimaryKeyConstraint('id') sa.Column("id", sa.Integer(), nullable=False),
sa.PrimaryKeyConstraint("id"),
) )
# ### end Alembic commands ### # ### end Alembic commands ###
generate_er_diagram(f'migrations/versions/{revision}_er_diagram.png') # generate_er_diagram(f'migrations/versions/{revision}_er_diagram.png')
generate_er_markdown(f'migrations/versions/{revision}_er_diagram.md', f'migrations/versions/er_diagram_{revision}.png') # generate_er_markdown(f'migrations/versions/{revision}_er_diagram.md', f'migrations/versions/er_diagram_{revision}.png')
def downgrade() -> None: def downgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ### # ### commands auto generated by Alembic - please adjust! ###
op.drop_table('pet') op.drop_table("pet")
op.drop_table('hero') op.drop_table("hero")
# ### end Alembic commands ### # ### end Alembic commands ###