diff --git a/AgroBase/AgroBase/bin/x64/Debug/Python/Scripts/workers/health_worker/modulos/gps.py b/AgroBase/AgroBase/bin/x64/Debug/Python/Scripts/workers/health_worker/modulos/gps.py index b7680c3fc..6e5132f7f 100644 --- a/AgroBase/AgroBase/bin/x64/Debug/Python/Scripts/workers/health_worker/modulos/gps.py +++ b/AgroBase/AgroBase/bin/x64/Debug/Python/Scripts/workers/health_worker/modulos/gps.py @@ -10,6 +10,10 @@ class ModuloGPS(ModuloDiagnosticoBase): self.nome = "UM982" self.timeout = 5 + self._rtk_expirado_desde = 0.0 + self._rtk_recuperado_desde = 0.0 + self._rtk_falha_persistente = False + def atualizar_saude(self): try: now = time.perf_counter() @@ -28,18 +32,43 @@ class ModuloGPS(ModuloDiagnosticoBase): fix = modulo.get("fix", 0) rtk = modulo.get("rtk", False) hAcc = modulo.get("hAcc", 0) - age = modulo.get("age", -1) + age_bruto = modulo.get("age", -1) ntrip = modulo.get("correcao_ntrip", False) - orientacao = modulo.get("orientacao") or {} - - status_ori = str( - orientacao.get("status", "") - ).strip().upper() - + status_ori = str(orientacao.get("status", "")).strip().upper() valor_ori_bruto = orientacao.get("valor", 9999.0) valida_redis = orientacao.get("valida", False) + try: + age = float(age_bruto) + except (TypeError, ValueError): + age = -1.0 + + AGE_WARN = 5.0 + AGE_FAIL = 15.0 + AGE_RECOVER = 3.0 + T_FAIL = 2.0 + T_RECOVER = 3.0 + agora_mono = time.monotonic() + age_valido = math.isfinite(age) and age >= 0.0 + correcao_expirada = not age_valido or age >= AGE_FAIL + correcao_recuperada = (age_valido and age <= AGE_RECOVER and bool(rtk)) + if correcao_expirada: + if self._rtk_expirado_desde <= 0: + self._rtk_expirado_desde = agora_mono + self._rtk_recuperado_desde = 0.0 + if (agora_mono - self._rtk_expirado_desde >= T_FAIL): + self._rtk_falha_persistente = True + elif correcao_recuperada: + self._rtk_expirado_desde = 0.0 + if self._rtk_recuperado_desde <= 0: + self._rtk_recuperado_desde = agora_mono + if (agora_mono - self._rtk_recuperado_desde >= T_RECOVER): + self._rtk_falha_persistente = False + else: + self._rtk_expirado_desde = 0.0 + self._rtk_recuperado_desde = 0.0 + # Proteção caso o Redis devolva booleano como texto. if isinstance(valida_redis, str): valida_redis = valida_redis.strip().lower() in ( @@ -56,27 +85,10 @@ class ModuloGPS(ModuloDiagnosticoBase): except (TypeError, ValueError): valor_ori = 9999.0 - valor_ori_valido = ( - math.isfinite(valor_ori) - and 0.0 <= valor_ori < 360.0 - ) - - orientacao_recebendo = ( - freq_ori > FREQ_MIN - and not fail_ori - ) - - posicao_recebendo = ( - freq_pos > FREQ_MIN - and not fail_pos - ) - - orientacao_valida = ( - orientacao_recebendo - and valida_redis - and status_ori == "A" - and valor_ori_valido - ) + valor_ori_valido = (math.isfinite(valor_ori) and 0.0 <= valor_ori < 360.0) + orientacao_recebendo = (freq_ori > FREQ_MIN and not fail_ori) + posicao_recebendo = (freq_pos > FREQ_MIN and not fail_pos) + orientacao_valida = (orientacao_recebendo and valida_redis and status_ori == "A" and valor_ori_valido) saude = 100 motivos = [] @@ -148,6 +160,11 @@ class ModuloGPS(ModuloDiagnosticoBase): if p_age > 0: saude -= p_age motivos.append(f"Correção RTK degradada (age={age:.1f}s, penalidade {p_age}%, ntrip: {ntrip})") + + if self._rtk_falha_persistente: + saude = 0 + motivos.append(f"Correção RTK expirada persistentemente: age={age:.1f}s, limite={AGE_FAIL:.1f}s") + # 🔹 hAcc p_hacc = self._penalidade_hacc(hAcc) if p_hacc > 0: