Importieren der QGIS-Verarbeitung in ein eigenständiges Python-Skript?

10

Ich möchte einige eigenständige Skripte schreiben, die die Verarbeitungs-Toolbox von Qgis verwenden.

Ich habe einige Themen gelesen ( hier und hier , z. B.), konnte aber noch keine funktionierende Lösung finden.

Verwenden von Qgis 2.16.1 unter Ubuntu Xenial 16.04 LTS

Der Importabschnitt meines Skripts sieht folgendermaßen aus:

# Python modules
import sys
import time
import os

# Qgis modules
from qgis.core import *
import qgis.utils
from PyQt4.QtCore import QFileInfo, QSettings

Weiß jemand, was mir fehlt, um das Verarbeitungsmodul importieren zu können?

Mit einer einfachen Importverarbeitung erhalte ich Folgendes:

Original exception was:
Traceback (most recent call last):
 File "/home/steph/Documents/Projets/20141227-CIM_Bishkek/Scripts/python/00-projets/20160811-AnalysesUAVs/20160811-UAVAnalyse.py", line 36, in <module>
import processing
 File "/usr/lib/python2.7/dist-packages/qgis/utils.py", line 607, in _import
mod = _builtin_import(name, globals, locals, fromlist, level)
ImportError: No module named processing

EDIT (nach Josephs Kommentar)

Ich habe es so versucht:

# Python modules
import sys
import time
import os

# Qgis modules
from qgis.core import *
import qgis.utils
from PyQt4.QtGui import *
app = QApplication([])
QgsApplication.setPrefixPath("/usr", True)
QgsApplication.initQgis()
from PyQt4.QtCore import QFileInfo, QSettings
#from PyQt4.QtGui import *

# Prepare processing framework 
sys.path.append('/home/steph/.qgis2/python/plugins')
from processing.core.Processing import Processing
Processing.initialize()
from processing.tools import *

aber das Verhalten ist seltsam: Mein Skript läuft bis zum Ende ohne Fehler, scheint aber über die Aufgaben zu "springen", die es ausführen soll :-) Mit anderen Worten, es läuft bis zum Ende, aber ohne etwas zu tun.

Ich gebe zu, dass meine Erklärung nicht sehr klar ist ... Ich werde weiter nachforschen, aber wenn jemand eine magische Lösung (keine Problemumgehung) hat, um dieses Modul zu importieren, dann bitte!

EDIT 2: mein gesamtes Skript hinzufügen. Entschuldigung, wenn es etwas lang ist ....

# -*- coding: cp1252 -*-
########################################################
## Name: Performs various analyses on UAV imagery using Qgis
## Source Name: UAVanalyse.py
## Version: Python 2.7
## Author: Stephane Henriod
## Usage: Performs a set of analyses on UAV imagery
## Date 11.08.2016
## Modified: 
########################################################


# Import required modules

# Python modules
import sys
import time
import os

# Qgis modules
from qgis.core import *
import qgis.utils
from PyQt4.QtCore import QFileInfo, QSettings

# Custom modules
from config_work import *
import display_msg as disp
import clean_time as cl

def make_raster_layer(raster, log_file):
    """Creates a raster layer from the path to a raster, if the path exists and if the raster is valid

    Param_in:
        raster (string) -- The path to the raster to be transformed into a layer
        log_file (string) -- The path to the log file to write in

    Param_out:
        list: 
            [0] = full path to the raster 
            [1] = raster layer

    """

    if os.path.exists(raster):
        fileName = raster
        fileInfo = QFileInfo(fileName)
        baseName = fileInfo.baseName()
        rlayer = QgsRasterLayer(fileName, baseName)
        if rlayer.isValid():
            return [raster, rlayer]
    else:
        return False

def study_raster(rlayer, log_file):
    """Returns properties of a raster, if this one exists and is valid

    Param_in:
        rlayer (bin) -- A raster layer
        log_file (string) -- The path to the log file to write in

    """

    infos = {}

    if rlayer:
        infos['a - Width'] = rlayer.width()
        infos['b - Height'] = rlayer.height()
        infos['c - Extent'] = rlayer.extent().toString()
        infos['d - # bands'] = rlayer.bandCount()
        infos['e - X resolution'] = rlayer.rasterUnitsPerPixelX()
        infos['f - Y resolution'] = rlayer.rasterUnitsPerPixelY()
        return infos
    else:
        return False


def project_raster(raster, to_crs, log_file):
    """Projects a raster into another crs

    Param_in:
        raster (string) -- The path to the raster to be transformed into a layer
        to_crs (string) -- The coordinate reference system to which the layer must be projected
        log_file (string) -- The path to the log file to write in

    """

    img_out_name = os.path.splitext(os.path.basename(raster))[0] + '_proj' + os.path.splitext(os.path.basename(raster))[1]
    img_out = os.path.join(output_folder, img_out_name)
    #processing.runalg("gdalwarp -overwrite -s_srs EPSG:32642 -t_srs " + to_crs + " " + rlayer[0] + " " + img_out)

    msg = img_out    
    disp.display_msg(log_file, msg, 'a')

    return img_out_name

if __name__ == "__main__":
    t_start_script = time.localtime()
    t_start_script_clean = time.strftime("%Y%m%d-%H%M", t_start_script)

    # Checking the folders
    if not os.path.exists(input_folder_path):
        os.makedirs(input_folder_path)
    if not os.path.exists(temp_folder_path):
        os.makedirs(temp_folder_path)
    if not os.path.exists(output_folder_path):
        os.makedirs(output_folder_path)

    # Creating the output and temp folders
    output_folder = os.path.join(output_folder_path, t_start_script_clean + '-UAVanalyse')
    temp_folder = os.path.join(temp_folder_path, t_start_script_clean + '-UAVanalyse')

    if not os.path.exists(output_folder):
        os.makedirs(output_folder)
    if not os.path.exists(temp_folder):
        os.makedirs(temp_folder)

    # Creating the log file
    log_file_name = t_start_script_clean + '-UAVanalyse.log'
    log_file = os.path.join(output_folder, log_file_name)

    # Heading of the log file
    msg = "Performs a set of analyses on UAV imagery" + os.linesep
    msg += "Input folder: " + input_folder_path
    msg += "\n RGB image: " + img_rgb_name
    msg += "\n NIR image: " + img_nir_name
    msg += "\n RGBIR image: " + img_rgbir_name
    msg += "\n DSM file: " + img_dsm_name
    disp.display_msg(log_file, msg, 'w')

    #msg = "Script started on " + cl.clean_time(t_start_script)
    #disp.display_msg(log_file, msg, 'a')


    # Initialize Qgis (source: http://docs.qgis.org/testing/en/docs/pyqgis_developer_cookbook/intro.html)
    msg = 'Initialize Qgis'
    disp.display_msg(log_file, msg, 'a')
    # supply path to qgis install location
    QgsApplication.setPrefixPath("/usr", True)

    # create a reference to the QgsApplication, setting the
    # second argument to False disables the GUI
    qgs = QgsApplication([], False)

    # load providers
    qgs.initQgis()


    # Write your code here to load some layers, use processing algorithms, etc.

    # Make raster layers
    rlayer_rgb = make_raster_layer(img_rgb, log_file)
    rlayer_nir = make_raster_layer(img_nir, log_file)
    rlayer_rgbir = make_raster_layer(img_rgbir, log_file)
    rlayer_dsm = make_raster_layer(img_dsm, log_file)

    all_valid_layers = []
    if rlayer_rgb: all_valid_layers.append(rlayer_rgb)
    if rlayer_nir: all_valid_layers.append(rlayer_nir)
    if rlayer_rgbir: all_valid_layers.append(rlayer_rgbir)
    if rlayer_dsm: all_valid_layers.append(rlayer_dsm)




    # (I) Infos about the layers
    msg = os.linesep + frm_separator + os.linesep + '(I) Infos about the layers' + os.linesep + frm_separator + os.linesep
    disp.display_msg(log_file, msg, 'a')

    i = 1
    for layer in all_valid_layers:
        infos = study_raster(layer[1], log_file)
        msg = '\n (' + str(i) + ') ' + layer[0] + os.linesep
        for item in sorted(infos):
            msg += '\n ' + str(item) + ': ' + str(infos[item]) + os.linesep

        i+=1
        disp.display_msg(log_file, msg, 'a')

    msg = 'List of valid layers:' + os.linesep
    for layer in all_valid_layers:
        msg += layer[0]+ os.linesep
    disp.display_msg(log_file, msg, 'a')


    # (II) Projects the layers into the national coordinate system or any desired system
    msg = os.linesep + frm_separator + os.linesep + '(II) Projecting of the layers' + os.linesep + frm_separator + os.linesep
    disp.display_msg(log_file, msg, 'a')

    i = 1
    for layer in all_valid_layers:
        project_raster(layer[0], to_crs, log_file)




    # When script is complete, call exitQgis() to remove the provider and
    # layer registries from memory
    qgs.exitQgis()
    msg = 'Qgis has been closed'
    disp.display_msg(log_file, msg, 'a')

    #raw_input("Press Enter to continue...")
Stéphane Henriod
quelle
Haben Sie in Ihrem zweiten Link den von @ GermánCarrillo bereitgestellten Code verwendet? Sein Code wird auch zum Ausführen von eigenständigen Skripten verwendet (ich bearbeite meine Pfade leicht, wenn ich Windows verwende).
Joseph
Was ist die Aufgabe, die Sie ausführen möchten? :). Könnten Sie bitte den Code in Ihre Frage aufnehmen? Dies könnte anderen helfen, herauszufinden, was falsch ist.
Joseph
Ich versuche, einige Funktionen zum Verarbeiten von UAV-Bildern zu schreiben. Das erste, was ich tun muss, ist eine Neuprojektion, weshalb ich das Verarbeitungsmodul benötige. Lassen Sie mich mein vollständiges Skript hinzufügen, obwohl ich mich ein bisschen schäme: Ich bin kein "echter" Entwickler und ich bin sicher, dass mein Code nicht der sauberste oder direkteste ist, den Sie jemals gesehen haben :-)
Stéphane Henriod
Schäme dich nicht! Nichts, was ich poste, ist das sauberste oder direkteste =)
Joseph
Also habe ich mein ganzes Skript hinzugefügt. Fühlen Sie sich frei, einen Blick darauf zu werfen :-)
Stéphane Henriod

Antworten:

6

Linux QGIS 2.18.1

Führen Sie mit diesem Code die Verarbeitung über ein eigenständiges Skript aus:

#!/usr/bin/env python
import qgis
from qgis.core import *
import sys

app = QgsApplication([],True, None)
app.setPrefixPath("/usr", True)
app.initQgis()
sys.path.append('/usr/share/qgis/python/plugins')
from processing.core.Processing import Processing
Processing.initialize()
from processing.tools import *

print Processing.getAlgorithm("qgis:creategrid")
Juanma Schriftart
quelle
Dies ist die einzige Kombination, die für die Umgebung funktioniert, in der ich arbeite (Pycharm C.Ed auf einem Ubuntu 14.04-Computer mit Python 2.7). Zuvor habe ich die Kombinationen von gis.stackexchange.com/questions/129513/… und gis.stackexchange.com/questions/176821/… ausprobiert , und leider hat keiner von ihnen " process.core.Processing " importiert. Ich weiß nicht, warum das Importieren eines Moduls so verwirrend ist. Für die Aufzeichnung: Es gibt ein reines Python-Paket, das auch "Verarbeitung" genannt wird und das QGIS-Paket beschattet.
Irene
3

Also habe ich es geschafft, es zum Laufen zu bringen, danke @Joseph für deine Hinweise:

# Import required modules

# Python modules
import sys
import time
import datetime
import os
from getpass import getuser

# Qgis modules and environment
from qgis.core import *
import qgis.utils
from PyQt4.QtCore import QFileInfo, QSettings

from PyQt4.QtGui import QApplication
app = QApplication([])

QgsApplication.setPrefixPath("/usr", True)
QgsApplication.initQgis()

# Prepare processing framework
sys.path.append('/home/' + getuser() + '/.qgis2/python/plugins')
from processing.core.Processing import Processing

Processing.initialize()

Und ich könnte es mit testen

print Processing.getAlgorithm("qgis:creategrid")

Mein Problem ist vermutlich darauf zurückzuführen, dass ich die Module am Anfang meines Skripts importiert und dann versucht habe, die Qgi-Objekte aus einer Funktion heraus zu erstellen. Ich denke, es wäre auch möglich, aber es gibt wahrscheinlich einen Fehler in meinen Python-Fähigkeiten.

Jetzt werde ich versuchen, das Verarbeitungsmodul tatsächlich zu ust :-)

Stéphane Henriod
quelle
Etwas hat sich verändert ? Ich versuche diesen Code (von Joseph), um die Verarbeitung in ein eigenständiges Skript zu verwenden, und erhalte Folgendes: ImportError: Kein Modul mit dem Namen process.core.Processing Using Linux QGIS 2.18.1
Juanma Font