def process_app_pay_receipt(receipt, shared_secret=None) -> Tuple[bool, dict]: bundle_id = os.environ['BUNDLE_ID'] # if True, automatically query sandbox endpoint # if validation fails on production endpoint if is_true(os.environ['AUTO_RETRY_WRONG_ENV_REQUEST']): auto_retry_wrong_env_request = True else: auto_retry_wrong_env_request = False validator = AppStoreValidator( bundle_id=bundle_id, sandbox=is_true(os.environ['RECEIPT_SANDBOX']), auto_retry_wrong_env_request=auto_retry_wrong_env_request, ) try: # if True, include only the latest renewal transaction exclude_old_transactions = False logging.debug("Validating AppStore Receipt:") validation_result: Dict[Any, Any] = validator.validate( receipt=receipt, shared_secret=shared_secret, exclude_old_transactions=exclude_old_transactions) logging.debug(f'Validation Result: {validation_result}') except InAppPyValidationError as ex: # handle validation error # contains actual response from AppStore service. response_from_apple = ex.raw_response logging.debug(f"validation failure: {response_from_apple}") return (False, response_from_apple) return (True, validation_result)
def main(event, context): stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.debug(f'entry_payment_google stage:{stage}') logging.debug(f'os.environ: {os.environ}') logging.debug(f'event: {event}') logging.debug(f'context: {context}') logging.debug(f'body: {body}') #receipt = body.get('receipt', '') #bundle_id = body.get('bundle_id', '') account_id = body.get('account_id', '') verify_receipt = True # todo: add optional existing account if os.environ['STAGE'] == 'dev': verify_receipt = is_true(body.get('verify_receipt', 'True')) if os.environ['STAGE'] != 'dev': if body.get('verify_receipt', None) is not None: return response(402, {'msg': 'invalid_dev_param'}) GOOGLE_SERVICE_ACCOUNT_KEY_FILE = get_secret( 'ORCHID_GOOGLE_SERVICE_ACCOUNT2') logging.debug(f'{GOOGLE_SERVICE_ACCOUNT_KEY_FILE}') GOOGLE_SERVICE_ACCOUNT_KEY = json.loads(GOOGLE_SERVICE_ACCOUNT_KEY_FILE) purchase_token = body.get('receipt', '') product_id = body.get('product_id', '') bundle_id = body.get('bundle_id', 'net.orchid.Orchid') msg, receipt_hash, total_usd = verify_(GOOGLE_SERVICE_ACCOUNT_KEY, purchase_token, product_id, bundle_id) if ((account_id is None) or (account_id == '')): account_id = receipt_hash if (msg == "success"): logging.debug(f'conditional writing receipt with hash: {receipt_hash}') try: w3_generic.dynamodb_cwrite1(os.environ['RECEIPT_TABLE_NAME'], 'receipt', receipt_hash) except Exception as e: logging.info(f'writing receipt exception: {str(e)} ') return response(403, {'msg': 'Receipt already redeemed'}) w3_generic.credit_account_balance(account_id, total_usd) return response(200, { 'msg': msg, 'account_id': account_id, 'total_usd': total_usd }) else: return response(402, {'msg': msg})
def test_is_true(self): trues = (1, "True", "true", "TRUE", "t", "T") for t in trues: res = utils.is_true(t) self.assertTrue(res) falses = (0, "False", "FALSE", "false", "f", "F") for f in falses: res = utils.is_true(f) self.assertFalse(res)
def main(event, context): stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.info(f'entry_send_raw() stage:{stage}') logging.info(f'event: {event}') logging.info(f'context: {context}') logging.info(f'body: {body}') txn_s = body.get('txn', '') sig = body.get('sig', '') if (sig != ''): if (verify_txn_sig(txn_s,sig) == False): return response(409,{'msg':'Signature verification failure','txnhash':0,'cost_usd':0.0}) txn = json.loads(txn_s) chainId = txn.get('chainId',1) w3wsmap = w3_generic.get_w3wsock_providers() txnhash,cost_usd,msg = new_txn(w3wsmap,txn) logging.info(f'send_raw txnhash({txnhash}) cost_usd({cost_usd}) msg({msg}) ') if (msg == 'success'): return response(200,{'msg':msg,'txnhash':txnhash,'cost_usd':cost_usd}) else: return response(401,{'msg':msg,'txnhash':0,'cost_usd':0.0})
def get_oxt_balance(address=get_secret(key=os.environ['PAC_FUNDER_PUBKEY_SECRET'])) -> float: token_addr = w3.toChecksumAddress(os.environ['TOKEN']) token_contract = w3.eth.contract( abi=token_abi, address=token_addr, ) token_name = get_token_name(token_addr) token_symbol = get_token_symbol(token_addr) token_decimals = get_token_decimals(token_addr) DECIMALS = 10 ** token_decimals raw_balance = token_contract.functions.balanceOf(address).call() balance = raw_balance / DECIMALS logging.info( f"Balance of {address}: {balance} {token_name} ({token_symbol})") if is_true(os.environ.get('ENABLE_MONITORING', '')): lambda_metric( f"orchid.pac.balance.{token_symbol.lower()}", balance, tags=[ f'account:{address}', f'token_name:{token_name}', f'token_symbol:{token_symbol}', f'token_decimals:{token_decimals}', ] ) return balance
def main(event, context): stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.debug(f'entry_send_raw() stage:{stage}') logging.debug(f'event: {event}') logging.debug(f'context: {context}') logging.debug(f'body: {body}') try: #W3WSock = body.get('W3WSock', '') W3WSock = os.environ['WEB3_WEBSOCKET'] txn = body.get('txn', '') account_id = body.get('account_id', '') txnhash, cost_usd, msg = w3_generic.send_raw(W3WSock, txn, account_id) logging.debug( f'send_raw txnhash({txnhash}) cost_usd({cost_usd}) msg({msg}) ') except ValueError as e: msg = str(e) except: msg = sys.exc_info()[0] if (msg == 'success'): return response_success(txnhash, cost_usd) else: return response_error(msg)
def main(event, context): stage = os.environ['STAGE'] logging.debug(f'verify stage:{stage}') logging.debug(f'event: {event}') body = json.loads(event.get('body', {})) logging.debug(f'body: {body}') if is_true(body.get('debug', '')): configure_logging(level="DEBUG") msg = body.get('msg', '') sig = body.get('sig', '') verified = verifyMessage(message_text=msg, signed_message=sig) resp_body = { 'message_text': msg, 'signed_message': sig, 'verified': verified, } response = { "isBase64Encoded": False, "statusCode": 200, "headers": {}, "body": json.dumps(resp_body) } logging.debug(f'verify response: {response}') return response
def metric(metric_name: str, value: float, timestamp=None, tags=None): if is_true(os.environ.get('ENABLE_MONITORING', '')): lambda_metric( metric_name=metric_name, value=value, timestamp=timestamp, tags=tags, )
def api_list_users(): details = request.args.get('details') all_users = praat.User.query.all() if utils.is_true(details): res = list(u.details() for u in all_users) else: res = list(u.summary() for u in all_users) return jsonify(res)
def api_list_groups(): details = request.args.get('details') all_groups = praat.Group.query.all() if utils.is_true(details): res = list(gp.details() for gp in all_groups) else: res = list(gp.summary() for gp in all_groups) return jsonify(res)
def main(event, context): stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.debug(f'refund_failed_txn() stage:{stage}') logging.debug(f'event: {event}') logging.debug(f'context: {context}') logging.debug(f'body: {body}') receipt = body.get('receipt', '') #bundle_id = body.get('bundle_id', '') account_id = body.get('account_id', '') product_id = body.get('product_id', None) verify_receipt = True # todo: add optional existing account if os.environ['STAGE'] == 'dev': verify_receipt = is_true(body.get('verify_receipt', 'True')) if os.environ['STAGE'] != 'dev': if body.get('verify_receipt'): return response(444,{'msg':'invalid_dev_param'}) msg, receipt_hash, total_usd = payments_apple.handle_receipt(receipt, product_id, stage, verify_receipt) if ((account_id is None) or (account_id == '')): account_id = receipt_hash if (msg == "success"): logging.debug(f'conditional writing receipt with hash: {receipt_hash}') try: w3_generic.dynamodb_cwrite1(os.environ['RECEIPT_TABLE_NAME'], 'receipt', receipt_hash ) except Exception as e: logging.info(f'writing receipt exception: {str(e)} ') return response(403,{'msg':f'Receipt {receipt_hash} already redeemed'}) w3_generic.credit_account_balance(account_id, total_usd) return response(200,{'msg':msg,'account_id':account_id,'total_usd':total_usd}) else: return response(402,{'msg':msg})
def do_create_nginx(options): if not utils.is_true('create_nginx', options['nginx']): return False config_path = options['system']['nginx_config_path'] content = utils.get_config_content(config_path) content = get_prepared_content(content, options, 'nginx') httpd_path = options['system']['nginx_path'] file_name = options['nginx']['site_name'] + '.conf' full_file_path = httpd_path + file_name utils.create_file(full_file_path, content) utils.success_msg("Nginx File was Created.")
def do_create_hosts(options): if not utils.is_true('add_hosts', options['default']): return False file_hosts_path = options['system']['file_hosts_path'] if not os.path.isfile(file_hosts_path): raise Exception('File Hosts Not Found') host_ip = options['system']['hosts_ip'] string = "\n" + host_ip + " " + options['default']['site_name'] #add conditions if record exists file = open(file_hosts_path, 'a') file.write(string) file.close() utils.success_msg("Record in Hosts was Added.")
def __init__(self, meta_configs, appname, use_kv_store=False): """ @meta_configs: dict like and contains checkpoint_dir, session_key, server_uri etc """ self._meta_configs = meta_configs self._appname = appname self._states_cache = {} self._kv_client = None if utils.is_true(use_kv_store): self._state_collection = "states" self._kv_client = kvc.KVClient(meta_configs["server_uri"], meta_configs["session_key"]) kvc.create_collection(self._kv_client, self._state_collection, self._appname) self._pop_states_cache()
def get_eth_balance(address=get_secret( key=os.environ['PAC_FUNDER_PUBKEY_SECRET'])) -> float: token_name = 'Ethereum' token_symbol = 'ETH' token_decimals = 18 DECIMALS = 10**token_decimals raw_balance = w3.eth.getBalance(address) balance = raw_balance / DECIMALS logging.info( f"Balance of {address}: {balance} {token_name} ({token_symbol})") if is_true(os.environ.get('ENABLE_MONITORING', '')): lambda_metric(f"orchid.pac.balance.{token_symbol.lower()}", balance, tags=[ f'account:{address}', f'token_name:{token_name}', f'token_symbol:{token_symbol}', f'token_decimals:{token_decimals}', ]) return balance
def main(event, context): stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.debug(f'recycle() stage:{stage}') logging.debug(f'event: {event}') logging.debug(f'context: {context}') logging.debug(f'body: {body}') funder = toChecksumAddress(address=body.get('funder', '')) signer = toChecksumAddress(address=body.get('signer', '')) password = body.get('password', '') if password != get_secret(key=os.environ['RECYCLE_KEY']): return incorrect_password() pac_funder = get_secret(key=os.environ['PAC_FUNDER_PUBKEY_SECRET']) if funder != pac_funder: return invalid_funder(funder, pac_funder) funder_keys = keys(funder) if signer == '' or signer not in funder_keys: return invalid_signer(signer) amount, escrow, unlock = look(funder, signer) amount_threshold = float("inf") escrow_threshold = float("inf") if amount > amount_threshold: return amount_too_high(amount, amount_threshold) if escrow > escrow_threshold: return escrow_too_high(escrow, escrow_threshold) store_account(funder, signer, unlock) return account_queued_response()
def main(event, context): stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.debug(f'refund_failed_txn() stage:{stage}') logging.debug(f'event: {event}') logging.debug(f'context: {context}') logging.debug(f'body: {body}') W3WSock = body.get('W3WSock', '') txnhash = body.get('txnhash', '') receiptHash = body.get('receiptHash', '') msg = w3_generic.refund_failed_txn(W3WSock,txnhash,receiptHash) if (msg == "success"): return response_success(txnhash) else: return response_error(msg)
def do_create_site(options): if not utils.is_true('create_test_folder', options['default']): return False if not os.path.isdir(options['default']['site_path']): utils.error_msg('Path to Folder Site Not Found') return False site_folder_path = options['default']['site_path'] + options['default'][ 'site_name'] if os.path.isdir(site_folder_path): utils.error_msg('Site Folder is Exist') return False os.makedirs(site_folder_path) template_path = options['system']['template_page_path'] content = utils.get_config_content(template_path) site_folder_path = site_folder_path + "/index.html" utils.create_file(site_folder_path, content) utils.success_msg("Site Folder was Created.")
def generic_audio_ops(user, group, method, audio=None, params=None): if group is None: return "Group does not exist" storage_svc = get_storage_service(praat.app.config) if method == 'GET': #g_info = group.details() #return jsonify(g_info['details']['audios']) audios = [] for audio in group.audios: info = audio.summary() if utils.is_true(params.get('show_versions')): info['versions'] = storage_svc.show_versions(audio.id) audios.append(info) resp = {"status": "success", "audios": audios} print resp return jsonify(resp) if not audio or not audio.filename: # If no audio file, stop status = "No audio file" audioName = "" elif not utils.isSound(audio.filename): # Stop if uploaded file is not a audio status = "Unknown file type" audioName = audio.filename else: audioName = audio.filename data = audio.read() key_seed = group.id + audioName key = utils.generate_id(group.id + audioName) attrs = { 'created_by': user.email, } audioObj = praat.Audio.query.get(key) retval = storage_svc.put(key, data, attrs) # save waveform temp_dir = '/tmp/waveform' + key + retval['version'] + '/' waveform_name = key + retval['version'] + '.png' utils.mkdir_p(temp_dir) with open(temp_dir + audioName, 'w') as fp: fp.write(data) script = praat._scripts_dir + 'drawWaveV2' params = [temp_dir + audioName, temp_dir + waveform_name] praat.runScript(script, params) with open(temp_dir + waveform_name, 'r') as fp: data = fp.read() attrs = {'name': audioName} attrs.update(retval) storage_svc.put(waveform_name, data, attrs) utils.rm_rf(temp_dir) if audioObj is None: print 'Creating new audio file' audioObj = praat.Audio(audioName, user, group, key_seed) praat.db_session.add(audioObj) praat.db_session.commit() else: print audioObj.summary() audioObj.updated_at = datetime.datetime.utcnow() praat.db_session.commit() print 'Updating existing audio file' status = "Success" result = { "status": status, "audio": audioName } #return jsonify(result) return redirect('/?context=workspace')
def annotation_ops(audio, vid=None): user = g.user audio_obj = praat.Audio.query.get(audio) if audio_obj is None: return jsonify({"status": "fail", "message": "Audio file does not exist"}) storage_svc = get_storage_service(praat.app.config) if request.method == 'GET': anns = [] for annotation in audio_obj.annotations: summary = annotation.summary() if vid and vid != annotation.audio_version: continue if utils.is_true(request.args.get('show_versions')): summary['versions'] = storage_svc.show_versions(annotation.id) anns.append(summary) resp = {"status": "success", 'annotations': anns} return jsonify(resp) payload = request.json audio_version = vid or payload.get('audio_version') all_versions = storage_svc.show_versions(audio_obj.id) if audio_version is None: if len(all_versions) > 0: audio_version = all_versions[0]['version'] else: return jsonify({"status": "fail", "message": "unable to find any version of audio"}) else: version_exists = False for v in all_versions: if v['version'] == audio_version: version_exists = True break if not version_exists: return jsonify({"status": "fail", "message": "Audio version " + audio_version + " does not exist"}) # Annotation key is a combinatiom of audio id, audio version, and annotation name name = payload['name'] a_key_seed = "%s:%s:%s" % (audio, audio_version, name) # create or update an annotation object start_time = payload['startTime'] end_time = payload['endTime'] if float(start_time) < 0 or float(end_time) < float(start_time): return jsonify({"status": "fail", "message": "Invalid annotation start/end time"}) annotation_obj = praat.AudioAnnotation.query.get(utils.generate_id(a_key_seed)) if annotation_obj is None: print "Creating new Annotation" annotation_obj = praat.AudioAnnotation(name, audio, audio_version, start_time, end_time, a_key_seed) praat.db_session.add(annotation_obj) praat.db_session.commit() else: if annotation_obj.start_time != start_time or annotation_obj.end_time != end_time: return jsonify({"status":"fail", "message": "Inconsistent start time or end time for annotation " + name}) annotation_obj.updated_at = datetime.datetime.utcnow() praat.db_session.commit() # save annotation details in annotation version attributes = { 'created_by': user.email, } contents = { 'commitMessage': payload.get('commitMessage', ''), 'tierOne': payload.get('tierOne', ''), 'tierTwo': payload.get('tierTwo', ''), 'tierThree': payload.get('tierThree', ''), } storage_svc.put(annotation_obj.id, json.dumps(contents), attributes) return jsonify({"status": "success", "summary": annotation_obj.summary()})
def populateDB(self): """ Download the required data from the OSM server, and populate the postresql database with it. 31dec2009 GJ ORIGINAL VERSION """ print "populateDB" #Convert the lat/long origin into mercator projection metres. prj = mapnik.Projection(self.srs) c0 = prj.forward(mapnik.Coord(self.lon,self.lat)) c0.x += self.map_size_x * self.tilesize c0.y += self.map_size_y * self.tilesize c1 = prj.inverse(c0) lon=c1.x lat=c1.y print "before = (%f,%f)" % (self.lon,self.lat) print c1 print "after = (%f,%f)" % (lon,lat) if is_true(self.preferences_list['xapi']): # XAPI Server print 'Using OSM XAPI Server for data download' url="http://www.openstreetmap.org/api/0.6/map?bbox=%f,%f,%f,%f" %\ (self.lon,self.lat,lon,lat) # url="http://www.informationfreeway.org/api/0.6/map?bbox=%f,%f,%f,%f" %\ # (self.lon,self.lat,lon,lat) else: # Live OSM Server print 'Using live OSM Server for data download' url="http://www.openstreetmap.org/api/0.6/map?bbox=%f,%f,%f,%f" %\ (self.lon,self.lat,lon,lat) osmFile = "%s/townguide.osm" % (self.preferences_list['outdir']) os.system("wget %s -O %s" % (url,osmFile)) if os.path.exists(osmFile): try: print 'Importing data into postgresql database....' osm2pgsqlStr = "osm2pgsql -m -S %s/%s -d %s -a %s" %\ (self.preferences_list['datadir'], "default.style", self.preferences_list['dbname'], osmFile) print "Calling osm2pgsql with: %s" % osm2pgsqlStr retval = os.system(osm2pgsqlStr) if (retval==0): print 'Data import complete.' else: print 'osm2pgsql returned %d - exiting' % retval # system.exit(-1) except: print "Exception Occurred running osm2pgsql" system.exit(-1) else: print "ERROR: Failed to download OSM data" print "Aborting...." system.exit(-1)
def getAmenities(self): """Extract the required map features from the database for each map square and store the data in the 'amenities' dictionary. An index of the street names is stored in self.streetIndex dictionary. FIXME: This is very inefficient - it queries the database for the bounding box and each required feature in turn. It sould be more efficient to get all of the data in the bounding box then query that, but I haven't done it. 01oct2009 GJ ORIGINAL VERSION 04oct2009 GJ Added use of expandWhereClause to allow grouping of different key values under the same heading in the features page. 11oct2009 GJ Added support for areas (polygons) as well as nodes. """ # Extract the data for each 1km square. if (self.debug): print "getAmenities()" c0 = self.c0 # lon, lat streetList = {} streetIndexSorted = {} print c0 # Get all the features and then create clusters === if is_true(self.preferences_list['clusters']): print "........... Trying out something .........." tilesize = self.preferences_list['tilesize'] map_width = self.map_size_x map_height = self.preferences_list['map_size_y'] min_lon = c0.x min_lat = c0.y max_lon = c0.x + (tilesize * map_width) max_lat = c0.y + (tilesize * map_height) # Experimental cluster markers # tolerance to become a cluster should change according to the zooming factor tolerance = 20 * self.map_size_x # k-means first iteration clusters = {} if HAS_MAPNIK2: bbox = mapnik.Box2d(min_lon, min_lat, max_lon, max_lat) else: bbox = mapnik.Envelope(min_lon, min_lat, max_lon, max_lat) for featureStr in self.features: title,wc = self.expandWhereClause(featureStr) print "::::", title, wc feature = title if self.debug: print "Extracting feature %s using %s." %\ (feature,featureStr) pois = self.getBBContents(bbox,wc) # poi[6]: lat # poi[7]: lon print "Current Contents for ", featureStr, pois for poi in pois: if not len(self.clusters) > 0: print "POI:", poi c = Cluster(feature) c.add_poi(poi) self.clusters.append(c) print "Created the First cluster: ", c.centroid else: # Look for the custer where the POI should be inserted # by noticing the difference with that cluster's centroid # If the distance to that cluster's centroid is less than # the tolerance it will be inserted there. # This should work like a non-optimal first iteration of k-means CLUSTER_FOUND = False for (scounter, cluster) in enumerate(self.clusters): distance = cluster.distance_from_poi(poi) print "This cluster", cluster.pois print distance if distance < tolerance: # Add POI to cluster print "--- POI should get in this cluster" cluster.add_poi(poi) CLUSTER_FOUND = True print "BREAK!!!" break if not CLUSTER_FOUND: print "_____ Could not find a suited cluster _____" # Create a new cluster print "------ Creating a new cluster for this poi" new_cluster = Cluster(feature) new_cluster.add_poi(poi) self.clusters.append(new_cluster) for kluster in self.clusters: print len(kluster.pois), vars(kluster) print "............................................." #=========================================================== for tx in range(0,self.map_size_x): minx = c0.x + self.preferences_list['tilesize'] * tx for ty in range(0,self.preferences_list['map_size_y']): # sys.stdout.write("%s" % self.cellLabel(tx,ty)) # sys.stdout.flush() print "%s " % self.cellLabel(tx,ty) miny = c0.y + self.preferences_list['tilesize'] * ty if HAS_MAPNIK2: bbox = mapnik.Box2d(minx, miny, minx + self.preferences_list['tilesize'], miny + self.preferences_list['tilesize']) else: bbox = mapnik.Envelope(minx, miny, minx + self.preferences_list['tilesize'], miny + self.preferences_list['tilesize']) fname = "image_%02d_%02d.png" % (tx,ty) #if self.debug: print bbox ######################################################## # Extract points of interest into amenities dictionary # ######################################################## for featureStr in self.features: title,wc = self.expandWhereClause(featureStr) # print "::::", title, wc feature = title if self.debug: print "Extracting feature %s using %s." %\ (feature,featureStr) # FIXME: This needs to be optimized for clustering pois = self.getBBContents(bbox,wc) for poi in pois: if feature in self.amenities: self.amenities[feature].append((tx,ty,poi)) else: self.amenities[feature]=[(tx,ty,poi)] # print self.amenities # print len(self.amenities) # print "__________________________________" ############################################## # Extract all of the streetnames in the cell # ############################################## bbStreets = self.getBBStreets(bbox) streetList[self.cellLabel(tx,ty)] = bbStreets # Render a high resolution tile of this cell. #fname = "%s/%s.png" % (self.outdir,self.cellLabel(tx,ty)) #self.drawTile(bbox,1000,1000,fname) ##################################################### # Sort the amenities list to remove duplicates # # The result is self.amenitiesSorted which is a # # dictionary of features. Each feature contains # # a dictionary of amenity names. Each amenity # # name entry contains a list of cell IDs as strings # # # ##################################################### for feature in self.amenities.keys(): # poi = (tx,ty,(id, name, operator)) # example: # (0, 0, (663528594, 'Tangerine', None, 'restaurant', None, None, 4546182.5512522003, -13628929.6157306)) for poi in self.amenities[feature]: cellId = self.cellLabel(poi[0],poi[1]) osm_id = poi[2][0] # 663528594 name = poi[2][1] # 'Tangerine' operator = poi[2][2] # Company that runs the place amenityVal = poi[2][3] # Type of amenity shopVal = poi[2][4] landuse = poi[2][5] if name == None: if amenityVal == None: if shopVal == None: if landuse == None: name = "Unidentified thing - osm_id=%d" % osm_id else: name = "Unnamed %s" % landuse else: name = "Unnamed %s" % shopVal else: name = "Unnamed %s" % amenityVal print "%s, %s, %s" % (feature, name, cellId) # Entertainment, Castro Theater, A1 if not feature in self.amenitiesSorted: print "creating dictionary for feature %s" % feature self.amenitiesSorted[feature]={} if name in self.amenitiesSorted[feature]: print "dictionary %s already exists in feature %s" % (name,feature) if not cellId in self.amenitiesSorted[feature][name]: print "appending cellid" self.amenitiesSorted[feature][name].append(cellId) else: print "skipping duplicate feature %s %s in %s\n" % (feature,name,cellId) else: print "adding cell id to list" self.amenitiesSorted[feature][name] = [cellId] print "self.amenitiesSorted=", self.amenitiesSorted[feature][name] ######################################################### # Sort the street index into a simple dictionary of # # street name mapped to a list of which cells contain # # parts of the street of that name # ######################################################### # In the following, streetList is a dictionary with keys which # are cell IDs - the contents of the dictionary is a list of all # of the streets in a given cell. # StreeetIndexSorted is a dictionary with streetnames as the keys # The contents is a list of all of the cells that contain a way # of the given name. # self.StreetIndex is a tidied up version of StreetIndexSorted - the # contents is a displayable string showing which cells contain the # given street name. # Now we need to sort the street index so that we have a schedule # of streets identifying which cells the street is in. for cell in streetList: for street in streetList[cell]: streetName = street[1] if streetName != 'None': if streetName in streetIndexSorted: # Avoid multiple entries of the same cell for a # given street name - if it exists in the list, # reject it, otherwise add it to the list.. try: i = streetIndexSorted[streetName].index(cell) if self.debug: print "Rejected Duplicate Entry ",\ streetName,cell,i except: streetIndexSorted[streetName].append(cell) else: streetIndexSorted[streetName] = [cell] streets = streetIndexSorted.keys() streets.sort() for street in streets: cellstr="" first = True cells = streetIndexSorted[street] cells.sort() for cell in cells: if first==True: cellstr = "%s" % cell first=False else: cellstr = "%s, %s" % (cellstr,cell) self.streetIndex[street]=cellstr
def drawOverviewMap(self,outdir='',addFeatures=False): """Draws the overview map of the full area requested and adds a grid with row and column identifiers to the map image. 29sep2009 GJ ORIGINAL VERSION 01jan2010 Added option to add feature markers to map. 17oct2010 GJ Separated grid and features out into separate overlay plugins. """ # First draw the basic map using mapnik. fname = "%s/overview.png" % outdir if self.debug: print "Drawing Overview Map - fname=",fname c0 = self.c0 if HAS_MAPNIK2: bbox = mapnik.Box2d(c0.x, c0.y, c0.x + self.preferences_list['tilesize'] * \ self.preferences_list['map_size_x'], c0.y + self.preferences_list['tilesize'] * \ self.preferences_list['map_size_y']) else: bbox = mapnik.Envelope(c0.x, c0.y, c0.x + self.preferences_list['tilesize'] * \ self.preferences_list['map_size_x'], c0.y + self.preferences_list['tilesize'] * \ self.preferences_list['map_size_y']) # print "tilesize=%d, map_size_x=%d, oscale=%f" % (self.preferences_list['tilesize'],self.preferences_list['map_size_x'],self.preferences_list['oscale']) imgXpix = int(self.preferences_list['tilesize'] * self.preferences_list['map_size_x'] / self.preferences_list['oscale']) imgYpix = int(self.preferences_list['tilesize'] * self.preferences_list['map_size_y'] / self.preferences_list['oscale']) # print "Rendering Map to image of size (%d,%d) pixels" % (imgXpix,imgYpix) self.drawTile_bbox(bbox, imgXpix, imgYpix, fname) # FINISHED RENDERING THE IMAGE === ############################################################### # Draw the grid on the map go = gridOverlay(self) go.render(fname) ############################################################## # Draw gpx Trace and waypoints on the map if requested overlay = gpxOverlay(self) overlay.render(fname) ############################################################### # Draw the point of interest markers on the map # (as long as the map is not too big). if self.preferences_list['map_size_x'] <= \ int(self.preferences_list['maxmapsize']) and \ self.preferences_list['map_size_y'] <= \ int(self.preferences_list['maxmapsize']): addFeatures = True else: print "Map is too big to look for features: width: %s, height: %s" % ( self.preferences_list['map_size_x'], self.preferences_list['map_size_y']) print "...but map size is %f x %f" % \ (self.preferences_list['map_size_x'], self.preferences_list['map_size_y']) addFeatures = False if addFeatures and not is_true(self.preferences_list['clusters']): print "Adding feature markers to map..." po = poiOverlay(self) po.render(fname) ############################################################### # Add clustered markers if requested. if is_true(self.preferences_list['clusters']): print "Adding Clusters to map ...." co = clusterOverlay(self) co.render(fname) # creating a thumbnail with the same image ############################################################## # Create a thumbnail image of the map. if is_true(self.preferences_list['withThumbnail']): thumbnail_name = "%s/thumbnail.png" % outdir thumb_im = Image.open(fname) # thumb_f = open(fname, 'w') size = 256, 256 thumb_im.thumbnail(size, Image.ANTIALIAS) thumb_im.save(thumbnail_name, "PNG")
def __init__(self, preferences): """Initialise the townguide generating class from the set of preferences specified in the dictionary 'preferences_list'. The required data is then extracted from the database, and the selected output renderer called. """ defaults_options = defaults.DEFAULT_PREFERENCES self.srs = "+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +no_defs +over" self.preferences = preferences self.preferences_list = preferences.getPrefs() print 'PREFERENCES_LIST!!!' print self.preferences_list self.preferences.applyDefaults(defaults_options) self.preferences_list = preferences.getPrefs() # print "datadir=%s" % self.preferences_list['datadir'] if is_true(self.preferences_list['debug']): self.debug = True else: self.debug = False # FIXME: import the fonts that are distributed with townguide. # if the font exists inside the data dir # fntPath = "%s/FreeSerif.ttf" % self.preferences_list['datadir'] if os.path.isfile(self.preferences_list['datadir']): print 'Custom font exists! Using that instead' else: # Use the FreeSerif font that is bundled with townguide print "Could not find custom font!!!" print "Using the bundled font from Townguide" pk_path, filename = os.path.split(os.path.abspath(__file__)) self.fntPath = os.path.join(pk_path, 'fonts', 'DroidSans.ttf') print "font located at: ", self.fntPath print "fntPath = %s." % self.fntPath # Getting lat and long (lat,lon) = self.preferences_list['origin'].split(',') lat = float(lat) lon = float(lon) (map_size_x,map_size_y) = self.preferences_list['mapsize'].split(',') map_size_x = int(map_size_x) map_size_y = int(map_size_y) self.preferences_list['map_size_x'] = map_size_x self.preferences_list['map_size_y'] = map_size_y self.preferences_list['tilesize'] = float(self.preferences_list['tilesize']) oscale = float(self.preferences_list['oscale']) self.preferences_list['oscale'] = float(self.preferences_list['oscale']) # self.features is the list of map features to be presented. self.features = [] featstrs = self.preferences_list['features'].split(',') for feat in featstrs: self.features.append(str(feat.strip())) # if self.debug: print self.features # if self.debug: print "lat=%f, lon=%f, map_size_x=%d, map_size_y=%d" % (lat,lon,map_size_x,map_size_y) #Convert the lat/long origin into mercator projection metres. prj = mapnik.Projection(self.srs) self.c0 = prj.forward(mapnik.Coord(lon,lat)) print "Origin (%f,%f) is equivalent to (%f,%f) in projection" %\ (lon,lat,self.c0.x,self.c0.y) self.lat = lat self.lon = lon self.map_size_x = map_size_x self.map_size_y = map_size_y self.tilesize = float(self.preferences_list['tilesize']) self.oscale = oscale self.uname = self.preferences_list['uname'] self.dbname = self.preferences_list['dbname'] self.title = self.preferences_list['title'] self.outdir = self.preferences_list['outdir'] if not os.path.exists(self.outdir): os.makedirs(self.outdir) # ====== DOWNLOAD WITH THE XAPI ============== downloadStr = self.preferences_list['download'] downloadStr = downloadStr.lower() if is_true(downloadStr): self.populateDB() # ============================================ print "Extracting Map Features from Database" self.streetIndex = {} self.amenities = {} # Experimental Cluster Markers self.clusters = [] self.amenitiesSorted = {} maxsize = int(self.preferences_list['maxmapsize']) if self.preferences_list['map_size_x'] <= int(self.preferences_list['maxmapsize']) and \ self.preferences_list['map_size_y'] <= int(self.preferences_list['maxmapsize']): #FIXME: This is wrong - we need to get the data even if we do not # want a street index. #if self.preferences_list['streetIndex'].lower() == 'true': self.getAmenities() else: print "Map is too big ===================================" print "Must be less than %d km across" % int(self.preferences_list['maxmapsize']) print "...but map size is %f x %f" % \ (self.preferences_list['map_size_x'], self.preferences_list['map_size_y']) # Supported plugins # Plugin support: change 2 {'book': self.renderBook, 'html': self.renderHTML, 'poster': self.renderPoster, 'newposter': self.renderNewPoster, 'simplelandscape': self.renderSimpleLandscape, 'simpleposter': self.renderSimplePoster, }[self.preferences_list['format']]()
def main(event, context): Stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.debug(f'main entry Stage:{Stage} ') logging.debug(f'event: {event}') logging.debug(f'context: {context}') logging.debug(f'body: {body}') receipt = body.get('receipt', '') dynamodb = boto3.resource('dynamodb') result_hash_table = dynamodb.Table(os.environ['RESULT_TABLE_NAME']) receipt_hash_table = dynamodb.Table(os.environ['RECEIPT_TABLE_NAME']) if os.environ['STAGE'] != 'dev': if body.get('verify_receipt') or body.get( 'product_id'): # todo: Use a whitelist rather than a blacklist response = { 'isBase64Encoded': False, 'statusCode': 400, 'headers': {}, 'body': json.dumps({ 'message': 'dev-only parameter included in request!', 'push_txn_hash': None, 'config': None, 'seller': None, }) } logging.debug( f'dev-only parameter included in request! response: {response}' ) return response receipt_hash = hashlib.sha256(receipt.encode('utf-8')).hexdigest() result = result_hash_table.query( ConsistentRead=True, KeyConditionExpression=Key('receipt').eq(receipt_hash)) if (Stage != 'dev' and result['Count'] > 0): # we found a match, return it item = result['Items'][0] config = item['config'] push_txn_hash = item['push_txn_hash'] response = { "isBase64Encoded": False, "statusCode": 200, "headers": {}, "body": json.dumps({ "push_txn_hash": push_txn_hash, "config": config, "seller": os.environ['VERIFIER'], }) } logging.debug( f'found existing match for receipt_hash({receipt_hash}), result: {response}' ) return response verify_receipt = body.get('verify_receipt', 'False') if (is_true(verify_receipt)): result = receipt_hash_table.query( ConsistentRead=True, KeyConditionExpression=Key('receipt').eq(receipt_hash)) if (result['Count'] > 0): # we found a match - reject on duplicate response = { "isBase64Encoded": False, "statusCode": 402, "headers": {}, "body": json.dumps({ "message": "Validation Failure: duplicate receipt!", "push_txn_hash": None, "config": None, "seller": None, }) } logging.debug(f'response: {response}') return response apple_response = process_app_pay_receipt(receipt) if (apple_response[0] or verify_receipt == 'False'): validation_result: dict = apple_response[1] if validation_result is None: bundle_id = '' else: bundle_id = validation_result.get('receipt', {}).get('bundle_id', '') if bundle_id != 'OrchidTechnologies.PAC-Test' and is_true( verify_receipt): # Bad bundle_id and set to verify_receipts logging.debug( f'Incorrect bundle_id: {bundle_id} (Does not match OrchidTechnologies.PAC-Test)' ) response = { "isBase64Encoded": False, "statusCode": 400, "headers": {}, "body": json.dumps({ 'message': f'Incorrect bundle_id: {bundle_id} (Does not match OrchidTechnologies.PAC-Test)', 'push_txn_hash': None, 'config': None, 'seller': None, }) } else: # Good bundle_id or not verifying receipts product_id = body.get( 'product_id', validation_result['receipt']['in_app'][0]['product_id']) quantity = int( validation_result['receipt']['in_app'][0]['quantity']) if os.environ['STAGE'] == 'dev': total_usd = wildcard_product_to_usd( product_id=product_id) * quantity else: total_usd = product_to_usd(product_id=product_id) * quantity logging.debug(f'product_id: {product_id}') logging.debug(f'quantity: {quantity}') logging.debug(f'total_usd: {total_usd}') if total_usd < 0: logging.debug('Unknown product_id') response = { "isBase64Encoded": False, "statusCode": 400, "headers": {}, "body": json.dumps({ 'message': f"Unknown product_id: {product_id}", 'push_txn_hash': None, 'config': None, 'seller': None, }) } else: push_txn_hash, config, signer_pubkey = get_account( price=total_usd) if config is None: response = { "isBase64Encoded": False, "statusCode": 404, "headers": {}, "body": json.dumps({ "message": "No Account Found", "push_txn_hash": None, "config": None, "seller": None, }) } else: response = { "isBase64Encoded": False, "statusCode": 200, "headers": {}, "body": json.dumps({ "push_txn_hash": push_txn_hash, "config": config, "seller": os.environ['VERIFIER'], }) } item = { 'receipt': receipt_hash, } ddb_item = json.loads( json.dumps(item), parse_float=Decimal ) # Work around DynamoDB lack of float support receipt_hash_table.put_item(Item=ddb_item) item = { 'receipt': receipt_hash, 'config': config, 'push_txn_hash': push_txn_hash, 'seller': os.environ['VERIFIER'], } ddb_item = json.loads( json.dumps(item), parse_float=Decimal ) # Work around DynamoDB lack of float support result_hash_table.put_item(Item=ddb_item) if is_true(os.environ.get('ENABLE_MONITORING', '')): # Jay may not like this token_name = get_token_name( address=os.environ['TOKEN']) token_symbol = get_token_symbol( address=os.environ['TOKEN']) token_decimals = get_token_decimals( address=os.environ['TOKEN']) pac_tokens = look(funder=get_secret( key=os.environ['PAC_FUNDER_PUBKEY_SECRET']), signer=signer_pubkey) # lambda_metric( # f"orchid.pac.sale.{token_symbol.lower()}", # pac_tokens, # tags=[ # f'token_name:{token_name}', # f'token_symbol:{token_symbol}', # f'token_decimals:{token_decimals}', # f'usd:{total_usd}', # ] # ) else: response = { "isBase64Encoded": False, "statusCode": 402, "headers": {}, "body": json.dumps({ "message": f"Validation Failure: {apple_response[1]}", "push_txn_hash": None, "config": None, "seller": None, }) } logging.debug(f'response: {response}') return response
def main(event, context): Stage = os.environ['STAGE'] body = json.loads(event.get('body', {})) if is_true(body.get('debug', '')): configure_logging(level="DEBUG") logging.debug(f'main entry Stage:{Stage} ') logging.debug(f'event: {event}') logging.debug(f'context: {context}') logging.debug(f'body: {body}') receipt = body.get('receipt', '') dynamodb = boto3.resource('dynamodb') result_hash_table = dynamodb.Table(os.environ['RESULT_TABLE_NAME']) receipt_hash_table = dynamodb.Table(os.environ['RECEIPT_TABLE_NAME']) #check for dev params, respond with error in prod if os.environ['STAGE'] != 'dev': if body.get('verify_receipt') or body.get('product_id'): return response_error_invalid_dev_param() #extract and hash the receipt body payload receipt_hash = hash_receipt_body(receipt) #find any matching previous pot result and conditionally return it (idempotency) response = find_previous_pot(result_hash_table, receipt_hash, os.environ['VERIFIER'], Stage) if (response != None): return response #find and error return for any previous claim of the receipt (replay prevention) todo: this is not concurrent-safe, claim needs to be atomic verify_receipt = body.get('verify_receipt', 'True') if (is_true(verify_receipt)): response = find_previous_receipt_claim(receipt_hash_table, receipt_hash) if (response != None): return response apple_response = process_app_pay_receipt(receipt) if (apple_response[0] or verify_receipt == 'False'): validation_result: dict = apple_response[1] if validation_result is None: bundle_id = '' else: bundle_id = validation_result.get('receipt', {}).get('bundle_id', '') if bundle_id != os.environ['BUNDLE_ID'] and is_true( verify_receipt): # Bad bundle_id and set to verify_receipts response = response_invalid_bundle(bundle_id) else: # Good bundle_id or not verifying receipts product_id = body.get( 'product_id', validation_result['receipt']['in_app'][0]['product_id']) quantity = int( validation_result['receipt']['in_app'][0]['quantity']) if os.environ['STAGE'] == 'dev': total_usd = wildcard_product_to_usd( product_id=product_id) * quantity else: total_usd = product_to_usd(product_id=product_id) * quantity logging.debug(f'product_id: {product_id}') logging.debug(f'quantity: {quantity}') logging.debug(f'total_usd: {total_usd}') if total_usd <= 0: response = response_invalid_product(product_id) else: #find/claim a valid pot push_txn_hash, config, signer_pubkey = get_account( price=total_usd) if config is None: response = response_no_account() else: response = response_valid_account(push_txn_hash, config, os.environ['VERIFIER']) #claim the receipt (conditionally atomically, exception fails if already exists) if (Stage != 'dev'): claim_receipt(receipt_hash_table, receipt_hash) #store result (idempotency) store_result(result_hash_table, receipt_hash, config, push_txn_hash, os.environ['VERIFIER']) if is_true(os.environ.get('ENABLE_MONITORING', '')): # Jay may not like this do_evil_monitoring() else: response = response_invalid_receipt(apple_response) logging.debug(f'response: {response}') return response
def get_account_( price: float, blocknum: int) -> Tuple[Optional[str], Optional[str], Optional[str]]: logging.debug(f'get_account_ price:{price}') dynamodb = boto3.resource('dynamodb') table = dynamodb.Table(os.environ['TABLE_NAME']) response = random_scan(table, price) ret = None signer_pubkey = '0xTODO' epoch_time = int(time.time()) for item in response['Items']: if float(price) == float(item['price']): signer_pubkey = item['signer'] config = item['config'] push_txn_hash = item['push_txn_hash'] creation_etime = item.get('creation_etime', 0) age = epoch_time - creation_etime if is_true(os.environ['DOUBLE_CHECK_ACCOUNTS']): old_status = item['status'] status = get_transaction_status(push_txn_hash, blocknum) if old_status != status: logging.warning( f'DynamoDB status of {old_status} for {push_txn_hash} ' f'does not match new status of {status}!') else: status = item['status'] if ((status != 'confirmed') and (age < 10 * 60 * 60)): # 10 hour grace period logging.debug( f'Skipping account ({push_txn_hash}) with status: {status} age: {age}' ) continue logging.debug( f'Found potential account ({push_txn_hash}) status: {status} age:{age} config: {config}' ) key = { 'price': item['price'], 'signer': signer_pubkey, } delete_response = table.delete_item(Key=key, ReturnValues='ALL_OLD') if (delete_response['Attributes'] is not None and len(delete_response['Attributes']) > 0): balance, escrow, _ = look( funder=get_secret( key=os.environ['PAC_FUNDER_PUBKEY_SECRET']), signer=signer_pubkey, ) # update succeeded if ((status == 'confirmed') and (escrow > get_min_escrow())): ret = push_txn_hash, config, signer_pubkey break else: logging.debug( f'broken account: {push_txn_hash} status: {status} age: {age} ' f'balance: {balance} deleted and skipped') else: logging.debug('Account was already deleted!') if ret: return ret return None, None, None