def _reverse_geocode(self, point): """Performs reverse geocoding""" providers, provider_name, ok = self._get_provider_input() if ok: provider = [ provider for provider in providers if provider['name'] == provider_name ][0] clnt = client.Client(provider) responsehandler = response_handler.ResponseHandler( QgsField('id', QVariant.String)) try: response = clnt.request(provider['endpoints']['reverse'], { 'point.lat': point.y(), 'point.lon': point.x(), 'size': 5 }) layer_out = responsehandler.get_layer('reverse', response) layer_out.updateExtents() self.project.addMapLayer(layer_out) except: raise finally: QApplication.restoreOverrideCursor() self.point_tool.canvasClicked.disconnect() self.iface.mapCanvas().setMapTool(self.last_maptool)
def _forward_geocode(self): """Performs quick forward geocoding""" address, ok = QInputDialog.getText(self.iface.mainWindow(), "Pelias Forward Geocoding", "Enter an address") if not ok: return providers, provider_name, ok = self._get_provider_input() if ok: provider = [ provider for provider in providers if provider['name'] == provider_name ][0] clnt = client.Client(provider) responsehandler = response_handler.ResponseHandler( QgsField('id', QVariant.String)) response = clnt.request(provider['endpoints']['search'], { 'text': address, 'size': 5 }) layer_out = responsehandler.get_layer('search', response) layer_out.updateExtents() self.project.addMapLayer(layer_out)
def _run_main_dialog(self): """Runs the main function when Apply is clicked.""" self.dlg.debug_text.clear() provider = self.dlg.provider_combo.currentData() clnt = client.Client( provider=provider) # provider object has all data from config.yml clnt_msg = '' # Notify user when query limit is reached sleep_notifier = "OverQueryLimit: Wait for {} seconds" clnt.overQueryLimit.connect( lambda sleep_for: self.dlg.debug_text.setText( sleep_notifier.format(str(sleep_for)))) # Collect base parameters common for both endpoints params = self._collect_base_params() if self.dlg.search_tab.currentIndex() == 0: method = 'search' params['text'] = self.dlg.search_free_text.value() elif self.dlg.search_tab.currentIndex() == 1: method = 'structured' layers_list = self.dlg.layer_list for idx in range(layers_list.count()): item = layers_list.item(idx).text() param, value = item.split("=") params[param] = value elif self.dlg.search_tab.currentIndex() == 2: method = 'reverse' params['point.lon'] = self.dlg.reverse_x.value() params['point.lat'] = self.dlg.reverse_y.value() responsehandler = response_handler.ResponseHandler( QgsField('id', QVariant.String), self.dlg.debug_check.isChecked()) try: response = clnt.request(provider['endpoints'][method], params) layer_out = responsehandler.get_layer(method, response) layer_out.updateExtents() self.project.addMapLayer(layer_out) except exceptions.Timeout: msg = "The connection has timed out!" logger.log(msg, 2) self.dlg.debug_text.setText(msg) except (exceptions.ApiError, exceptions.InvalidKey, exceptions.GenericServerError) as e: msg = [e.__class__.__name__, str(e)] logger.log("{}: {}".format(*msg), 2) clnt_msg += "<b>{}</b>: ({})<br>".format(*msg) except Exception as e: msg = [e.__class__.__name__, str(e)] logger.log("{}: {}".format(*msg), 2) clnt_msg += "<b>{}</b>: {}<br>".format(*msg) raise finally: # Write some output if clnt.warnings is not None: for warning in clnt.warnings: clnt_msg += "<b>Warning</b>: {}<br>".format(warning) logger.log(warning, 1) clnt_msg += '<a href="{0}">{0}</a><br>'.format(clnt.url) self.dlg.debug_text.setHtml(clnt_msg)
def processAlgorithm(self, parameters, context, feedback): providers = configmanager.read_config()['providers'] # Init client provider = providers[self.parameterAsEnum(parameters, self.IN_PROVIDER, context)] in_source = self.parameterAsSource(parameters, self.IN_POINTS, context) in_id_field_name = self.parameterAsString(parameters, self.IN_ID_FIELD, context) in_country = self.parameterAsString(parameters, self.IN_COUNTRY, context) in_layers = self.parameterAsEnums(parameters, self.IN_LAYERS, context) in_sources = self.parameterAsEnums(parameters, self.IN_SOURCES, context) in_size = self.parameterAsInt(parameters, self.IN_SIZE, context) # Get user specified ID field as object in_id_field = in_source.fields().field(in_id_field_name) clnt = client.Client(provider) clnt.overQueryLimit.connect(lambda sleep_for: feedback.reportError( "OverQueryLimit: Wait for {} seconds".format(sleep_for))) params = dict() if in_country: params['boundary.country'] = in_country if in_layers: params['layers'] = convert.comma_list( [LAYERS[idx] for idx in in_layers]) if in_sources: params['sources'] = convert.comma_list( [SOURCES[idx] for idx in in_sources]) params['size'] = str(in_size) responsehandler = response_handler.ResponseHandler(in_id_field) (sink, dest_id) = self.parameterAsSink(parameters, self.OUT, context, responsehandler.get_fields(), QgsWkbTypes.Point, self.crs_out) xformer = transform.transformToWGS(in_source.sourceCrs()) for num, feat_in in enumerate(in_source.getFeatures()): if feedback.isCanceled(): break x_point = xformer.transform(feat_in.geometry().asPoint()) params['point.lon'] = x_point.x() params['point.lat'] = x_point.y() in_id_field_value = feat_in[in_id_field_name] try: response = clnt.request( provider['endpoints'][self.ALGO_NAME_LIST[1]], params) except (exceptions.ApiError, exceptions.GenericServerError, exceptions.InvalidKey) as e: msg = "Feature ID {} caused a {}:\n{}".format( in_id_field_value, e.__class__.__name__, str(e)) feedback.reportError(msg) logger.log(msg, 2) continue features_out = responsehandler.generate_out_features( response, in_id_field_value) for feat_out in features_out: sink.addFeature(feat_out) feedback.setProgress(int(100.0 / in_source.featureCount() * num)) return {self.OUT: dest_id}
def processAlgorithm(self, parameters, context, feedback): providers = configmanager.read_config()['providers'] # Init client provider = providers[self.parameterAsEnum(parameters, self.IN_PROVIDER, context)] in_source = self.parameterAsSource(parameters, self.IN_POINTS, context) in_id_field_name = self.parameterAsString(parameters, self.IN_ID_FIELD, context) in_text_field_name = self.parameterAsString(parameters, self.IN_TEXT_FIELD, context) in_focus = self.parameterAsPoint(parameters, self.IN_FOCUS, context, self.crs_out) in_rectangle = self.parameterAsExtent(parameters, self.IN_RECTANGLE, context, self.crs_out) in_circle = self.parameterAsPoint(parameters, self.IN_CIRCLE, context, self.crs_out) in_circle_radius = self.parameterAsInt(parameters, self.IN_CIRCLE_RADIUS, context) in_country = self.parameterAsString(parameters, self.IN_COUNTRY, context) in_layers = self.parameterAsEnums(parameters, self.IN_LAYERS, context) in_sources = self.parameterAsEnums(parameters, self.IN_SOURCES, context) in_size = self.parameterAsInt(parameters, self.IN_SIZE, context) # Get user specified ID field as object in_id_field = in_source.fields().field(in_id_field_name) clnt = client.Client(provider) clnt.overQueryLimit.connect(lambda sleep_for: feedback.reportError( "OverQueryLimit: Wait for {} seconds".format(sleep_for))) params = dict() if in_focus.x() and in_focus.y(): params['focus.lon'], params['focus.lat'] = [ convert.format_float(coord) for coord in in_focus ] if not in_rectangle.isNull(): (params['boundary.rect.min_lon'], params['boundary.rect.min_lat'], params['boundary.rect.max_lon'], params['boundary.rect.max_lat']) = [ convert.format_float(coord) for coord in in_rectangle.toRectF().getCoords() ] if in_circle.x() and in_circle.y(): (params['boundary.circle.lon'], params['boundary.circle.lat']) = [ convert.format_float(coord) for coord in in_circle ] params['boundary.circle.radius'] = str(in_circle_radius) if in_country: params['boundary.country'] = in_country if in_layers: params['layers'] = convert.comma_list( [LAYERS[idx] for idx in in_layers]) if in_sources: params['sources'] = convert.comma_list( [SOURCES[idx] for idx in in_sources]) params['size'] = str(in_size) responsehandler = response_handler.ResponseHandler(in_id_field) (sink, dest_id) = self.parameterAsSink(parameters, self.OUT, context, responsehandler.get_fields(), QgsWkbTypes.Point, self.crs_out) for num, feat_in in enumerate(in_source.getFeatures()): if feedback.isCanceled(): break params_feat = dict() if in_text_field_name and feat_in[in_text_field_name]: params_feat['text'] = feat_in[in_text_field_name] in_id_field_value = feat_in[in_id_field_name] try: response = clnt.request( provider['endpoints'][self.ALGO_NAME_LIST[1]], { **params, **params_feat }) except (exceptions.ApiError, exceptions.GenericServerError, exceptions.InvalidKey) as e: msg = "Feature ID {} caused a {}:\n{}".format( in_id_field_value, e.__class__.__name__, str(e)) feedback.reportError(msg) logger.log(msg, 2) continue features_out = responsehandler.generate_out_features( response, in_id_field_value) for feat_out in features_out: sink.addFeature(feat_out) feedback.setProgress(int(100.0 / in_source.featureCount() * num)) return {self.OUT: dest_id}