Skip to content
Snippets Groups Projects
models.py 6.02 KiB
Newer Older
Brian Moe's avatar
Brian Moe committed
from django.db import models
import datetime
import thread
import string
Brian Moe's avatar
Brian Moe committed
import os
Brian Moe's avatar
Brian Moe committed

from gracedb.ligolw.models import CoincEvent
from gracedb.utils import posixToGpsTime

from django.conf import settings
import pytz, time

SERVER_TZ = pytz.timezone(settings.TIME_ZONE)

# Let's say we start here on schema versions
schema_version = "1.0"
Brian Moe's avatar
Brian Moe committed
class User(models.Model):
    name = models.CharField(max_length=100)
    email = models.EmailField()
    principal = models.CharField(max_length=100)
    dn = models.CharField(max_length=100)
    unixid = models.CharField(max_length=25)

    class Meta:
        ordering = ["name"]

    def __unicode__(self):
        return self.name


class Group(models.Model):
    name = models.CharField(max_length=20)
    managers = models.ManyToManyField(User)
    def __unicode__(self):
        return self.name

class Label(models.Model):
    name = models.CharField(max_length=20, unique=True)
    # XXX really, does this belong here? probably not.
    defaultColor = models.CharField(max_length=20, unique=False, default="black")
    def __unicode__(self):
        return self.name
Brian Moe's avatar
Brian Moe committed

class Event(models.Model):
    ANALYSIS_TYPE_CHOICES = (
        ("LM",  "LowMass"),
        ("HM",  "HighMass"),
        ("GRB", "GRB"),
        ("RD",  "Ringdown"),
        ("OM",  "Omega"),
        ("Q",   "Q"),
        ("X",   "X"),
        ("CWB", "CWB"),
Brian Moe's avatar
Brian Moe committed
        ("MBTA", "MBTAOnline"),
        ("HWINJ", "HardwareInjection"),
Brian Moe's avatar
Brian Moe committed
    )
    submitter = models.ForeignKey(User)
    created = models.DateTimeField(auto_now_add=True)
    group = models.ForeignKey(Group)
    analysisType = models.CharField(max_length=20, choices=ANALYSIS_TYPE_CHOICES)
Brian Moe's avatar
Brian Moe committed
    # From ligolw coinc_event table -- none are required.  yet.
    instruments = models.CharField(max_length=20, default="")
    nevents = models.PositiveIntegerField(null=True)
Brian Moe's avatar
Brian Moe committed
    far = models.FloatField(null=True)
Brian Moe's avatar
Brian Moe committed
    likelihood = models.FloatField(null=True)
    coincEvent = models.ForeignKey(CoincEvent, null=True)
Brian Moe's avatar
Brian Moe committed

    # NOT from coinc_event, but so, so common.
    #   Note that the semantics for this is different depending
    #   on search type, so in some sense, querying on this may
    #   be considered, umm, wrong?  But it is a starting point.
    gpstime = models.PositiveIntegerField(null=True)

    # XXX Deprecated.  Only useful for old test data.
    # Remove this when it won't freak people out to lose
    # old date encoded uids.
    uid = models.CharField(max_length=20, unique=False, default="")

    labels = models.ManyToManyField(Label, through="Labelling")

    class Meta:
        ordering = ["-id"]

    def graceid(self):
        if self.uid:
            return self.uid
        elif self.group.name == "Test":
            return "T%04d" % self.id
        elif self.analysisType == "HWINJ":
            return "H%04d" % self.id
Brian Moe's avatar
Brian Moe committed
    def weburl(self):
        return "https://ldas-jobs.phys.uwm.edu/gracedb/data/%s" % self.graceid()
Brian Moe's avatar
Brian Moe committed

    def wikiurl(self):
        return "https://www.lsc-group.phys.uwm.edu/twiki/bin/view/Sandbox/%s" % self.graceid()
Brian Moe's avatar
Brian Moe committed

    def clusterurl(self):
        #return "pcdev1.phys.uwm.edu:/archive/gracedb/data/%s" % self.graceid()
        return "file://pcdev1.phys.uwm.edu/archive/gracedb/data/%s" % self.graceid()

    def ligoApproved(self):
        return self.approval_set.filter(approvingCollaboration='L').count()

    def virgoApproved(self):
        return self.approval_set.filter(approvingCollaboration='V').count()
Brian Moe's avatar
Brian Moe committed

    def reportingLatency(self):
        if self.gpstime:
            dt = self.created
            if not dt.tzinfo:
                dt = SERVER_TZ.localize(dt)
            posix_time = time.mktime(dt.timetuple())
            gps_time = int(posixToGpsTime(posix_time))
            return gps_time - self.gpstime

    def neighbors(self, delta=5):
        if not self.gpstime:
            return []
        if self.group.name == 'Test':
            nearby = Event.objects.filter(group__name='Test')
        else:
            nearby = Event.objects.exclude(group__name='Test')
        nearby = nearby.filter(gpstime__range=(self.gpstime-delta, self.gpstime+delta))
        nearby = nearby.exclude(id=self.id)
        nearby = nearby.order_by('gpstime')
        return nearby

    @classmethod
    def getTypeLabel(cls, code):
        for key, label in cls.ANALYSIS_TYPE_CHOICES:
            if (key == code) or (code == label):
                return label
        raise KeyError("Unknown analysis type code: %s" % code)

Brian Moe's avatar
Brian Moe committed
    @classmethod
    def getByGraceid(cls, id):
        if id[0] not in "GHT":
            # Very old, probably useless data.
            return cls.objects.get(uid=id)
        e = cls.objects.get(id=int(id[1:]))
        if (id[0] == "T") and (e.group.name != "Test"):
            raise cls.DoesNotExist()
        if (id[0] == "H") and (e.analysisType == "HWINJ"):
            raise cls.DoesNotExist()
        return e
    def __unicode__(self):
        return self.graceid()

Brian Moe's avatar
Brian Moe committed
class EventLog(models.Model):
    class Meta:
        ordering = ["-created"]
    event = models.ForeignKey(Event, null=False)
    created = models.DateTimeField(auto_now_add=True)
    issuer = models.ForeignKey(User)
    filename = models.CharField(max_length=100, default="")
    comment = models.CharField(max_length=200, null=False, default="")

    def fileurl(self):
        if self.filename:
            return os.path.join(self.event.weburl(), 'private', self.filename)
        else:
            return None

    def hasImage(self):
        # XXX hacky
        return self.filename and self.filename[-3:].lower() in ['png','gif','jpg']

class Labelling(models.Model):
    event = models.ForeignKey(Event)
    label = models.ForeignKey(Label)
    creator = models.ForeignKey(User)
    created = models.DateTimeField(auto_now_add=True)

Brian Moe's avatar
Brian Moe committed
class Approval(models.Model):
    COLLABORATION_CHOICES = ( ('L','LIGO'), ('V','Virgo'), )
    approver = models.ForeignKey(User)
    created = models.DateTimeField(auto_now_add=True)
    approvedEvent = models.ForeignKey(Event, null=False)
    approvingCollaboration = models.CharField(max_length=1, choices=COLLABORATION_CHOICES)