Priprava modelu na GPX v DB

This commit is contained in:
Michal Kváček
2024-06-24 16:22:50 +02:00
parent 2bf737b9d6
commit ac3b496459
8 changed files with 139 additions and 23 deletions
@@ -0,0 +1,28 @@
"""add flight_plan.description
Revision ID: a3e1f1a37899
Revises: 8a67af3909aa
Create Date: 2024-06-11 16:46:29.786830
"""
from alembic import op
import sqlalchemy as sa
# revision identifiers, used by Alembic.
revision = 'a3e1f1a37899'
down_revision = '8a67af3909aa'
branch_labels = None
depends_on = None
def upgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.add_column('flight_plan', sa.Column('description', sa.Text(), server_default='', nullable=False))
# ### end Alembic commands ###
def downgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.drop_column('flight_plan', 'description')
# ### end Alembic commands ###
@@ -0,0 +1,54 @@
"""add track to flight
Revision ID: f9e1e8a01683
Revises: a3e1f1a37899
Create Date: 2024-06-24 16:08:01.084570
"""
from alembic import op
import sqlalchemy as sa
from sqlalchemy.dialects import mysql
# revision identifiers, used by Alembic.
revision = 'f9e1e8a01683'
down_revision = 'a3e1f1a37899'
branch_labels = None
depends_on = None
def upgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.create_table('track',
sa.Column('id', sa.Integer(), nullable=False),
sa.Column('bounds', mysql.JSON(), nullable=False),
sa.Column('created_by_id', sa.Integer(), nullable=False),
sa.Column('created_at', sa.DateTime(), server_default=sa.text('now()'), nullable=False),
sa.ForeignKeyConstraint(['created_by_id'], ['user.id'], ),
sa.PrimaryKeyConstraint('id')
)
op.create_table('track_point',
sa.Column('id', sa.Integer(), nullable=False),
sa.Column('timestamp', sa.DateTime(), nullable=False),
sa.Column('track_id', sa.Integer(), nullable=False),
sa.Column('gps_latitude', sa.Float(), nullable=False),
sa.Column('gps_longitude', sa.Float(), nullable=False),
sa.Column('elevation', sa.Float(), nullable=True),
sa.ForeignKeyConstraint(['track_id'], ['track.id'], ),
sa.PrimaryKeyConstraint('id')
)
op.add_column('flight', sa.Column('track_id', sa.Integer(), nullable=True))
op.create_foreign_key(None, 'flight', 'track', ['track_id'], ['id'])
op.add_column('flight_plan', sa.Column('track_id', sa.Integer(), nullable=True))
op.create_foreign_key(None, 'flight_plan', 'track', ['track_id'], ['id'])
# ### end Alembic commands ###
def downgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.drop_constraint(None, 'flight_plan', type_='foreignkey')
op.drop_column('flight_plan', 'track_id')
op.drop_constraint(None, 'flight', type_='foreignkey')
op.drop_column('flight', 'track_id')
op.drop_table('track_point')
op.drop_table('track')
# ### end Alembic commands ###
+2 -1
View File
@@ -74,7 +74,6 @@ copilot_has_photo = Table(
Column("photo_id", ForeignKey("photo.id"), primary_key=True),
)
airport_has_reporting_point = Table(
"airport_has_reporting_point",
BaseModel.metadata,
@@ -105,6 +104,7 @@ class FlightPlan(BaseModel):
is_default_name: Mapped[bool] = mapped_column(Boolean, server_default='0')
is_public: Mapped[bool] = mapped_column(Boolean, server_default='0')
is_editable_by_copilot: Mapped[bool] = mapped_column(Boolean, server_default='0')
description: Mapped[str] = mapped_column(Text, nullable=False, server_default="")
planned_speed: Mapped[int] = mapped_column(Integer, nullable=False, default=150)
planned_takeoff_datetime: Mapped[datetime] = mapped_column(DateTime, nullable=True)
aircraft_id: Mapped[int] = mapped_column(Integer, ForeignKey("aircraft.id"), nullable=True)
@@ -130,6 +130,7 @@ class FlightPlanMarker(BaseModel):
gps_longitude: Mapped[float] = mapped_column(Float, nullable=False)
weather_info_id: Mapped[int] = mapped_column(Integer, ForeignKey('weather_info.id'), nullable=True)
class Airport(BaseModel):
__tablename__ = "airport"
+1 -1
View File
@@ -11,7 +11,7 @@ from graphql_schema.entities.types.types import Airport
class AirportQueries:
@strawberry.field()
@error_logging
@authenticated_user_only()
# @authenticated_user_only()
async def airports(root, info) -> List[Airport]:
return await BaseQueryResolver(Airport, models.Airport).get_list(info.context.user_id)
+19 -9
View File
@@ -1,11 +1,10 @@
from typing import List
from typing import List, Optional
import strawberry
from strawberry.types import Info
from database import models
from decorators.error_logging import error_logging
from decorators.endpoints import authenticated_user_only, allow_public
from graphql_schema.entities.resolvers.base import BaseQueryResolver
from graphql_schema.entities.resolvers.flight_plan import FlightPlanMutationResolver
from decorators.error_logging import error_logging
from graphql_schema.entities.helpers.detail import get_detail_filters
from graphql_schema.entities.resolvers.flight_plan import FlightPlanMutationResolver, FlightPlanQueryResolver
from graphql_schema.entities.types.mutation_input import CreateFlightPlanInput, EditFlightPlanInput
from graphql_schema.entities.types.types import FlightPlan
@@ -16,15 +15,26 @@ class FlightPlanQueries:
@error_logging
@authenticated_user_only()
async def flight_plans(root, info: Info) -> List[FlightPlan]:
return await BaseQueryResolver(FlightPlan, models.FlightPlan).get_list(info.context.user_id)
return await FlightPlanQueryResolver().get_list(info.context.user_id)
@strawberry.field()
@error_logging
@allow_public
async def flight_plan(root, info: Info, id: int) -> FlightPlan:
return await BaseQueryResolver(FlightPlan, models.FlightPlan).get_one(
async def flight_plan(
root,
info: Info,
id: int,
username: Optional[str] = None,
public: Optional[bool] = False
) -> FlightPlan:
filter_params = get_detail_filters(id)
if username:
filter_params['username'] = username
return await FlightPlanQueryResolver().get_one(
user_id=info.context.user_id,
object_id=id
only_public=public,
**filter_params
)
@@ -2,7 +2,7 @@ from typing import Optional
from graphql import GraphQLError
def get_detail_filters(id: Optional[int], url_slug: Optional[str]) -> dict:
def get_detail_filters(id: Optional[int] = None, url_slug: Optional[str] = None) -> dict:
filter_params = {}
if id:
filter_params['object_id'] = id
@@ -28,17 +28,11 @@ class FlightQueryResolver(BaseQueryResolver):
def get_query(
self,
user_id: Optional[int] = None,
object_id: Optional[int] = None,
url_slug: Optional[str] = None,
only_public: Optional[bool] = False,
*args,
**kwargs
):
filters = {}
if object_id:
filters['object_id'] = object_id
if url_slug:
filters['url_slug'] = url_slug
filters = {key: kwargs[key] for key in ("object_id", "url_slug") if key in kwargs}
query = super().get_query(
user_id,
@@ -1,19 +1,48 @@
import asyncio
from typing import Optional
from sqlalchemy import delete, select
from sqlalchemy.dialects.mysql import insert
from database import models
from database.models import flight_plan_has_copilot
from database.transaction import get_session
from graphql_schema.entities.helpers.combobox import handle_combobox_save
from graphql_schema.entities.resolvers.base import BaseMutationResolver
from graphql_schema.entities.resolvers.base import BaseMutationResolver, BaseQueryResolver
from graphql_schema.entities.resolvers.flight import handle_aircraft_save
from graphql_schema.entities.types.mutation_input import CreateFlightPlanInput, EditFlightPlanInput
from graphql_schema.entities.types.types import FlightPlan
from utils.str_utils import random_str
class FlightPlanQueryResolver(BaseQueryResolver):
def __init__(self):
super().__init__(graphql_type=FlightPlan, model=models.FlightPlan)
def get_query(
self,
user_id: Optional[int] = None,
only_public: Optional[bool] = False,
object_id: Optional[int] = None,
*args,
**kwargs
):
filters = {"object_id": object_id} if object_id else {}
query = super().get_query(
user_id,
**filters,
order_by=[models.FlightPlan.planned_takeoff_datetime.desc(), models.FlightPlan.id.desc()],
only_public=only_public,
only_my=not only_public
)
if kwargs.get('username'):
query = (
query.join(models.FlightPlan.created_by)
.filter(models.User.public_username == kwargs['username'])
)
return query
class FlightPlanMutationResolver(BaseMutationResolver):
def __init__(self):
super().__init__(graphql_type=FlightPlan, model=models.FlightPlan)
@@ -100,4 +129,4 @@ def evenly_spaced_elements(lst: list, count: int) -> list:
if count > len(lst):
return lst
interval = (len(lst) - 1) / (count - 1) if count > 1 else 0
return [lst[int(round(i * interval))] for i in range(count)]
return [lst[int(round(i * interval))] for i in range(count)]