I'm trying to make a script tool that reorders the fields in an attribute table and exports a new shapefile with the updated field order. I found a previous discussion (arctoolbox - How to re-order fields permanently using ArcGIS Make Query Table tool? - Geographic Inf... ) with code that used the Merge tool to accomplish this, and when I hardcoded it for a test shapefile, it worked well (despite having to list out the fields in the order desired in a string - line 59). In making a script tool, I'm not sure how to set the parameter to define new_field_order. I tried setting the parameter as a string, but am getting the exception in line 38 raised. How do I set this parameter to read a user-defined order for the fields in the same way I hardcoded it? Also, is there any way to reorder the fields in a temporary attribute table in ArcMap, write code to read the temporary order, and use that order to export the new shapefile (in order to avoid having to type out the desired order)?
Thanks!
Dave
import arcpy
def reorder_fields(table, out_table, field_order, add_missing=True):
"""
Reorders fields in input featureclass/table
:table: input table (fc, table, layer, etc)
:out_table: output table (fc, table, layer, etc)
:field_order: order of fields (objectid, shape not necessary)
:add_missing: add missing fields to end if True (leave out if False)
-> path to output table
"""
existing_fields = arcpy.ListFields(table)
existing_field_names = [field.name for field in existing_fields]
existing_mapping = arcpy.FieldMappings()
existing_mapping.addTable(table)
new_mapping = arcpy.FieldMappings()
def add_mapping(field_name):
mapping_index = existing_mapping.findFieldMapIndex(field_name)
# required fields (OBJECTID, etc) will not be in existing mappings
# they are added automatically
if mapping_index != -1:
field_map = existing_mapping.fieldMappings[mapping_index]
new_mapping.addFieldMap(field_map)
# add user fields from field_order
for field_name in field_order:
if field_name not in existing_field_names:
raise Exception("Field: {0} not in {1}".format(field_name, table))
add_mapping(field_name)
# add missing fields at end
if add_missing:
missing_fields = [f for f in existing_field_names if f not in field_order]
for field_name in missing_fields:
add_mapping(field_name)
# use merge with single input just to use new field_mappings
arcpy.Merge_management(table, out_table, new_mapping)
return out_table
intable = r"Y:\Huggins_D\2016\Tool\Export_Output.shp"
outtable = r"Y:\Huggins_D\2016\Tool\Export_Output_TEST.shp"
new_field_order = ['ZIP4', 'NAME', 'TYPE', 'ADDRESS', 'CITY', 'ZIP5', 'STATE' ,'TYPE2', 'PHONE']
reorder_fields(intable, outtable, new_field_order, add_missing=True)