0

I am trying to import a CSV to GDB using an ArcMap script tool and preserve some string fields that look like numbers as strings. I added some code to create and populate a schema.ini file in the CSV's source directory but ArcMap doesn't seem to recognize/honor it. It is created immediately but appears to only be populated a minute or so later once the rest of the tool is finished running. The new schema.ini file appears to be identical to one I manually edited that does work. It seems to possibly be an order of operations issue, any suggestions? Here is my code for this piece of the workflow so far:

addressTable = arcpy.GetParameterAsText(0)
tableName = os.path.basename(addressTable)
inputDir = os.path.dirname(addressTable)
schemaFile = str(inputDir) + "\schema.ini"
schemaHeader = "[" + str(tableName) + "]\n"

file = open(schemaFile, 'w')
file.write(schemaHeader)
file.write("Format=CSVDelimited\n")
file.write("ColNameHeader=True\n")
fieldList = arcpy.ListFields(addressTable)
for field in fieldList:
    file.write(field.name + " TEXT Width 128\n")
file.close               
arcpy.conversion.TableToTable(addressTable, workingGDB, tempTable)


And this is what the schema.ini file created by the script looks like:

[Sample_200.csv]
Format=CSVDelimited
ColNameHeader=True
REGISTRATION_NUMBER TEXT Width 128
Address TEXT Width 128
City TEXT Width 128
State TEXT Width 128
ZIP TEXT Width 128
8
  • 1
    Shouldn't it be file.close()? That could be why your schema.ini is being ignored: when you fail to close the file it is empty when ArcGIS reads it but at the end of execution, as part of the cleanup, all file handles are flushed and closed so when you look at your schema.ini after the script is complete it looks fine. I suggest you use a with statement: with open(schemaFile, 'w') as file: then indent under and the file will be flushed and closed as soon as the execution exits the with block. Commented Feb 20 at 0:56
  • 1
    P.S. try not to use simple words that could be reserved words like file for your objects, make it ThisFile, pFile, xFile... or something similar - it's not just style, python will let you overwrite existing objects, you could inadvertently overwrite something you need later and that sort of bug is really hard to chase down. I hope this comment saves you some facepalms in the future. Commented Feb 20 at 1:00
  • 1
    Even better than file.close() (arguably) is to use the 'with' syntax. This will automatically close the file at the end of the 'with' clause. Eg: with open(schemaFile, 'w') as f: , then indent all the file processing (writing) commands below the 'with'. (See more at: note.nkmk.me/en/python-file-io-open-with ) Commented Feb 20 at 2:24
  • 1
    If this doesn't resolve it, you could try creating the schema.ini file in the validation part of the script tool. But that's getting a bit clunky, and has the potential to create schema.ini files where you don't want them. Commented Feb 20 at 2:24
  • @SonofaBeach that's a interesting concept of writing in the validation phase. Another method I've employed is keeping a pre-written (using Notepad, they were .prj files in my case) file in the same folder as the script then copy it (shutil.copyfile()) to the required location; you can get the location of your script with os.path.dirname(sys.argv[0]) to make up your copy from and to paths. Commented Feb 20 at 2:40

1 Answer 1

0

Quick answer: Change file.close to file.close() (to call the function rather than just reference the function). This will close the file as intended and cause the changes to the file to be written.

Without this correct call, the file will be closed automatically at the end of the script, but of course, that is too late for your arcpy.conversion.TableToTable(), which will read the file before the end of the script (ie, before it has been written to).

Also, it better to avoid reserved words, or words that could be reserved words, as variable names. Ie, avoid using 'file' or 'field' as variable names.

Alternatively, you can also use the 'with' syntax which will automatically close the file (without having to use the close() function) at the end of the with clause, like this:

with open(schemaFile, 'w') as schema_file:
    schema_file.write(schemaHeader)
    schema_file.write("Format=CSVDelimited\n")
    schema_file.write("ColNameHeader=True\n")
    fieldList = arcpy.ListFields(addressTable)
    for fld in fieldList:
        schema_file.write(fld.name + " TEXT Width 128\n")

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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