Pro 2.9.5
Touching up a tool I wrote last year, including migrating it from a scripting tool (ATBX) to a python toolbox (PYT). Part of the workflow involves accessing CIM, using a layer from the map as an input.
The tool runs great in the ATBX.
cim_lyr= FC.getDefinition('V2') However, something REALLY WEIRD happens in the PYT.
I get the following error message:

AttributeError: 'MappingLayerObject' object has no attribute 'getDefinition'
Hmm, let's investigate this and make sure that I'm putting in what I think I am.
In the map:
aprx = arcpy.mp.ArcGISProject("CURRENT")
mp = aprx.activeMap
lay = mp.listLayers("colton*")
lay= lay[0]
print(type(lay))
#<class 'arcpy._mp.Layer'>
print(dir(lay))
# ['URI', '__class__', '__delattr__', '__dict__', '__dir__', '__doc__',
# '__eq__', '__format__', '__from_scripting_arc_object__', '__ge__',
# '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__',
# '__le__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__',
# '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__',
# '__subclasshook__', '__weakref__', '_arc_object', 'brightness',
# 'connectionProperties', 'contrast', 'dataSource', 'definitionQuery',
# 'disableTime', 'enableTime', 'extrusion', 'getDefinition',
# 'getSelectionSet', 'is3DLayer', 'isBasemapLayer', 'isBroken',
# 'isFeatureLayer', 'isGroupLayer', 'isNetworkAnalystLayer',
# 'isNetworkDatasetLayer', 'isRasterLayer', 'isSceneLayer', 'isTimeEnabled',
# 'isWebLayer', 'listDefinitionQueries', 'listLabelClasses', 'listLayers',
# 'listTables', 'longName', 'maxThreshold', 'metadata', 'minThreshold',
# 'name', 'saveACopy', 'setDefinition', 'setSelectionSet', 'showLabels',
# 'supports', 'symbology', 'time', 'transparency',
# 'updateConnectionProperties', 'updateDefinitionQueries',
# 'updateLayerFromJSON', 'visible'] Okay, so clearly a layer and definitely supports getDefinition.
Cool. Let's check in the ATBX script.
arcpy.AddMessage(type(FC))
#<class 'arcpy._mp.Layer'>
arcpy.AddMessage(dir(FC))
# ['URI', '__class__', '__delattr__', '__dict__', '__dir__', '__doc__',
# '__eq__', '__format__', '__from_scripting_arc_object__', '__ge__',
# '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__',
# '__le__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__',
# '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__',
# '__subclasshook__', '__weakref__', '_arc_object', 'brightness',
# 'connectionProperties', 'contrast', 'dataSource', 'definitionQuery',
# 'disableTime', 'enableTime', 'extrusion', 'getDefinition',
# 'getSelectionSet', 'is3DLayer', 'isBasemapLayer', 'isBroken',
# 'isFeatureLayer', 'isGroupLayer', 'isNetworkAnalystLayer',
# 'isNetworkDatasetLayer', 'isRasterLayer', 'isSceneLayer', 'isTimeEnabled',
# 'isWebLayer', 'listDefinitionQueries', 'listLabelClasses', 'listLayers',
# 'listTables', 'longName', 'maxThreshold', 'metadata', 'minThreshold',
# 'name', 'saveACopy', 'setDefinition', 'setSelectionSet', 'showLabels',
# 'supports', 'symbology', 'time', 'transparency',
# 'updateConnectionProperties', 'updateDefinitionQueries',
# 'updateLayerFromJSON', 'visible']
Still supports getDefinition.
Let's check the PYT.
arcpy.AddMessage(type(FC))
<class 'MappingLayerObject'>
arcpy.AddMessage(dir(FC))
# ['GetCimJSONString', 'SetCimJSONString', 'URI', 'UpdateLayerFromJSON',
# '_XML', '__class__', '__delattr__', '__dir__', '__doc__', '__eq__',
# '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__',
# '__init__', '__init_subclass__', '__le__', '__lt__', '__ne__', '__new__',
# '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__',
# '__str__', '__subclasshook__', '_id', '_pUnk', 'brightness',
# 'connectionProperties', 'contrast', 'dataSource', 'definitionQuery',
# 'disableTime', 'enableTime', 'extrusion', 'getSelectionSet', 'is3DLayer',
# 'isBasemapLayer', 'isBroken', 'isFeatureLayer', 'isGroupLayer',
# 'isLayerSame', 'isNetworkAnalystLayer', 'isNetworkDatasetLayer',
# 'isRasterLayer', 'isSceneLayer', 'isTimeEnabled', 'isWebLayer',
# 'listDefinitionQueries', 'listLabelClasses', 'listLayers', 'listTables',
# 'longName', 'maxThreshold', 'metadata', 'minThreshold', 'name',
# 'saveACopy', 'setSelectionSet', 'showLabels', 'supports', 'symbology',
# 'time', 'transparency', 'updateConnectionProperties',
# 'updateDefinitionQueries', 'visible']
Definitely does not support getDefinition. But it has GetCimJSONString, which only appears to be documented in @SamSzotkowski 's post here. (That exact query in Google will yield the same post, as well as site that is actually AliExpress)
He writes, as I have also found, that instead of getting a layer object, we get a mappinglayer object. I can't find any documentation for this.
'''ATBX'''
inFCs = GetParameter(2)
arcpy.AddMessage(type(inFCs))
# <class 'list'>
arcpy.AddMessage(type(inFCs[0]))
# <class 'arcpy._mp.Layer'>
return
'''PYT'''
arcpy.AddMessage(type(parameters[2].value))
#<class 'geoprocessing value table object'>
arcpy.AddMessage(type(parameters[2].value.GetTrueValue(0,0)))
#<class 'MappingLayerObject'>
# I also checked with .GetTrueRow(0), etc.
So uh. What is a mappinglayer and where is anything written down about it?
What about a python toolbox causes a multivalue FeatureLayer parameter to be considered a value table, and the features within to be "MappingLayer"s instead of normal layers? And seriously, why is this not written down anywhere? Why is this not mentioned on the CIM Access Documentation?
Like, cool, I guess I can rewrite the code to use JSON instead of the CIM object. But it would have been great to have been warned about this beforehand.