So for example I want to create a simple hillshade from a DEM. This works with my code from my Spyder IDE if I run it once. When I run it another time, it causes python to stop working. When I run it as a bat file, I still get the hillshade, but again I get the message 'python.exe has stopped working'. This is not clean and helpfull at all if I want to develop something more complex and let it run in an automated way. This answer didn't work for me unfortunately. Also, either way the processing module copies its folder structure (only the folders though, not its content) into my working directory together with a qgis-auth.db file. This also seems not clean at all.

Here my code with a download link provided to a small DEM sample file:

Again, this code work in my Spyder IDE when run once, but causes python to stop working when run another time. It also works when run from a bat file, but also crashes my python.exe. Any ideas? That way I can't replace ArcPy with PyQGIS unfortunately.

The problem definitely seems to be related to how QApplication and QgsApplication is initialised (or not correctly ended?). I just tried an NDVI calculation without the messy processing library and I still get the same crashing errors.

Yes, most definitely a Qt problem that is caused by not properly closing the app. This was reported quite frequently. Unfortunately, none of the proposed solutions work for me (or I just don't know how to implement correctly).

1 Answer
1

The problem definitely seems to be related to how QApplication and QgsApplication is initialised

Yes, the thing is: QgsApplication is a subclass of PyQt's QApplication, so basically you do not need (and should not) instantiate a QApplication here, instead just use the QgsApplication.

The problem can also be related to the QgsApplication.exitQgis() as it seems to cause a sigsegv on the exit. Using QgsApplication.exit() solve it for me

Try this:

import sys
# Import only what you're going to use
from qgis.core import QgsApplication, QgsRasterLayer
# You can add this path to your system's environment so you don't have to type it here
sys.path.append('C:/OSGeo4W64/apps/qgis/python/plugins')
import processing
# This is a 'fake' iface since we are not using a interface here
class DummyIface(object):
def __init__(self):
self.destCrs = None
# Pass QgsApplication to an object and you can use it just like a QApplication
app = QgsApplication([], True)
app.initQgis()
print "QGIS successfully Initialised"
# I took the freedom to change the way you used processing here, just to be sure it will work
processing.classFactory(DummyIface())
rasterLyr = QgsRasterLayer("dem.asc", "hillshade")
# An assertion check, because we do not want to continue if we do not have this layer right
assert rasterLyr.isValid()
processing.runalg("gdalogr:hillshade", rasterLyr, 1, False, False, 1.0, 1.0, 315.0, 45.0,"qgis_hs.tif")
app.exit()

sidenote: you may have problems with the processing module as it tries to set a progress for you while you have no interface. Have a look at this question if that is the case