def handleStartButton(self) -> None: self.btnStart.setEnabled(False) self.btnClose.setEnabled(False) self.cboStates.setEnabled(False) self.cboCounties.setEnabled(False) self.grpDataSource.setEnabled(False) self.grpMetric.setEnabled(False) self.chkSavePlotImage.setEnabled(False) chartFocus: cfg.ChartFocus = cfg.ChartFocus.NEW_CASES try: if self.radNewCases.isChecked(): chartFocus = cfg.ChartFocus.NEW_CASES elif self.radNewDeaths.isChecked(): chartFocus = cfg.ChartFocus.NEW_DEATHS launchOptions = { "chartFocus": chartFocus, "isFromServer": self.radServerData.isChecked(), "saveChart": self.chkSavePlotImage.isChecked(), "state": self.cboStates.currentText(), "county": self.cboCounties.currentText(), } launchCharting(launchOptions) except: errMsg = f"An error occurred: {sys.exc_info()[0]}; {sys.exc_info()[1] if len(sys.exc_info()) > 1 else ''}\n{traceback.format_exc()}" utl.processLogMessage(logging.ERROR, errMsg, loggers) finally: self.btnStart.setEnabled(True) self.btnClose.setEnabled(True) self.cboStates.setEnabled(True) self.cboCounties.setEnabled(True) self.grpDataSource.setEnabled(True) self.grpMetric.setEnabled(True) self.chkSavePlotImage.setEnabled(True)
def reduceTicks(self, tickCount: int, percentReduction: float) -> int: retVal: int = 0 if tickCount > 1 and percentReduction > 0: retVal = int(round(tickCount * (1 - percentReduction), 0)) utl.processLogMessage( logging.INFO, f"Using {tickCount} with a {percentReduction} reduction, reduceTicks() returned {retVal}", loggers, ) return retVal
def loadStateCountyData(self, localDataFile: str) -> pd.DataFrame: dfRetVal: pd.DataFrame = pd.DataFrame() try: if os.path.exists(cfg.LOCAL_DATA_FILE_NAME): dfRetVal = self.__loadLookupFromPreviousData( cfg.LOCAL_DATA_FILE_NAME) else: dfRetVal = self.__loadLookupFromStaticFile( cfg.LOCAL_STATES_COUNTIES_FILE_NAME) except OSError as oserr: utl.processLogMessage( logging.ERROR, f"Unable to load lookup data: '{oserr}'", loggers, ) return dfRetVal
def __loadLookupFromStaticFile(self, localStaticDataFile: str) -> pd.DataFrame: dfStCo: pd.DataFrame = pd.DataFrame() try: dfStCo = pd.read_csv(cfg.LOCAL_STATES_COUNTIES_FILE_NAME, delimiter=None, encoding="mbcs") except Exception as ex: utl.processLogMessage( logging.ERROR, f"Unable to read local static data, '{cfg.LOCAL_STATES_COUNTIES_FILE_NAME}'. {ex.__doc__}", loggers, ) raise OSError( f"Unable to read local static data, '{cfg.LOCAL_STATES_COUNTIES_FILE_NAME}'. {ex.__doc__}" ) return dfStCo
def __loadLookupFromPreviousData( self, localPreviousDataFile: str) -> pd.DataFrame: dfStCo: pd.DataFrame = pd.DataFrame() try: dfAll = pd.read_csv(localPreviousDataFile, delimiter=None, encoding="mbcs") dfStCo = dfAll[["state", "county"]] except Exception as ex: utl.processLogMessage( logging.ERROR, f"Unable to read local previous data, '{localPreviousDataFile}'. {ex.__doc__}", loggers, ) raise OSError( f"Unable to read local previous data, '{localPreviousDataFile}'. {ex.__doc__}" ) return dfStCo
def getFilteredData(self, whichState: str, whichCounty: str) -> pd.DataFrame: dfFiltered: pd.DataFrame = None try: df = pd.read_csv(cfg.LOCAL_DATA_FILE_NAME, delimiter=None, encoding="mbcs") except Exception as ex: utl.processLogMessage( logging.ERROR, f"Unable to read local data, '{cfg.LOCAL_DATA_FILE_NAME}'. {ex.__doc__}", loggers, ) else: # filter just for the requested fips value. When the dataframe was created, # fips was imported as a float64 dfFiltered = df[df.apply(lambda f: f["state"] == whichState and f[ "county"] == whichCounty, axis=1)] dfFiltered = dfFiltered.drop(cfg.UNUSED_COLUMNS, axis=1) return dfFiltered
def getLatestData(self, fromServer: bool) -> bool: retVal: bool = True wasRemoteCallSuccessful: bool = True if fromServer: # make a call to get the latest CSV file try: csv = requests.get(url=cfg.DATA_URL) if (csv.status_code != 200) or (len(csv.text) < 1000): wasRemoteCallSuccessful = False utl.processLogMessage( logging.WARNING, f"Unable to retrieve data from server. HTTP status code: {csv.status_code}. Using local data, if possible.", loggers, ) except Exception as ex: utl.processLogMessage( logging.ERROR, f"The following error occurred. '{ex.__doc__}'. Using local data, if possible.", loggers, ) retVal = False # when the call succeeds and there is some text then # make a copy of the old file and create the new one if retVal and wasRemoteCallSuccessful: try: with open(cfg.LOCAL_DATA_FILE_NAME, "w") as f: f.write(csv.text) except Exception as ex: utl.processLogMessage( logging.ERROR, f"The following error occurred. '{ex.__doc__}'", loggers, ) retVal = False return retVal
def launchCharting(chartingOptions: dict) -> None: cvd = Covid19() useServerData = chartingOptions["isFromServer"] utl.processLogMessage( logging.INFO, f"Selected data for {chartingOptions['county']} County, {chartingOptions['state']}: {cfg.ChartFocus(chartingOptions['chartFocus']).name}", loggers) # this was chosen by the user in the GUI if they want fresh data or not utl.processLogMessage( logging.INFO, "Retrieving data from server..." if useServerData else "Retrieving from local file...", loggers) if (not cvd.getLatestData(useServerData)) and (not os.path.isfile( cfg.LOCAL_DATA_FILE_NAME)): utl.processLogMessage( logging.CRITICAL, "Unable to download latest data nor able to use local data.", loggers, ) else: utl.processLogMessage(logging.INFO, "Filtering data...", loggers) dfCovidForCounty = cvd.getFilteredData(chartingOptions["state"], chartingOptions["county"]) if not dfCovidForCounty.empty: utl.processLogMessage(logging.INFO, "Computing daily deltas...", loggers) cvd.addComputedColumns(dfCovidForCounty) # dfCovidForCounty fields (columns) are: date,county,state,fips,cases,deaths pd.set_option("display.max_rows", None) utl.processLogMessage(logging.INFO, "\n" + str(dfCovidForCounty.tail()), loggers) cvd.showChart( dfCovidForCounty, chartingOptions["chartFocus"], chartingOptions["county"], chartingOptions["state"], chartingOptions["saveChart"], )