def file_upload(filename, user=None, title=None, skip=True, overwrite=False, keywords=()): """Saves a layer in GeoNode asking as little information as possible. Only filename is required, user and title are optional. """ # Do not do attemt to do anything unless geonode is running check_geonode_is_up() # Get a valid user theuser = get_valid_user(user) # Set a default title that looks nice ... if title is None: basename = os.path.splitext(os.path.basename(filename))[0] title = basename.title().replace('_', ' ') # ... and use a url friendly version of that title for the name name = slugify(title).replace('-', '_') # Note that this will replace any existing layer that has the same name # with the data that is being passed. try: layer = Layer.objects.get(name=name) except Layer.DoesNotExist: layer = name new_layer = save(layer, filename, theuser, overwrite, keywords=keywords, title=title) return new_layer
def form_save(req): """ Main view to save a odk submission """ # Only accept requests from localhost if not settings.FORMHUB_TRUSTED_IP == req.META['REMOTE_ADDR']: return HttpResponse(status=403) check_geonode_is_up() if not check_feature_store(): raise ValueError('No postgis database found.') layername = req.POST.get('_xform_id_string', None) if not layername: # Normal post from odk body = json.loads(req.body) layername = body['_xform_id_string'] else: # Test environment body = req.POST.dict() body['_geolocation'] = json.loads(body['_geolocation']) try: layer = Layer.objects.get(name=layername) except Layer.DoesNotExist: raise Layer.DoesNotExist if not check_user(body['_userform_id'].split('_')[0], layer): raise ValueError('User not found in the database') # Don't trust the id from ODK, look into the db sequence to get the right one valid_id = get_valid_id(layername) # Guess the list of fields from the layer's attributes attributes = layer.attribute_set.all() # Compile the context context, image = compile_context(valid_id, body, attributes) template = render_to_string('formhub/transaction_insert.xml',context) # Instanciate the client and post the insert request geoserver = Gs_client() try: response = geoserver.client.request(geoserver.wfs_url, method='POST', body=template) #Update the layer bounds and the thumbnail geoserver.updatebounds(layername) layer.update_thumbnail() context_to_feature(layer, context, image) return HttpResponse('Inserted') except: raise
def upload(incoming, user=None, overwrite=False, keywords=(), skip=True, ignore_errors=True, verbosity=1, console=None): """Upload a directory of spatial data files to GeoNode This function also verifies that each layer is in GeoServer. Supported extensions are: .shp, .tif, and .zip (of a shapfile). It catches GeoNodeExceptions and gives a report per file """ if verbosity > 1: print >> console, "Verifying that GeoNode is running ..." check_geonode_is_up() if console is None: console = open(os.devnull, 'w') potential_files = [] if os.path.isfile(incoming): ___, short_filename = os.path.split(incoming) basename, extension = os.path.splitext(short_filename) filename = incoming if extension in ['.tif', '.shp', '.zip']: potential_files.append((basename, filename)) elif not os.path.isdir(incoming): msg = ('Please pass a filename or a directory name as the "incoming" ' 'parameter, instead of %s: %s' % (incoming, type(incoming))) logger.exception(msg) raise GeoNodeException(msg) else: datadir = incoming for root, dirs, files in os.walk(datadir): for short_filename in files: basename, extension = os.path.splitext(short_filename) filename = os.path.join(root, short_filename) if extension in ['.tif', '.shp', '.zip']: potential_files.append((basename, filename)) # After gathering the list of potential files, # let's process them one by one. number = len(potential_files) if verbosity > 1: msg = "Found %d potential layers." % number print >> console, msg output = [] for i, file_pair in enumerate(potential_files): basename, filename = file_pair existing_layers = Layer.objects.filter(name=basename) if existing_layers.count() > 0: existed = True else: existed = False if existed and skip: save_it = False status = 'skipped' layer = existing_layers[0] if verbosity > 0: msg = ('Stopping process because ' '--overwrite was not set ' 'and a layer with this name already exists.') print >> sys.stderr, msg else: save_it = True if save_it: try: layer = file_upload(filename, user=user, overwrite=overwrite, keywords=keywords, ) if not existed: status = 'created' else: status = 'updated' except Exception, e: if ignore_errors: status = 'failed' exception_type, error, traceback = sys.exc_info() else: if verbosity > 0: msg = ('Stopping process because ' '--ignore-errors was not set ' 'and an error was found.') print >> sys.stderr, msg msg = 'Failed to process %s' % filename raise Exception(msg, e), None, sys.exc_info()[2] msg = "[%s] Layer for '%s' (%d/%d)" % (status, filename, i + 1, number) info = {'file': filename, 'status': status} if status == 'failed': info['traceback'] = traceback info['exception_type'] = exception_type info['error'] = error else: info['name'] = layer.name output.append(info) if verbosity > 0: print >> console, msg
def upload(incoming, user=None, overwrite=False, keywords=(), skip=True, ignore_errors=True, verbosity=1, console=None): """Upload a directory of spatial data files to GeoNode This function also verifies that each layer is in GeoServer. Supported extensions are: .shp, .tif, and .zip (of a shapfile). It catches GeoNodeExceptions and gives a report per file """ if verbosity > 1: print >> console, "Verifying that GeoNode is running ..." check_geonode_is_up() if console is None: console = open(os.devnull, 'w') potential_files = [] if os.path.isfile(incoming): ___, short_filename = os.path.split(incoming) basename, extension = os.path.splitext(short_filename) filename = incoming if extension in ['.tif', '.shp', '.zip']: potential_files.append((basename, filename)) elif not os.path.isdir(incoming): msg = ('Please pass a filename or a directory name as the "incoming" ' 'parameter, instead of %s: %s' % (incoming, type(incoming))) logger.exception(msg) raise GeoNodeException(msg) else: datadir = incoming for root, dirs, files in os.walk(datadir): for short_filename in files: basename, extension = os.path.splitext(short_filename) filename = os.path.join(root, short_filename) if extension in ['.tif', '.shp', '.zip']: potential_files.append((basename, filename)) # After gathering the list of potential files, # let's process them one by one. number = len(potential_files) if verbosity > 1: msg = "Found %d potential layers." % number print >> console, msg output = [] for i, file_pair in enumerate(potential_files): basename, filename = file_pair existing_layers = Layer.objects.filter(name=basename) if existing_layers.count() > 0: existed = True else: existed = False if existed and skip: save_it = False status = 'skipped' layer = existing_layers[0] if verbosity > 0: msg = ('Stopping process because ' '--overwrite was not set ' 'and a layer with this name already exists.') print >> sys.stderr, msg else: save_it = True if save_it: try: layer = file_upload( filename, user=user, overwrite=overwrite, keywords=keywords, ) if not existed: status = 'created' else: status = 'updated' except Exception, e: if ignore_errors: status = 'failed' exception_type, error, traceback = sys.exc_info() else: if verbosity > 0: msg = ('Stopping process because ' '--ignore-errors was not set ' 'and an error was found.') print >> sys.stderr, msg msg = 'Failed to process %s' % filename raise Exception(msg, e), None, sys.exc_info()[2] msg = "[%s] Layer for '%s' (%d/%d)" % (status, filename, i + 1, number) info = {'file': filename, 'status': status} if status == 'failed': info['traceback'] = traceback info['exception_type'] = exception_type info['error'] = error else: info['name'] = layer.name output.append(info) if verbosity > 0: print >> console, msg