degrees_accumulated.py 3.0 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697
  1. from datetime import datetime
  2. from pprint import pprint
  3. from config.settings import DECIMAL_PLACES
  4. from database.mongo import mongo_measures
  5. from routes.calculations.pipelines import count_temp_measures_pipeline, get_percent
  6. from schemas.fincas import FincaBase as FincaBaseSchema
  7. from schemas.tables import (
  8. DegreesAccumulatedAvgMonth as DegreesAccumulatedAvgMonthSchema,
  9. )
  10. def ensure_non_empty(result, key):
  11. """
  12. Ensures that the result list is not empty and that we are not rounding None
  13. """
  14. if len(result) > 0:
  15. value = result[0].get(key)
  16. if value is not None:
  17. return round(value, 2)
  18. def monthly_avr_day_degrees(
  19. finca: FincaBaseSchema, start_datetime: datetime, end_datetime: datetime
  20. ) -> DegreesAccumulatedAvgMonthSchema:
  21. finca_data = mongo_measures[finca.station_code]
  22. degrees_accumulated_agg = finca_data.aggregate(
  23. [
  24. {
  25. "$match": {
  26. "date": {
  27. "$gte": start_datetime,
  28. "$lte": end_datetime,
  29. },
  30. "temp": {"$ne": None},
  31. },
  32. },
  33. {
  34. "$group": {
  35. "_id": {
  36. "day": {"$dayOfMonth": "$date"},
  37. "month": {"$month": "$date"},
  38. "year": {"$year": "$date"},
  39. },
  40. "dailyDegrees": {"$avg": "$temp"},
  41. }
  42. },
  43. {
  44. "$set": {
  45. "dailyDegrees": {
  46. "$cond": [
  47. {"$gt": ["$dailyDegrees", 10]},
  48. {"$add": ["$dailyDegrees", -10]},
  49. 0,
  50. ],
  51. }
  52. }
  53. },
  54. {
  55. "$group": {
  56. "_id": {
  57. "month": "$_id.month",
  58. "year": "$_id.year",
  59. },
  60. "avgDailyDegrees": {"$avg": "$dailyDegrees"},
  61. }
  62. },
  63. ]
  64. )
  65. degrees_accumulated = list(degrees_accumulated_agg)
  66. months = {}
  67. for month in degrees_accumulated:
  68. value = month.get("avgDailyDegrees")
  69. if value is not None:
  70. value = round(value, DECIMAL_PLACES)
  71. months[str(month.get("_id", {}).get("month"))] = value
  72. data_count = finca_data.count(
  73. count_temp_measures_pipeline(start_datetime, end_datetime)
  74. )
  75. total_count = (end_datetime - start_datetime).total_seconds() // (60 * 10)
  76. data_percentage = get_percent(data_count, total_count)
  77. summary = DegreesAccumulatedAvgMonthSchema(
  78. station=FincaBaseSchema(
  79. station_code=finca.station_code,
  80. title=finca.title,
  81. ),
  82. initial_date=start_datetime,
  83. final_date=end_datetime,
  84. months=months,
  85. data_percentage=data_percentage,
  86. )
  87. return summary