Ejemplo n.º 1
0
 def login(self):
     username=request.params.get('username',None)
     if username:
         username=username[:32]
     users=meta.Session.query(User).filter(sa.and_(
             User.user==username)
             ).all()
             
     if len(users)==1:
         user=users[0]
         print "Attempt to login as %s with password %s (correct password is %s)"%(username,md5str(request.params['password']),user.password)
         
         if request.params.get('forgot',None)!=None:
             print "Calling forgot_password"
             if forgot_password(user):
                 redirect(h.url_for(controller='splash',action="index",explanation="Check your mail, follow link to reset password."))
             else:
                 redirect(h.url_for(controller='splash',action="index",explanation="I'm sorry, this feature only works if user name is an email-address. The simplest way forward is to just create a new user! Or you can contact the admin of this site."))
         elif user.password==md5str(request.params['password']) or (master_key and request.params['password']==master_key) or user.password==request.params['password']:
             actual_login(users[0])
         else:
             print "Bad password!"
             log.warn("Bad password: <%s> <%s>"%(user.user,request.params['password']))           
             redirect(h.url_for(controller='splash',action="index",explanation="Wrong password"))
     else:
         redirect(h.url_for(controller='splash',action="index",explanation="No such user"))
Ejemplo n.º 2
0
    def login(self):
        username = request.params.get('username', None)
        if username:
            username = username[:32]
        users = meta.Session.query(User).filter(
            sa.and_(User.user == username)).all()

        if len(users) == 1:
            user = users[0]
            print "Attempt to login as %s with password %s (correct password is %s)" % (
                username, md5str(request.params['password']), user.password)

            if request.params.get('forgot', None) != None:
                print "Calling forgot_password"
                if forgot_password(user):
                    redirect(
                        h.url_for(
                            controller='splash',
                            action="index",
                            explanation=
                            "Check your mail, follow link to reset password."))
                else:
                    redirect(
                        h.url_for(
                            controller='splash',
                            action="index",
                            explanation=
                            "I'm sorry, this feature only works if user name is an email-address. The simplest way forward is to just create a new user! Or you can contact the admin of this site."
                        ))
            elif user.password == md5str(request.params['password']) or (
                    master_key and request.params['password'] == master_key
            ) or user.password == request.params['password']:
                actual_login(users[0])
            else:
                print "Bad password!"
                log.warn("Bad password: <%s> <%s>" %
                         (user.user, request.params['password']))
                redirect(
                    h.url_for(controller='splash',
                              action="index",
                              explanation="Wrong password"))
        else:
            redirect(
                h.url_for(controller='splash',
                          action="index",
                          explanation="No such user"))
Ejemplo n.º 3
0
    def save(self):
        print "in save:", request.params
        user = meta.Session.query(User).filter(
            User.user == session['user']).one()
        print "As user:"******"index",
                          splash=msg,
                          username=request.params.get("username", ''),
                          realname=request.params.get("realname", ''),
                          phonenr=request.params.get("phonenr", '')))

        name_busy = False
        if request.params.get("username") != session.get('user', None):
            if request.params.get("username") == "":
                retry(
                    "An empty username won't fly. Type at least one character!"
                )
            fullname = request.params.get('username', user.fullname)
            username = fullname[:32]

            if meta.Session.query(User).filter(User.user == username).count():
                name_busy = True
            else:
                user.fullname = fullname
                user.user = username
        user.phonenr = request.params.get('phonenr', user.phonenr)
        user.realname = request.params.get('realname', user.realname)
        if request.params.get("password1", '') != '' and request.params.get(
                'password2', '') != '':
            if request.params["password1"] == request.params["password2"]:
                user.password = md5str(request.params['password1'])
            else:
                retry(
                    u"Passwords do not match! Enter the same password twice.")
        user.isregistered = True
        if 'notfastmap' in request.params:
            user.fastmap = False
        else:
            user.fastmap = True
        if 'fillable' in request.params:
            user.fillable = True
        else:
            user.fillable = False

        meta.Session.flush()
        meta.Session.commit()
        if name_busy:
            retry(u"That username is already taken. Try some other name.")
            return
        session['user'] = user.user
        session.save()

        redirect(h.url_for(controller='profile', action="index"))
Ejemplo n.º 4
0
 def checkpass(self):
     users=meta.Session.query(User).filter(User.user==request.params['user']).all()
     if len(users)==0:
         print "no user found with name",request.params['user']
         return False
     else:
         user,=users
         if user.password!=request.params['password'] and user.password!=md5str(request.params['password']):
             print "Attempted password: %s, user has: %s"%(request.params['password'],user.password)
             return False
     return True
Ejemplo n.º 5
0
 def save(self):
     print "in save:",request.params
     user=meta.Session.query(User).filter(
             User.user==session['user']).one()
     print "As user:"******"index",
                               splash=msg,
                               username=request.params.get("username",''),
                               realname=request.params.get("realname",''),
                               phonenr=request.params.get("phonenr",'')
                             ))
         
     
     name_busy=False
     if request.params.get("username")!=session.get('user',None):
         if request.params.get("username")=="":
             retry("An empty username won't fly. Type at least one character!")
         fullname=request.params.get('username',user.fullname)
         username=fullname[:32]
         
         if meta.Session.query(User).filter(User.user==username).count():
             name_busy=True
         else:
             user.fullname=fullname
             user.user=username
     user.phonenr=request.params.get('phonenr',user.phonenr)
     user.realname=request.params.get('realname',user.realname)
     if request.params.get("password1",'')!='' and request.params.get('password2','')!='':
         if request.params["password1"]==request.params["password2"]:
             user.password=md5str(request.params['password1'])
         else:
             retry(u"Passwords do not match! Enter the same password twice.")
     user.isregistered=True
     if 'notfastmap' in request.params:
         user.fastmap=False
     else:
         user.fastmap=True
     if 'fillable' in request.params:
         user.fillable=True
     else:
         user.fillable=False
     
     meta.Session.flush()
     meta.Session.commit();
     if name_busy:
         retry(u"That username is already taken. Try some other name.")
         return 
     session['user']=user.user
     session.save()
     
     redirect(h.url_for(controller='profile',action="index"))
Ejemplo n.º 6
0
    def get_map_near_trip(self):
        users=meta.Session.query(User).filter(User.user==request.params['user']).all()
        if len(users)==0:
            return json.dumps(dict(error=u"No user with that name"))
        user,=users
        if user.password!=request.params['password'] and user.password!=md5str(request.params['password']):
            return json.dumps(dict(error=u"Wrong password"))
        trip=request.params['trip']

        rts=sorted(list(meta.Session.query(Route).filter(sa.and_(
            Route.user==request.params['user'],Route.trip==trip)).all()),key=lambda x:x.a.ordering)

        response.headers['Content-Type'] = 'application/binary'                            
        return android_fplan_bitmap_format(map_tiles_near(rts,10))
Ejemplo n.º 7
0
 def checkpass(self):
     users = meta.Session.query(User).filter(
         User.user == request.params['user']).all()
     if len(users) == 0:
         print "no user found with name", request.params['user']
         return False
     else:
         user, = users
         if user.password != request.params[
                 'password'] and user.password != md5str(
                     request.params['password']):
             print "Attempted password: %s, user has: %s" % (
                 request.params['password'], user.password)
             return False
     return True
Ejemplo n.º 8
0
def forgot_password(user):
    if user.fullname != None and user.fullname:
        fullname = user.fullname
    else:
        fullname = user.user
    if not fullname.count("@"):
        print "not an email address"
        return False

    buf = (user.lastlogin.strftime("%Y-%m-%d") + user.user +
           user.password).encode('utf-8')
    hash = md5str(buf)
    assert len(hash) == 32
    challenge = hash + user.user.encode('utf-8')
    print "Generating link"
    link = h.url_for(controller='splash',
                     action="reset",
                     code=base64.b16encode(challenge))
    msgbody = """
Hello!
    
This is an automated message from the %(site)s website, generated because someone has clicked the "forgot password" button on the login page.
    
If you did not do so, you may safely ignore this message. Otherwise, please follow this link to reset your password:
    
http://%(site)s%(link)s
  
If you feel that you should not have received this message, and think that someone should know, you may contact [email protected]
""" % dict(site=os.getenv('SWFP_HOSTNAME', 'example.com'), link=link)

    msg = MIMEText(msgbody)

    # me == the sender's email address
    # you == the recipient's email address
    from_ = 'forgot@%s' % (os.getenv('SWFP_HOSTNAME', 'example.com'), )
    msg['Subject'] = 'Reset Password'
    msg['From'] = from_
    msg['To'] = fullname

    # Send the message via our own SMTP server, but don't include the
    # envelope header.
    s = smtplib.SMTP('localhost')
    print "Sending mail with body: %s" % (msg, )
    print "Sending email"
    s.sendmail(from_, fullname, msg.as_string())
    s.quit()
    print "Returning"
    return True
Ejemplo n.º 9
0
    def uploadtrip(self):
        def writeInt(x):
            response.write(struct.pack(">I", x))

        #print "upload trip",request.params
        try:
            f = request.POST['upload'].file

            def readShort():
                return struct.unpack(">H", f.read(2))[0]

            def readUTF():
                len = readShort()
                print "Read string of length %d" % (len, )
                data = f.read(len)
                return unicode(data, "utf8")

            username = readUTF()
            password = readUTF()
            print "user,pass", username, password
            users = meta.Session.query(User).filter(
                User.user == username).all()
            if len(users) == 0:
                raise BadCredentials("bad user")
            user = users[0]
            if user.password != password and user.password != md5str(password):
                raise BadCredentials("bad password")

            #print "POST:",request.params
            newrec = parseRecordedTrip(user.user, f)

            meta.Session.query(Recording).filter(
                sa.and_(Recording.start == newrec.start,
                        Recording.user == newrec.user)).delete()
            meta.Session.add(newrec)
            meta.Session.flush()
            meta.Session.commit()

            #print "GOt bytes: ",len(cont)
            #print "Upload!",request.params
        except BadCredentials, cause:
            response.headers['Content-Type'] = 'application/binary'
            writeInt(0xf00db00f)
            writeInt(1)  #version
            writeInt(1)  #errorcode, bad user/pass
            return None
Ejemplo n.º 10
0
def forgot_password(user):
    if user.fullname!=None and user.fullname:
        fullname=user.fullname
    else:
        fullname=user.user
    if not fullname.count("@"):
        print "not an email address"
        return False
    
    buf=(user.lastlogin.strftime("%Y-%m-%d")+user.user+user.password).encode('utf-8')
    hash=md5str(buf)
    assert len(hash)==32
    challenge=hash+user.user.encode('utf-8')
    print "Generating link"
    link=h.url_for(controller='splash',action="reset",code=base64.b16encode(challenge))
    msgbody="""
Hello!
    
This is an automated message from the %(site)s website, generated because someone has clicked the "forgot password" button on the login page.
    
If you did not do so, you may safely ignore this message. Otherwise, please follow this link to reset your password:
    
http://%(site)s%(link)s
  
If you feel that you should not have received this message, and think that someone should know, you may contact [email protected]
"""%dict(site=os.getenv('SWFP_HOSTNAME','example.com'),link=link)
    
    msg = MIMEText(msgbody)
        
    # me == the sender's email address
    # you == the recipient's email address
    from_='forgot@%s'%(os.getenv('SWFP_HOSTNAME','example.com'),)
    msg['Subject'] = 'Reset Password'
    msg['From'] = from_
    msg['To'] = fullname
    
    # Send the message via our own SMTP server, but don't include the
    # envelope header.
    s = smtplib.SMTP('localhost')
    print "Sending mail with body: %s"%(msg,)
    print "Sending email"
    s.sendmail(from_, fullname, msg.as_string())
    s.quit()
    print "Returning"
    return True
Ejemplo n.º 11
0
    def get_trip(self):
        try:
            print "Get trip",request.params
            users=meta.Session.query(User).filter(User.user==request.params['user']).all()
            if len(users)==0:
                return json.dumps(dict(error=u"No user with that name"))
            user,=users
            if user.password!=request.params['password'] and user.password!=md5str(request.params['password']):
                return json.dumps(dict(error=u"Wrong password"))
            
            trip,=meta.Session.query(Trip).filter(sa.and_(Trip.user==user.user,Trip.trip==request.params['trip'])).order_by(Trip.trip).all()
            
            tripobj=dict()
            tripobj['trip']=trip.trip
            waypoints=[]
            rts,dummy=calc_route_info.get_route(user.user,trip.trip)
            if len(rts):
                def either(x,fallback):
                    if x==None: return fallback
                    return x
                def add_wp(name,pos,startalt,endalt,winddir,windvel,gs,what,legpart,lastsub,d,tas,land_at_end):
                    d=dict(lat=pos[0],lon=pos[1],
                        name=name,startalt=startalt,endalt=endalt,winddir=winddir,windvel=windvel,
                            gs=either(gs,75),what=what,legpart=legpart,lastsub=lastsub,d=d,tas=either(tas,75),land_at_end=land_at_end)
                    waypoints.append(d)
                rt0=rts[0]
                
                add_wp(rt0.a.waypoint,rt0.startpos,rt0.startalt,rt0.endalt,rt0.winddir,rt0.windvel,rt0.gs,
                        "start","start",1,0,rt0.tas,False)
                                        
                for rt in rts:                        
                    land_at_end=not not (rt.b.stay and rt.lastsub)
                    print "Land at end of leg:",rt.b.waypoint,":",land_at_end
                    add_wp(rt.b.waypoint,rt.endpos,rt.startalt,rt.endalt,rt.winddir,rt.windvel,rt.gs,rt.what,rt.legpart,rt.lastsub,rt.d,rt.tas,land_at_end)

            tripobj['waypoints']=waypoints
            print "returning json:", waypoints
            response.headers['Content-Type'] = 'text/plain'            
            return json.dumps(tripobj)
        except Exception,cause:
            response.headers['Content-Type'] = 'text/plain'            
            print "Exception",cause
            return json.dumps(dict(error=repr(cause)))
Ejemplo n.º 12
0
def decode_challenge(challenge):
    d = base64.b16decode(challenge)
    dhash = d[0:32]
    username = unicode(d[32:], 'utf-8')

    users = meta.Session.query(User).filter(
        sa.and_(User.user == username)).all()
    if len(users) == 0: return None
    user, = users

    buf = (user.lastlogin.strftime("%Y-%m-%d") + user.user +
           user.password).encode('utf-8')
    hash = md5str(buf)
    assert len(hash) == 32
    challenge = hash + user.user.encode('utf-8')
    print "Challenge: %s, Should be: %s" % (d, challenge)
    if challenge == d:
        return user
    return None
Ejemplo n.º 13
0
 def uploadtrip(self):
     def writeInt(x):
         response.write(struct.pack(">I",x))
     
     #print "upload trip",request.params
     try:
         f=request.POST['upload'].file
         def readShort():
             return struct.unpack(">H",f.read(2))[0]
         def readUTF():
             len=readShort()
             print "Read string of length %d"%(len,)
             data=f.read(len)
             return unicode(data,"utf8")
         
         username=readUTF()
         password=readUTF()
         print "user,pass",username,password
         users=meta.Session.query(User).filter(User.user==username).all()
         if len(users)==0:
             raise BadCredentials("bad user")
         user=users[0]
         if user.password!=password and user.password!=md5str(password):
             raise BadCredentials("bad password")
         
         #print "POST:",request.params
         newrec=parseRecordedTrip(user.user,f)
         
         meta.Session.query(Recording).filter(
             sa.and_(Recording.start==newrec.start,
                     Recording.user==newrec.user)).delete()
         meta.Session.add(newrec)
         meta.Session.flush()
         meta.Session.commit()
         
         #print "GOt bytes: ",len(cont)
         #print "Upload!",request.params
     except BadCredentials,cause:
         response.headers['Content-Type'] = 'application/binary'        
         writeInt(0xf00db00f)
         writeInt(1) #version
         writeInt(1) #errorcode, bad user/pass
         return None
Ejemplo n.º 14
0
def decode_challenge(challenge):
    d=base64.b16decode(challenge)
    dhash=d[0:32]
    username=unicode(d[32:],'utf-8')

    users=meta.Session.query(User).filter(sa.and_(
            User.user==username)
            ).all()
    if len(users)==0: return None
    user,=users
    
    buf=(user.lastlogin.strftime("%Y-%m-%d")+user.user+user.password).encode('utf-8')
    hash=md5str(buf)
    assert len(hash)==32
    challenge=hash+user.user.encode('utf-8')
    print "Challenge: %s, Should be: %s"%(d,challenge)
    if challenge==d:
        return user
    return None
Ejemplo n.º 15
0
 def get_trips(self):
     try:
         print "Get trips",request.params
         users=meta.Session.query(User).filter(User.user==request.params['user']).all()
         if len(users)==0:
             return json.dumps(dict(error=u"No user with that name"))
         user,=users
         if user.password!=request.params['password'] and user.password!=md5str(request.params['password']):
             return json.dumps(dict(error=u"Wrong password"))
             
         out=[]        
         for trip in meta.Session.query(Trip).filter(Trip.user==user.user).order_by(Trip.trip).all():
             out.append(trip.trip)
         response.headers['Content-Type'] = 'text/plain'            
         s=json.dumps(dict(trips=out))
         print "Returning",repr(s)
         return s
     except Exception,cause:
         response.headers['Content-Type'] = 'text/plain'            
         return json.dumps(dict(error=repr(cause)))
Ejemplo n.º 16
0
    def get_map_near_trip(self):
        users = meta.Session.query(User).filter(
            User.user == request.params['user']).all()
        if len(users) == 0:
            return json.dumps(dict(error=u"No user with that name"))
        user, = users
        if user.password != request.params[
                'password'] and user.password != md5str(
                    request.params['password']):
            return json.dumps(dict(error=u"Wrong password"))
        trip = request.params['trip']

        rts = sorted(list(
            meta.Session.query(Route).filter(
                sa.and_(Route.user == request.params['user'],
                        Route.trip == trip)).all()),
                     key=lambda x: x.a.ordering)

        response.headers['Content-Type'] = 'application/binary'
        return android_fplan_bitmap_format(map_tiles_near(rts, 10))
Ejemplo n.º 17
0
    def get_trips(self):
        try:
            print "Get trips", request.params
            users = meta.Session.query(User).filter(
                User.user == request.params['user']).all()
            if len(users) == 0:
                return json.dumps(dict(error=u"No user with that name"))
            user, = users
            if user.password != request.params[
                    'password'] and user.password != md5str(
                        request.params['password']):
                return json.dumps(dict(error=u"Wrong password"))

            out = []
            for trip in meta.Session.query(Trip).filter(
                    Trip.user == user.user).order_by(Trip.trip).all():
                out.append(trip.trip)
            response.headers['Content-Type'] = 'text/plain'
            s = json.dumps(dict(trips=out))
            print "Returning", repr(s)
            return s
        except Exception, cause:
            response.headers['Content-Type'] = 'text/plain'
            return json.dumps(dict(error=repr(cause)))
Ejemplo n.º 18
0
    def getmap(self):

        users = meta.Session.query(User).filter(
            User.user == request.params['user']).all()
        badpass = False
        if len(users) == 0:
            badpass = True
        else:
            user, = users
            if user.password != request.params[
                    'password'] and user.password != md5str(
                        request.params['password']):
                badpass = True
        maptype = request.params.get('maptype', 'nolabel')

        def writeInt(x):
            response.write(struct.pack(">I", x))

        def writeLong(x):
            response.write(struct.pack(">Q", x))

        response.headers['Content-Type'] = 'application/binary'

        version,level,offset,maxlen,maxlevel=\
            [int(request.params[x]) for x in "version","level","offset","maxlen","maxlevel"]

        writeInt(0xf00df00d)
        writeInt(1)  #version
        if badpass:
            print "badpassword"
            writeInt(1)  #error, bad pass
            return None
        #print "Correct password"

        totalsize = 0
        stamp = 0
        for lev in xrange(maxlevel + 1):
            tlevelfile = os.path.join(os.getenv("SWFP_DATADIR"),
                                      "tiles/" + maptype + "/level" + str(lev))
            totalsize += os.path.getsize(tlevelfile)
            stamp = max(stamp, os.stat(tlevelfile)[stat.ST_MTIME])
        #print "Maxlevel: %d, stamp: %d"%(maxlevel,stamp)
        levelfile = os.path.join(os.getenv("SWFP_DATADIR"),
                                 "tiles/" + maptype + "/level" + str(level))
        curlevelsize = os.path.getsize(levelfile)
        cursizeleft = curlevelsize - offset
        #print "cursize left:",cursizeleft
        #print "maxlen:",maxlen
        if cursizeleft < 0:
            cursizeleft = 0
        if maxlen > cursizeleft:
            maxlen = cursizeleft
        if maxlen > 1000000:
            maxlen = 1000000

        writeInt(0)  #no error
        #print "No error"
        writeLong(stamp)  #"data version"
        #print "stamp:",stamp
        writeLong(curlevelsize)
        writeLong(totalsize)
        writeLong(cursizeleft)
        writeInt(0xa51c2)
        latest = meta.Session.query(Download).filter(
            Download.user == user.user).order_by(sa.desc(
                Download.when)).first()
        if not latest or datetime.utcnow() - latest.when > timedelta(0, 3600):
            down = Download(user.user, maxlen)
            meta.Session.add(down)
        else:
            down = latest
            down.bytes += maxlen
        meta.Session.flush()
        meta.Session.commit()

        f = open(levelfile)

        if offset < curlevelsize:
            #print "seeking to %d of file %s, then reading %d bytes"%(offset,levelfile,maxlen)
            f.seek(offset)
            data = f.read(maxlen)
            #print "Writing %d bytes to client"%(len(data),)
            response.write(data)
        f.close()
        return None
Ejemplo n.º 19
0
    def get_trip(self):
        try:
            print "Get trip", request.params
            users = meta.Session.query(User).filter(
                User.user == request.params['user']).all()
            if len(users) == 0:
                return json.dumps(dict(error=u"No user with that name"))
            user, = users
            if user.password != request.params[
                    'password'] and user.password != md5str(
                        request.params['password']):
                return json.dumps(dict(error=u"Wrong password"))

            trip, = meta.Session.query(Trip).filter(
                sa.and_(Trip.user == user.user,
                        Trip.trip == request.params['trip'])).order_by(
                            Trip.trip).all()

            tripobj = dict()
            tripobj['trip'] = trip.trip
            waypoints = []
            rts, dummy = calc_route_info.get_route(user.user, trip.trip)
            if len(rts):

                def either(x, fallback):
                    if x == None: return fallback
                    return x

                def add_wp(name, pos, startalt, endalt, winddir, windvel, gs,
                           what, legpart, lastsub, d, tas, land_at_end):
                    d = dict(lat=pos[0],
                             lon=pos[1],
                             name=name,
                             startalt=startalt,
                             endalt=endalt,
                             winddir=winddir,
                             windvel=windvel,
                             gs=either(gs, 75),
                             what=what,
                             legpart=legpart,
                             lastsub=lastsub,
                             d=d,
                             tas=either(tas, 75),
                             land_at_end=land_at_end)
                    waypoints.append(d)

                rt0 = rts[0]

                add_wp(rt0.a.waypoint, rt0.startpos, rt0.startalt, rt0.endalt,
                       rt0.winddir, rt0.windvel, rt0.gs, "start", "start", 1,
                       0, rt0.tas, False)

                for rt in rts:
                    land_at_end = not not (rt.b.stay and rt.lastsub)
                    print "Land at end of leg:", rt.b.waypoint, ":", land_at_end
                    add_wp(rt.b.waypoint, rt.endpos, rt.startalt, rt.endalt,
                           rt.winddir, rt.windvel, rt.gs, rt.what, rt.legpart,
                           rt.lastsub, rt.d, rt.tas, land_at_end)

            tripobj['waypoints'] = waypoints
            print "returning json:", waypoints
            response.headers['Content-Type'] = 'text/plain'
            return json.dumps(tripobj)
        except Exception, cause:
            response.headers['Content-Type'] = 'text/plain'
            print "Exception", cause
            return json.dumps(dict(error=repr(cause)))
Ejemplo n.º 20
0
class ApiController(BaseController):

    no_login_required = True  #But we don't show personal data without user/pass

    def get_airspaces(self):
        print "Get airspaces called"

        getsectors = int(request.params.get("sectors", "0"))

        out = []
        if 1:
            for space in extracted_cache.get_airspaces(
            ) + get_notam_objs_cached(
            )['areas'] + extracted_cache.get_aip_sup_areas():
                lat, lon = mapper.from_str(space['points'][0])
                #if lat<57 or lat>62:
                #    continue
                if getsectors == 0 and space.get('type', None) == 'sector':
                    continue
                name = space['name']
                if space['type'] == "notamarea":
                    name = "NOTAM:" + name
                clnd = cleanup_poly(
                    [mapper.from_str(x) for x in space['points']], name)
                if not clnd:
                    print "Skipped area", name, space
                    continue
                out.append(
                    dict(
                        name=name,
                        freqs=space['freqs'] if space.get('freqs', "") else [],
                        floor=space.get('floor', ""),
                        type=space['type'],
                        ceiling=space.get('ceiling', ""),
                        points=[dict(lat=p[0], lon=p[1]) for p in clnd]))

        aiptexts = []
        points = []
        version = request.params.get("version", None)
        getaiptext = int(request.params.get("aip", "0"))
        print "version", version
        if version and int(version.strip()) >= 5:
            user_aipgen = request.params.get("aipgen", "")
        else:
            user_aipgen = ""
        for airp in extracted_cache.get_airfields():
            lat, lon = mapper.from_str(airp['pos'])
            if lat < 54 or lon < 4 or lon >= 30.5:
                try:
                    if not version or int(version.strip()) <= 7:
                        continue
                except:
                    continue

            #if lat<58.5 or lat>60.5:
            #    continue
            aname = airp['name']

            notams = []
            icao = None
            taf = None
            metar = None
            kind = 'field'
            if airp.get('icao', 'zzzz').lower() != 'zzzz':
                icao = airp['icao']
                notams = notam_geo_search.get_notam_for_airport(icao)
                metar = metartaf.get_metar(icao)
                taf = metartaf.get_taf(icao)
                kind = 'port'

            ap = dict(name=aname,
                      lat=lat,
                      lon=lon,
                      kind=kind,
                      notams=notams,
                      remark=airp.get('remark', ''),
                      alt=float(airp.get('elev', 0)))
            if 'runways' in airp:
                ap['runways'] = airp['runways']
            if icao:
                ap['icao'] = icao
                if taf.text:
                    ap['taf'] = taf.text
                if metar.text:
                    ap['metar'] = metar.text

                if getaiptext and 'aiptext' in airp:
                    for aiptext in airp['aiptext']:
                        if aip_text_documents.check_doc(
                                aiptext['icao'], aiptext['category'],
                                aiptext['checksum']):
                            #^^^Okay, this really needs an explanation^^^
                            #Nominally, each aiptext item in aipdata.cache (from which the get_airfields() function
                            #ultimately gets all its data, should always have its corresponding aiptext in html format
                            #available on disk. Now, if the on-disk file is deleted (should never happen), we will
                            #get an exception later down where we try to send this data (with the checksum we have here)
                            #over http to the client. Unfortunately, the routine that sends the data is not at liberty
                            #to modify "what was sent", so the entire sync operation fails. This hack here makes the
                            #failure happen earlier, and in that case the given aiptext-document is suppressed
                            #completely, meaning that the sync operation succeeds, albeit without one specific document
                            #(hey, better than nothing!).
                            #
                            #Of course, the real question is why a document may be missing. A bug of some sort right now,
                            #2012-08-28, makes this bug occur every now and then. Investigation is ongoing.
                            aiptexts.append(
                                dict(name=icao + "_" + aiptext['category'],
                                     icao=icao,
                                     data=aiptext))

            if 'adcharts' in airp and '' in airp['adcharts'] and airp[
                    'adcharts'][""]['blobname']:
                ret = airp['adcharts'][""]
                try:
                    cksum = ret['checksum']
                    try:
                        aprojmatrix = get_proj(cksum).matrix
                    except Exception:
                        #print traceback.format_exc()
                        #print "Using 0-proj for ",aname
                        aprojmatrix = [0 for x in xrange(6)]

                    ap['adchart_matrix'] = list(aprojmatrix)
                    ap['adchart_width'] = ret['render_width']
                    ap['adchart_height'] = ret['render_height']
                    ap['adchart_name'] = ret['blobname']
                    ap['adchart_checksum'] = cksum
                    ap['adchart_url'] = ret['url']
                except Exception, cause:
                    print "Couldn't get projection for airport %s (%s)" % (
                        aname, cause)

            points.append(ap)
        for sigp in extracted_cache.get_sig_points():
            lat, lon = mapper.from_str(sigp['pos'])
            kind = sigp.get('kind', 'sigpoint')
            if kind == 'sig. point':
                kind = 'sigpoint'
            if not kind in ['sigpoint', 'city', 'town']:
                kind = 'sigpoint'
            points.append(
                dict(name=sigp['name'],
                     lat=lat,
                     lon=lon,
                     kind=kind,
                     alt=-9999.0))

        user = request.params.get('user', None)
        correct_pass = False
        if user:
            try:
                print "Received password", request.params[
                    'password'], "user:"******"Bad password")
                correct_pass = True
                trips = get_user_trips(user)
            except Exception:
                print traceback.format_exc()
                trips = []
        else:
            trips = []

            #print "Just added:",points[-1]
        #add sig. points!
        if 1:
            for obst in chain(
                    notam_geo_search.get_notam_objs_cached()['obstacles'],
                    extracted_cache.get_obstacles()):
                lat, lon = mapper.from_str(obst['pos'])
                #if lat<58.5 or lat>59.5:
                #    continue
                tname = obst.get('name', 'Unknown')
                if obst.get('kind', '').startswith("notam"):
                    tname = "Notam Obst."
                points.append(
                    dict(name=tname,
                         lat=lat,
                         lon=lon,
                         kind="obstacle",
                         alt=float(obst['elev'])))

        if request.params.get('csv', '').strip() != "":
            #use CSV format
            meta.Session.flush()
            meta.Session.commit()
            buf = StringIO.StringIO()
            w = csv.writer(buf)
            for space in out:
                freq = ''
                if len(space['freqs']) > 0:
                    freq = " ".join(u"%s" % (x[1], ) for x in space['freqs'])
                    freq = freq
                line = [
                    space['name'], '*', freq, '*', space['floor'],
                    space['ceiling']
                ]
                for point in space['points']:
                    lat, lon = point['lat'], point['lon']
                    line.append(lat)
                    line.append(lon)
                for i in xrange(len(line)):
                    if type(line[i]) == unicode:
                        line[i] = line[i].encode('utf8')
                w.writerow(line)
            response.headers['Content-Type'] = 'text/plain'
            return buf.getvalue()
        elif request.params.get('binary', '').strip() != '':
            response.headers['Content-Type'] = 'application/binary'
            ret = android_fplan_map_format(airspaces=out,
                                           points=points,
                                           aiptexts=aiptexts,
                                           trips=trips,
                                           version=version,
                                           user_aipgen=user_aipgen,
                                           correct_pass=correct_pass)

            print "meta.Session.flush/commit"
            meta.Session.flush()
            meta.Session.commit()
            if 'zip' in request.params:
                zobj = zlib.compressobj(9)  #,zlib.DEFLATED,14)
                ret = zobj.compress(ret)
                ret += zobj.flush()
            print "Android map download from:", request.environ.get(
                "REMOTE_ADDR", 'unknown'), " size: ", len(ret), "bytes"
            return ret
        else:
            meta.Session.flush()
            meta.Session.commit()

            rawtext = json.dumps(dict(airspaces=out, points=points), indent=1)

            if 'zip' in request.params:
                response.headers[
                    'Content-Type'] = 'application/x-gzip-compressed'
                return zlib.compress(rawtext)
            else:
                response.headers['Content-Type'] = 'text/plain'
                return rawtext
Ejemplo n.º 21
0
    def getmap(self):

        users=meta.Session.query(User).filter(User.user==request.params['user']).all()
        badpass=False
        if len(users)==0:
            badpass=True
        else:
            user,=users
            if user.password!=request.params['password'] and user.password!=md5str(request.params['password']):
                badpass=True
        maptype=request.params.get('maptype','nolabel')
        def writeInt(x):
            response.write(struct.pack(">I",x))
        def writeLong(x):
            response.write(struct.pack(">Q",x))
        response.headers['Content-Type'] = 'application/binary'        

        version,level,offset,maxlen,maxlevel=\
            [int(request.params[x]) for x in "version","level","offset","maxlen","maxlevel"];
        
        writeInt(0xf00df00d)
        writeInt(1) #version
        if badpass:
            print "badpassword"
            writeInt(1) #error, bad pass
            return None
        #print "Correct password"
        
        totalsize=0
        stamp=0
        for lev in xrange(maxlevel+1):
            tlevelfile=os.path.join(os.getenv("SWFP_DATADIR"),"tiles/"+maptype+"/level"+str(lev))
            totalsize+=os.path.getsize(tlevelfile)
            stamp=max(stamp,os.stat(tlevelfile)[stat.ST_MTIME])
        #print "Maxlevel: %d, stamp: %d"%(maxlevel,stamp)
        levelfile=os.path.join(os.getenv("SWFP_DATADIR"),"tiles/"+maptype+"/level"+str(level))
        curlevelsize=os.path.getsize(levelfile)    
        cursizeleft=curlevelsize-offset
        #print "cursize left:",cursizeleft
        #print "maxlen:",maxlen
        if cursizeleft<0:
            cursizeleft=0
        if maxlen>cursizeleft:
            maxlen=cursizeleft
        if maxlen>1000000:
            maxlen=1000000
        
         
        writeInt(0) #no error
        #print "No error"
        writeLong(stamp) #"data version"
        #print "stamp:",stamp
        writeLong(curlevelsize)
        writeLong(totalsize)
        writeLong(cursizeleft)
        writeInt(0xa51c2)
        latest=meta.Session.query(Download).filter(Download.user==user.user).order_by(sa.desc(Download.when)).first()
        if not latest or datetime.utcnow()-latest.when>timedelta(0,3600):
            down=Download(user.user, maxlen)
            meta.Session.add(down)
        else:
            down=latest
            down.bytes+=maxlen
        meta.Session.flush()
        meta.Session.commit()

        f=open(levelfile)

        if offset<curlevelsize:
            #print "seeking to %d of file %s, then reading %d bytes"%(offset,levelfile,maxlen)
            f.seek(offset)
            data=f.read(maxlen)
            #print "Writing %d bytes to client"%(len(data),)
            response.write(data)
        f.close()
        return None