def _get_station_codes(self, force=False):
if not force and self.station_codes is not None:<EOL><INDENT>return self.station_codes<EOL><DEDENT>state_urls = self._get_state_urls()<EOL>state_matches = None<EOL>if self.bbox:<EOL><INDENT>with collection(<EOL>os.path.join(<EOL>"<STR_LIT>",<EOL>"<STR_LIT>",<EOL>),<EOL>"<STR_LIT:r>",<EOL>) as c:<EOL><INDENT>geom_matches = [<EOL>x["<STR_LIT>"] for x in c.filter(bbox=self.bbox)<EOL>]<EOL>state_matches = [<EOL>x["<STR_LIT>"] if x["<STR_LIT>"] != "<STR_LIT>" else "<STR_LIT>"<EOL>for x in geom_matches<EOL>]<EOL><DEDENT><DEDENT>self.station_codes = []<EOL>for state_url in state_urls:<EOL><INDENT>if state_matches is not None:<EOL><INDENT>state_abbr = state_url.split("<STR_LIT:/>")[-<NUM_LIT:1>].split("<STR_LIT:.>")[<NUM_LIT:0>]<EOL>if state_abbr not in state_matches:<EOL><INDENT>continue<EOL><DEDENT><DEDENT>self.station_codes.extend(self._get_stations_for_state(state_url))<EOL><DEDENT>if self.bbox:<EOL><INDENT>metadata = self._get_metadata(self.station_codes)<EOL>parsed_metadata = self.parser._parse_metadata(metadata)<EOL>def in_bbox(code):<EOL><INDENT>lat = parsed_metadata[code]["<STR_LIT>"]<EOL>lon = parsed_metadata[code]["<STR_LIT>"]<EOL>return (<EOL>lon >= self.bbox[<NUM_LIT:0>]<EOL>and lon <= self.bbox[<NUM_LIT:2>]<EOL>and lat >= self.bbox[<NUM_LIT:1>]<EOL>and lat <= self.bbox[<NUM_LIT:3>]<EOL>)<EOL><DEDENT>self.station_codes = list(filter(in_bbox, self.station_codes))<EOL><DEDENT>return self.station_codes<EOL>
Gets and caches a list of station codes optionally within a bbox.

Will return the cached version if it exists unless force is True.