def datacoveragebrowser(): """ Creates the datacoveragebrowser view and edits the link which directs to the actual datacoverage image which is created according to the given parameters """ from polyfemos.front import forms importlib.reload(forms) form = forms.DatacoverageForm() if not form.validate_on_submit(): enddate = UTCDateTime().now() startdate = enddate - 86400 * 30 form.station_ids.data = [] form.channel_codes.data = [] form.startdate.data = startdate.date form.enddate.data = enddate.date startdate = parse_date(form.startdate.data) enddate = parse_date(form.enddate.data) + 86399 station_ids = form.station_ids.data channel_codes = form.channel_codes.data func_ = userdef.datacoveragebrowser_func() fig = func_(station_ids, channel_codes, startdate, enddate, userdef.filepathformats("rawdata")) data = get_image_data(fig) return render_base(render_template)("datacoveragebrowser.htm", form=form, station_ids=station_ids, channel_codes=channel_codes, dcimage=data)
def _get_stf_filepath(self, date): """ :type date: :class:`~obspy.core.utcdatetime.UTCDateTime` :param date: :rtype: str :return: Filepath following the filepathformat defined in YAML config files. """ return self._get_filepath(date, userdef.filepathformats("stf"), ".stf")
def sohtable(): """ A state of health table with every station and parameter combination, incorporating current alerts and alert history. """ from polyfemos.front import forms importlib.reload(forms) form = forms.SohTableForm() if not form.validate_on_submit(): form.date.data = UTCDateTime().now().date form.show_all.data = True form.realtimeness_bool.data = True form.realtimeness_limit.data = 120 realtimeness_limit = form.realtimeness_limit.data realtimeness_bool = form.realtimeness_bool.data realtimeness = None if realtimeness_bool: realtimeness = UTCDateTime() - 60 * realtimeness_limit date = form.date.data if form.submit_pd.data: date += timedelta(days=1) elif form.submit_sd.data: date -= timedelta(days=1) form.date.data = date julday, year = get_jY(date) visibilities = {1, 2} if form.show_all.data else {1} sohpar_names = userdef.sohpars(visibilities=visibilities) station_ids = userdef.station_ids() fpf = userdef.filepathformats("alert") sohdict = get_sohdict(station_ids, year, julday, fpf, realtimeness=realtimeness) header = "" header = "{}.{}".format(year, julday) return render_base(render_template)('sohtable.htm', alertdict=sohdict['alerts'], header=header, station_ids=station_ids, sohpar_names=sohpar_names, form=form)
def _get_csv_filepath(self, date, extension=".csv", force=False): """ :type date: :class:`~obspy.core.utcdatetime.UTCDateTime` :param date: :type force: bool :param force: see :func:`~polyfemos.front.request.filepath` :type extension: str :param extension: file extension, defaults to ``".csv"`` :rtype: str :return: Filepath following the filepathformat defined in YAML config files. """ return self._get_filepath(date, userdef.filepathformats("csv"), extension, force=force)
def alertheat(): """ Creates a state of health table with every station and parameter combination. Timespan selection available for time interval anaysis. """ from polyfemos.front import forms importlib.reload(forms) form = forms.AlertHeatForm() enddate = UTCDateTime().now() startdate = enddate - 86400 * 20 if not form.validate_on_submit(): form.startdate.data = startdate.date form.enddate.data = enddate.date form.log_color.data = False form.points_per_thbb.data = 1 form.points_per_tib.data = 2 startdate = parse_date(form.startdate.data) enddate = parse_date(form.enddate.data) log_color = form.log_color.data points = { "0": 0, "1": form.points_per_thbb.data, "2": form.points_per_tib.data, } sohpar_names = userdef.sohpars(visibilities={1, 2}) station_ids = userdef.station_ids() fpf = userdef.filepathformats("alert") results = {} while startdate <= enddate: julday, year = get_jY(startdate) sohdict = get_sohdict(station_ids, year, julday, fpf) for k, v in sohdict['alerts'].items(): if k not in results: results[k] = {'count': 0, 'max': 0} if v in points: results[k]['count'] += points[v] results[k]['max'] += 2. startdate += 86400 cmap = LinearSegmentedColormap.from_list("", [ colors.ALERT_GREEN, colors.ALERT_YELLOW, colors.ALERT_RED, ]) for k, v in results.items(): if v['max'] <= 0.: v['color'] = colors.GREY_3 v['tooltip'] = "0 / 0\n0.0%" continue else: percentage = v['count'] / v['max'] percents = round(100. * percentage, 2) if log_color: color = 255. * np.log(max(1, percents)) / np.log(100) else: color = 255. * percentage color = int(round(color)) v['color'] = rgb2hex(cmap(color)[:3]) v['tooltip'] = "{} / {:.0f}\n{:.1f}%" \ .format(v['count'], v['max'], percents) return render_base(render_template)('alertheat.htm', alertdict=results, station_ids=station_ids, sohpar_names=sohpar_names, form=form)
def sohmap(): """ A map of the network area with stations. Alerts are sorted by their priorities. The innermost circle consists of the alerts of the highest priority. """ alertcolors = { 0: colors.ALERT_GREEN, 1: colors.ALERT_YELLOW, 2: colors.ALERT_RED, } filename = userdef.paths("map_file") filename, extension = os.path.splitext(filename) imgfile = "web_static/{}{}".format(filename, extension) mapfile = "web_static/{}{}".format(filename, ".map") msg = "Img and map files: {}, {}".format(imgfile, mapfile) messenger(msg, "R") if not os.path.isfile(imgfile): return render_base(render_template)('sohmap.htm') if not os.path.isfile(mapfile): return render_base(render_template)('sohmap.htm') # get transformation from WGS84 to pixels pixel_transform = coordinator.transform_from_ozi_map(mapfile) # open background map pil_image = Image.open(imgfile) draw = ImageDraw.Draw(pil_image) today = UTCDateTime().now() julday, year = get_jY(today) sohpar_names = userdef.sohpars() station_ids = userdef.station_ids() # get alerts and priorities with each station and parameter combination fpf = userdef.filepathformats("alert") sohdict = get_sohdict(station_ids, year, julday, fpf) for station_id in station_ids: sohplot = SOHPlot( station_id=station_id, headerdate=today, ) epsg = sohplot.header["EPSG"] locx = sohplot.header["LOCX"] locy = sohplot.header["LOCY"] if epsg is None: continue # Convert stations coordinates into WGS84 transform = coordinator.get_transform(epsg, "4326") px, py = pixel_transform(*transform(locx, locy)) def get_bbox(radius): return (px - radius, py - radius, px + radius, py + radius) # Alerts are stored in 3x3 matrix # Priority in x axis # Alert (red, yellow or green) in y axis # Red alert with the highest priority is stored in [0,2] alertcount = np.zeros((3, 3)) for sohpar_name in sohpar_names: key = station_id + sohpar_name if key not in sohdict['alerts']: continue alert = to.int_(sohdict['alerts'][key]) priority = to.int_(sohdict['priorities'][key]) if alert is None or priority is None or priority > 4: continue priority = min(3, priority) - 1 alertcount[alert, priority] += 1 # TODO clean plotting, own function? # TODO Scalable map radius = 21 for i in range(3)[::-1]: bbox = get_bbox(radius) draw.ellipse(bbox, fill=colors.BLACK) radius -= 1 alerts = alertcount[:, i] alertsum = np.sum(alerts) bbox = get_bbox(radius) if alertsum <= 0: draw.pieslice(bbox, start=0, end=360, fill=colors.GREY_3) else: alerts *= 360. / alertsum start = 0 for j in range(3): alert = alerts[j] color = alertcolors[j] end = start + alert draw.pieslice(bbox, start=start, end=end, fill=color) start += alert radius -= 5 - i fontpath = userdef.paths("ttf_file") font = None if os.path.isfile(fontpath): font = ImageFont.truetype(fontpath, 20) str_ = "{} UTC".format(today.strftime("%Y-%m-%d %H:%M:%S")) draw.text((10, 10), str_, font=font, fill=(0, 0, 0, 128)) max_height = 1500 width, height = pil_image.size scale = int(max_height / height) pil_image = pil_image.resize((scale * width, scale * height), resample=Image.ANTIALIAS) data = get_image_data(pil_image) return render_base(render_template)('sohmap.htm', sohmapimg=data)