4

The following is currently unsuccessful at fulfilling a table field join to a point shapefile in Qgis.
All instances of the join object will print the proper values, and no error is flagged when processing - but the target layer does not exhibit any effect.

Something missing?

    Heads = QgsVectorLayer(headCSV, 'Heads', 'ogr')
    QgsMapLayerRegistry.instance().addMapLayer(Heads)
    self.iface.legendInterface().setLayerVisible(Heads,False)
    grid = ftools_utils.getMapLayerByName(unicode('Grid'))
    joinObject = QgsVectorJoinInfo()
    joinObject.targetFieldName = str('ID')
    joinObject.joinLayerID = Heads.id()
    joinObject.joinFieldName = str('cellID')
    grid.addJoin(joinObject)
    grid.reload()

UPDATE:

The following returns 'None'. I expect this is actually supposed to return the field names to be joined? (e.g. - a clue to the mistake)

    print joinObject.joinFieldNamesSubset()

FURTHER UPDATE:

Added the following, and now the previous update command returns the accurate fields to be joined - yet the destination layer does not show 'joined' fields...

    joinObject.setJoinFieldNamesSubset(['someFieldName'])
8

This has worked for me:

# Get input (csv) and target (Shapefile) layers
shp=iface.activeLayer()
csv=iface.mapCanvas().layers()[0]

# Set properties for the join
shpField='code'
csvField='codigo'
joinObject = QgsVectorJoinInfo()
joinObject.joinLayerId = csv.id()
joinObject.joinFieldName = csvField
joinObject.targetFieldName = shpField
shp.addJoin(joinObject)

The error you are facing is, believe it or not, by a typo in joinLayerId. The question is, why QGIS doesn't throw an error there?

  • 1
    You are exactly right. Works beautifully now. Highly appreciate the help. A mistake easily overlooked it seems without a syntax error. Thanks! – Katalpa Feb 8 '15 at 15:10
  • @gcarrillo "The question is, why QGIS doesn't throw an error there?" because your are creating a new python variable. Did you check if addJoin return false? – Luigi Pirelli Mar 11 '15 at 11:48
  • @LuigiPirelli addJoin returns True, giving no clue about any error or typo. – Germán Carrillo Mar 12 '15 at 16:25
  • 1
    There's also an excellent tutorial using this method. – chip Aug 22 '16 at 15:54
3

If it's ok for you to use Processing algorithms for that, it's as simple as this (from the QGIS Python console):

import processing
res = processing.runalg("qgis:joinattributestable","/path/to/shape.shp","/path/to/table.csv","fieldShp","fieldTable","/path/to/output.shp")
layer = QgsVectorLayer(res['OUTPUT_LAYER'], "joined layer", "ogr")
QgsMapLayerRegistry.instance().addMapLayer(layer)

You can have a look at the algorithm source code so that you decide whether you want to adapt it for your own script.

  • While this is a great alternative, the need is a 'virtual join', as accomplished from the properties menu of a layer. This is because the operation might be done repeatedly, and avoidance of data overhead is a must. – Katalpa Feb 8 '15 at 13:51
  • Well, you could still use temporary layers setting the last parameter of the algorithm to None, but I see your point. – Germán Carrillo Feb 8 '15 at 14:48
0

Excellent example, I was very useful, combine a shp with a csv file, here my example performed:


import processing
res = processing.runalg("qgis:joinattributestable","d:/areas_geoestadisticas_estatales.shp","d:/poblacion.csv","cve_ent","cve_ent","d:/union_shp_csv.shp")
layer = QgsVectorLayer(res['OUTPUT_LAYER'], "Capa Unida", "ogr")
QgsMapLayerRegistry.instance().addMapLayer(layer)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.