Skip to content

Commit

Permalink
Improved non available values
Browse files Browse the repository at this point in the history
  • Loading branch information
MarcoGos committed Oct 15, 2023
1 parent b8b8a22 commit da932a2
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 50 deletions.
10 changes: 5 additions & 5 deletions custom_components/davis_vantage/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -77,11 +77,7 @@ async def get_davis_time(call: ServiceCall) -> dict[str, Any]:
"error": "Couldn't get davis time, please try again later"
}

def safe_serialize(obj: Any):
default = lambda o: f"<<non-serializable: {type(o).__qualname__}>>"
return json.dumps(obj, default=default)

async def get_raw_data(call: ServiceCall) -> SupportsResponse:
async def get_raw_data(call: ServiceCall) -> dict[str, Any]:
raw_data = client.get_raw_data()
json_data = safe_serialize(raw_data)
return json.loads(json_data)
Expand All @@ -97,6 +93,10 @@ async def get_raw_data(call: ServiceCall) -> SupportsResponse:
DOMAIN, SERVICE_GET_RAW_DATA, get_raw_data, supports_response=SupportsResponse.ONLY
)

def safe_serialize(obj: Any):
default = lambda o: f"<<non-serializable: {type(o).__qualname__}>>" # type: ignore
return json.dumps(obj, default=default) # type: ignore

return True

async def async_unload_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
Expand Down
74 changes: 37 additions & 37 deletions custom_components/davis_vantage/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ def __init__(
self._windrose8 = windrose8
self._rain_collector = rain_collector
self._last_data: LoopDataParserRevB = {} # type: ignore
self._last_raw_data: DataParser = {}
self._last_raw_data: DataParser = {} # type: ignore
self._vantagepro2 = VantagePro2.from_url(self.get_link())
self._vantagepro2.link.close()

Expand All @@ -64,12 +64,13 @@ def get_current_data(self) -> LoopDataParserRevB | None:
async def async_get_current_data(self) -> LoopDataParserRevB | None:
"""Get current date from weather station async."""
data = self._last_data
now = convert_to_iso_datetime(datetime.now(), ZoneInfo(self._hass.config.time_zone))
try:
loop = asyncio.get_event_loop()
new_data = await loop.run_in_executor(None, self.get_current_data)
new_raw_data = self.__get_full_raw_data(new_data)
now = convert_to_iso_datetime(datetime.now(), ZoneInfo(self._hass.config.time_zone))
if new_data:
new_raw_data = self.__get_full_raw_data(new_data)
self._last_raw_data = new_raw_data
self.remove_all_incorrect_data(new_raw_data, new_data)
self.add_additional_info(new_data)
self.convert_values(new_data)
Expand All @@ -90,17 +91,16 @@ async def async_get_current_data(self) -> LoopDataParserRevB | None:
data['LastErrorTime'] = now

self._last_data = data
self._last_raw_data = new_raw_data
return data

def __get_full_raw_data(self, data: LoopDataParserRevB) -> DataParser:
raw_data = DataParser(data.raw_bytes, LoopDataParserRevB.LOOP_FORMAT)
raw_data['HumExtra'] = struct.unpack(b'7B', raw_data['HumExtra'])
raw_data['ExtraTemps'] = struct.unpack(b'7B', raw_data['ExtraTemps'])
raw_data['SoilMoist'] = struct.unpack(b'4B', raw_data['SoilMoist'])
raw_data['SoilTemps'] = struct.unpack(b'4B', raw_data['SoilTemps'])
raw_data['LeafWetness'] = struct.unpack(b'4B', raw_data['LeafWetness'])
raw_data['LeafTemps'] = struct.unpack(b'4B', raw_data['LeafTemps'])
raw_data['HumExtra'] = struct.unpack(b'7B', raw_data['HumExtra']) # type: ignore
raw_data['ExtraTemps'] = struct.unpack(b'7B', raw_data['ExtraTemps']) # type: ignore
raw_data['SoilMoist'] = struct.unpack(b'4B', raw_data['SoilMoist']) # type: ignore
raw_data['SoilTemps'] = struct.unpack(b'4B', raw_data['SoilTemps']) # type: ignore
raw_data['LeafWetness'] = struct.unpack(b'4B', raw_data['LeafWetness']) # type: ignore
raw_data['LeafTemps'] = struct.unpack(b'4B', raw_data['LeafTemps']) # type: ignore
raw_data.tuple_to_dict("ExtraTemps")
raw_data.tuple_to_dict("LeafTemps")
raw_data.tuple_to_dict("SoilTemps")
Expand Down Expand Up @@ -150,56 +150,56 @@ async def async_set_davis_time(self) -> None:
_LOGGER.error("Couldn't set davis time: %s", e)

def add_additional_info(self, data: dict[str, Any]) -> None:
if data['TempOut'] and data['HumOut']:
data['HeatIndex'] = calc_heat_index(data['TempOut'], data['HumOut'])
if data['TempOut'] and data['WindSpeed']:
data['WindChill'] = calc_wind_chill(data['TempOut'], data['WindSpeed'])
if data['TempOut'] and data['HumOut'] and data['WindSpeed']:
data['FeelsLike'] = calc_feels_like(data['TempOut'], data['HumOut'], data['WindSpeed'])
if data['WindDir']:
data['WindDirRose'] = get_wind_rose(data['WindDir'], self._windrose8)
if data['TempOut'] and data['HumOut']:
data['DewPoint'] = calc_dew_point(data['TempOut'], data['HumOut'])
if data['WindSpeed10Min']:
if data['TempOut'] is not None:
if data['HumOut'] is not None:
data['HeatIndex'] = calc_heat_index(data['TempOut'], data['HumOut'])
data['DewPoint'] = calc_dew_point(data['TempOut'], data['HumOut'])
if data['WindSpeed'] is not None:
data['WindChill'] = calc_wind_chill(data['TempOut'], data['WindSpeed'])
if data['HumOut'] is not None:
data['FeelsLike'] = calc_feels_like(data['TempOut'], data['HumOut'], data['WindSpeed'])
if data['WindDir'] is not None:
data['WindDirRose'] = get_wind_rose(data['WindDir'], self._windrose8)
if data['WindSpeed10Min'] is not None:
data['WindSpeedBft'] = convert_kmh_to_bft(convert_to_kmh(data['WindSpeed10Min']))
if data['RainRate']:
if data['RainRate'] is not None:
data['IsRaining'] = data['RainRate'] > 0

def convert_values(self, data: dict[str, Any]) -> None:
del data['Datetime']
if data['BarTrend']:
if data['BarTrend'] is not None:
data['BarTrend'] = get_baro_trend(data['BarTrend'])
if data['UV']:
if data['UV'] is not None:
data['UV'] = get_uv(data['UV'])
if data['SolarRad']:
if data['SolarRad'] is not None:
data['SolarRad'] = get_solar_rad(data['SolarRad'])
if data['ForecastRuleNo']:
if data['ForecastRuleNo'] is not None:
data['ForecastRuleNo'] = get_forecast_string(data['ForecastRuleNo'])
data['RainCollector'] = self._rain_collector
data['WindRoseSetup'] = 8 if self._windrose8 else 16
if data['RainCollector'] == RAIN_COLLECTOR_METRIC:
self.correct_rain_values(data)

def correct_rain_values(self, data: dict[str, Any]):
if data['RainDay']:
if data['RainDay'] is not None:
data['RainDay'] *= 2/2.54
if data['RainMonth']:
if data['RainMonth'] is not None:
data['RainMonth'] *= 2/2.54
if data['RainYear']:
if data['RainYear'] is not None:
data['RainYear'] *= 2/2.54
if data['RainRate']:
if data['RainRate'] is not None:
data['RainRate'] *= 2/2.54

def remove_all_incorrect_data(self, raw_data: DataParser, data: LoopDataParserRevB):
data_info = { key: value for key, value in LoopDataParserRevB.LOOP_FORMAT }
for key in data.keys():
info_key = re.sub(r'\d+$', '', key)
for key in data.keys(): # type: ignore
info_key = re.sub(r'\d+$', '', key) # type: ignore
if data_info.get(info_key, '') in ["B", "7s"]:
if raw_data.get(key, 0) == 255:
data[key] = None
if data_info.get(key, '') == 'H':
if raw_data.get(key, '') == 32767 or raw_data.get(key, '') == 65535:
data[key] = None
if raw_data.get(key, 0) == 255: # type: ignore
data[key] = None # type: ignore
if data_info.get(key, '') == 'H': # type: ignore
if raw_data.get(key, '') == 32767 or raw_data.get(key, '') == 65535: # type: ignore
data[key] = None # type: ignore

def get_link(self) -> str | None:
"""Get device link for use with vproweather."""
Expand Down
10 changes: 2 additions & 8 deletions custom_components/davis_vantage/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -366,16 +366,10 @@ def get_forecast_string(wrule: int) -> str:
return ForecastStrings[wrule]

def get_uv(value: int) -> float:
if value == 255:
return None
else:
return round(value / 10, 1)
return round(value / 10, 1)

def get_solar_rad(value: int) -> float:
if value == 32767:
return None
else:
return value
return value

def calc_dew_point(temperature_f: float, humidity: float) -> float:
temperature_c = convert_to_celcius(temperature_f)
Expand Down

0 comments on commit da932a2

Please sign in to comment.