Select to view content in your preferred language

Copy Feature Class to new DB

1147
2
Jump to solution
03-21-2023 04:33 AM
kapalczynski
Frequent Contributor

I am moving Feature Classes up our stack.  Some of these have attachments, Editor Tracking, Archiving some dont

When I use COPY in my python script it disables Archiving and as such screws up the Attribute indexes on Feature Class and the accompanying Attachments etc.  

I am trying to find the best way to fix everything the COPY has disconnected/disabled/destroyed.  I could DIABLE Editor Tracking and attachments and then ENABLE Editor Tracking then Attachments then Archiving. 

When I go to publish in Survey123 (referencing this FC in Portal that resides on my oracle server, NOT hosted) I am still getting errors that "The Supports ApplyEdits with Global IDs parameter is set to false"

I am now up in the stack where I no longer have access to the DBs. And all the examples I am seeing are to rebuild indexes with the tool etc.... I do not have access to modify them via Catalog or Pro  VERY FRUSTRATING...

Is there a process that I can run that actually copies the Feature Classes, attachments, other configs etc to a new DB that actually works? 

Any thoughts would be appreciated.

0 Kudos
1 Solution

Accepted Solutions
kapalczynski
Frequent Contributor

This is how I did it... 

  • COPY feature classes 
  • Set Permissions
  • Deleted Indexes made on GLOBALID
  • Create New indexes with SAME name on GLOBAL ID
  • Enable Archiving

Hope this helps someone out... 

This has eliminated the error I was getting when only a copy was done... they key is to rebuild the broken indexes and enabling archiving..

 

layers_to_Copy variable is a dictionary that provides the From and To datasets to copy

layers_to_Index variable is a dictionary that defines the layers and attribute tables to delete and rebuild indexes on

user_permissions_toSet variable is a dictionary that defines the users to set permissions for...the first part of the dictionary alerts the script to whether or not is a view or edit user... the second apart is the actual user name

 

# -*- coding: utf-8 -*-
# -----------------------------------------------------------------------------------------------------------
# Feature Class migration from One DB to Another - Permissions, Index Rebuild, Archving Enabled
# Created on: 2023-03-22
# Description:
#           This script will migrate Feature Classes from one Db to Another for those included in 'layers_to_Copy'
#           Permissions will be granted to those in the Dictionary below 'user_permissions_toSet'
#           Indexes for GlobalID will be deleted and recreated on the FCs in the Dictionary 'layers_to_Index'
#           Finally Archiving will be enabled on the New Feature Classes for those included in 'layers_to_Copy'
#
# THIS SCRIPT ASSUMES:
#   That the users used to set permissions will have VIEW or EDIT in their names
#   VIEW and EDIT keys are used to determine wether they are given view or edit permissions
# -----------------------------------------------------------------------------------------------------------

# --Import arcpy module--------------------------------------------------------------------------------------
import arcpy
import json
import sys


# --Variables to modify--------------------------------------------------------------------------------------

layers_to_Copy = {
"Database Connections\\GIS_DATA@_From.sde\\GIS_DATA.SDE_FC1": "Database Connections\\GIS_DATA@_To.sde\\GIS_DATA.SDE_FC1",
"Database Connections\\GIS_DATA@_From.sde\\GIS_DATA.SDE_FC2": "Database Connections\\GIS_DATA@_To.sde\\GIS_DATA.SDE_FC2"
}

layers_to_Index = {
"FC1": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC1",
"FC1Attach": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC1__ATTACH",
"FC2": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC2",
"FC2Attach": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC2__ATTACH"
}

# Define the User Accounts that need to be given permissions
user_permissions_toSet = {
"VIEW": "ViewUser",
"EDIT": "EditUser",
"VIEW": "gis_guest"
}

# -------------------------------------
# -----DONT EDIT BELOW THIS LINE --------------------------------------------------------------------------------
# -------------------------------------





# -----COPY------------------------------------------------------------------------------------------------------

def verifyFCAbsent():
    print("")
    print("VERIFY DATASETS DO NOT EXIST IN NEW DB")
    print("")
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        fc = toFeatureClass
        if arcpy.Exists(fc):
            print(fc)
            print("This Feature Class already exists, Exiting the Program")
            sys.exit()
   
def copyFeatures():
    print("-------------------------------------------")
    print("process - COPYING FEATURES")
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        print("Starting to copy " + fromFeatureClass)
        print("To new location " + toFeatureClass)       
        # Loop and Copy Feature Class to new Database
        arcpy.Copy_management(fromFeatureClass, toFeatureClass)
        print("Finished Copying " + fromFeatureClass + " to its new location")
        print("")
    print("-------------------------------------------")

def changePrivileges():
    print("")
    print("process - GRANTING PERMISSIONS")
    print("")
    count = 0
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        for user in user_permissions_toSet.keys():
            userName = user
            userToSet = user_permissions_toSet[user]
            #print(toFeatureClass)
            if "VIEW" in user:
                print(userToSet)
                arcpy.ChangePrivileges_management(toFeatureClass, userToSet, "GRANT","")
                print("-View Permissions Granted " + "to " + toFeatureClass)
            if "EDIT" in user:
                print(userToSet)
                arcpy.ChangePrivileges_management(toFeatureClass, userToSet, "GRANT","GRANT")
                print("-Edit Permissions Granted " + "to " + toFeatureClass)
        print("---------")
    print("Priviliges are granted moving on")
    print("-------------------------------------------")
   
    print("Script completed, exiting....")


# -----INDEXES------------------------------------------------------------------------------------------------------

def rebuildIndexes(): 
    print("")
    for layer in layers_to_Index.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Index[layer]
        listIndexes(toFeatureClass)
    print("Script Completed")

def listIndexes(p_toFeatureClass):
    featureclass = p_toFeatureClass
    # Get list of indexes for roads.shp and print properties
    indexes = arcpy.ListIndexes(featureclass)
    for index in indexes:
        for fieldname in index.fields:
            listofIndexes = []
            indexname = index.name
            ascending = index.isAscending
            isUnique = index.isUnique
            fieldname = fieldname.name
            listofIndexes.append(featureclass)
            listofIndexes.append(indexname)
            listofIndexes.append(ascending)
            listofIndexes.append(isUnique)
            listofIndexes.append(fieldname)
            if fieldname == "GLOBALID":
                infoIndexes(featureclass,listofIndexes)
            else:
                print("this is a SHAPE doing nothing")
                print("")                
        
def infoIndexes(featureclass,listofIndexes):
    print("GLOBALID Index Processing")
    pfeatureClass = featureclass
    arrayIndexes = listofIndexes
    featurename = str(arrayIndexes[0])
    indexname = str(arrayIndexes[1])
    ascending = arrayIndexes[2]
    isUnique = arrayIndexes[3]
    fieldName = str(arrayIndexes[4])
    print(featurename)
    print("   " + str(indexname))
    print("   " + str(ascending))
    print("   " + str(isUnique))
    print("   " + str(fieldName))
    print("")
    deleteIndexes(pfeatureClass,featurename,indexname,fieldName)

def deleteIndexes(pfeatureClass,deleteIndexesFeatureName,deleteIndexesName,deleteIndexesFieldName):
    rfeatureClass = pfeatureClass
    deleteIndexFeatureName = deleteIndexesFeatureName
    deleteIndexName = deleteIndexesName
    deleteFieldName = deleteIndexesFieldName
    print("-----------")
    print("Deleting FC index : {0}".format(rfeatureClass))
    print("Deleting Index    : {0} on field {1}".format(deleteIndexName,deleteFieldName))
    print("")
    arcpy.RemoveIndex_management(rfeatureClass, [deleteIndexName])
    rebuildingIndexes(rfeatureClass,deleteIndexFeatureName,deleteIndexName,deleteFieldName)
    
def rebuildingIndexes(rfeatureClass,deleteIndexFeatureName,deleteIndexName,deleteFieldName):
    ffeatureClass = rfeatureClass
    rebuildIndexFeatureName = deleteIndexFeatureName
    rebuildIndexName = str(deleteIndexName)
    rebuildFieldName = deleteFieldName
    print("Rebuilding FC     : {0}".format(ffeatureClass))
    print("Rebuiling Index   : {0} on field {1}".format(rebuildIndexName,rebuildFieldName))    
    print("-----------") 
    arcpy.AddIndex_management(ffeatureClass, ["GLOBALID"], rebuildIndexName, "UNIQUE", "ASCENDING")


# -----ARCHIVING------------------------------------------------------------------------------------------------------
def enableArchiving(): 
    print("")
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        turnonArchiving(toFeatureClass)
    print("Script Completed")

def turnonArchiving(p_toFeatureClass):
    print("")
    print("process - ARCHIVING REVIEW")
    rebuildArchiveFC = p_toFeatureClass
    print("---Enabling Archiving on " + rebuildArchiveFC)
    arcpy.management.EnableArchiving(rebuildArchiveFC)
    print("---DONE - Enabling Archiving on " + rebuildArchiveFC)

          
if __name__ == '__main__':

    # Verify Feature Classes do not exist in new DB
    verifyFCAbsent()
    ## Copy Features
    copyFeatures()
    ## Grant Priviliges
    changePrivileges()
    # REBUILDING INDEXES
    rebuildIndexes()
    # ENABLE ARCHIVING
    enableArchiving()

 

 

 

View solution in original post

2 Replies
BlakeTerhune
MVP Regular Contributor

Maybe Geodatabase Replication is what you need.

0 Kudos
kapalczynski
Frequent Contributor

This is how I did it... 

  • COPY feature classes 
  • Set Permissions
  • Deleted Indexes made on GLOBALID
  • Create New indexes with SAME name on GLOBAL ID
  • Enable Archiving

Hope this helps someone out... 

This has eliminated the error I was getting when only a copy was done... they key is to rebuild the broken indexes and enabling archiving..

 

layers_to_Copy variable is a dictionary that provides the From and To datasets to copy

layers_to_Index variable is a dictionary that defines the layers and attribute tables to delete and rebuild indexes on

user_permissions_toSet variable is a dictionary that defines the users to set permissions for...the first part of the dictionary alerts the script to whether or not is a view or edit user... the second apart is the actual user name

 

# -*- coding: utf-8 -*-
# -----------------------------------------------------------------------------------------------------------
# Feature Class migration from One DB to Another - Permissions, Index Rebuild, Archving Enabled
# Created on: 2023-03-22
# Description:
#           This script will migrate Feature Classes from one Db to Another for those included in 'layers_to_Copy'
#           Permissions will be granted to those in the Dictionary below 'user_permissions_toSet'
#           Indexes for GlobalID will be deleted and recreated on the FCs in the Dictionary 'layers_to_Index'
#           Finally Archiving will be enabled on the New Feature Classes for those included in 'layers_to_Copy'
#
# THIS SCRIPT ASSUMES:
#   That the users used to set permissions will have VIEW or EDIT in their names
#   VIEW and EDIT keys are used to determine wether they are given view or edit permissions
# -----------------------------------------------------------------------------------------------------------

# --Import arcpy module--------------------------------------------------------------------------------------
import arcpy
import json
import sys


# --Variables to modify--------------------------------------------------------------------------------------

layers_to_Copy = {
"Database Connections\\GIS_DATA@_From.sde\\GIS_DATA.SDE_FC1": "Database Connections\\GIS_DATA@_To.sde\\GIS_DATA.SDE_FC1",
"Database Connections\\GIS_DATA@_From.sde\\GIS_DATA.SDE_FC2": "Database Connections\\GIS_DATA@_To.sde\\GIS_DATA.SDE_FC2"
}

layers_to_Index = {
"FC1": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC1",
"FC1Attach": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC1__ATTACH",
"FC2": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC2",
"FC2Attach": "Database Connections\\GIS_DATA_To.sde\\GIS_DATA.SDE_FC2__ATTACH"
}

# Define the User Accounts that need to be given permissions
user_permissions_toSet = {
"VIEW": "ViewUser",
"EDIT": "EditUser",
"VIEW": "gis_guest"
}

# -------------------------------------
# -----DONT EDIT BELOW THIS LINE --------------------------------------------------------------------------------
# -------------------------------------





# -----COPY------------------------------------------------------------------------------------------------------

def verifyFCAbsent():
    print("")
    print("VERIFY DATASETS DO NOT EXIST IN NEW DB")
    print("")
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        fc = toFeatureClass
        if arcpy.Exists(fc):
            print(fc)
            print("This Feature Class already exists, Exiting the Program")
            sys.exit()
   
def copyFeatures():
    print("-------------------------------------------")
    print("process - COPYING FEATURES")
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        print("Starting to copy " + fromFeatureClass)
        print("To new location " + toFeatureClass)       
        # Loop and Copy Feature Class to new Database
        arcpy.Copy_management(fromFeatureClass, toFeatureClass)
        print("Finished Copying " + fromFeatureClass + " to its new location")
        print("")
    print("-------------------------------------------")

def changePrivileges():
    print("")
    print("process - GRANTING PERMISSIONS")
    print("")
    count = 0
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        for user in user_permissions_toSet.keys():
            userName = user
            userToSet = user_permissions_toSet[user]
            #print(toFeatureClass)
            if "VIEW" in user:
                print(userToSet)
                arcpy.ChangePrivileges_management(toFeatureClass, userToSet, "GRANT","")
                print("-View Permissions Granted " + "to " + toFeatureClass)
            if "EDIT" in user:
                print(userToSet)
                arcpy.ChangePrivileges_management(toFeatureClass, userToSet, "GRANT","GRANT")
                print("-Edit Permissions Granted " + "to " + toFeatureClass)
        print("---------")
    print("Priviliges are granted moving on")
    print("-------------------------------------------")
   
    print("Script completed, exiting....")


# -----INDEXES------------------------------------------------------------------------------------------------------

def rebuildIndexes(): 
    print("")
    for layer in layers_to_Index.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Index[layer]
        listIndexes(toFeatureClass)
    print("Script Completed")

def listIndexes(p_toFeatureClass):
    featureclass = p_toFeatureClass
    # Get list of indexes for roads.shp and print properties
    indexes = arcpy.ListIndexes(featureclass)
    for index in indexes:
        for fieldname in index.fields:
            listofIndexes = []
            indexname = index.name
            ascending = index.isAscending
            isUnique = index.isUnique
            fieldname = fieldname.name
            listofIndexes.append(featureclass)
            listofIndexes.append(indexname)
            listofIndexes.append(ascending)
            listofIndexes.append(isUnique)
            listofIndexes.append(fieldname)
            if fieldname == "GLOBALID":
                infoIndexes(featureclass,listofIndexes)
            else:
                print("this is a SHAPE doing nothing")
                print("")                
        
def infoIndexes(featureclass,listofIndexes):
    print("GLOBALID Index Processing")
    pfeatureClass = featureclass
    arrayIndexes = listofIndexes
    featurename = str(arrayIndexes[0])
    indexname = str(arrayIndexes[1])
    ascending = arrayIndexes[2]
    isUnique = arrayIndexes[3]
    fieldName = str(arrayIndexes[4])
    print(featurename)
    print("   " + str(indexname))
    print("   " + str(ascending))
    print("   " + str(isUnique))
    print("   " + str(fieldName))
    print("")
    deleteIndexes(pfeatureClass,featurename,indexname,fieldName)

def deleteIndexes(pfeatureClass,deleteIndexesFeatureName,deleteIndexesName,deleteIndexesFieldName):
    rfeatureClass = pfeatureClass
    deleteIndexFeatureName = deleteIndexesFeatureName
    deleteIndexName = deleteIndexesName
    deleteFieldName = deleteIndexesFieldName
    print("-----------")
    print("Deleting FC index : {0}".format(rfeatureClass))
    print("Deleting Index    : {0} on field {1}".format(deleteIndexName,deleteFieldName))
    print("")
    arcpy.RemoveIndex_management(rfeatureClass, [deleteIndexName])
    rebuildingIndexes(rfeatureClass,deleteIndexFeatureName,deleteIndexName,deleteFieldName)
    
def rebuildingIndexes(rfeatureClass,deleteIndexFeatureName,deleteIndexName,deleteFieldName):
    ffeatureClass = rfeatureClass
    rebuildIndexFeatureName = deleteIndexFeatureName
    rebuildIndexName = str(deleteIndexName)
    rebuildFieldName = deleteFieldName
    print("Rebuilding FC     : {0}".format(ffeatureClass))
    print("Rebuiling Index   : {0} on field {1}".format(rebuildIndexName,rebuildFieldName))    
    print("-----------") 
    arcpy.AddIndex_management(ffeatureClass, ["GLOBALID"], rebuildIndexName, "UNIQUE", "ASCENDING")


# -----ARCHIVING------------------------------------------------------------------------------------------------------
def enableArchiving(): 
    print("")
    for layer in layers_to_Copy.keys():
        fromFeatureClass = layer
        toFeatureClass = layers_to_Copy[layer]
        turnonArchiving(toFeatureClass)
    print("Script Completed")

def turnonArchiving(p_toFeatureClass):
    print("")
    print("process - ARCHIVING REVIEW")
    rebuildArchiveFC = p_toFeatureClass
    print("---Enabling Archiving on " + rebuildArchiveFC)
    arcpy.management.EnableArchiving(rebuildArchiveFC)
    print("---DONE - Enabling Archiving on " + rebuildArchiveFC)

          
if __name__ == '__main__':

    # Verify Feature Classes do not exist in new DB
    verifyFCAbsent()
    ## Copy Features
    copyFeatures()
    ## Grant Priviliges
    changePrivileges()
    # REBUILDING INDEXES
    rebuildIndexes()
    # ENABLE ARCHIVING
    enableArchiving()