diff --git a/GWalarm.kv b/GWalarm.kv index c5d3eb881609aea8a4d2d5c48b94972856c917f6..b96c6aaeb81c45fbcd11f1d0b36aed5cfd419c97 100644 --- a/GWalarm.kv +++ b/GWalarm.kv @@ -1,30 +1,349 @@ #:kivy 1.11.0 : + text_size: root.width, None + size:self.texture_size + halign: 'center' + valign: 'middle' + font_size: 14 + +: + imgsource:'./neutral.png' + sorttype: + newsort: canvas.before: Color: rgba: 0.2,0.25,0.4,1 Rectangle: size:self.size pos:self.pos + canvas: + Color: + rgba: 0.2,0.2,0.2,1 Line: - width: 2 - rectangle: self.x, self.y, self.width, self.height + width: 1 + rectangle: self.x, self.y, self.width, 2 + canvas.after: + Rectangle: + pos:self.pos[0]+self.width*0.87,self.pos[1]+self.height*0.25 + size:self.width*0.13,self.height*0.5 + source:root.imgsource text_size: root.width, None - size_hint_y: 0.2 + size:self.texture_size halign: 'center' valign: 'middle' font_size: 14 +: + valign:'top' + iam: 'Button' + color:(0,0,0,1) + bg_col:(1,1,1,1) + canvas.before: + Color: + rgba: self.bg_col + Rectangle: + pos:self.pos + size:self.size + +: + det1props: ['test1','test2','test3',[1,0,1,1]] + det2props: ['test1','test2','test3',[1,0,1,1]] + det3props: ['test1','test2','test3',[1,0,1,1]] + det4props: ['test1','test2','test3',[1,0,1,1]] + det5props: ['test1','test2','test3',[1,0,1,1]] + + GridLayout: + canvas.before: + Color: + rgba:238/255,238/255,235/255,1 + Rectangle: + size:self.size + pos:self.pos + rows:3 + BoxLayout: + size_hint_y:0.1 + BoxLayout: + DetectLabel: + bg_col:root.det1props[3] + text:root.det1props[0] + on_press:root.retract(self) + valign:'top' + DetectLabel: + bg_col:root.det1props[3] + text:root.det1props[1] + on_press:root.retract(self) + valign:'top' + + DetectLabel: + bg_col:root.det1props[3] + text:root.det1props[2] + on_press:root.retract(self) + valign:'top' + BoxLayout + DetectLabel: + bg_col:root.det2props[3] + text:root.det2props[0] + on_press:root.retract(self) + valign:'top' + DetectLabel: + bg_col:root.det2props[3] + text:root.det2props[1] + on_press:root.retract(self) + valign:'top' + DetectLabel: + bg_col:root.det2props[3] + text:root.det2props[2] + on_press:root.retract(self) + valign:'top' + GridLayout: + cols:2 + GridLayout: + rows:3 + Label: + text:'Detector Network' + WrapLabel: + text:'Detector spiel here: Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis pretium interdum orci quis condimentum. Nunc cursus lorem dolor, at auctor velit aliquet et. Suspendisse potenti. Donec ac hendrerit ex. Maecenas et lectus dapibus, lacinia quam eget, consectetur elit. Donec non imperdiet quam, in imperdiet est. Suspendisse laoreet elementum libero a semper. Duis in molestie tortor, id interdum urna. Sed ultrices nisl at elit facilisis, ac scelerisque mi lacinia. Pellentesque eu orci at quam porta bibendum at et risus. Nam sed risus bibendum, convallis augue ut, suscipit eros. Ut viverra nec odio sit amet pulvinar. Aenean lorem purus, mollis in elementum ac, porttitor eget diam. ' + Button: + on_press:root.manager.current='main' + text:'Main menu' + size_hint_y:0.1 + AsyncImage: + source:"./Detector_Plot_3.png" + + BoxLayout: + size_hint_y:0.1 + BoxLayout: + DetectLabel: + bg_col:root.det3props[3] + text:root.det3props[0] + on_press:root.retract(self) + valign:'bottom' + DetectLabel: + bg_col:root.det3props[3] + text:root.det3props[1] + on_press:root.retract(self) + valign:'bottom' + DetectLabel: + bg_col:root.det3props[3] + text:root.det3props[2] + on_press:root.retract(self) + valign:'bottom' + BoxLayout: + DetectLabel: + bg_col:root.det4props[3] + text:root.det4props[0] + on_press:root.retract(self) + DetectLabel: + bg_col:root.det4props[3] + text:root.det4props[1] + on_press:root.retract(self) + valign:'bottom' + DetectLabel: + bg_col:root.det4props[3] + text:root.det4props[2] + on_press:root.retract(self) + + BoxLayout: + DetectLabel: + bg_col:root.det5props[3] + text:root.det5props[0] + on_press:root.retract(self) + valign:'bottom' + DetectLabel: + bg_col:root.det5props[3] + text:root.det5props[1] + on_press:root.retract(self) + valign:'bottom' + DetectLabel: + bg_col:root.det5props[3] + text:root.det5props[2] + on_press:root.retract(self) + valign:'bottom' + +: + GridLayout: + cols:2 + BoxLayout: + Label: + text:'Title' + Label: + text:'Status' + Label: + text:'Bio: Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis pretium interdum orci quis condimentum. Nunc cursus lorem dolor, at auctor velit aliquet et. Suspendisse potenti. Donec ac hendrerit ex. Maecenas et lectus dapibus, lacinia quam eget, consectetur elit. Donec non imperdiet quam, in imperdiet est. Suspendisse laoreet elementum libero a semper. Duis in molestie tortor, id interdum urna. Sed ultrices nisl at elit facilisis, ac scelerisque mi lacinia. Pellentesque eu orci at quam porta bibendum at et risus. Nam sed risus bibendum, convallis augue ut, suscipit eros. Ut viverra nec odio sit amet pulvinar. Aenean lorem purus, mollis in elementum ac, porttitor eget diam. ' + Button: + text:'Return to Detector Summary' + on_press:root.change() + size_hint_y:0.1 + AsyncImage: + source:None + +: + size_hint_y:None + text_size: root.width, None + height:self.texture_size[1] + halign: 'justify' + font_size:12 + line_height:0.9 + markup:True : - canvas.before: + canvas: Color: rgba: 1,1,1,1 Rectangle: size:self.size pos:self.pos + +: + bg_col:(0,0,0,0) + color:(1,1,1,1) + canvas.before: + Color: + rgba:self.bg_col + Rectangle: + size:self.size + pos:self.pos + + +: + part1info:['HasRemnant','HasNS'] + part2info:['GraceID','Distance','FAR','DetectionTime','UpdateTime','Revision'] + part3info:['BBH','BNS','NSBH','MassGap','Terrestrial'] + + namelist: ['GraceID','Distance','FAR','DetectionTime','UpdateTime','Revision','BBH','BNS','NSBH','MassGap','Terrestrial','HasRemnant','HasNS'] + row: ['GraceID','Distance','FAR','DetectionTime','UpdateTime','Revision','BBH','BNS','NSBH','MassGap','Terrestrial','HasRemnant','HasNS'] + rowdict:dict(zip(self.namelist,self.row)) + background_color: [.2,.2,.4,1] + size_hint:(0.97,0.97) + + Carousel: + GridLayout: + cols:3 + GridLayout: + size_hint:(0.2,1) + rows:3 + padding: 10,2 + canvas.after: + Color: + rgba: 0.6,0.6,0.6,1 + Line: + width:1 + rectangle: self.x, self.y, self.width, self.height + Label: + text:'Glossary' + size_hint_y:0.1 + Glossary: + size_hint:(1,0.8) + Button: + text:'Exit Info Scrn' + size_hint_y:0.1 + on_press:root.dismiss() + GridLayout: + rows:3 + size_hint:(0.3,1) + BoxLayout: + size_hint_y:0.15 + canvas.after: + Color: + rgba:1,0,0,1 + Line: + width:2 + rectangle: self.x+1, self.y+1, self.width+1, self.height+1 + + orientation:'vertical' + InfoLabel: + text:root.part1info[0] + ':' + root.rowdict[root.part1info[0]] + bg_col:(188/255,189/255,34/255,1) + InfoLabel: + text:root.part1info[1] + ':' + root.rowdict[root.part1info[1]] + bg_col:(23/255,190/255,207/255,1) + + GridLayout: + rows: len(root.part2info) + size_hint_y:0.45 + canvas.before: + Color: + rgba: (0.2,0.2,0.2,1) + Rectangle: + size:self.size + pos:self.pos + InfoLabel: + text:root.part2info[0] + ':' + root.rowdict[root.part2info[0]] + InfoLabel: + text:root.part2info[1] + ':' + root.rowdict[root.part2info[1]] + InfoLabel: + text: root.part2info[2] + ':' + root.rowdict[root.part2info[2]] + InfoLabel: + text:root.part2info[3] + ':' + root.rowdict[root.part2info[3]] + InfoLabel: + text: root.part2info[4] + ':' + root.rowdict[root.part2info[4]] + InfoLabel: + text:root.part2info[5] + ':' + root.rowdict[root.part2info[5]] + GridLayout: + size_hint_y:0.4 + rows: len(root.part3info) + canvas.after: + Color: + rgba:0,0,1,1 + Line: + width:2 + rectangle: self.x, self.y, self.width, self.height + InfoLabel: + text:root.part3info[0] + ':' + root.rowdict[root.part3info[0]] + bg_col:(44/255,160/255,44/255,1) + InfoLabel: + text:root.part3info[1] + ':' + root.rowdict[root.part3info[1]] + bg_col:(31/255,119/255,180/255,1) + InfoLabel: + text: root.part3info[2] + ':' + root.rowdict[root.part3info[2]] + bg_col:(1,127/255,14/255,1) + InfoLabel: + text:root.part3info[3] + ':' + root.rowdict[root.part3info[3]] + bg_col:(214/255,39/255,40/255,1) + InfoLabel: + text: root.part3info[4] + ':' + root.rowdict[root.part3info[4]] + bg_col:(148/255,103/255,189/255,1) + + GridLayout: + spacing:10 + rows:2 + size_hint:(0.4,1) + canvas.before: + Color: + rgba: 1,1,1,1 + Rectangle: + size:self.size + pos:self.pos + + BoxLayout: + size_hint:(1,0.3) + canvas.after: + Color: + rgba: 1,0,0,1 + Line: + width:2 + rectangle: self.x+1, self.y+1, self.width+1, self.height+1 + + AsyncImage: + source:root.rowdict['GraceID']+'_bar.png' + + BoxLayout: + size_hint:(1,0.7) + canvas.after: + Color: + rgba: 0,0,1,1 + Line: + width:2 + rectangle: self.x+1, self.y+1, self.width+1, self.height+1 + AsyncImage: + source:root.rowdict['GraceID']+'_pie.png' + AsyncImage: + source:root.rowdict['skymap'] + + + : canvas.before: Color: @@ -41,18 +360,53 @@ rgba: self.current_color Rectangle: size:self.size - pos:self.pos + pos:self.pos +: + rows:2 + orientation:'vertical' + nom:'tobereplaced' + desc:'tobereplaced' + padding:(3,10) + spacing:(0,3) + + GlossDefLabel: + text:'[b][u]'+root.nom+'[/b][/u] \n' + root.desc + valign:'top' : on_press:self.nav() - -: - orientation: 'vertical' - spacing:10 + +: + color:0,0,0,1 + font_size:14 : - on_press:self.details() - -: - viewclass:'EventContainer' - \ No newline at end of file + name: None + text0:'tobereplaced' + text1:'tobereplaced' + text2:'tobereplaced' + text3:'tobereplaced' + text4:'tobereplaced' + on_press: self.details() + canvas.before: + Color: + rgba: 0.9,0.9,0.9,1 + Rectangle: + pos:self.pos + size:self.size + canvas: + Color: + rgba:0.2,0.2,0.2,0.4 + Line: + width: 1 + rectangle: self.x, self.y, self.width, self.height + HisMainLabel: + text:root.text0 + HisMainLabel: + text:root.text1 + HisMainLabel: + text:root.text2 + HisMainLabel: + text:root.text3 + HisMainLabel: + text:root.text4 \ No newline at end of file diff --git a/GWalarm.py b/GWalarm.py index acb83b365d245f3882505b610a6b4bfb987bf8e8..6803016ea266e9ec79d22b6a014d1adfd3782e2f 100644 --- a/GWalarm.py +++ b/GWalarm.py @@ -1,31 +1,44 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +""" +Created on Mon Aug 5 17:04:33 2019 + +@author: christian +""" + import kivy kivy.require('1.11.0') +from kivy.config import Config +Config.set('graphics','width','800') +Config.set('graphics','height','480') +Config.set('kivy','default_font',[ + './fonts/OpenSans-Light.ttf','./fonts/OpenSans-Regular.ttf','./fonts/OpenSans-LightItalic.ttf', + './fonts/OpenSans-Bold.ttf']) + import threading import time from kivy.app import App from kivy.uix.button import Button from kivy.uix.gridlayout import GridLayout from kivy.uix.image import AsyncImage -from kivy.uix.slider import Slider from kivy.clock import Clock -from kivy.uix.pagelayout import PageLayout from kivy.uix.boxlayout import BoxLayout -from kivy.uix.spinner import Spinner from kivy.uix.label import Label from kivy.graphics import Color, Rectangle -from kivy.properties import StringProperty, NumericProperty, ListProperty -from kivy.graphics.instructions import Callback -from kivy.uix.screenmanager import ScreenManager, Screen, FadeTransition, SlideTransition +from kivy.properties import ListProperty, ObjectProperty, StringProperty, AliasProperty, DictProperty, NumericProperty +from kivy.uix.screenmanager import ScreenManager, Screen, FadeTransition, SlideTransition, NoTransition from kivy.uix.scrollview import ScrollView from kivy.uix.carousel import Carousel from kivy.uix.popup import Popup -from kivy.uix.behaviors import ButtonBehavior +from kivy.uix.behaviors import ButtonBehavior, ToggleButtonBehavior +from kivy.animation import Animation #import RPi.GPIO as GPIO from kivy.lang.builder import Builder -from souptest import statusdetect +from detector_monitorv2 import statusdetect +from sync_database import sync_database import gcn from gcn_test import process_gcn import requests @@ -33,6 +46,8 @@ from bs4 import BeautifulSoup from tables import * import datetime import os +import re +import numpy as np class Event(IsDescription): AlertType=StringCol(30) @@ -50,23 +65,34 @@ class Event(IsDescription): skymap=StringCol(30) DetectionTime=StringCol(30) UpdateTime=StringCol(30) - + MassGap=StringCol(30) + Distance=StringCol(30) + Revision=StringCol(30) + #FIXME: DECLARE ALL GPIO PINS AND INITIAL INS/OUTS HERE + +global flag +global main_flag +global newevent_flag +flag = 0 +main_flag=0 +newevent_flag=0 - -Builder.load_file('GWalarm.kv',rulesonly=True) +Builder.load_file('GWalarm.kv') class MainButton(Button): + name=ObjectProperty() def nav(self): app=App.get_running_app() - if self.id=='history': + app.root.transition=SlideTransition() + if self.name=='history': app.root.current='history' - elif self.id=='status': + elif self.name=='status': app.root.current='status' - elif self.id=='main': + elif self.name=='main': app.root.current='main' - elif self.id=='plots': + elif self.name=='plots': app.root.current='plots' class MainScreen(Screen): def __init__(self,**kwargs): @@ -76,18 +102,120 @@ class MainScreen(Screen): Color(.2,.2,.2,1) self.rect=Rectangle(size=(800,600), pos=layout.pos) - def exit(obj): + def stop(obj): + global main_flag + main_flag=1 App.get_running_app().stop() - quitButton=Button(text='Quit') - quitButton.bind(on_press=exit) self.add_widget(layout) ids=('history','status','plots') texts=('Event History','Detector Status','Test Plots') - [layout.add_widget(MainButton(text=texts[i],id=ids[i])) for i in range(0,len(ids))] -# hbut = MainButton(text=texts[i],id=ids[i]) -# layout.add_widget(hbut) + [layout.add_widget(MainButton(text=texts[i],name=ids[i])) for i in range(0,len(ids))] + quitButton=Button(text='Quit') + quitButton.bind(on_press=stop) layout.add_widget(quitButton) + + def event_waiting(): + '''New event popup handler''' + global newevent_flag + global main_flag + newevent_flag=0 + main_flag=0 + while True: + while True: + #check for the flag once per minute (same rate the file is polled) + if newevent_flag == 1: + newevent_flag=0 + #skip a level up to execute the rest of the loop, then back to waiting. + print('New event has been detected!!') + break + if main_flag == 1: + print('Event listener #2 closing...') + #return takes you right out of the function + return + time.sleep(5) + + #Read in the new event + if os.path.basename(os.getcwd()) != "event_data": + try: + os.chdir("./event_data") + except: + os.mkdir("./event_data") + os.chdir("./event_data") + while True: + try: + h5file = open_file("Event Database",mode="r",title="eventinfo") + break + except: + print("file in use... trying again in 5s") + time.sleep(5) + try: + h5file.root.events + except NoSuchNodeError: + time.sleep(5) + pass + + #parse the event data file for the most recent event to be loaded: that's the name + file = open("PreviousEventToRead.xml").read() + def search(line): + result = re.search('\n', + str(line)) + return result.group(1) + eventid = search(file) + print(str(eventid)) + for tab in h5file.list_nodes("/events"): + print(tab.name) + if str(tab.name) in eventid: + new_event_table=tab +# if tab.name == eventid: +# new_event_table = tab + namelist = new_event_table.colnames + new_event_row = new_event_table[-1] + orderedrow = [] + for key in namelist: + orderedrow.append(new_event_row[key].decode()) + pop = InfoPop(title='New Event Detected!',namelist=namelist,row=orderedrow) + pop.open() + h5file.close() + + event_waiting_thread = threading.Thread(target=event_waiting) + event_waiting_thread.start() + +class HisColLabel(ToggleButtonBehavior,Label): + sorttype=ObjectProperty() + newsort=ObjectProperty() + names=ObjectProperty() + specialnames=ObjectProperty() + primed=NumericProperty() + + def on_press(self): +# self.primed = 1 + for child in self.parent.children: + child.imgsource='./neutral.png' + + def on_state(self,widget,value): + Clock.schedule_once(lambda dt:self.on_state_for_real(widget,value),0) + def on_state_for_real(self,widget,value): + print('Pressed' ) + print(self.primed) +# if self.primed == 1: + global flag + flag = 1 + if value == 'down': + self.newsort = self.sorttype+' Descending' + self.imgsource='./ascending.png' + + else: + self.newsort = self.sorttype+' Ascending' + self.imgsource='./descending.png' + #time.sleep(0.1) + t2 = threading.Thread(target=historyUpdate,args=(App.get_running_app().root.children[0].children[0].children[1].children[0], + self.names,self.specialnames,self.newsort),daemon=True) + t2.start() +# elif self.primed == 0: +# self.imgsource='./neutral.png' +# self.primed=0 + class HistoryScreen(Screen): def __init__(self,**kwargs): @@ -102,13 +230,18 @@ class HistoryScreen(Screen): os.mkdir("./event_data") os.chdir("./event_data") - h5file = open_file("Event Database",mode="a",title="eventinfo") + while True: + try: + h5file = open_file("Event Database",mode="r",title="eventinfo") + break + except: + print("file in use... trying again in 5s") + time.sleep(5) try: - h5file.create_group("/",'events') - except NodeError: + h5file.root.events + except NoSuchNodeError: + time.sleep(5) pass - - #grab a table, it doesn't matter which one! x=0 for table in h5file.iter_nodes(where="/events",classname="Table"): @@ -117,32 +250,57 @@ class HistoryScreen(Screen): break def receive(): + #host="209.208.78.170" gcn.listen(host="209.208.78.170",handler=process_gcn) t4 = threading.Thread(target=receive,daemon=True) t4.start() - -# if 'tables' in locals(): names = tables.colnames - nameLay = GridLayout(cols=len(names),size_hint_y=0.2) - specialnames=['GraceID','Instruments','FAR','DetectionTime','UpdateTime'] + num_events = len(h5file.list_nodes(where="/events",classname="Table")) + h5file.close() + nameLay = GridLayout(cols=len(names),size_hint_y=0.1) + specialnames=['GraceID','Distance','Instruments','FAR','UpdateTime'] for name in specialnames: - lab = WrapLabel(text=name) + lab = HisColLabel(text=name,color=(0,0,0,1),sorttype=name) + lab.names=names + lab.specialnames=specialnames nameLay.add_widget(lab) layout.add_widget(nameLay) - hisScroll = ScrollView(do_scroll_x=False,size_hint=(1,1)) + hisScroll = ScrollView(do_scroll_x=False,do_scroll_y=True,size_hint=(1,0.7)) layout.add_widget(hisScroll) - - hisBox = BoxLayout(orientation='vertical',size_hint_y=None,height=1000) - hisScroll.add_widget(hisBox) - - t2 = threading.Thread(target=historyUpdate,args=(hisBox,names,specialnames),daemon=True) + hisGrid = GridLayout(rows=num_events*100,size_hint_y=None) + hisGrid.bind(minimum_height=hisGrid.setter('height')) + hisGrid.height=num_events*50 + hisScroll.add_widget(hisGrid) + + t2 = threading.Thread(target=historyUpdate,args=(hisGrid,names,specialnames),daemon=True) t2.start() -# else: -# lab = WrapLabel(text='No events to be listed here') -# layout.add_widget(lab) - button2 =MainButton(text='Main Menu',id='main',size_hint_y=0.1) - layout.add_widget(button2) + '''backup stuff''' + + smalls=BoxLayout(size_hint_y=0.1) + def refresh_all(arg): + App.get_running_app().stop() + App.get_running_app().root_window.close() + print('shutdown') + #time.sleep(5) + sync_database() + #Wait for it to finish.... + print('done - restart away') + + backupTestButton=Button(text='Back up database (takes ages)') + smalls.add_widget(backupTestButton) + + def stupid(obj): + content = Button(text='Ok') + content.bind(on_press=refresh_all) + confirm = Popup(title='Are you sure?',content=content,size_hint=(0.4,0.4)) + confirm.open() + + backupTestButton.bind(on_press=stupid) + + button2 =MainButton(text='Main Menu',name='main')#,size_hint_y=0.1) + smalls.add_widget(button2) + layout.add_widget(smalls) class DetGrid(GridLayout): def __init__(self,**kwargs): @@ -157,103 +315,294 @@ class DetLabel(Label): class WrapLabel(Label): pass -class NestedBox(BoxLayout): - pass - -class PressableLabel(Label): +class HeadingLabel(ToggleButtonBehavior,Label): + def on_state(self,widget,value): + if value == 'down': + print('down') + else: + print('up') pass -class EventContainer(ButtonBehavior,GridLayout): - namelist=ListProperty(None) - row = ListProperty(None) - def details(self): - #print(self.names) - #specialnames=['AlertType','] +class InfoPop(Popup): + namelist=ObjectProperty() + row=ObjectProperty() - content=Carousel() - img = self.row[self.namelist.index('GraceID')]+'.png' - content.add_widget(AsyncImage(source=img)) - testbut = Button(text='get me out') - content.add_widget(testbut) - infoPopup = Popup(title="Superevent Information", content=content,size_hint=(0.8,0.8)) - testbut.bind(on_press=infoPopup.dismiss) +class GlossLabel(BoxLayout): + nom=ObjectProperty() + desc=ObjectProperty() + +class Glossary(ScrollView): + descs = ListProperty() + namelist = ListProperty() + def __init__(self,**kwargs): + super().__init__(**kwargs) + Clock.schedule_once(self.finish_init,0) + def finish_init(self,dt): + descdict = {'GraceID': 'Identifier in GraceDB', 'AlertType': 'VOEvent alert type', + 'Instruments': 'List of instruments used in analysis to identify this event', + 'FAR': 'False alarm rate for GW candidates with this strength or greater', + 'Group': 'Data analysis working group', + 'BNS': 'Probability that the source is a binary neutron star merger (both objects lighter than 3 solar masses)', + 'NSBH': 'Probability that the source is a neutron star-black hole merger (primary heavier than 5 solar masses, secondary lighter than 3 solar masses)', + 'BBH': 'Probability that the source is a binary black hole merger (both objects heavier than 5 solar masses)', + 'Terrestrial': 'Probability that the source is terrestrial (i.e., a background noise fluctuation or a glitch)', + 'HasNS': 'Source classification: binary neutron star (BNS), neutron star-black hole (NSBH), binary black hole (BBH), MassGap, or terrestrial (noise)', + 'HasRemnant': 'Probability that at least one object in the binary has a mass that is less than 3 solar masses', + 'Distance':'Posterior mean distance to the event (with standard deviation) in MPc', + 'DetectionTime':'The mean date & time at which the event was first detected', + 'UpdateTime': "The date & time of the most recent update to this event's parameters", + 'MassGap':"Compact binary systems with at least one compact object whose mass is in the hypothetical 'mass gap' between neutron stars and black holes, defined here as 3-5 solar masses.", + 'Revision':"The number of revisions (updates) made to this event's parameters"} + descripts=[] + names = [] + for key,value in descdict.items(): + names.append(key) + descripts.append(value) + self.namelist = sorted(names) + self.descs=[x for _,x in sorted(zip(names,descripts))] + layout2 = GridLayout(rows=len(self.descs),size_hint_y=None) + #layout2.bind(minimum_height=self.setter('height')) + for i in range(len(self.namelist)): + #lab = WrapLabel(text=self.namelist[i]+':'+self.discs[i]) + #layout2.add_widget(lab) + gloss = GlossLabel() + gloss.nom=self.namelist[i] + gloss.desc=self.descs[i] + layout2.add_widget(gloss) + self.add_widget(layout2) + self.do_scroll_x=False + #self.add_widget(layout) + layout2.height=sum([c.height for c in layout2.children])+20 + +class EventContainer(ButtonBehavior,GridLayout): + name=ObjectProperty() + namelist=ListProperty(['test1','test2']) + row = ListProperty(['test1','test2']) + pop = ObjectProperty() + img= StringProperty() + text0=StringProperty('tobereplaced') + text1=StringProperty('tobereplaced') + text2=StringProperty('tobereplaced') + text3=StringProperty('tobereplaced') + text4=StringProperty('tobereplaced') + + def __init__(self,**kwargs): + super().__init__(**kwargs) + Clock.schedule_once(self.finish_init,0) - infoPopup.open() + def finish_init(self,dt): + self.pop = InfoPop(title="Superevent Information",namelist=self.namelist,row=self.row) -def historyUpdate(obj,names,specialnames): + def details(self): + self.pop.namelist = self.namelist + self.pop.row = self.row + self.pop.open() +def historyUpdate(obj,names,specialnames,sorttype='Time Descending'): + '''An important function that is responsible for populating and repopulating the history screen.''' + global flag + global main_flag + #reset stop flag + main_flag=0 if os.path.basename(os.getcwd()) != "event_data": try: os.chdir("./event_data") except: os.mkdir("./event_data") - os.chdir("./event_data") + os.chdir("./event_data") #initial check to ensure file exists with necessary groupings - h5file = open_file("Event Database",mode="a",title="eventinfo") + while True: + try: + h5file = open_file("Event Database",mode="r",title="eventinfo") + break + except: + print("file in use... trying again in 5s") + time.sleep(5) try: - h5file.create_group("/","events") - except NodeError: + h5file.root.events + except NoSuchNodeError: + time.sleep(5) pass - h5file.close() - obj.clear_widgets() + + #initial stat + stats = os.stat("./Event Database") + lastaccess= stats.st_mtime + first = 1 while True: - h5file = open_file("Event Database",mode="a",title="eventinfo") - #get all them tables - totalno=len(h5file.list_nodes(where="/events",classname="Table")) - tables = [table for table in h5file.iter_nodes(where="/events",classname="Table")] - j=0 - for table in tables: - #read in the last row (most up to date) - #names = table.colnames - row = table[-1] - grid = EventContainer(cols=len(row)) - grid.namelist=names - orderedrow = [] - for key in names: - orderedrow.append(row[key].decode()) - grid.row=orderedrow - specialnames=['GraceID','Instruments','FAR','DetectionTime','UpdateTime'] - for string in row[specialnames]: - #FIXME: ADD NEAT TEXT BY PARSING INPUT TEXT - decoded = string.decode() - if decoded == '': - decoded = row['UpdateTime'].decode() - lab = Label(text=decoded,color=(0,0,0,1)) - grid.add_widget(lab) - #output_info[names[i]] = decoded - #for key, item in output_info.items(): - # lab = WrapLabel(text=key+' : '+item) - # grid.add_widget(lab) - obj.add_widget(grid,index=totalno-j) - j+=1 - - h5file.close() - time.sleep(60) - + stats = os.stat("./Event Database") + access = stats.st_mtime + if access != lastaccess or first == 1: + lastaccess=access + + + #Clear widgets + #obj.clear_widgets() + while True: + try: + h5file = open_file("Event Database",mode="r",title="eventinfo") + break + except: + print("file in use... trying again in 5s") + time.sleep(5) + + #get all tables + tables = [table for table in h5file.iter_nodes(where="/events",classname="Table")] + sort_vars = [] + + '''Check the table list and compare with current labels to see if boxes need changed''' + children = [child for child in obj.children] + #ids IN THE DISPLAY + widgetids = [] + for child in children: + widgetids.append(child.name) + #ids IN THE DATABASE + presentids = [child[-1]['GraceID'].decode() for child in h5file.root.events] + + '''Iterate through all events, re-drawing row-by-row the history viewer''' + for table in tables: + row=table[-1] + if 'Time' in sorttype: + sort_vars.append(row['UpdateTime'].decode().split()[0]) + elif 'Distance' in sorttype: + sort_vars.append(float(row['Distance'].decode().split()[0])) + elif 'GraceID' in sorttype: + string = str(row['GraceID'].decode()) + sort_vars.append(int(re.sub("[a-zA-Z]","",string))) + elif 'FAR' in sorttype: + sort_vars.append(float(row['FAR'].decode().split()[2])) + elif 'Instruments' in sorttype: + sort_vars.append(row['Instruments'].decode()) + if sort_vars != []: + if 'Descending' in sorttype: + try: + tables = [x for _,x in sorted(zip(sort_vars,tables),key=len[0])] + except TypeError: + tables2=[] + sort_indexes = np.argsort(np.array(sort_vars)) + for index in sort_indexes: + tables2.append(tables[index]) + tables=tables2 + elif 'Ascending' in sorttype: + try: + tables = [x for _,x in reversed(sorted(zip(sort_vars,tables)))] + except TypeError: + tables2=[] + sort_indexes = reversed(np.argsort(np.array(sort_vars))) + for index in sort_indexes: + tables2.append(tables[index]) + tables=tables2 + + #print(widgetids,presentids) + for i,table in enumerate(tables): + #read in the last row (most up to date) + row = table[-1] + orderedrow = [] + for key in names: + orderedrow.append(row[key].decode()) + if row['GraceID'].decode() not in widgetids: + if first == 0: + '''LAZY SOLUTION - NOT VERY FUTUREPROOF''' #FIXME + '''NEW EVENT!!!''' + global newevent_flag + newevent_flag=1 + + grid = EventContainer(cols=len(specialnames)+1,name=row['GraceID'].decode()) + grid.namelist=names +# for i in range(len(specialnames)): + #string=row[specialnames[i]] +# if specialnames[i] == 'Distance': +# getattr(grid,'text'+str(i))=string.decode().replace('+-',u'\xb1') + #else: + #FIXME: ADD NEAT TEXT BY PARSING INPUT TEXT + #getattr(grid,'text'+str(i)) = string.decode() + #lab2 = Label(text=decoded,color=(0,0,0,1),font_size=(16)) +# lab2 = Label(text=getattr(grid,'text'+str(i)),color=(0,0,0,1),font_size=(16)) +# grid.add_widget(lab2) + obj.add_widget(grid,i) + else: + grid = obj.children[i] + grid.row=orderedrow + for i in range(len(specialnames)): + string=row[specialnames[i]] + if specialnames[i] == 'Distance': + setattr(grid,'text'+str(i),string.decode().replace('+-',u'\xb1')) + elif specialnames[i] == 'GraceID': + grid.name=string.decode() + setattr(grid,'text'+str(i),string.decode()) + else: + #FIXME: ADD NEAT TEXT BY PARSING INPUT TEXT + setattr(grid,'text'+str(i),string.decode()) + for i,child in enumerate(children): + if widgetids[i] not in presentids: + obj.remove_widget(child) + #orderedrow = [] +# for key in names: +# orderedrow.append(row[key].decode()) +# grid.row=orderedrow +# +# for i in range(len(specialnames)): +# string=row[specialnames[i]] +# if specialnames[i] == 'Distance': +# decoded=string.decode().replace('+-',u'\xb1') +# else: +# #FIXME: ADD NEAT TEXT BY PARSING INPUT TEXT +# decoded = string.decode() +# lab2 = Label(text=decoded,color=(0,0,0,1),font_size=(16)) +# grid.add_widget(lab2) +# obj.add_widget(grid,len(obj.children)) + obj.do_layout() + print('Event History Updated...') + h5file.close() + #reset the flag + first = 0 + + waittime = 10 + i=0 + while i < waittime: + if flag ==1: + print('his_thread restart') + flag=0 + return + if main_flag ==1: + print('history thread closing...') + return + i+=1 + time.sleep(1) def statusupdate(obj): + global main_flag + main_flag=0 while True: - (detnames,stats,dettimes) = statusdetect() + data = statusdetect() - names = ['GEO 600', 'LIGO Hanford', 'LIGO Livingston','Virgo'] - order = [dettimes,detnames,names] - j=0 - for child in obj.children: - if stats[j] != 2: - child.current_color=[1-stats[j],0,stats[j],1] - else: - child.current_color=[0,1,0,1] - with child.canvas: - Color(rgba=child.current_color) - i=0 - for label in child.children: - label.text=order[i][j] - i+=1 - j+=1 - - time.sleep(30) + for i,elem in enumerate(data): + setattr(obj,'det'+str(i+1)+'props',elem) +# j=0 +# for child in obj.children: +# if stats[j] != 2: +# child.current_color=[1-stats[j],0,stats[j],1] +# else: +# child.current_color=[0,1,0,1] +# with child.canvas: +# Color(rgba=child.current_color) +# i=0 +# for label in child.children: +# label.text=order[i][j] +# i+=1 +# j+=1 + + waittime = 300 + i = 0 + while i < waittime: + if main_flag == 1: + print('statusthread closing...') + return + i+=1 + time.sleep(1) def plotupdate(obj): + global main_flag + main_flag=0 while True: if os.path.basename(os.getcwd()) != 'event_data': try: @@ -266,15 +615,17 @@ def plotupdate(obj): sort_date = [str(date.year),str(date.month).zfill(2),str(date.day).zfill(2)] datestring = sort_date[0]+sort_date[1]+sort_date[2] url = "https://www.gw-openscience.org/detector_status/day/"+datestring+"/" - + url2 = "https://www.gw-openscience.org/detector_status/day/"+datestring+"/instrument_performance/analysis_time/" #grab the soup and parse for links + descripts try: resp=requests.get(url) r = resp.text soup=BeautifulSoup(r,"lxml") + resp2 = requests.get(url2) + r2 = resp2.text + soup2 = BeautifulSoup(r2,"lxml") except: print("URL Error: URL to the Range plots is broken : check online") - obj.clear_widgets() sources=[] @@ -284,54 +635,100 @@ def plotupdate(obj): if 'png' in linkstr: sources.append('https://www.gw-openscience.org'+linkstr) descripts.append(str(link.get("title"))) - + for link in soup2.find_all("a"): + linkstr=str(link) + if 'png' and 'COINC' in linkstr: + descripts.append(str(link['title'])) + sources.append('https://www.gw-openscience.org'+str(link.get("href"))) + break + for i in range(0,len(sources)): lay = GridLayout(rows=2,padding=15) filepath = 'Detector_Plot_'+str(i)+'.png' os.system("curl -0 "+ sources[i] + ' > ' + filepath) img = AsyncImage(source = filepath,size_hint_y=0.8) - desc = WrapLabel(text=descripts[i]) + desc = WrapLabel(text=descripts[i],size_hint_y=0.2,color=(0,0,0,1)) obj.add_widget(lay) lay.add_widget(img) lay.add_widget(desc) - - #j=0 - #for source in sources: - # os.system("curl -0 "+ source + ' > ' + filepaths[j]) - # j+=1 - - time.sleep(3600) -class StatusScreen(Screen): - def __init__(self,**kwargs): - super().__init__(**kwargs) - layout = GridLayout(cols=1,rows=2,spacing=30,padding=30, row_default_height=150) - with layout.canvas.before: - Color(.2,.2,.2,1) - self.rect=Rectangle(size=(800,600),pos=layout.pos) - - self.add_widget(layout) - - detLay = NestedBox() + waittime=3600 + i=0 + while i < waittime: + if main_flag == 1: + print('plotthread closing...') + return + i+=5 + time.sleep(5) - for i in range(0,4): - lay = DetGrid(cols=3,spacing=10,padding=10) - for j in range(0,3): - box = DetLabel(text='test'+str(j)) - lay.add_widget(box) - with lay.canvas.before: - lay.col = Color(1,0,1,0) - lay.rect=Rectangle(pos=lay.pos) - detLay.add_widget(lay) - - layout.add_widget(detLay) +class DetectLabel(ButtonBehavior,Label): + pass - t = threading.Thread(target=statusupdate,args=(detLay,),daemon=True) +class StatusScreenv2(Screen): + def __init__(self,**kwargs): + super().__init__(**kwargs) + t = threading.Thread(target=statusupdate,args=(self,),daemon=True) t.start() + + def retract(self,presser): + for child in self.children[0].children: + if child.pos[1] < 240: + anim = Animation(x=child.pos[0],y=child.pos[1]-240-child.height,duration=0.5) + anim.start(child) + elif child.pos[1] > 240: + anim=Animation(x=child.pos[0],y=240+child.pos[1]+child.height,duration=0.5) + anim.start(child) + + App.get_running_app().root.transition=FadeTransition(duration=0.3) + def change(dt): + App.get_running_app().root.current='statinfo' + Clock.schedule_once(change,0.5) + +#class StatusScreen(Screen): +# '''DETECTOR STATUS SCREEN''' +# def __init__(self,**kwargs): +# super().__init__(**kwargs) +# layout = GridLayout(cols=1,rows=2,spacing=30,padding=30, row_default_height=150) +# with layout.canvas.before: +# Color(.2,.2,.2,1) +# self.rect=Rectangle(size=(800,600),pos=layout.pos) +# +# self.add_widget(layout) +# +# detLay = BoxLayout(orientation='vertical',spacing=10) +# +# for i in range(0,4): +# lay = DetGrid(cols=3,spacing=10,padding=10) +# for j in range(0,3): +# box = DetLabel(text='test'+str(j)) +# lay.add_widget(box) +# with lay.canvas.before: +# lay.col = Color(1,0,1,0) +# lay.rect=Rectangle(pos=lay.pos) +# detLay.add_widget(lay) +# +# layout.add_widget(detLay) +# +# t = threading.Thread(target=statusupdate,args=(detLay,),daemon=True) +# t.start() +# +# button3 = MainButton(text='Main Menu',name='main',size_hint_y=0.25) +# layout.add_widget(button3) - button3 = MainButton(text='Main Menu',id='main',size_hint_y=0.25) - layout.add_widget(button3) +class StatBio(Screen): + def change(obj): + App.get_running_app().root.current = 'status' + App.get_running_app().root.transition=NoTransition() + for child in App.get_running_app().root.current_screen.children[0].children: + if child.pos[1] < 240: + anim = Animation(x=child.pos[0],y=240+child.pos[1]+child.height) + anim.start(child) + elif child.pos[1] > 240: + anim=Animation(x=child.pos[0],y=child.pos[1]-240-child.height) + anim.start(child) + App.get_running_app().root.transition=SlideTransition() + pass class PlotsScreen(Screen): def __init__(self,**kwargs): @@ -339,35 +736,45 @@ class PlotsScreen(Screen): layout=GridLayout(rows=2) carousel = Carousel(direction='right',size_hint_y=0.9) - #layout2=GridLayout(rows=2) - self.add_widget(layout) layout.add_widget(carousel) - #carousel.add_widget(layout2) -# current_plot = Image(source='./event_data/Detector_Plot_0.png') -# current_desc = Label(text='Nothing yet...',size_hint_y=None,height=75) -# -# layout2.add_widget(current_plot) -# layout2.add_widget(current_desc) -# t3 = threading.Thread(target=plotupdate,args=(carousel,),daemon=True) t3.start() - button4 = MainButton(text='Main Menu',id='main',size_hint_y=0.1) + button4 = MainButton(text='Main Menu',name='main',size_hint_y=0.1) layout.add_widget(button4) -sm = ScreenManager() -sm.add_widget(MainScreen(name='main')) -sm.add_widget(HistoryScreen(name='history')) -sm.add_widget(StatusScreen(name='status')) -sm.add_widget(PlotsScreen(name='plots')) - class MyApp(App): -# def on_start(self): - + def build_config(self,config): + config.setdefaults('Section',{'InitialBackup':'0'}) + def on_start(self): + global flag + global main_flag + global newevent_flag + flag = 0 + main_flag=0 + newevent_flag=0 def build(self): + config = self.config + if config.get('Section','InitialBackup') == '0': + print('Performing Initial Event Sync. Please be patient - this may take a while...') + sync_database() + config.set('Section','InitialBackup','1') + config.write() + print('Initial Event Sync Complete...') + elif config.get('Section','InitialBackup') == '1': + print('Event Sync not required...') + + sm = ScreenManager() + sm.add_widget(MainScreen(name='main')) + sm.add_widget(HistoryScreen(name='history')) + sm.add_widget(StatusScreenv2(name='status')) + sm.add_widget(PlotsScreen(name='plots')) + sm.add_widget(StatBio(name='statinfo')) + + print('Initialising application...') return sm #Spyder test functionality @@ -379,7 +786,7 @@ def reset(): window.Window = window.core_select_lib('window', window.window_impl, True) Cache.print_usage() for cat in Cache._categories: - Cache._objects[cat] = {} + Cache._objects[cat] = {} if __name__ == '__main__': reset() diff --git a/MS181101ab-1-Preliminary.xml b/MS181101ab-1-Preliminary.xml deleted file mode 100644 index 0f2ed64769ce63628d221f142af467c8ba01be00..0000000000000000000000000000000000000000 --- a/MS181101ab-1-Preliminary.xml +++ /dev/null @@ -1,108 +0,0 @@ - - - - 2018-11-01T22:34:49 - - LIGO Scientific Collaboration and Virgo Collaboration - - - - - Indicates whether this event should be distributed to LSC/Virgo members only - - - The Notice Type number is assigned/used within GCN, eg type=150 is an LVC_PRELIMINARY notice - - - A number that increments by 1 each time a new revision is issued for this event - - - Identifier in GraceDB - - - VOEvent alert type - - - Indicates that this event is a hardware injection if 1, no if 0 - - - Indicates that this event is an open alert if 1, no if 0 - - - Web page for evolving status of this GW candidate - - - List of instruments used in analysis to identify this event - - - False alarm rate for GW candidates with this strength or greater - - - Data analysis working group - - - Low-latency data analysis pipeline - - - Specific low-latency search - - - - Sky Map FITS - - - - Source classification: binary neutron star (BNS), neutron star-black hole (NSBH), binary black hole (BBH), MassGap, or terrestrial (noise) - - Probability that the source is a binary neutron star merger (both objects lighter than 3 solar masses) - - - Probability that the source is a neutron star-black hole merger (primary heavier than 5 solar masses, secondary lighter than 3 solar masses) - - - Probability that the source is a binary black hole merger (both objects heavier than 5 solar masses) - - - Probability that the source has at least one object between 3 and 5 solar masses - - - Probability that the source is terrestrial (i.e., a background noise fluctuation or a glitch) - - - - Qualitative properties of the source, conditioned on the assumption that the signal is an astrophysical compact binary merger - - Probability that at least one object in the binary has a mass that is less than 3 solar masses - - - Probability that a nonzero mass was ejected outside the central remnant object - - - - - - - - - - - - - - - - Candidate gravitational wave event identified by low-latency analysis - H1: LIGO Hanford 4 km gravitational wave detector - L1: LIGO Livingston 4 km gravitational wave detector - V1: Virgo 3 km gravitational wave detector - - Report of a candidate gravitational wave event - - diff --git a/__pycache__/detector_monitor.cpython-36.pyc b/__pycache__/detector_monitor.cpython-36.pyc new file mode 100644 index 0000000000000000000000000000000000000000..cac4f0c3a9fe91d0f70647e36f02c2832afe7d4c Binary files /dev/null and b/__pycache__/detector_monitor.cpython-36.pyc differ diff --git a/__pycache__/detector_monitorv2.cpython-36.pyc b/__pycache__/detector_monitorv2.cpython-36.pyc new file mode 100644 index 0000000000000000000000000000000000000000..b694560b73841ed232e89996120b024a594cd29c Binary files /dev/null and b/__pycache__/detector_monitorv2.cpython-36.pyc differ diff --git a/__pycache__/gcn_test.cpython-36.pyc b/__pycache__/gcn_test.cpython-36.pyc index cbbff2cf304b99a60498ba9a613d4abc2f70c076..a49dcb86d8755b7dd011dedb92dde0f448b79edc 100644 Binary files a/__pycache__/gcn_test.cpython-36.pyc and b/__pycache__/gcn_test.cpython-36.pyc differ diff --git a/__pycache__/sync_database.cpython-36.pyc b/__pycache__/sync_database.cpython-36.pyc new file mode 100644 index 0000000000000000000000000000000000000000..12bbc3fa11d41c45904ba030805adc02c203e136 Binary files /dev/null and b/__pycache__/sync_database.cpython-36.pyc differ diff --git a/detector_monitorv2.py b/detector_monitorv2.py new file mode 100644 index 0000000000000000000000000000000000000000..4cf99a81d9c9fe18d5a5aeddbaa1e31e7c01eea0 --- /dev/null +++ b/detector_monitorv2.py @@ -0,0 +1,58 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +""" +Created on Tue Aug 13 10:19:09 2019 + +@author: christian +""" + +def statusdetect(): + from bs4 import BeautifulSoup + import requests + url = "https://ldas-jobs.ligo.caltech.edu/~gwistat/gwistat/gwistat.html" + r =requests.get(url) + soup = BeautifulSoup(r.text,"lxml") + names = ['GEO 600','LIGO Hanford','LIGO Livingston','Virgo','KAGRA'] + detrows = [] + to_add=[] + i=0 + for row in soup.find_all('td'): + if i > 0: + to_add.append(row.text) + i-=1 + if i == 0: + detrows.append(to_add) + to_add=[] + if row.text in names: + i = 4 + to_add.append(row.text) + i-=1 + statuses = [] + for row in detrows: + if row[2] == 'Timestamp error' or row[2] == 'Future addition': + row[3] = 'N/A' + statuses.append(1) + elif row[2] == 'Observing': + statuses.append(2) + elif row[2] == 'Down': + statuses.append(0) + else: + statuses.append(1) + export=[] + for i,row in enumerate(detrows): + if names[i] == 'Kagra': + #yellow + toput=[1,1,0,1] + elif statuses[i] == 0: + #red + toput = [1,0,0,1] + elif statuses[i] == 1: + #blue + toput=[0,0,1,1] + elif statuses[i] == 2: + #green + toput=[0,1,0,1] + temp=[row[0],row[2],row[3],toput] + export.append(temp) + export[0],export[2] = export[2],export[0] + return export \ No newline at end of file diff --git a/event_data/Detector_Plot_0.png b/event_data/Detector_Plot_0.png index 54a175dcb214d81e6fa7e0f74a4a03b029426c3e..946981a18a16c78f8a7ad73bfe8fccebd919a584 100644 Binary files a/event_data/Detector_Plot_0.png and b/event_data/Detector_Plot_0.png differ diff --git a/event_data/Detector_Plot_1.png b/event_data/Detector_Plot_1.png index 5443dd083578f5b55f01d0342ffb0c4bb17ae6e0..cf9ff2532a6a804d663e7085d28e273e76372150 100644 Binary files a/event_data/Detector_Plot_1.png and b/event_data/Detector_Plot_1.png differ diff --git a/event_data/Detector_Plot_2.png b/event_data/Detector_Plot_2.png index 68f67f104fb326b5e2f281f5af0e0e16d03f1b1f..d05592c156b0a98b24a5823fa94f7ce96c926813 100644 Binary files a/event_data/Detector_Plot_2.png and b/event_data/Detector_Plot_2.png differ diff --git a/event_data/Detector_Plot_3.png b/event_data/Detector_Plot_3.png new file mode 100644 index 0000000000000000000000000000000000000000..b9216e196340403eef032afa1267ff3103e85420 Binary files /dev/null and b/event_data/Detector_Plot_3.png differ diff --git a/event_data/Event Database b/event_data/Event Database index f6a3dbaffe727a7e1ba5ef410cb73926a74a5aba..05e0d9e9eeee0fe07848174c3a3ecb9d380f0b3d 100644 Binary files a/event_data/Event Database and b/event_data/Event Database differ diff --git a/event_data/S190408an_bar.png b/event_data/S190408an_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..dbcf1f7badf380ec6f6ea2197abcd22166156ab2 Binary files /dev/null and b/event_data/S190408an_bar.png differ diff --git a/event_data/S190408an_pie.png b/event_data/S190408an_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..d265bc661af1a653a7a6b3e6b5e25daa632edee6 Binary files /dev/null and b/event_data/S190408an_pie.png differ diff --git a/event_data/S190412m_bar.png b/event_data/S190412m_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..9832e03af0254a9a8d9c7ed5cbaa6f0eee4a771d Binary files /dev/null and b/event_data/S190412m_bar.png differ diff --git a/event_data/S190412m_pie.png b/event_data/S190412m_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..d265bc661af1a653a7a6b3e6b5e25daa632edee6 Binary files /dev/null and b/event_data/S190412m_pie.png differ diff --git a/event_data/S190421ar_bar.png b/event_data/S190421ar_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190421ar_bar.png differ diff --git a/event_data/S190421ar_pie.png b/event_data/S190421ar_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..f89bb2cc77a0bb6ae9fe6d907c848648d7140d4c Binary files /dev/null and b/event_data/S190421ar_pie.png differ diff --git a/event_data/S190425z_bar.png b/event_data/S190425z_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..377957b64fef6a1b560276021249b26c4eb79732 Binary files /dev/null and b/event_data/S190425z_bar.png differ diff --git a/event_data/S190425z_pie.png b/event_data/S190425z_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..a612b4ddab1c84e279d3124febb7ca2f564e2ed9 Binary files /dev/null and b/event_data/S190425z_pie.png differ diff --git a/event_data/S190426c_bar.png b/event_data/S190426c_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..377957b64fef6a1b560276021249b26c4eb79732 Binary files /dev/null and b/event_data/S190426c_bar.png differ diff --git a/event_data/S190426c_pie.png b/event_data/S190426c_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..b11ac1ea3bda995df2b06250be9ab908bb87a330 Binary files /dev/null and b/event_data/S190426c_pie.png differ diff --git a/event_data/S190503bf_bar.png b/event_data/S190503bf_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190503bf_bar.png differ diff --git a/event_data/S190503bf_pie.png b/event_data/S190503bf_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..fbfeaf9d112c63af0b4ea969c4bfbdac3ae37051 Binary files /dev/null and b/event_data/S190503bf_pie.png differ diff --git a/event_data/S190510g_bar.png b/event_data/S190510g_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..377957b64fef6a1b560276021249b26c4eb79732 Binary files /dev/null and b/event_data/S190510g_bar.png differ diff --git a/event_data/S190510g_pie.png b/event_data/S190510g_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..4f5d615ef0d7df005434d13d0921a316291c514a Binary files /dev/null and b/event_data/S190510g_pie.png differ diff --git a/event_data/S190512at_bar.png b/event_data/S190512at_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190512at_bar.png differ diff --git a/event_data/S190512at_pie.png b/event_data/S190512at_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..7f7ecdd745743be4c2ff9928cdf80c7b03550cd2 Binary files /dev/null and b/event_data/S190512at_pie.png differ diff --git a/event_data/S190513bm_bar.png b/event_data/S190513bm_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190513bm_bar.png differ diff --git a/event_data/S190513bm_pie.png b/event_data/S190513bm_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..8865f3657e20941d1e8f669338cc1b1e0e9ca9c1 Binary files /dev/null and b/event_data/S190513bm_pie.png differ diff --git a/event_data/S190517h_bar.png b/event_data/S190517h_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190517h_bar.png differ diff --git a/event_data/S190517h_pie.png b/event_data/S190517h_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..e46f1be2fbffa0524358bb01d205f7fbad59eaaa Binary files /dev/null and b/event_data/S190517h_pie.png differ diff --git a/event_data/S190519bj_bar.png b/event_data/S190519bj_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190519bj_bar.png differ diff --git a/event_data/S190519bj_pie.png b/event_data/S190519bj_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..e7adf70fedff3c519cdc6fe9825f3b421642ddf2 Binary files /dev/null and b/event_data/S190519bj_pie.png differ diff --git a/event_data/S190521g_bar.png b/event_data/S190521g_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190521g_bar.png differ diff --git a/event_data/S190521g_pie.png b/event_data/S190521g_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..02abdc8b272c4acbe5372b3befd0f7472c39df3d Binary files /dev/null and b/event_data/S190521g_pie.png differ diff --git a/event_data/S190521r_bar.png b/event_data/S190521r_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190521r_bar.png differ diff --git a/event_data/S190521r_pie.png b/event_data/S190521r_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..67aae9c4d90bdae4d86f41573be8fcd2d6a7a681 Binary files /dev/null and b/event_data/S190521r_pie.png differ diff --git a/event_data/S190602aq_bar.png b/event_data/S190602aq_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190602aq_bar.png differ diff --git a/event_data/S190602aq_pie.png b/event_data/S190602aq_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..101b33503f22e32110f9f40fb4a912c1df2fd7c7 Binary files /dev/null and b/event_data/S190602aq_pie.png differ diff --git a/event_data/S190630ag_bar.png b/event_data/S190630ag_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190630ag_bar.png differ diff --git a/event_data/S190630ag_pie.png b/event_data/S190630ag_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..c824e3968565a6910026c93ab3b638c54f42c6db Binary files /dev/null and b/event_data/S190630ag_pie.png differ diff --git a/event_data/S190701ah_bar.png b/event_data/S190701ah_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190701ah_bar.png differ diff --git a/event_data/S190701ah_pie.png b/event_data/S190701ah_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..fadda03f4525d027d8f00212634a6954a4d0e803 Binary files /dev/null and b/event_data/S190701ah_pie.png differ diff --git a/event_data/S190706ai_bar.png b/event_data/S190706ai_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190706ai_bar.png differ diff --git a/event_data/S190706ai_pie.png b/event_data/S190706ai_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..e7bd921445eb5a517e9f5c682a150bf05713ba79 Binary files /dev/null and b/event_data/S190706ai_pie.png differ diff --git a/event_data/S190707q_bar.png b/event_data/S190707q_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190707q_bar.png differ diff --git a/event_data/S190707q_pie.png b/event_data/S190707q_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..f57108de99dae78c1f9fcf4e580c8d168a4b5374 Binary files /dev/null and b/event_data/S190707q_pie.png differ diff --git a/event_data/S190718y_bar.png b/event_data/S190718y_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..377957b64fef6a1b560276021249b26c4eb79732 Binary files /dev/null and b/event_data/S190718y_bar.png differ diff --git a/event_data/S190718y_pie.png b/event_data/S190718y_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..b864b5963b960fc3e6a024a217b5b1532b5e1785 Binary files /dev/null and b/event_data/S190718y_pie.png differ diff --git a/event_data/S190720a_bar.png b/event_data/S190720a_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190720a_bar.png differ diff --git a/event_data/S190720a_pie.png b/event_data/S190720a_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..4f7519a2bb777732c3fe42c168aad4bfae4e798f Binary files /dev/null and b/event_data/S190720a_pie.png differ diff --git a/event_data/S190727h_bar.png b/event_data/S190727h_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190727h_bar.png differ diff --git a/event_data/S190727h_pie.png b/event_data/S190727h_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..f1f84e030f9eff318febf1e27aa84ca78dafebb9 Binary files /dev/null and b/event_data/S190727h_pie.png differ diff --git a/event_data/S190728q_bar.png b/event_data/S190728q_bar.png new file mode 100644 index 0000000000000000000000000000000000000000..4bf9fed84fdc496e6957c5da6e8738ca9df7a08d Binary files /dev/null and b/event_data/S190728q_bar.png differ diff --git a/event_data/S190728q_pie.png b/event_data/S190728q_pie.png new file mode 100644 index 0000000000000000000000000000000000000000..9ce734d10cd60aeb6eee0bbff776c19281d30c16 Binary files /dev/null and b/event_data/S190728q_pie.png differ diff --git a/event_data/ascending.png b/event_data/ascending.png new file mode 100644 index 0000000000000000000000000000000000000000..3c3da969ef417581ea17fa76338e3fecc2767595 Binary files /dev/null and b/event_data/ascending.png differ diff --git a/event_data/descending.png b/event_data/descending.png new file mode 100644 index 0000000000000000000000000000000000000000..00bdf263d7bf84410ec06554a29bee10f6664281 Binary files /dev/null and b/event_data/descending.png differ diff --git a/event_data/neutral.png b/event_data/neutral.png new file mode 100644 index 0000000000000000000000000000000000000000..33519efcda1786a0eac3f5c1cbffcedf0d07526c Binary files /dev/null and b/event_data/neutral.png differ diff --git a/fonts/OpenSans-Bold.ttf b/fonts/OpenSans-Bold.ttf new file mode 100644 index 0000000000000000000000000000000000000000..efdd5e84a0397ecada7b9cfde51db87db08766bd Binary files /dev/null and b/fonts/OpenSans-Bold.ttf differ diff --git a/fonts/OpenSans-BoldItalic.ttf b/fonts/OpenSans-BoldItalic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..9bf9b4e97b6576c8cc3d4527073731fd9cc57493 Binary files /dev/null and b/fonts/OpenSans-BoldItalic.ttf differ diff --git a/fonts/OpenSans-ExtraBold.ttf b/fonts/OpenSans-ExtraBold.ttf new file mode 100644 index 0000000000000000000000000000000000000000..67fcf0fb2af0c069495fbc7fe7ab0e442a86e357 Binary files /dev/null and b/fonts/OpenSans-ExtraBold.ttf differ diff --git a/fonts/OpenSans-ExtraBoldItalic.ttf b/fonts/OpenSans-ExtraBoldItalic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..086722809c74d5031c2427b31262de14e4a10560 Binary files /dev/null and b/fonts/OpenSans-ExtraBoldItalic.ttf differ diff --git a/fonts/OpenSans-Light.ttf b/fonts/OpenSans-Light.ttf new file mode 100644 index 0000000000000000000000000000000000000000..6580d3a169e895d914f159c060b947e36746f275 Binary files /dev/null and b/fonts/OpenSans-Light.ttf differ diff --git a/fonts/OpenSans-LightItalic.ttf b/fonts/OpenSans-LightItalic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..1e0c3319810ad7a0312e10c3d62da6beea7f1c58 Binary files /dev/null and b/fonts/OpenSans-LightItalic.ttf differ diff --git a/fonts/OpenSans-Regular.ttf b/fonts/OpenSans-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..29bfd35a2bfdd92b6e8b4ec2970f4d1eebf49357 Binary files /dev/null and b/fonts/OpenSans-Regular.ttf differ diff --git a/fonts/OpenSans-RegularItalic.ttf b/fonts/OpenSans-RegularItalic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..117856707b9b867863a9b48b127f756ee25fe109 Binary files /dev/null and b/fonts/OpenSans-RegularItalic.ttf differ diff --git a/fonts/OpenSans-SemiBold.ttf b/fonts/OpenSans-SemiBold.ttf new file mode 100644 index 0000000000000000000000000000000000000000..54e7059cf36359cb5a3860085714a95306af0dea Binary files /dev/null and b/fonts/OpenSans-SemiBold.ttf differ diff --git a/fonts/OpenSans-SemiBoldItalic.ttf b/fonts/OpenSans-SemiBoldItalic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..aebcf1421226d045b8043d26433d780fa365b7de Binary files /dev/null and b/fonts/OpenSans-SemiBoldItalic.ttf differ diff --git a/gcn_test.py b/gcn_test.py index 54243381027f9268e8c1de8f574a5d55c1251068..3db72ee031b1ca76c20afc989d74bea99b613af0 100644 --- a/gcn_test.py +++ b/gcn_test.py @@ -11,7 +11,9 @@ from tables import * import os from bs4 import BeautifulSoup import requests -import time +import scipy.constants +import matplotlib.pyplot as plt +import numpy as np class Event(IsDescription): @@ -30,7 +32,8 @@ class Event(IsDescription): Distance=StringCol(30) DetectionTime=StringCol(30) UpdateTime=StringCol(30) - + MassGap=StringCol(30) + Revision=StringCol(30) # Function to call every time a GCN is received. # Run only for notices of type # LVC_PRELIMINARY, LVC_INITIAL, or LVC_UPDATE. @@ -45,12 +48,10 @@ def process_gcn(payload, root): # Respond only to 'test' events. # VERY IMPORTANT! Replace with the following code # to respond to only real 'observation' events. - # if root.attrib['role'] != 'observation': - # return if root.attrib['role'] != 'observation': return #acknowledge - print('I have received a notice!') + #print('I have received a notice!!') #ensure correct working directory and open the table if os.path.basename(os.getcwd()) != "event_data": @@ -59,7 +60,13 @@ def process_gcn(payload, root): except: os.mkdir('./event_data') os.chdir('./event_data') - h5file = open_file("Event Database",mode="a",title="eventinfo") + while True: + try: + h5file = open_file("Event Database",mode="a",title="eventinfo") + break + except ValueError: + print("file in use... trying again in 5s") + time.sleep(5) try: h5file.create_group("/",'events') except NodeError: @@ -69,7 +76,9 @@ def process_gcn(payload, root): params = {elem.attrib['name']: elem.attrib['value'] for elem in root.iterfind('.//Param')} + descs = [elem.text for elem in root.iterfind('.//Description')] + if params['AlertType'] == 'Retraction': #Remove the event info if a retraction is issued - we don't care anymore #FIXME: in future flag the event instead and display seperately for interest/ref @@ -91,55 +100,156 @@ def process_gcn(payload, root): all_files = [a['href'] for a in soup.find_all("a")] imglinks = [] - htmllink=[] - + htmllinks=[] + if any('LALInferenceOffline.png' in s for s in all_files): imglinks = [s for s in all_files if 'LALInferenceOffline.png' in s] else: imglinks = [s for s in all_files if 'bayestar.png' in s] - imgfile = imglinks[-1] - imgfilepath = "https://gracedb.ligo.org"+imgfile - os.system("curl -0 "+imgfilepath + '> ' + './'+skymap) #os.system("curl -0 "+filepath + '> ' + fitspath) #os.system("ligo-skymap-plot map_to_convert.fits.gz"+" -o "+skymap+" --annotate --contour 50 90 --geo") - - #group name: events - try: table = h5file.create_table(h5file.root.events,params['GraceID'],Event,'CBC event') except: table=h5file.get_node("/events",params['GraceID']) + if any('bayestar.html' in s for s in all_files): + htmllinks = [s for s in all_files if 'bayestar.html' in s] + htmlfile = htmllinks[-1] + htmlfilepath = "https://gracedb.ligo.org"+htmlfile + r2 = requests.get(htmlfilepath) + soup2 = BeautifulSoup(r2.text,"lxml") + for col in soup2.tbody.find_all("tr"): + if 'DISTMEAN' in str(col): + dist = col.text.split('\n')[2] + dist = str("{0:.3f}".format(float(dist))) + elif 'DISTSTD' in str(col): + diststd = col.text.split('\n')[2] + diststd= str("{0:.3f}".format(float(diststd))) + finaldist = dist + ' +- '+diststd + ' Mpc' + det_event = table.row - + lookoutfor = ['BBH','BNS','MassGap','NSBH','Terrestrial'] + lookoutfor2=['HasNS','HasRemnant'] + order = [] + order2=[] + vals = [] + vals2=[] + descriptions={} # Print all parameters. + i=0 for key, value in params.items(): - print(key, '=', value) - try: + #print(key, '=', value) + if key == 'FAR': + per_yr = float(value)*scipy.constants.year + if per_yr <= 1: + oneinyr = 1/per_yr + else: + oneinyr = per_yr + if len(str(oneinyr).split('.')[0]) >= 5 or 'e' in str(oneinyr): + val = "One every "+str("{0:.2e}".format(oneinyr))+" yrs" + else: + val = "One every "+str("{0:.3f}".format(oneinyr))+" yrs" + det_event[key] = val + descriptions[key]=descs[i] + elif key == 'Pkt_Ser_Num': + key = 'Revision' det_event[key] = value - except: - continue + descriptions[key] = descs[i] + elif key in lookoutfor: + order.append(key) + vals.append(float(value)) + det_event[key]=value + descriptions[key]=descs[i] + elif key in lookoutfor2: + order2.append(key) + vals2.append(float(value)) + det_event[key]=value + descriptions[key]=descs[i] + else: + try: + det_event[key] = value + descriptions[key]=descs[i] + except: + i+=1 + continue + i+=1 + #print(descriptions) det_event['skymap'] = skymap - #timing - if params['AlertType'] == 'Preliminary': - det_event['DetectionTime'] = str(time.time()) - det_event['UpdateTime'] = str(time.time()) - else: - det_event['UpdateTime'] = str(time.time()) + det_event['Distance'] = finaldist + det_time = root.find('.//ISOTime') + det_text = det_time.text + [one,two] = det_text.split('T') + one=one.replace(':','-') + two = two.split('.')[0] + det_formtime = one+' at '+two + + det_event['DetectionTime']=det_formtime + + upt_time = root.find('.//Date') + upt_text = upt_time.text + [one1,two1] = upt_text.split('T') + one1=one1.replace(':','-') + two1=two1.split('.')[0] + upt_formtime = one1+' at '+two1 + det_event['UpdateTime'] = upt_formtime + #save the pie of possibilities + specindex = np.argmax(vals) + + fig1, ax1 = plt.subplots(figsize=(5,5)) + ax1.pie(vals,labels=order,wedgeprops=dict(width=0.5),labeldistance=None) + ax1.axis('equal') +# plt.text(0,0.1,'Type:',fontsize=20,transform=ax1.transAxes) +# plt.text(0,0,order[specindex],fontsize=20,transform=ax1.transAxes) + plt.text(0.365,0.55,'Event Type:',transform=ax1.transAxes,fontsize=16) + if order[specindex] == 'NSBH': + plt.text(0.395,0.42,order[specindex],fontsize=26,transform=ax1.transAxes) + elif order[specindex] == 'Terrestrial': + plt.text(0.335,0.44,order[specindex],fontsize=22,transform=ax1.transAxes) + elif order[specindex] == 'MassGap': + plt.text(0.335,0.44,order[specindex],fontsize=26,transform=ax1.transAxes) + else: + plt.text(0.42,0.42,order[specindex],fontsize=28,transform=ax1.transAxes) + plt.tight_layout() + plt.savefig(params['GraceID']+'_pie.png') + + pos=[0,1] + tickpos=np.array([0,0.2,0.4,0.6,0.8,1])*100 + data = np.array(vals2)*100 + + fig2,ax2 = plt.subplots(figsize=(4,1.5)) + # Hide the right and top spines + ax2.spines['right'].set_visible(False) + ax2.spines['top'].set_visible(False) + + # Only show ticks on the left and bottom spines + ax2.yaxis.set_ticks_position('left') + ax2.xaxis.set_ticks_position('bottom') + ax2.barh(pos,data,height=0.7,color=['C8','C9']) + plt.xlabel('Probability (%)') + plt.xticks(tickpos) + plt.yticks(pos,order2) + plt.tight_layout() + plt.savefig(params['GraceID']+'_bar.png') + plt.close(fig1) + plt.close(fig2) + det_event.append() table.flush() h5file.close() + #gcn.listen(host="209.208.78.170",handler=process_gcn) # # -##testing +#testing +#os.chdir('./event_data') #import lxml -#payload = open('MS181101ab-1-Preliminary.xml', 'rb').read() +#payload = open('PreviousEventToRead.xml', 'rb').read() #root = lxml.etree.fromstring(payload) #process_gcn(payload, root) diff --git a/my.ini b/my.ini new file mode 100644 index 0000000000000000000000000000000000000000..1d756ca65f5ac0cb2818a769fea010a08762472a --- /dev/null +++ b/my.ini @@ -0,0 +1,3 @@ +[Section] +initialbackup = 1 + diff --git a/souptest.py b/souptest.py deleted file mode 100644 index 675b7107cd050a636bf22f17af60cfe7b2ed40b1..0000000000000000000000000000000000000000 --- a/souptest.py +++ /dev/null @@ -1,58 +0,0 @@ -def statusdetect(): - - from bs4 import BeautifulSoup - import requests - import re - - url = "https://ldas-jobs.ligo.caltech.edu/~gwistat/gwistat/gwistat.html" - r =requests.get(url) - soup = BeautifulSoup(r.text,"lxml") - - def identifystring(line): - result = re.search('>(.*)<',str(line)) - return result.group(1) - - detectornames = [] - detectortimes = [] - - for row in soup("td"): - res = identifystring(row) - - if len(res) > 20 : - continue - - - for char in res: - if char == '': - if once == True: - res = '' - break - once = 1 - continue - if char == '<': - res='' - break - if char == ':': - detectortimes.append(res) - res='' - break - - finalcheck = ['Detector','Status','Duration',''] - - if res not in finalcheck: - detectornames.append(res) - - statuses=[] - for element in detectornames: - if element in ['Observing','Science']: - statuses.append(2) - elif element == 'Down': - statuses.append(0) - else: - statuses.append(1) - - return detectornames,statuses,detectortimes -# obj.detectornames=detectornames -# obj.statuses=statuses, -# obj.detectortimes=detectortimes -#print(statusdetect()) diff --git a/souptest2.py b/souptest2.py deleted file mode 100644 index dc0423c98300ba5c6619be4b0be5920a8bb2e856..0000000000000000000000000000000000000000 --- a/souptest2.py +++ /dev/null @@ -1,84 +0,0 @@ -#!/usr/bin/env python3 -# -*- coding: utf-8 -*- -""" -Created on Fri Aug 2 10:30:58 2019 - -@author: christian -""" -from bs4 import BeautifulSoup -import requests -from gcn_test import process_gcn -import os -import lxml - -#Get old links by parsing properly, and download + save to file! - -if os.path.basename(os.getcwd()) != "event_data": - try: - os.chdir("./event_data") - except: - os.mkdir("./event_data") - os.chdir("./event_data") - - -url = "https://gracedb.ligo.org/superevents/public/O3/" -r =requests.get(url) -soup = BeautifulSoup(r.text,"lxml") - -eventlinks = [] -eventnames = [] - -def hasstylenotclass(tag): - return tag.has_attr('style') and not tag.has_attr('class') - -for col in soup.tbody.find_all("tr"): - #print(row) - #for col in row("tr"): - if 'RETRACTED' in str(col): - continue - #link = col.find(hasstylenotclass).a.extract() - name = col.find(hasstylenotclass).a.string - eventnames.append(name) - eventlinks.append("https://gracedb.ligo.org/superevents/"+name+"/files/") - - -for i,link in enumerate(eventlinks): - r =requests.get(link) - soup = BeautifulSoup(r.text,"lxml") - - all_files = [a['href'] for a in soup.find_all("a")] - - bestfiles = [] - imglinks = [] - htmllink=[] - - if any('Update' in s for s in all_files): - bestfiles = [s for s in all_files if 'Update' in s] - elif any('Initial' in s for s in all_files): - bestfiles= [s for s in all_files if 'Initial' in s] - else: - bestfiles = [s for s in all_files if 'Preliminary' in s] - - if any('LALInferenceOffline.png' in s for s in all_files): - imglinks = [s for s in all_files if 'LALInferenceOffline.png' in s] - else: - imglinks = [s for s in all_files if 'bayestar.png' in s] - - imgfile = imglinks[-1] - datafile = bestfiles[-1] - - imgfilepath = "https://gracedb.ligo.org"+imgfile - datafilepath = "https://gracedb.ligo.org"+datafile - - imgpath = eventnames[i]+'.png' - datapath = 'PreviousEventToRead.xml' - os.system("curl -0 "+datafilepath + '> ' + './'+datapath) - os.system("curl -0 "+imgfilepath + '> ' + './'+imgpath) - - payload = open(datapath,'rb').read() - root=lxml.etree.fromstring(payload) - process_gcn(payload,root) - - - - \ No newline at end of file diff --git a/sync_database.py b/sync_database.py new file mode 100644 index 0000000000000000000000000000000000000000..36497000ef3a23ff583e5eb96e55aab89df490d5 --- /dev/null +++ b/sync_database.py @@ -0,0 +1,84 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +""" +Created on Fri Aug 2 10:30:58 2019 + +@author: christian +""" + +def sync_database(): + from bs4 import BeautifulSoup + import requests + from gcn_test import process_gcn + import os + import lxml + + #Get old links by parsing properly, and download + save to file! + + if os.path.basename(os.getcwd()) != "event_data": + try: + os.chdir("./event_data") + except: + os.mkdir("./event_data") + os.chdir("./event_data") + + + url = "https://gracedb.ligo.org/superevents/public/O3/" + r =requests.get(url) + soup = BeautifulSoup(r.text,"lxml") + + eventlinks = [] + eventnames = [] + + def hasstylenotclass(tag): + return tag.has_attr('style') and not tag.has_attr('class') + + for col in soup.tbody.find_all("tr"): + #print(row) + #for col in row("tr"): + if 'RETRACTED' in str(col): + continue + #link = col.find(hasstylenotclass).a.extract() + name = col.find(hasstylenotclass).a.string + eventnames.append(name) + eventlinks.append("https://gracedb.ligo.org/superevents/"+name+"/files/") + + + for i,link in enumerate(eventlinks): + r =requests.get(link) + soup = BeautifulSoup(r.text,"lxml") + + all_files = [a['href'] for a in soup.find_all("a")] + + bestfiles = [] + imglinks = [] + htmllink=[] + + if any('Update' in s for s in all_files): + bestfiles = [s for s in all_files if 'Update' in s] + elif any('Initial' in s for s in all_files): + bestfiles= [s for s in all_files if 'Initial' in s] + else: + bestfiles = [s for s in all_files if 'Preliminary' in s] + + if any('LALInferenceOffline.png' in s for s in all_files): + imglinks = [s for s in all_files if 'LALInferenceOffline.png' in s] + else: + imglinks = [s for s in all_files if 'bayestar.png' in s] + + imgfile = imglinks[-1] + datafile = bestfiles[-1] + + imgfilepath = "https://gracedb.ligo.org"+imgfile + datafilepath = "https://gracedb.ligo.org"+datafile + + imgpath = eventnames[i]+'.png' + datapath = 'PreviousEventToRead.xml' + os.system("curl -0 "+datafilepath + '> ' + './'+datapath) + os.system("curl -0 "+imgfilepath + '> ' + './'+imgpath) + + payload = open(datapath,'rb').read() + root=lxml.etree.fromstring(payload) + process_gcn(payload,root) +# if i == 0: +# break \ No newline at end of file diff --git a/threadtest.py b/threadtest.py deleted file mode 100644 index 24103babf792b88bb87d47a83c1f23e5d33f343e..0000000000000000000000000000000000000000 --- a/threadtest.py +++ /dev/null @@ -1,157 +0,0 @@ -#!/usr/bin/env python3 -# -*- coding: utf-8 -*- -""" -Created on Mon Jul 29 14:59:14 2019 - -@author: christian -""" - -import threading -import time - -from kivy.app import App -from kivy.lang import Builder -from kivy.factory import Factory -from kivy.animation import Animation -from kivy.clock import Clock, mainthread -from kivy.uix.gridlayout import GridLayout - - -Builder.load_string(""" -: - canvas: - Color: - rgba: 0.7, 0.3, 0.9, 1 - Rectangle: - pos: self.pos - size: self.size - size_hint: None, None - size: 400, 30 - - -: - cols: 1 - - canvas: - Color: - rgba: 0.9, 0.9, 0.9, 1 - Rectangle: - pos: self.pos - size: self.size - - anim_box: anim_box - but_1: but_1 - lab_1: lab_1 - lab_2: lab_2 - - Button: - id: but_1 - font_size: 20 - text: 'Start second thread' - on_press: root.start_second_thread(lab_2.text) - - Label: - id: lab_1 - font_size: 30 - color: 0.6, 0.6, 0.6, 1 - text_size: self.width, None - halign: 'center' - - AnchorLayout: - id: anim_box - - Label: - id: lab_2 - font_size: 100 - color: 0.8, 0, 0, 1 - text: '3' -""") - - -class RootWidget(GridLayout): - - stop = threading.Event() - - def start_second_thread(self, l_text): - threading.Thread(target=self.second_thread, args=(l_text,)).start() - - def second_thread(self, label_text): - # Remove a widget, update a widget property, create a new widget, - # add it and animate it in the main thread by scheduling a function - # call with Clock. - Clock.schedule_once(self.start_test, 0) - - # Do some thread blocking operations. - time.sleep(5) - l_text = str(int(label_text) * 3000) - - # Update a widget property in the main thread by decorating the - # called function with @mainthread. - self.update_label_text(l_text) - - # Do some more blocking operations. - time.sleep(2) - - # Remove some widgets and update some properties in the main thread - # by decorating the called function with @mainthread. - self.stop_test() - - # Start a new thread with an infinite loop and stop the current one. - threading.Thread(target=self.infinite_loop).start() - - def start_test(self, *args): - # Remove the button. - self.remove_widget(self.but_1) - - # Update a widget property. - self.lab_1.text = ('The UI remains responsive while the ' - 'second thread is running.') - - # Create and add a new widget. - anim_bar = Factory.AnimWidget() - self.anim_box.add_widget(anim_bar) - - # Animate the added widget. - anim = Animation(opacity=0.3, width=100, duration=0.6) - anim += Animation(opacity=1, width=400, duration=0.8) - anim.repeat = True - anim.start(anim_bar) - - @mainthread - def update_label_text(self, new_text): - self.lab_2.text = new_text - - @mainthread - def stop_test(self): - self.lab_1.text = ('Second thread exited, a new thread has started. ' - 'Close the app to exit the new thread and stop ' - 'the main process.') - - self.lab_2.text = str(int(self.lab_2.text) + 1) - - self.remove_widget(self.anim_box) - - def infinite_loop(self): - iteration = 0 - while True: - if self.stop.is_set(): - # Stop running this thread so the main Python process can exit. - return - iteration += 1 - print('Infinite loop, iteration {}.'.format(iteration)) - time.sleep(1) - - -class ThreadedApp(App): - - def on_stop(self): - # The Kivy event loop is about to stop, set a stop signal; - # otherwise the app window will close, but the Python process will - # keep running until all secondary threads exit. - self.root.stop.set() - - def build(self): - return RootWidget() - -if __name__ == '__main__': - ThreadedApp().run() \ No newline at end of file