0

I am trying to create a table within a Python toolbox (.pyt). This works with file GDB's, but I would like to use a memory dataset if possible.

A table can be created in memory manually or by calling a script (e.g., cut-and-paste in the ArcGIS Pro Python window), and when that's done, the pyt tools are able to access it using the arcpy.da classes.

However, I would like to have the pyt tool check for the table's existence & create one in memory as needed. However, the code that works in a script fails in a Python toolbox (which doesn't happen with file GDBs).

The following is my test code; I'm running ArcGIS Pro 2.9 on Windows 10.

The following routine appears to work as expected when pasted into the ArcGIS Pro Python window:

import arcpy
from arcpy import da
import ctypes

MessageBox = ctypes.windll.user32.MessageBoxW

PARAMETERTABLE = 'Data_table'

# Check for parameters table; create one if none exists
def CreateDataTable():
    if (arcpy.Exists(PARAMETERTABLE)):
        MessageBox(None,'Table exists in memory already','Parameters',0)
    else:
        MessageBox(None,'Create table in memory','Parameters',0)
        arcpy.CreateTable_management('memory',PARAMETERTABLE)
        MessageBox(None,'Add 1st field to table','Parameters',0)
        arcpy.AddField_management('memory\\'+PARAMETERTABLE,
            'Pdouble','DOUBLE')
        MessageBox(None,'Add 2nd field to table','Parameters',0)
        arcpy.AddField_management('memory\\'+PARAMETERTABLE,
            'Pstring','TEXT',field_length=32)
        if (arcpy.Exists(PARAMETERTABLE)):
            MessageBox(None,'Add a record to the table','Parameters',0)
            ic = da.InsertCursor(PARAMETERTABLE,['Pdouble','Pstring'])
            rw = [12.34,'ABC']
            ic.insertRow(rw)
            del rw,ic
            MessageBox(None,'Table in memory prepared','Parameters',0)
        else:
            MessageBox(None,
                'Failed to create table in memory','Parameters',0)
        return

# Execute the above routine
CreateDataTable()

However, the same (essentially) code doesn't create the table and fails when attempting to insert data in the following Python toolbox:

import arcpy
from arcpy import da

PARAMETERTABLE = 'Data_table'

class Toolbox(object):
    def __init__(self):
        """Define the toolbox (the name of the toolbox is the name of the
        .pyt file)."""
        self.label = 'Create table test'
        self.alias = ''

        # List of tool classes associated with this toolbox
        self.tools = [TableCheckl]

class TableCheck(object):
    def __init__(self):
        """Define the tool (tool name is the name of the class)."""
        self.label = 'Table Check'
        self.description = ''
        self.canRunInBackground = False

    def getParameterInfo(self):
        """Define parameter definitions"""
        params = None
        return params

    def isLicensed(self):
        """Set whether tool is licensed to execute."""
        return True

    def updateParameters(self, parameters):
        """Modify the values and properties of parameters before internal
        validation is performed.  This method is called whenever a parameter
        has been changed."""
        return

    def updateMessages(self, parameters):
        """Modify the messages created by internal validation for each tool
        parameter.  This method is called after internal validation."""
        return

    def execute(self, parameters, messages):
        """The source code of the tool."""
# Check for parameters table; create one if none exists
        if (arcpy.Exists(PARAMETERTABLE)):
            messages.addMessage('Table exists in memory already')
        else:
            messages.addMessage('Create table in memory')
            arcpy.CreateTable_management('memory',PARAMETERTABLE)
            messages.addMessage('Add 1st field to table')
            arcpy.AddField_management('memory\\'+PARAMETERTABLE,
                'Pdouble','DOUBLE')
            messages.addMessage('Add 2nd field to table')
            arcpy.AddField_management('memory\\'+PARAMETERTABLE,
                'Pstring','TEXT',field_length=32)
            if (arcpy.Exists(PARAMETERTABLE)):
                messages.addMessage('Add a record to the table')
                ic = da.InsertCursor(PARAMETERTABLE,['Pdouble','Pstring'])
                rw = [12.34,'ABC']
                ic.insertRow(rw)
                del rw,ic
                messages.addMessage('Table in memory prepared')
            else:
                messages.addErrorMessage('Failed to create table in memory')
            return

Has anyone else encountered this?

1
  • 1
    Welcome to GIS SE! Thank you for having taken the Tour to learn about our focussed Q&A format. It emphasizes that there should be only one question asked per question. I recommend reviewing meta.gis.stackexchange.com/a/3353/115 for tips on how to structure a good question for GIS SE.
    – PolyGeo
    Aug 13, 2022 at 22:08

1 Answer 1

1

The .pyt isn't working because you're not being consistent with how you provide the path to your table. When you add your fields, you are correctly specifying the location and the table name with

'memory\\'+PARAMETERTABLE

But subsequently, when you check if the table exists and use the insert cursor, you are just using the name and not the path

PARAMETERTABLE

Update your Exists() and InserCursor() to use the full path ('memory\\'+PARAMETERTABLE) and it should work.

4
  • 1
    I think you need the double slashes or a forward slash. 'memory\\'+ or 'memory/'+
    – dslamb
    Aug 16, 2022 at 11:50
  • Thanks dslamb, I didn't realize they weren't displaying correctly. Looks like you need to type out 4 slashes to get 2 to display.
    – Brennan
    Aug 16, 2022 at 11:55
  • I can see that I need to work on honing down the examples I submit. I will resubmit the question with more compact code.
    – cmagagnosc
    Aug 16, 2022 at 17:35
  • @cmagagnosc I'd try the *.pyt with the suggested edits before resubmitting a new question - I was able to reproduce your error and that is the fix that worked for me.
    – Brennan
    Aug 17, 2022 at 11:30

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.