def http_url_key(self, uri, parameters): #Strip type information parameters = {x:parameters[x][0] for x in parameters} uri = uri[0][:-1] cookie = parameters[HTTP_COOKIE_KEY] app_id = parameters[HTTP_APP_ID_KEY] del parameters[HTTP_COOKIE_KEY] del parameters[HTTP_APP_ID_KEY] log.info(uri) log.info(json.dumps(parameters)) req = urllib2.Request(uri) req.add_header('Content-Type', 'application/json') req.add_header('X-Pebble-ID', self._id) try: response = urllib2.urlopen(req, json.dumps(parameters)) code = response.getcode() data = json.load(response) if type(data) != dict: code = 0 raise ValueError("Server did not return a dictionary") except urllib2.URLError: code = 0 data = {} except ValueError: data = {} log.info("%d: %s" % (code, data)) vals = [ (HTTP_STATUS_KEY, "UINT", pack("<H", code)), (HTTP_URL_KEY, "UINT", pack("<B", (1 if code is 200 else 0))), (HTTP_COOKIE_KEY, "UINT", pack("<I", cookie)), (HTTP_APP_ID_KEY, "UINT", pack("<I", app_id)) ] for k in data: v = data[k] k = int(k) if type(v) is list: assert len(v) == 2 t = v[0] v = v[1] if t == 'd': vals.append((k, "BYTE_ARRAY", b64decode(v))) else: assert t in self.type_conversion t = self.type_conversion[t] vals.append((k, t[0], pack('<%s' % t[1], v))) elif type(v) is int: vals.append((k, "INT", pack('<i', v))) else: vals.append((k, "CSTRING", v)) tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_location_key(self, code, parameters): assert code[0] == 1, "Expected 1, got %s" % repr(code) assert len(parameters) == 0 try: pos = self._locationProvider.lastKnownPosition() lat = pos.coordinate().latitude() lon = pos.coordinate().longitude() alt = pos.coordinate().altitude() if math.isnan(lat): lat = 0 if math.isnan(lon): lon = 0 if math.isnan(alt): alt = 0 except: lat = 0 lon = 0 alt = 0 vals = [ (HTTP_LOCATION_KEY, 5.0), (HTTP_LATITUDE_KEY, lat), (HTTP_LONGITUDE_KEY, lon), (HTTP_ALTITUDE_KEY, alt), ] tuples = [AppMessage.construct_tuple(x[0], "UINT", pack("<f", x[1])) for x in vals] return AppMessage.construct_dict(tuples)
def request_screenshot(self): vals = [(HTTP_FRAMEBUFFER_SLICE, "UINT", pack("<B", 1))] tuples = [AppMessage.construct_tuple(*x) for x in vals] #TODO: Global transaction counter? msg = AppMessage.construct_message(AppMessage.construct_dict(tuples), "PUSH", self.UUID.bytes, "\x10") self._pebble._send_message("APPLICATION_MESSAGE", msg)
def http_url_key(self, uri, parameters): #Strip type information parameters = {x: parameters[x][0] for x in parameters} uri = uri[0][:-1] cookie = parameters[HTTP_COOKIE_KEY] app_id = parameters[HTTP_APP_ID_KEY] del parameters[HTTP_COOKIE_KEY] del parameters[HTTP_APP_ID_KEY] log.info(uri) log.info(json.dumps(parameters)) req = urllib2.Request(uri) req.add_header('Content-Type', 'application/json') req.add_header('X-Pebble-ID', self._id) try: response = urllib2.urlopen(req, json.dumps(parameters)) code = response.getcode() data = json.load(response) if type(data) != dict: code = 0 raise ValueError("Server did not return a dictionary") except urllib2.URLError: code = 0 data = {} except ValueError: data = {} log.info("%d: %s" % (code, data)) vals = [(HTTP_STATUS_KEY, "UINT", pack("<H", code)), (HTTP_URL_KEY, "UINT", pack("<B", (1 if code is 200 else 0))), (HTTP_COOKIE_KEY, "UINT", pack("<I", cookie)), (HTTP_APP_ID_KEY, "UINT", pack("<I", app_id))] for k in data: v = data[k] k = int(k) if type(v) is list: assert len(v) == 2 t = v[0] v = v[1] if t == 'd': vals.append((k, "BYTE_ARRAY", b64decode(v))) else: assert t in self.type_conversion t = self.type_conversion[t] vals.append((k, t[0], pack('<%s' % t[1], v))) elif type(v) is int: vals.append((k, "INT", pack('<i', v))) else: vals.append((k, "CSTRING", v)) tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def request_screenshot(self): vals = [ (HTTP_FRAMEBUFFER_SLICE, "UINT", pack("<B", 1)) ] tuples = [AppMessage.construct_tuple(*x) for x in vals] #TODO: Global transaction counter? msg = AppMessage.construct_message(AppMessage.construct_dict(tuples), "PUSH", self.UUID.bytes, "\x10") self._pebble._send_message("APPLICATION_MESSAGE", msg)
def http_location_key(self, code, parameters): assert code[0] == 1, "Expected 1, got %s" % repr(code) assert len(parameters) == 0 vals = [ (HTTP_LOCATION_KEY, 5.0), (HTTP_LATITUDE_KEY, 47.62052), (HTTP_LONGITUDE_KEY, -122.32408), (HTTP_ALTITUDE_KEY, 31.337), ] tuples = [AppMessage.construct_tuple(x[0], "UINT", pack("<f", x[1])) for x in vals] return AppMessage.construct_dict(tuples)
def __init__(self, pebble, locationProvider): self._pebble = pebble self._id = pebble.id self._cookies = collections.defaultdict(dict) #TODO: Serialize/deserialize to disk self._locationProvider = locationProvider if len(self._id) > 4: self._id = self._id[-5:-3] + self._id[-2:] #TODO: Verify this doesn't break non-lightblue folks. vals = [(HTTP_CONNECT_KEY, 'INT', pack("<B", 1))] tuples = [AppMessage.construct_tuple(*x) for x in vals] msg = AppMessage.construct_message(AppMessage.construct_dict(tuples), "PUSH", self.UUID.bytes, '\x01') #TODO: Transaction handling. pebble._send_message("APPLICATION_MESSAGE", msg)
def http_location_key(self, code, parameters): assert code[0] == 1, "Expected 1, got %s" % repr(code) assert len(parameters) == 0 vals = [ (HTTP_LOCATION_KEY, 5.0), (HTTP_LATITUDE_KEY, 47.62052), (HTTP_LONGITUDE_KEY, -122.32408), (HTTP_ALTITUDE_KEY, 31.337), ] tuples = [ AppMessage.construct_tuple(x[0], "UINT", pack("<f", x[1])) for x in vals ] return AppMessage.construct_dict(tuples)
def http_cookie_store(self, request_id, parameters): request_id = request_id[0] app_id = parameters[HTTP_APP_ID_KEY][0] del parameters[HTTP_APP_ID_KEY] for key in parameters: self._cookies[app_id][key] = parameters[key] vals = [ (HTTP_COOKIE_STORE_KEY, 'INT', pack("<i", request_id)), (HTTP_APP_ID_KEY, 'INT', pack("<i", app_id)), ] tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_cookie_fsync(self, code, parameters): assert code[0] == 1, "Expected 1, got %s" % repr(code) app_id = parameters[HTTP_APP_ID_KEY] del parameters[HTTP_APP_ID_KEY] assert len(parameters) == 0 #TODO: Currently a no-op until persistent data store is set up. #NOTE: This is within spec. vals = [ (HTTP_COOKIE_FSYNC_KEY, 'UINT', pack("<B", 1)), (HTTP_APP_ID_KEY, 'INT', pack("<i", app_id)), ] tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_time_key(self, code, parameters): assert code[0] == 1, "Expected 1, got %s" % repr(code) assert len(parameters) == 0 if time.daylight: vals = [ (HTTP_TIME_KEY, 'UINT', pack("<I", int(time.time()))), (HTTP_UTC_OFFSET_KEY, 'INT', pack("<i", time.altzone)), (HTTP_IS_DST_KEY, 'UINT', pack("<B", time.daylight)), (HTTP_TZ_NAME_KEY, 'CSTRING', time.tzname[1]), ] else: vals = [ (HTTP_TIME_KEY, 'UINT', pack("<I", int(time.time()))), (HTTP_UTC_OFFSET_KEY, 'INT', pack("<i", time.timezone)), (HTTP_IS_DST_KEY, 'UINT', pack("<B", time.daylight)), (HTTP_TZ_NAME_KEY, 'CSTRING', time.tzname[0]), ] tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_cookie_delete(self, request_id, parameters): request_id = request_id[0] app_id = parameters[HTTP_APP_ID_KEY][0] del parameters[HTTP_APP_ID_KEY] #NOTE: The spec does not define what to do if a deletion fails unlike with load - so we warn. for key in parameters: assert parameters[key][0] == 1 try: del self._cookies[app_id][key] except KeyError: log.warn("App %x tried to delete non-existent key %x in request %x" % (app_id, key, request_id)) vals = [ (HTTP_COOKIE_DELETE_KEY, 'INT', pack("<i", request_id)), (HTTP_APP_ID_KEY, 'INT', pack("<i", app_id)), ] tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_cookie_load(self, request_id, parameters): request_id = request_id[0] app_id = parameters[HTTP_APP_ID_KEY][0] del parameters[HTTP_APP_ID_KEY] vals = [ (HTTP_COOKIE_LOAD_KEY, 'INT', pack("<i", request_id)), (HTTP_APP_ID_KEY, 'INT', pack("<i", app_id)), ] for key in parameters: assert parameters[key][0] == 1 try: (v,t) = self._cookies[app_id][key] vals.append((key,AppMessage.struct_to_tuple_type[t[-1]],pack("<%s" % t, v))) except KeyError: #Spec says to ignore missing keys. log.debug("App %x tried to retrieve non-existent key %x in request %x" % (app_id, key, request_id)) tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_cookie_delete(self, request_id, parameters): request_id = request_id[0] app_id = parameters[HTTP_APP_ID_KEY][0] del parameters[HTTP_APP_ID_KEY] #NOTE: The spec does not define what to do if a deletion fails unlike with load - so we warn. for key in parameters: assert parameters[key][0] == 1 try: del self._cookies[app_id][key] except KeyError: log.warn( "App %x tried to delete non-existent key %x in request %x" % (app_id, key, request_id)) vals = [ (HTTP_COOKIE_DELETE_KEY, 'INT', pack("<i", request_id)), (HTTP_APP_ID_KEY, 'INT', pack("<i", app_id)), ] tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_cookie_load(self, request_id, parameters): request_id = request_id[0] app_id = parameters[HTTP_APP_ID_KEY][0] del parameters[HTTP_APP_ID_KEY] vals = [ (HTTP_COOKIE_LOAD_KEY, 'INT', pack("<i", request_id)), (HTTP_APP_ID_KEY, 'INT', pack("<i", app_id)), ] for key in parameters: assert parameters[key][0] == 1 try: (v, t) = self._cookies[app_id][key] vals.append((key, AppMessage.struct_to_tuple_type[t[-1]], pack("<%s" % t, v))) except KeyError: #Spec says to ignore missing keys. log.debug( "App %x tried to retrieve non-existent key %x in request %x" % (app_id, key, request_id)) tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)
def http_url_key(self, uri, parameters): #Strip type information newparams = {} for x in parameters: newparams[x] = parameters[x][0] parameters = newparams uri = uri[0] cookie = parameters[HTTP_COOKIE_KEY] app_id = parameters[HTTP_APP_ID_KEY] del parameters[HTTP_COOKIE_KEY] del parameters[HTTP_APP_ID_KEY] log.info("URI: %s" % repr(uri)) log.info(json.dumps(parameters)) req = urllib2.Request(uri) req.add_header('Content-Type', 'application/json') req.add_header('X-Pebble-ID', self._id) try: response = urllib2.urlopen(req, json.dumps(parameters)) code = response.getcode() success = 1 if code is 200 else 0 data = json.load(response) if type(data) is not dict: log.warn("Received invalid (non-dictionary) JSON from server.") success = 0 except urllib2.URLError as e: log.warn("URLError: %s" % e.reason) success = 0 except: exctype, value = sys.exc_info()[:2] log.warn("%s: %s" % (exctype, value)) success = 0 vals = [ (HTTP_STATUS_KEY, "UINT", pack("<H", code)), (HTTP_URL_KEY, "UINT", pack("<B", success)), (HTTP_COOKIE_KEY, "UINT", pack("<I", cookie)), (HTTP_APP_ID_KEY, "UINT", pack("<I", app_id)) ] if success: log.info("%d: %s" % (code, data)) for k in data: v = data[k] k = int(k) if type(v) is list: assert len(v) == 2 t = v[0] v = v[1] if t == 'd': vals.append((k, "BYTE_ARRAY", b64decode(v))) else: assert t in self.type_conversion t = self.type_conversion[t] vals.append((k, t[0], pack('<%s' % t[1], v))) elif type(v) is int: vals.append((k, "INT", pack('<i', v))) else: vals.append((k, "CSTRING", v)) tuples = [AppMessage.construct_tuple(*x) for x in vals] return AppMessage.construct_dict(tuples)