da.UpdateCursor - Runtime Error: Object invalid or no longer set

3311
3
Jump to solution
06-16-2015 03:52 PM
MikeFowler2
New Contributor II

Anybody have any insight on why this is failing? (Line 62 below).

I am trying to update a text field using a DA Update Cursor.  Please help!

Traceback (most recent call last):
  File "\\bctsdata.bcgov\tsg_root\General_User_Workspace\Recce_Data\scripts\UploadPDFReports\UploadPDFReports.py", line 135, in <module>
    UploadPDFReports(fcBlockPolygons, dirReceivedReports)
  File "\\bctsdata.bcgov\tsg_root\General_User_Workspace\Recce_Data\scripts\UploadPDFReports\UploadPDFReports.py", line 105, in UploadPDFReports
    cursor.updateRow(row)
RuntimeError: Object invalid or no longer set.

def GetOperArea_SpatialIntersect(fcOperArea, flds, shp):
    fcOperArea = gp.MakeFeatureLayer_management(fcOperArea)
    gp.SelectLayerByLocation_management(fcOperArea, "INTERSECT", shp )
    with arcpy.da.SearchCursor(fcOperArea, flds) as cursor:
        for row in cursor:
            #gp.AddMessage("District:{0} OpArea:{1}".format(row[0], row[1]))
            sDist = row[0]
            sOp = row[1]
            sBlkRepDir = os.path.join(sReportDir, sDist, sOp)
            #gp.AddMessage(sBlkRepDir)
            if os.path.exists(sBlkRepDir):
                return sBlkRepDir
            else:
                os.makedirs(sBlkRepDir)
                gp.AddMessage("**Need to create output directory:{}".format(sBlkRepDir))
                return sBlkRepDir


def UploadPDFReports(fcRecceBlks, dirReports):
  lstDist = []
  startDir = sReportDir
  #--Hardcoded field values that must exist
  #--Block Polygon attributes
  fldBlkName = "BLOCK_NAME"
  fldLink = "FILE_LINK"
  #--Operating Area attributes
  fldDist = "MOF_DISTRI"
  fldOpCode = "OP_AREA"
  fldOpArea = "AREA_NAME"
  #------------------------------------------------------------------------------------------------------------
  #Loop through PDF Reports
  #------------------------------------------------------------------------------------------------------------
  #print dirReports
  #gp.AddMessage(dirReports)
  for dirpath, dirnames, filenames in os.walk(dirReports, True):
      for file in filenames:
          if "_RecceReport.pdf" in file:
              sBlock = file.split("_")[0]
              gp.AddMessage("Recce Report: " + sBlock)
              #------------------------------------------------------------------------------------------------------------
              #Loop through associated block spatial
              #------------------------------------------------------------------------------------------------------------
              iCnt = 0
              exp = fldBlkName + " = '{0}'".format(sBlock)
              gp.AddMessage(exp)
              with arcpy.da.UpdateCursor(fcRecceBlks, ("SHAPE@XY", fldLink), where_clause=exp) as cursor:
                  for row in cursor:
                      #--Get the centroid of the polygon.  Use the polygon centroid to determine which Op Area it's in
                      pnt = row[0]
                      shp = arcpy.Point()
                      shp.X = pnt[0]
                      shp.Y = pnt[1]
                      gp.AddMessage(row[1])
                      sCurrLink = NzStr(row[1])
                      pntGeom = arcpy.PointGeometry(shp)
                      #--Get the directory to store the report based on the spatial operating area
                      #lyrOpArea = gp.MakeFeatureLayer_management(fcOpArea)
                      sBlkRepDir = GetOperArea_SpatialIntersect(fcOpArea, (fldDist, fldOpArea), pntGeom)
                      sLink = os.path.join(sReportDir, sBlkRepDir, file)
                      gp.AddMessage("*{0}".format(sLink))
                      row[1] = sLink
                      cursor.updateRow(row)
0 Kudos
1 Solution

Accepted Solutions
MikeFowler2
New Contributor II

I solved the problem. 

The outer da.UpdateCursor is open on a feature class in the same workspace as the featureclass where the da.SearchCursor is open in the 'GetOperArea_SpatialIntersect' function.  So, it seems you cannot open an Update Cursor and then open a SearchCursor on the same workspace and expect to update the original cursor.

I am sure I could rewrite the code to start and end edit operations on the Update cursor.  I only structured the data in the same workspace for testing purposes - in production this will not be an issue in my case. 

View solution in original post

3 Replies
TomSellsted
MVP Regular Contributor

Mike,

Any chance that the length of sLink that you are putting back in row[1] exceeds the maximum length of the column?

Regards,

Tom

0 Kudos
MikeFowler2
New Contributor II

Good thought.  I just ran it over a few records.  The file path is coming back in the 120 - 130 length range.  Field is defined up to 200. 

0 Kudos
MikeFowler2
New Contributor II

I solved the problem. 

The outer da.UpdateCursor is open on a feature class in the same workspace as the featureclass where the da.SearchCursor is open in the 'GetOperArea_SpatialIntersect' function.  So, it seems you cannot open an Update Cursor and then open a SearchCursor on the same workspace and expect to update the original cursor.

I am sure I could rewrite the code to start and end edit operations on the Update cursor.  I only structured the data in the same workspace for testing purposes - in production this will not be an issue in my case.