ArcGIS Pro 2.6
Yesterday I successfully created a multi-role locator using the Create Locator tool. Three of the four data sources are rest-end services.
I would like to automate the task in a python script and things aren't quite working for me and I'm not sure why. The history of the tool is my source for the parameters. I've used it before but the data sources were feature classes rather than services. At any rate, here is what I use and the ensuing error:
countryCode = 'USA'
addressPrimary = r'https://path/to/rest/services/Reference/MapServer/5'
centerlinesPrimary = r'https://path/to/rest/services/Transportation/MapServer/0'
parcelsPrimary = r'https://path/tos/rest/services/Land/MapServer/1'
poiPrimary = r'\\SDE\Connection\To\Our.sde\owner.AddressGridCoordinatePoints'
#primaryReferenceData = "{} PointAddress;{} StreetAddress;{} POI".format(addressPrimary,centerlinesPrimary,
#parcelsPrimary)
primaryReferenceData = f'{addressPrimary} PointAddress;{centerlinesPrimary} StreetAddress;{parcelsPrimary} Parcel;{poiPrimary} POI'
outLocator = r'M:\HansenSQL\HansenGeocodingTestMultiRole'
fieldMapping = "'PointAddress.HOUSE_NUMBER 5.ADDR_HN';"\
"'PointAddress.STREET_PREFIX_DIR 5.ADDR_PD';"\
"'PointAddress.STREET_NAME 5.ADDR_SN';"\
"'PointAddress.STREET_SUFFIX_TYPE 5.ADDR_ST';"\
"'PointAddress.STREET_SUFFIX_DIR 5.ADDR_SD';"\
"'PointAddress.SUB_ADDRESS_UNIT 5.UNIT_DESIG';"\
"'PointAddress.CITY 5.CITY';"\
"'StreetAddress.HOUSE_NUMBER_FROM_LEFT 0.FROMADDR_L';"\
"'StreetAddress.HOUSE_NUMBER_TO_LEFT 0.TOADDR_L';"\
"'StreetAddress.HOUSE_NUMBER_FROM_RIGHT 0.FROMADDR_R';"\
"'StreetAddress.HOUSE_NUMBER_TO_RIGHT 0.TOADDR_R';"\
"'StreetAddress.STREET_PREFIX_DIR 0.PREDIR';"\
"'StreetAddress.STREET_NAME 0.NAME';"\
"'StreetAddress.STREET_SUFFIX_TYPE 0.POSTTYPE';"\
"'StreetAddress.STREET_SUFFIX_DIR 0.POSTDIR';"\
"'Parcel.PARCEL_NAME 1.parcel_id';"\
"POI.PLACE_NAME 'owner.AddressGridCoordinatePoints'.Coordinates"
Error:
Failed to execute. Parameters are not valid.
ERROR 002782: Selected Primary Table does not contain geometry.
I don't care for this new code editor as it doesn't list line numbers, but I'll limp through this.
Notice in the field mapping portion it refers to the feature id only; does it need to be fully qualified with the entire url?
The help page has a sample; I'll see what I need to do to get it to work for me...
Following the example towards the bottom of the help page mentioned, I am trying to create a single role street address locator with a service as the data source: (sorry for the lame code editing, but I'm at the mercy of the new geonet)
import arcpy
arcpy.env.overwriteOutput = True
arcpy.SetLogHistory(False)
outLocator = r'M:\HansenSQL\HansenGeocoding\TestLocator'
language = 'ENG'
country = 'USA'
inTable = "https://blah/blahlah/rest/services/Transportation/MapServer/0 StreetAddress"
fieldMapping = "'StreetAddress.HOUSE_NUMBER_FROM_LEFT 0.FROMADDR_L';"\
"'StreetAddress.HOUSE_NUMBER_TO_LEFT 0.TOADDR_L';"\
"'StreetAddress.HOUSE_NUMBER_FROM_RIGHT 0.FROMADDR_R';"\
"'StreetAddress.HOUSE_NUMBER_TO_RIGHT 0.TOADDR_R';"\
"'StreetAddress.STREET_PREFIX_DIR 0.PREDIR';"\
"'StreetAddress.STREET_NAME 0.NAME';"\
"'StreetAddress.STREET_SUFFIX_TYPE 0.POSTTYPE';"\
"'StreetAddress.STREET_SUFFIX_DIR 0.POSTDIR'"
arcpy.geocoding.CreateLocator(country, inTable, fieldMapping, outLocator, language)
However, it errors out with:
ExecuteError: Failed to execute. Parameters are not valid.
ERROR 002782: Selected Primary Table does not contain geometry.
Failed to execute (CreateLocator).
I can think of two things:
I can get to the service via the create locator tool, but perhaps there is a security setting that does not allow me to hit it with python; I don't think that's it because in a console window I can use arcpy.ListFields(inTable) and get a list.
or
Creating a locator with a service as the data source simply does not work in python....
Joe,
You need to call
arcpy.SignInToPortal(“https://machinename.domainname.com/portal”, “username”, “password”)
and then using services as data sources should work just fine for CreateLocator using Python. The data sources need to be on the server federated with the Portal you are signing into.
If your data sources are shared with everyone (public) you don’t need to call SignInToPortal() first.
Brad
Turns out the arcpy.SignInToPotal() call isn't needed for me. The game changer is while the create locator tool is able to exploit a map service as a data source, arcpy cannot; arcpy wants a feature service.
The portal I have access to is behind a firewall and is available 'publicly' to those users logged into the network which I am. All I had to do is change the urls to the various feature services and I'm good to go.
One of the data sources in my multi-role locator is on our SDE-Egdb, so it's part of inTable variable as shown below in the final code:
import arcpy
arcpy.env.overwriteOutput = True
arcpy.SetLogHistory(False)
outLocator = r'M:\path_to\my_locator'
language = 'ENG'
country = 'USA'
inTable = "https://www.yady_yady.org/gisfed/rest/services/Internal/FeatureServer/1 PointAddress;"\
"https://www.yady_yady.org/gisfed/rest/services/Internal/FeatureServer/9 StreetAddress;"\
"https://www.yady_yady.org/gisfed/rest/services/Internal/FeatureServer/3 Parcel;"\
"\\\sharedDrive\to\connectionFile.sde\OurSde.AddressGridCoordinatePoints POI"
fieldMapping = "'PointAddress.HOUSE_NUMBER 1.ADDR_HN';"\
"'PointAddress.STREET_PREFIX_DIR 1.ADDR_PD';"\
"'PointAddress.STREET_NAME 1.ADDR_SN';"\
"'PointAddress.STREET_SUFFIX_TYPE 1.ADDR_ST';"\
"'PointAddress.STREET_SUFFIX_DIR 1.ADDR_SD';"\
"'PointAddress.SUB_ADDRESS_UNIT 1.UNIT_DESIG';"\
"'PointAddress.CITY 1.CITY';"\
"'StreetAddress.HOUSE_NUMBER_FROM_LEFT 9.FROMADDR_L';"\
"'StreetAddress.HOUSE_NUMBER_TO_LEFT 9.TOADDR_L';"\
"'StreetAddress.HOUSE_NUMBER_FROM_RIGHT 9.FROMADDR_R';"\
"'StreetAddress.HOUSE_NUMBER_TO_RIGHT 9.TOADDR_R';"\
"'StreetAddress.STREET_PREFIX_DIR 9.PREDIR';"\
"'StreetAddress.STREET_NAME 9.NAME';"\
"'StreetAddress.STREET_SUFFIX_TYPE 9.POSTTYPE';"\
"'StreetAddress.STREET_SUFFIX_DIR 9.POSTDIR';"\
"'Parcel.PARCEL_NAME 3.parcel_id';"\
"POI.PLACE_NAME 'OurSde.AddressGridCoordinatePoints'.Coordinates"
arcpy.geocoding.CreateLocator(country, inTable, fieldMapping, outLocator, language)