Partial correction in persistence and geometry_helper.py

This commit is contained in:
Guille Gutierrez 2023-05-18 16:15:57 -04:00
parent 1c4920d0b0
commit 5fb361e74c
9 changed files with 97 additions and 69 deletions

View File

@ -12,6 +12,7 @@ import numpy as np
from PIL import Image
from trimesh import Trimesh
from trimesh import intersections
from typing import Dict
from hub.city_model_structure.attributes.polygon import Polygon
from hub.city_model_structure.attributes.polyhedron import Polyhedron
@ -25,10 +26,16 @@ class MapPoint:
@property
def x(self):
"""
Get X Coordinate
"""
return self._x
@property
def y(self):
"""
Get Y Coordinate
"""
return self._y
def __str__(self):
@ -57,6 +64,10 @@ class GeometryHelper:
@staticmethod
def factor():
"""
Set minimap resolution
:return: None
"""
return 0.5
def __init__(self, delta=0, area_delta=0):
@ -65,15 +76,24 @@ class GeometryHelper:
@staticmethod
def coordinate_to_map_point(coordinate, city):
"""
Transform a real world coordinate to a minimap one
:param coordinate: real world coordinate
:param city: current city
:return: None
"""
factor = GeometryHelper.factor()
return MapPoint(
((coordinate[0] - city.lower_corner[0]) * factor), ((coordinate[1] - city.lower_corner[1]) * factor)
)
@staticmethod
def city_mapping(city, building_names=None, plot=False):
def city_mapping(city, building_names=None, plot=False) -> Dict:
"""
Returns a shared_information dictionary
:param city: city to be mapped
:param building_names: list of building names to be mapped or None
:param plot: True if minimap image should be displayed
:return: shared_information dictionary
"""
lines_information = {}
if building_names is None:
@ -182,7 +202,8 @@ class GeometryHelper:
@staticmethod
def segment_list_to_trimesh(lines) -> Trimesh:
"""
Transform a list of segments into a Trimesh
:param lines: lines
:return: Transform a list of segments into a Trimesh
"""
# todo: trimesh has a method for this
line_points = [lines[0][0], lines[0][1]]
@ -262,6 +283,9 @@ class GeometryHelper:
def get_location(latitude, longitude) -> Location:
"""
Get Location from latitude and longitude
:param latitude: Latitude
:param longitude: Longitude
:return: Location
"""
_data_path = Path(Path(__file__).parent.parent / 'data/geolocation/cities15000.txt').resolve()
latitude = float(latitude)

View File

@ -36,7 +36,6 @@ class CityObject(Models):
created = Column(DateTime, default=datetime.datetime.utcnow)
updated = Column(DateTime, default=datetime.datetime.utcnow)
# def __init__(self, city_id, name, alias, object_type, year_of_construction, function, usage, volume, area):
def __init__(self, city_id, building: Building):
self.city_id = city_id
self.name = building.name
@ -49,7 +48,6 @@ class CityObject(Models):
self.area = building.floor_area
storeys = building.storeys_above_ground
if storeys is None:
print(building.average_storey_height)
storeys = building.max_height / building.average_storey_height
self.total_heating_area = building.floor_area * storeys
wall_area = 0

View File

@ -5,12 +5,12 @@ Copyright © 2022 Concordia CERC group
Project Coder Guille Gutierrez Guillermo.GutierrezMorote@concordia.ca
"""
import logging
import datetime
from typing import Union, Dict
import logging
from sqlalchemy import select
from sqlalchemy.exc import SQLAlchemyError
from hub.persistence import Repository
from hub.persistence.models import Application as Model
@ -32,33 +32,33 @@ class Application(Repository):
cls._instance = super(Application, cls).__new__(cls)
return cls._instance
def insert(self, name: str, description: str, application_uuid: str) -> Union[Model, Dict]:
def insert(self, name: str, description: str, application_uuid: str):
"""
Inserts a new application
:param name: Application name
:param description: Application description
:param application_uuid: Unique identifier for the application
:return: application and dictionary
:return: None
"""
application = self.get_by_uuid(application_uuid)
if application is None:
try:
application = Model(name=name, description=description, application_uuid=application_uuid)
if application is not None:
raise SQLAlchemyError('application already exists')
try:
application = Model(name=name, description=description, application_uuid=application_uuid)
self.session.add(application)
self.session.commit()
except SQLAlchemyError as err:
error_message = f'An error occurred while creating application: {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
self.session.add(application)
self.session.commit()
return application
except SQLAlchemyError as err:
logging.error('An error occurred while creating application: %s', err)
return {'message': f'An error occurred while creating application {application_uuid}'}
def update(self, application_uuid: str, name: str, description: str) -> Union[Dict, None]:
def update(self, application_uuid: str, name: str, description: str):
"""
Updates an application
:param application_uuid: the application uuid of the application to be updated
:param name: the application name
:param description: the application description
:return:
:return: None
"""
try:
self.session.query(Model).filter(
@ -66,9 +66,9 @@ class Application(Repository):
).update({'name': name, 'description': description, 'updated': datetime.datetime.utcnow()})
self.session.commit()
except SQLAlchemyError as err:
logging.error('Error while updating application %s', err)
return {'message': 'Error occurred while updating application'}
return None
error_message = f'Error while updating application {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
def delete(self, application_uuid: str):
"""
@ -81,21 +81,27 @@ class Application(Repository):
self.session.flush()
self.session.commit()
except SQLAlchemyError as err:
logging.error('Error while deleting application: %s', err)
error_message = f'Error while deleting application {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
def get_by_uuid(self, application_uuid: str) -> Union[Model, None]:
def get_by_uuid(self, application_uuid: str) -> Model:
"""
Fetch Application based on the application uuid
:param application_uuid: the application uuid
:return: Application with the provided application_uuid or None
:return: Application with the provided application_uuid
"""
result_set = None
try:
result_set = self.session.execute(select(Model).where(
Model.application_uuid == application_uuid)
).first()
return result_set[0]
except SQLAlchemyError as err:
logging.error('Error while fetching application by application_uuid: %s', err)
if result_set is None:
return None
return result_set[0]
error_message = f'Error while fetching application by application_uuid {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
except IndexError as err:
error_message = f'Error while fetching application, empty result {err}'
logging.error(error_message)
raise IndexError(error_message)

View File

@ -4,9 +4,8 @@ SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2022 Concordia CERC group
Project Coder Peter Yefi peteryefi@gmail.com
"""
import logging
import datetime
from typing import Union
import logging
from sqlalchemy import select
from sqlalchemy.exc import SQLAlchemyError
@ -35,14 +34,14 @@ class City(Repository):
cls._instance = super(City, cls).__new__(cls)
return cls._instance
def insert(self, city: CityHub, pickle_path, application_id, user_id: int) -> Union[Model, None]:
def insert(self, city: CityHub, pickle_path, application_id, user_id: int):
"""
Inserts a city
:param city: The complete city instance
:param pickle_path: Path to the pickle
:param application_id: Application id owning the instance
:param user_id: User id owning the instance
:return: City and None
:return: None
"""
city.save_compressed(pickle_path)
try:
@ -64,39 +63,43 @@ class City(Repository):
self.session.add(db_city_object)
self.session.flush()
self.session.commit()
return db_city
except SQLAlchemyError as err:
logging.error('An error occurred while creating city: %s', err)
return None
error_message = f'An error occurred while creating a city: {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
def update(self, city_id: int, city: CityHub):
"""
Updates a city name (other updates makes no sense)
:param city_id: the id of the city to be updated
:param city: the city object
:return:
:return: None
"""
try:
now = datetime.datetime.utcnow()
self.session.query(Model).filter(Model.id == city_id).update({'name': city.name, 'updated': now})
self.session.commit()
except SQLAlchemyError as err:
logging.error('Error while updating city: %s', err)
error_message = f'Error while updating city {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
def delete(self, city_id: int):
"""
Deletes a City with the id
:param city_id: the city id
:return: a city
:return: None
"""
try:
self.session.query(CityObject).filter(CityObject.city_id == city_id).delete()
self.session.query(Model).filter(Model.id == city_id).delete()
self.session.commit()
except SQLAlchemyError as err:
logging.error('Error while fetching city: %s', err)
error_message = f'Error while fetching city {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
def get_by_user_id_application_id_and_name(self, user_id, application_id, city_name):
def get_by_user_id_application_id_and_name(self, user_id, application_id, city_name) -> Model:
"""
Fetch city based on the user who created it
:param user_id: the user id
@ -113,8 +116,9 @@ class City(Repository):
result_set = result_set[0]
return result_set
except SQLAlchemyError as err:
logging.error('Error while fetching city by name: %s', err)
return None
error_message = f'Error while fetching city by name {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
def get_by_user_id_and_application_id(self, user_id, application_id) -> [Model]:
"""
@ -129,5 +133,6 @@ class City(Repository):
)
return [r[0] for r in result_set]
except SQLAlchemyError as err:
logging.error('Error while fetching city by name: %s', err)
return None
error_message = f'Error while fetching city by name {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)

View File

@ -30,27 +30,27 @@ class CityObject(Repository):
cls._instance = super(CityObject, cls).__new__(cls)
return cls._instance
def insert(self, city_id: int, building: Building) -> Union[Model, Dict]:
def insert(self, city_id: int, building: Building):
"""
Inserts a new city object
:param city_id: city id for the city owning this city object
:param building: the city object (only building for now) to be inserted
return CityObject model and dictionary
return None
"""
city_object = self.get_by_name_and_city(building.name, city_id)
if city_object is None:
try:
city_object = Model(city_id=city_id,
building=building)
self.session.add(city_object)
self.session.flush()
self.session.commit()
if city_object is not None:
raise SQLAlchemyError(f'A city_object named {building.name} already exists in that city')
try:
city_object = Model(city_id=city_id,
building=building)
self.session.add(city_object)
self.session.flush()
self.session.commit()
except SQLAlchemyError as err:
logging.error('An error occurred while creating city_object: %s', err)
else:
return {'message': f'A city_object named {building.name} already exists in that city'}
return city_object
except SQLAlchemyError as err:
error_message = f'An error occurred while creating city_object {err}'
logging.error(error_message)
raise SQLAlchemyError(error_message)
def update(self, city_id: int, building: Building) -> Union[Dict, None]:
"""

View File

@ -18,13 +18,11 @@ class TestCostsCatalog(TestCase):
self.assertIsNotNone(catalog, 'catalog is none')
content = catalog.entries()
self.assertTrue(len(content.archetypes) == 2)
print(catalog)
# retrieving all the entries should not raise any exceptions
for category in catalog_categories:
for value in catalog_categories[category]:
catalog.get_entry(value)
print(value)
with self.assertRaises(IndexError):
catalog.get_entry('unknown')

View File

@ -4,6 +4,7 @@ SPDX - License - Identifier: LGPL - 3.0 - or -later
Copyright © 2022 Concordia CERC group
Project Coder Peter Yefi peteryefi@gmail.com
"""
import logging
import os
import unittest
from unittest import TestCase
@ -48,7 +49,7 @@ class Control:
connection = engine.connect()
connection.close()
except ProgrammingError:
print(f'Database does not exist. Nothing to delete')
logging.info('Database does not exist. Nothing to delete')
except sqlalchemy.exc.OperationalError as operational_error:
self._skip_test = True
self._skip_reason = f'{operational_error}'

View File

@ -86,7 +86,6 @@ class TestGeometryFactory(TestCase):
elif input_key == 'hft':
for building in city.buildings:
building.function = Dictionaries().hft_function_to_hub_function[building.function]
print(construction_key, usage_key)
ConstructionFactory(construction_key, city).enrich()
UsageFactory(usage_key, city).enrich()

View File

@ -14,9 +14,6 @@ class TestSystemsCatalog(TestCase):
def test_montreal_custom_catalog(self):
catalog = EnergySystemsCatalogFactory('montreal_custom').catalog
catalog_categories = catalog.names()
for archetype in catalog.entries('archetypes'):
for equipment in archetype.equipments:
print(equipment._equipment_id)
archetypes = catalog.names('archetypes')
self.assertEqual(18, len(archetypes['archetypes']))
equipments = catalog.names('equipments')