Replace() string function isn't working within Field Calculator and arcpy

4918
12
Jump to solution
11-23-2015 12:06 PM
EugeneDurshpek
New Contributor III

I'm trying to figure out what's wrong with my python syntax.

I have an attribute table with 4 fields containing paths to media files. I'm trying to convert the paths so that they behave more like hyperlinks on our network. The existing paths (added to the tables via 3rd party proprietary software) include network drive i.e. M:\GraniteXP\...

I'm trying to use find and replace to replace "M:\GraniteXP" with "\\vancouver.root.local\...\GraniteXP".

I can do this perfectly fine using field calculator in ArcMap as well as Model Builder. However, when I export the model to Python; the script runs (successfully), but the values are not updated. There is not error to tell me what's failing.

Here's a snippet from my script. I do have a MakeFeatureLayer prior to this snippet. (Note: this particular script is trying to change it back to the network drive pathing for testing purposes).

arcpy.SelectLayerByAttribute_management("lyrsdePipeInsp", "NEW_SELECTION", "Photo1 is not null")

arcpy.CalculateField_management("lyrsdePipeInsp", "Photo1", "Replace( [Photo1], \"\\\\vancouver.root.local\\cityapps\\GraniteXP\", \"M:\\GraniteXP\" )", "VB", "")

arcpy.SelectLayerByAttribute_management("lyrsdePipeInsp", "NEW_SELECTION", "Photo2 is not null")

    arcpy.CalculateField_management("lyrsdePipeInsp", "Photo2", "Replace( [Photo2],  \"\\\\vancouver.root.local\\cityapps\\GraniteXP\", \"M:\\GraniteXP\" )", "VB", "")

arcpy.SelectLayerByAttribute_management("lyrsdePipeInsp", "NEW_SELECTION", "Photo3 is not null")

arcpy.CalculateField_management("lyrsdePipeInsp", "Photo3", "Replace( [Photo3], \"\\\\vancouver.root.local\\cityapps\\GraniteXP\", \"M:\\GraniteXP\" )", "VB", "")

arcpy.SelectLayerByAttribute_management("lyrsdePipeInsp", "NEW_SELECTION", "Video is not null")

arcpy.CalculateField_management("lyrsdePipeInsp", "Video", "Replace( [Video], \"\\\\vancouver.root.local\\cityapps\\GraniteXP\", \"M:\\GraniteXP\" )", "VB", "")

Thanks!

Eugene Durshpek

0 Kudos
1 Solution

Accepted Solutions
Luke_Pinner
MVP Regular Contributor

You've got your find string and replacement string in the wrong order.

Try:

arcpy.CalculateField_management("lyrsdePipeInsp", "Photo1", r'Replace( [Photo1],"M:", "\\vancouver.root.local")',"VB")

Or:

arcpy.CalculateField_management("lyrsdePipeInsp", "Photo1", r"!Photo1!.replace('M:', r'\\vancouver.root.local')", "PYTHON_9.3")

View solution in original post

12 Replies
DanPatterson_Retired
MVP Emeritus

a pain with the double slash replacement, you could try replacement with "/"

>>> a = "c:\\path\\subpath\\file.tiff"
>>> b = a.replace("\\","/")
>>> b
'c:/path/subpath/file.tiff'
EugeneDurshpek
New Contributor III

Thanks Dan. I will combine your suggestion with Luke's suggestion (below) and will hopefully have best of both worlds.

Eugene D.

0 Kudos
LukeSturtevant
Occasional Contributor III

It is a lot faster and easier to code this type of processing with an update cursor​.

something like this would work for the code example you gave:

import arcpy
fc = #the path to your feature class
with arcpy.da.UpdateCursor(fc,["Photo1","Photo2","Photo3","Video"]) as update:
     for row in update:
          if row[0] is not None:
                row[0] = row[0].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP")
         if row[1] is not None:
                row[1] = row[1].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP")        
         if row[2] is not None:
                row[2] = row[2].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP")
         if row[3] is not None:
                row[3] = row[3].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP")
           update.updateRow(row)
0 Kudos
EugeneDurshpek
New Contributor III

Thank you Luke, I will give this a try. I'm a novice and wasn't sure how to apply the update cursor function to my scenario. I appreciate your quick response.

Eugene D.

0 Kudos
EugeneDurshpek
New Contributor III

I am testing this within a session of ArcMap and am getting Runtime Error: Insufficient permissions to edit the feature class [STATE_ID = 207215] which is odd because I can edit and save outside of python.

0 Kudos
LukeSturtevant
Occasional Contributor III

Are you working from an SDE geodatabase? In either case when I see this error I find that opening a da Editor​ helps:

import arcpy  
workspace = # path to you workspace
fc = # the path to your feature class  
with arcpy.da.Editor(workspace) as edit:
     with arcpy.da.UpdateCursor(fc,["Photo1","Photo2","Photo3","Video"]) as update:  
           for row in update:  
              if row[0] is not None
                     row[0] = row[0].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP"
              if row[1] is not None
                     row[1] = row[1].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP")          
              if row[2] is not None
                     row[2] = row[2].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP"
              if row[3] is not None
                     row[3] = row[3].replace("\\vancouver.root.local\\cityapps\\GraniteXP", "M:\\GraniteXP"
              update.updateRow(row) 
0 Kudos
EugeneDurshpek
New Contributor III

Thank you Luke;

Yes, I am editing an SDE feature class. I have updated my script (see below) but am now getting a "RuntimeError: cannot open workspace"; I will clean it up once I can get it to work.

import arcpy
workspace = "M:/GIS/Support_Files/DataConnectionsADMIN/SewerVan_NT_SQLGIS1.sde/SewerVan.VANSEWER.SwrPipeInspected"
fc = "SewerVan.VANSEWER.SwrPipeInspected"
with arcpy.da.Editor(workspace) as edit:
    with arcpy.da.UpdateCursor(fc,["Photo1","Photo2","Photo3","Video"]) as update:
        for row in update:
            if row[0] is not None:
                    row[0] = row[0].replace("//vancouver.root.local/cityapps/GraniteXP", "M:/GraniteXP")
            if row[1] is not None:
                    row[1] = row[1].replace("//vancouver.root.local/cityapps/GraniteXP", "M:/GraniteXP")
            if row[2] is not None:
                    row[2] = row[2].replace("//vancouver.root.local/cityapps/GraniteXP", "M:/GraniteXP")
            if row[3] is not None:
                row[3] = row[3].replace("//vancouver.root.local/cityapps/GraniteXP", "M:/GraniteXP")
            update.updateRow(row)
0 Kudos
LukeSturtevant
Occasional Contributor III

I'm not sure if there is an easy way to use the cursors in an ArcSDE geodatabase environment. You could look at this forum here​ that shows a work around. If you cannot get that figured out you may want to attempt  Luke Pinner's suggestion below.

0 Kudos
WesMiller
Regular Contributor III

Not by chance a 64-bit? see below

Caution:

Field calculations with a VB Expression type are not supported on 64-bit products, including ArcGIS Pro, ArcGIS for DesktopBackground Geoprocessing (64-bit) and ArcGIS for Server. To successfully use Calculate Field in these products, expressions should be converted to Python, or in the case of Background Geoprocessing (64-bit), background processing can alternatively be disabled.

Calculate Field—Help | ArcGIS for Desktop

0 Kudos