This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

Sync Process Fails for User with Locked Property

Details

I'm currently testing methods of preventing updates on certain properties for specific users in our non-production environment. We have selected 'prohibit modification' for the CCC_JobCodeType property field on a test Person.

 

Configuration

  • We have a scheduled process that syncs employee data from a custom that is view built by a CSV to the Person table.
  • The custom view has a column called JobCodeType that passes through to Person.CCC_JobCodeType.

 

Requirements

  • If any column for that Person has modification prohibited, update only the properties that are not prohibited.

 

Results

  • The sync process will run and complete but the logs show that the users with one property prohibited from modification, failed to update.
  • Log error: Error in line 1317: [810025] Person: Write permission denied for value "CCC_JobCodeType".
  • Person record in Manager confirms that no other fields were updated due to the failure.

 

Question

  • I think that I need to modify the script that the custom sync process uses so that it checks if a property has modification prohibited and skips it instead of failing it completely. Would this solve the issue, and how would identify prohibited properties within the script?

 

Script

  • See attached.

 

CCC_Person_Import.txt
#If Not SCRIPTDEBUGGER Then
References VI.DataImport.dll

Imports System.Collections.Generic
Imports System.IO
Imports System.Globalization
Imports VI.DB.Entities
Imports VI.DB.Specialized
Imports VI.DataImport
#End If

Public Sub CCC_Person_Import (ByVal dfImport As DataFileImport)

	' Standard variables
	Dim logSection As IDisposable

	' Table
	Dim table = Connection.Tables("Person")

	' Line counter
	Dim counter As New LineCounter()
	
	' Value provider
	Dim lineData As New LineValueProvider(New String() {"ID", "FName", "LName", "SiteRegion", "OrigCostCenter", "ZeroFilledCostCenter", "Department", "employee_status", "Company", "DefaultYardID", "DefaultSiteID", "ExceptSiteID", "Title", "ExceptTitle", "ExceptTelephone", "ExceptFax", "UID_PersonHead","JobCode","JobCodeText", "JobCodeType", "", ""})

	' Import from an external database
	Dim lineProvider As ILineProvider
	Dim dbLineProvider As New DbLineProvider()
	dbLineProvider.ProviderName = "System.Data.SqlClient.SqlClientFactory, System.Data, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"
	dbLineProvider.ConnectionString = "Data Source=" + Connection.GetConfigParm("Custom\DataImport\EmployeeImport\dataSource") _
		+ ";Initial Catalog=" + Connection.GetConfigParm("Custom\DataImport\EmployeeImport\catalog") _
		+ ";User ID=" + Connection.GetConfigParm("Custom\DataImport\EmployeeImport\user") + ";Password=" + dfIMport.Options + ";Pooling=False"
	dbLineProvider.TimeZone = TimeZoneInfo.FindSystemTimeZoneById("Central Standard Time")

	' SQL statement
	Dim statement As New PlainSqlStatement()
	statement.Statement = "select ID,FName,LName,SiteRegion,OrigCostCenter,ZeroFilledCostCenter,Department,employee_status,Company,DefaultYardID,DefaultSiteID,ExceptSiteID,Title,ExceptTitle,ExceptTelephone,ExceptFax,UID_PersonHead,JobCode, JobCodeText, JobCodeType " & _
"  from [dbo].[CCC_D1_Employee_Build]"
                                  '0     1     2          3              4                    5          6               7       8             9            10           11    12          13               14       15              16     17           18           19
    'DefaultSiteID = CustomProperty08
	'ExceptSiteID = CustomProperty03

	dbLineProvider.Statement = statement
	lineProvider = dbLineProvider

	'
	' Configure column resolution
	'

	' Column indices
	Const iPersonnelNumber  = 0
	Const iFirstName        = 1
	Const iLastName         = 2	
	Const iCustomProperty02 = 3
	Const iCustomProperty04 = 4
	Const iUID_ProfitCenter = 5
	Const iUID_Department   = 6
	Const iCustomProperty10 = 7
	Const iCompanyMember    = 8
	Const iCustomProperty01 = 9
	Const iCustomProperty08 = 10
	Const iCustomProperty03 = 11
	Const iPersonalTitle    = 12
	Const iCustomProperty05 = 13
	Const iCustomProperty06 = 14
	Const iCustomProperty07 = 15
	Const iUID_PersonHead   = 16
	Const iCCC_JobCode      = 17
	Const iCCC_JobCodeText  = 18
	Const iCCC_JobCodeType  = 19
 
	
	' Resolver to get column data from import data
	Dim columnCompanyMember As IResolveImportValue = New ResolveImportValueSimple("CompanyMember")
	Dim columnCustomProperty01 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty01")
	Dim columnCustomProperty02 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty02")
	Dim columnCustomProperty03 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty03")
	Dim columnCustomProperty04 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty04")
	Dim columnCustomProperty05 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty05")
	Dim columnCustomProperty06 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty06")
	Dim columnCustomProperty07 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty07")
	Dim columnCustomProperty08 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty08")
	Dim columnCustomProperty09 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty09")
	Dim columnCustomProperty10 As IResolveImportValue = New ResolveImportValueSimple("CustomProperty10")
	Dim columnFirstName As IResolveImportValue = New ResolveImportValueSimple("FirstName")
	Dim columnLastName As IResolveImportValue = New ResolveImportValueSimple("LastName")
	Dim columnPersonalTitle As IResolveImportValue = New ResolveImportValueSimple("PersonalTitle")
	Dim columnPersonnelNumber As IResolveImportValue = New ResolveImportValueSimple("PersonnelNumber")

	' Build a dictionary: The last parameter forces exceptions when duplicate keys are found
	Dim columnUID_Department As New ResolveImportValueHashed( _
		Connection, _
		ObjectWalker.ColDefs(table, "FK(UID_Department).DepartmentName"), False)

	' Build a dictionary: The last parameter forces exceptions when duplicate keys are found
	Dim columnUID_Locality As New ResolveImportValueHashed( _
		Connection, _
		ObjectWalker.ColDefs(table, "FK(UID_Locality).Ident_locality"), False)
		
	' Build a dictionary: The last parameter forces exceptions when duplicate keys are found
	Dim columnUID_PersonHead As New ResolveImportValueHashed( _
		Connection, _
		ObjectWalker.ColDefs(table, "FK(UID_PersonHead).PersonnelNumber"), False)	
	
	'Dim columnUID_PersonHead As IResolveImportValue = New ResolveImportValueSimple("UID_PersonHead")
    Dim columnCCC_JobCode As IResolveImportValue = New ResolveImportValueSimple("CCC_JobCode")
	Dim columnCCC_JobCodeText As IResolveImportValue = New ResolveImportValueSimple("CCC_JobCodeText")
	Dim columnCCC_JobCodeType As IResolveImportValue = New ResolveImportValueSimple("CCC_JobCodeType")
	
	' Build a dictionary: The last parameter forces exceptions when duplicate keys are found
	Dim columnUID_ProfitCenter As New ResolveImportValueHashed( _
		Connection, _
		ObjectWalker.ColDefs(table, "FK(UID_ProfitCenter).AccountNumber"), False)

	Try

		'
		' Create a dictionary for the destination table
		'
		Dim colImport As IEntityCollection
		Dim elemsByKey As New Dictionary(Of String, IEntity)(StringComparer.OrdinalIgnoreCase)
		Dim imported As New HashSet(Of DbObjectKey)()

		logSection = dfImport.LogSection(#LD("Indexing existing data...")#)
		Try
			Dim query As Query = Query.From("Person").SelectNone()

			' Set keys and values as display items to load them with the collection
			query = query.Select("CompanyMember")
			query = query.Select("CustomProperty01")
			query = query.Select("CustomProperty02")
			query = query.Select("CustomProperty03")
			query = query.Select("CustomProperty04")
			query = query.Select("CustomProperty05")
			query = query.Select("CustomProperty06")
			query = query.Select("CustomProperty07")
			query = query.Select("CustomProperty08")
			query = query.Select("CustomProperty09")
			query = query.Select("CustomProperty10")
			query = query.Select("FirstName")
			query = query.Select("LastName")
			query = query.Select("PersonalTitle")
			query = query.Select("PersonnelNumber")
			query = query.Select("UID_Department")
			query = query.Select("UID_Locality")
			query = query.Select("UID_PersonHead")
			query = query.Select("UID_ProfitCenter")
			query = query.Select("xmarkedfordeletion")
			query = query.Select("CCC_JobCode")
			query = query.Select("CCC_JobCodeText")
			query = query.Select("CCC_JobCodeType")

			' Load the collection
			colImport = Session.Source().GetCollection(query, EntityCollectionLoadType.Slim)

			' Put the entries in the dictionary
			For Each elem In colImport
				Dim key As String

				key = elem.GetValue("PersonnelNumber").String

				If elemsByKey.ContainsKey(key) Then
					dfImport.Log(MsgSeverity.Serious, #LD("Duplicate key: {0}", key)#)
				Else
					elemsByKey.Add(key, elem)
				End If
			Next
		Finally
			If Not logSection Is Nothing Then
				logSection.Dispose()
				logSection = Nothing
			End If
		End Try

		logSection = dfImport.LogSection(#LD("Import data from file")#)
		Try
			For Each line As Line In lineProvider.GetLines(counter)

				' Pay attention to the Stop flag
				If StopProcessing Then
					dfImport.Log(MsgSeverity.Warning, #LD("Import was stopped.")#)
					Exit For
				End If

				Try
					' Get raw data from the current line
					Dim key As String

					line.Add("Fixed value")
					line.Add("Fixed value")
					
					Dim valCCC_JobCode As String
					Dim resCCC_JobCode As String
					
					Dim valCCC_JobCodeText As String
					Dim resCCC_JobCodeText As String
					
					Dim valCCC_JobCodeType As String
					Dim resCCC_JobCodeType As String

					Dim valCompanyMember As String
					Dim resCompanyMember As String

					Dim valCustomProperty01 As String
					Dim resCustomProperty01 As String
					
					Dim valCustomProperty02 As String
					Dim resCustomProperty02 As String

					Dim valCustomProperty03 As String
					Dim resCustomProperty03 As String

					Dim valCustomProperty04 As String
					Dim resCustomProperty04 As String

					Dim valCustomProperty05 As String
					Dim resCustomProperty05 As String

					Dim valCustomProperty06 As String
					Dim resCustomProperty06 As String

					Dim valCustomProperty07 As String
					Dim resCustomProperty07 As String

					Dim valCustomProperty08 As String
					Dim resCustomProperty08 As String
					
					Dim valCustomProperty09 As String
					Dim resCustomProperty09 As String
					
					Dim valCustomProperty10 As String
					Dim resCustomProperty10 As String

					Dim valFirstName As String
					Dim resFirstName As String

					Dim valLastName As String
					Dim resLastName As String

					Dim valPersonalTitle As String
					Dim resPersonalTitle As String

					Dim valPersonnelNumber As String
					Dim resPersonnelNumber As String

					Dim valUID_Department As String
					Dim resUID_Department As String

					Dim valUID_Locality As String
					Dim resUID_Locality As String

					Dim valUID_PersonHead As String
					Dim resUID_PersonHead As String

					Dim valUID_ProfitCenter As String
					Dim resUID_ProfitCenter As String
						valCompanyMember = line.GetValue(iCompanyMember)
						valCustomProperty01 = line.GetValue(iCustomProperty01)
						valCustomProperty02 = line.GetValue(iCustomProperty02)
						valCustomProperty03 = line.GetValue(iCustomProperty03)
						valCustomProperty04 = line.GetValue(iCustomProperty04)
						valCustomProperty05 = line.GetValue(iCustomProperty05)
						valCustomProperty06 = line.GetValue(iCustomProperty06)
						valCustomProperty07 = line.GetValue(iCustomProperty07)
						valCustomProperty08 = line.GetValue(iCustomProperty08)
						valCustomProperty09 = "Fixed value"
						valCustomProperty10 = line.GetValue(iCustomProperty10)
						valFirstName = line.GetValue(iFirstName)
						valLastName = line.GetValue(iLastName)
						valPersonalTitle = line.GetValue(iPersonalTitle)
						valPersonnelNumber = line.GetValue(iPersonnelNumber)
						valUID_Department = line.GetValue(iUID_Department)
						valUID_Locality = "Fixed value"
						valUID_PersonHead = line.GetValue(iUID_PersonHead)
						valUID_ProfitCenter = line.GetValue(iUID_ProfitCenter)
						valCCC_JobCode = line.GetValue(iCCC_JobCode)
						valCCC_JobCodeText = line.GetValue(iCCC_JobCodeText)
						valCCC_JobCodeType = line.GetValue(iCCC_JobCodeType)

						'
						' Here is the place to check and change raw data
						'
						lineData.Line = line
						
						Value = valCustomProperty09
						
						' Start of convert script for CustomProperty09
						Value="Feed Employee"
						' End of convert script for CustomProperty09
						
						valCustomProperty09 = DbVal.ConvertTo(Of String)(Value)
						
						'DefaultSiteID = CustomProperty08
						'ExceptSiteID = CustomProperty03
						
						Value = valUID_Locality
						'VID_WRITE2LOG("\\DC1IAMOPSQAS01\c$\working\Data_Import_Logs\personimport_locality.log", "Locality value = " & valUID_Locality)
						'VID_WRITE2LOG("\\DC1IAMOPSQAS01\c$\working\Data_Import_Logs\personimport_locality.log", "ExceptSiteID   = " & valCustomProperty03)
						'VID_WRITE2LOG("\\DC1IAMOPSQAS01\c$\working\Data_Import_Logs\personimport_locality.log", "DefaultSiteID  = " & valCustomProperty08)
						' Start of convert script for UID_Locality
						If Not String.IsNullOrEmpty(valCustomProperty03)
							'Value = line.GetValue("ExceptSiteID").String
							Value = valCustomProperty03
						Else
							'Value = GetValue("DefaultSiteID").String
							Value = valCustomProperty08
						End If
						' End of convert script for UID_Locality
						
						valUID_Locality = DbVal.ConvertTo(Of String)(Value)
						'VID_WRITE2LOG("\\DC1IAMOPSQAS01\c$\working\Data_Import_Logs\personimport_locality.log", "Ending value = " & valUID_Locality)
						
						' Convert raw data to final column data values
						resCompanyMember = DbVal.ConvertTo(Of String)(columnCompanyMember.ResolveValue(valCompanyMember), lineProvider.Culture)
						resCustomProperty01 = DbVal.ConvertTo(Of String)(columnCustomProperty01.ResolveValue(valCustomProperty01), lineProvider.Culture)
						resCustomProperty02 = DbVal.ConvertTo(Of String)(columnCustomProperty02.ResolveValue(valCustomProperty02), lineProvider.Culture)
						resCustomProperty03 = DbVal.ConvertTo(Of String)(columnCustomProperty03.ResolveValue(valCustomProperty03), lineProvider.Culture)
						resCustomProperty04 = DbVal.ConvertTo(Of String)(columnCustomProperty04.ResolveValue(valCustomProperty04), lineProvider.Culture)
						resCustomProperty05 = DbVal.ConvertTo(Of String)(columnCustomProperty05.ResolveValue(valCustomProperty05), lineProvider.Culture)
						resCustomProperty06 = DbVal.ConvertTo(Of String)(columnCustomProperty06.ResolveValue(valCustomProperty06), lineProvider.Culture)
						resCustomProperty07 = DbVal.ConvertTo(Of String)(columnCustomProperty07.ResolveValue(valCustomProperty07), lineProvider.Culture)
						resCustomProperty08 = DbVal.ConvertTo(Of String)(columnCustomProperty08.ResolveValue(valCustomProperty08), lineProvider.Culture)
						resCustomProperty09 = DbVal.ConvertTo(Of String)(columnCustomProperty09.ResolveValue(valCustomProperty09), lineProvider.Culture)
						resCustomProperty10 = DbVal.ConvertTo(Of String)(columnCustomProperty10.ResolveValue(valCustomProperty10), lineProvider.Culture)
						resFirstName = DbVal.ConvertTo(Of String)(columnFirstName.ResolveValue(valFirstName), lineProvider.Culture)
						resLastName = DbVal.ConvertTo(Of String)(columnLastName.ResolveValue(valLastName), lineProvider.Culture)
						resPersonalTitle = DbVal.ConvertTo(Of String)(columnPersonalTitle.ResolveValue(valPersonalTitle), lineProvider.Culture)
						resPersonnelNumber = DbVal.ConvertTo(Of String)(columnPersonnelNumber.ResolveValue(valPersonnelNumber), lineProvider.Culture)
						resUID_Department = DbVal.ConvertTo(Of String)(columnUID_Department.ResolveValue(valUID_Department), lineProvider.Culture)
						resUID_Locality = DbVal.ConvertTo(Of String)(columnUID_Locality.ResolveValue(valUID_Locality), lineProvider.Culture)
						resUID_PersonHead = DbVal.ConvertTo(Of String)(columnUID_PersonHead.ResolveValue(valUID_PersonHead), lineProvider.Culture)
						resUID_ProfitCenter = DbVal.ConvertTo(Of String)(columnUID_ProfitCenter.ResolveValue(valUID_ProfitCenter), lineProvider.Culture)
						resCCC_JobCode = DbVal.ConvertTo(Of String)(columnCCC_JobCode.ResolveValue(valCCC_JobCode), lineProvider.Culture)
						resCCC_JobCodeText = DbVal.ConvertTo(Of String)(columnCCC_JobCodeText.ResolveValue(valCCC_JobCodeText), lineProvider.Culture)
						resCCC_JobCodeType = DbVal.ConvertTo(Of String)(columnCCC_JobCodeType.ResolveValue(valCCC_JobCodeType), lineProvider.Culture)
						
						'
						' Here is the place to check and change final column data
						'

						'
						' Here starts the standard handling. It is recommended to not change anything beyond this point.
						'

						'
						' Create key for this line
						'
						key = DbVal.ConvertTo(Of String)(resPersonnelNumber)
					Dim elem As IEntity = Nothing
					Dim entity As IEntity = Nothing

					If elemsByKey.TryGetValue(key, elem) Then
						'
						' Found -> Update
						'

						' Mark element for superset handling
						imported.Add(New DbObjectKey(table, elem))


						' Map values
						Dim fullEntity As New Lazy(Of IEntity)(Function() elem.Create(Session))

						If DbVal.Compare(elem.GetRaw("CompanyMember"), resCompanyMember, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CompanyMember", resCompanyMember)
						End If

						If DbVal.Compare(elem.GetRaw("CustomProperty01"), resCustomProperty01, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty01", resCustomProperty01)
						End If

						If DbVal.Compare(elem.GetRaw("CustomProperty02"), resCustomProperty02, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty02", resCustomProperty02)
						End If						
						
						If DbVal.Compare(elem.GetRaw("CustomProperty03"), resCustomProperty03, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty03", resCustomProperty03)
						End If

						If DbVal.Compare(elem.GetRaw("CustomProperty04"), resCustomProperty04, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty04", resCustomProperty04)
						End If

						If DbVal.Compare(elem.GetRaw("CustomProperty05"), resCustomProperty05, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty05", resCustomProperty05)
						End If

						If DbVal.Compare(elem.GetRaw("CustomProperty06"), resCustomProperty06, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty06", resCustomProperty06)
						End If

						If DbVal.Compare(elem.GetRaw("CustomProperty07"), resCustomProperty07, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty07", resCustomProperty07)
						End If

						If DbVal.Compare(elem.GetRaw("CustomProperty08"), resCustomProperty08, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty08", resCustomProperty08)
						End If
					
						If DbVal.Compare(elem.GetRaw("CustomProperty09"), resCustomProperty09, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty09", resCustomProperty09)
						End If
					
						If DbVal.Compare(elem.GetRaw("CustomProperty10"), resCustomProperty10, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CustomProperty10", resCustomProperty10)
						End If

						If DbVal.Compare(elem.GetRaw("FirstName"), resFirstName, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("FirstName", resFirstName)
						End If

						If DbVal.Compare(elem.GetRaw("LastName"), resLastName, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("LastName", resLastName)
						End If

						If DbVal.Compare(elem.GetRaw("PersonalTitle"), resPersonalTitle, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("PersonalTitle", resPersonalTitle)
						End If

						If DbVal.Compare(elem.GetRaw("UID_Department"), resUID_Department, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("UID_Department", resUID_Department)
						End If

						If DbVal.Compare(elem.GetRaw("UID_Locality"), resUID_Locality, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("UID_Locality", resUID_Locality)
						End If

						If DbVal.Compare(elem.GetRaw("UID_PersonHead"), resUID_PersonHead, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("UID_PersonHead", resUID_PersonHead)
						End If

						If DbVal.Compare(elem.GetRaw("UID_ProfitCenter"), resUID_ProfitCenter, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("UID_ProfitCenter", resUID_ProfitCenter)
						End If

						If DbVal.Compare(elem.GetRaw("CCC_JobCode"), resCCC_JobCode, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CCC_JobCode", resCCC_JobCode)
						End If
						
						If DbVal.Compare(elem.GetRaw("CCC_JobCodeText"), resCCC_JobCodeText, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CCC_JobCodeText", resCCC_JobCodeText)
						End If
						
						If DbVal.Compare(elem.GetRaw("CCC_JobCodeType"), resCCC_JobCodeType, ValType.String) <> 0 Then
							fullEntity.Value.PutValue("CCC_JobCodeType", resCCC_JobCodeType)
						End If
						
						If fullEntity.IsValueCreated Or elem.IsDeleted() Then

							entity = fullEntity.Value
						Else
							counter.Increment(LineType.Unchanged)
						End If

					Else
						'
						' Not found -> Insert
						'

						entity = Session.Source().CreateNew("Person")

						' Fill keys and values
						entity.PutValue("CompanyMember", resCompanyMember)
						entity.PutValue("CustomProperty01", resCustomProperty01)
						entity.PutValue("CustomProperty02", resCustomProperty02)
						entity.PutValue("CustomProperty03", resCustomProperty03)
						entity.PutValue("CustomProperty04", resCustomProperty04)
						entity.PutValue("CustomProperty05", resCustomProperty05)
						entity.PutValue("CustomProperty06", resCustomProperty06)
						entity.PutValue("CustomProperty07", resCustomProperty07)
						entity.PutValue("CustomProperty08", resCustomProperty08)
						entity.PutValue("CustomProperty09", resCustomProperty09)
						entity.PutValue("CustomProperty10", resCustomProperty10)
						entity.PutValue("FirstName", resFirstName)
						entity.PutValue("LastName", resLastName)
						entity.PutValue("PersonalTitle", resPersonalTitle)
						entity.PutValue("PersonnelNumber", resPersonnelNumber)
						entity.PutValue("UID_Department", resUID_Department)
						entity.PutValue("UID_Locality", resUID_Locality)
						entity.PutValue("UID_PersonHead", resUID_PersonHead)
						entity.PutValue("UID_ProfitCenter", resUID_ProfitCenter)
						entity.PutValue("CCC_JobCode", resCCC_JobCode)
						entity.PutValue("CCC_JobCodeText", resCCC_JobCodeText)
						entity.PutValue("CCC_JobCodeType", resCCC_JobCodeType)

					End If

					'
					' Additional values can be put into the entity here
					'

					If Not entity Is Nothing Then

						If entity.IsDeleted() Then
							' Recall deleted entity
							entity.MarkForRecall()
						End If

						Dim isUpdate As Boolean = entity.IsLoaded

						' Save it
						If entity.IsDifferent Then
							entity.Save(Session)

							If isUpdate Then
								counter.Increment(LineType.Updated)
							Else
								counter.Increment(LineType.Inserted)
							End If
						Else
							counter.Increment(LineType.Unchanged)
						End If

						If elem Is Nothing Then
							' Include in our collection to avoid double imports of elements

							Dim keyInsert As String
							keyInsert = entity.GetValue("PersonnelNumber").String

							elemsByKey(keyInsert) = entity
							imported.Add(New DbObjectKey(table, entity))
						End If
					End If

				Catch ex As Exception
					dfImport.Log(MsgSeverity.Serious, #LD("Error in line {0}: {1}", counter(LineType.Total), ViException.ErrorString(ex))#)
					dfImport.Log(MsgSeverity.Serious, #LD("Line data was: {0}", line.ToString())#)

					counter.Increment(LineType.Error)
				End Try

				If (counter(LineType.Total) Mod 100) = 0 Then
					dfImport.SetProgressInfo(#LD("{0} lines imported, {1} ignored, {2} inserted, {3} updated, {4} errors", counter(LineType.Total), counter(LineType.Unchanged), counter(LineType.Inserted), counter(LineType.Updated), counter(LineType.Error))#)
				End If

			Next ' ForEach line

		Finally
			If Not logSection Is Nothing Then
				logSection.Dispose()
				logSection = Nothing
			End If
		End Try

		'
		' No superset handling
		'
	Finally

	End Try

	Using dfImport.LogSection(#LD("Results")#)
		dfImport.Log(#LD("{0} lines imported", counter(LineType.Total))#)
		dfImport.Log(#LD("{0} header lines", counter(LineType.Header))#)
		dfImport.Log(#LD("{0} inserted", counter(LineType.Inserted))#)
		dfImport.Log(#LD("{0} changed", counter(LineType.Updated))#)
		dfImport.Log(#LD("{0} deleted", counter(LineType.Deleted))#)
		dfImport.Log(#LD("{0} not changed", counter(LineType.Unchanged))#)
		dfImport.Log(#LD("{0} not found", counter(LineType.NotFound))#)
		dfImport.Log(#LD("{0} empty lines", counter(LineType.Empty))#)
		dfImport.Log(#LD("{0} errors", counter(LineType.Error))#)
	End Using
End Sub

  • Yes, you do need to modify your custom sync script but it is easy to detect the prohibited properties for your use-case.

    What you are really interested in is if you are allowed to edit a property. The object layer integrates the lock functionality into its permission handling, so that a test if a column is editable is sufficient to prevent writing to a locked property.

    In your case the test would be something like the following

    elem.Columns("CCC_JobCodeType").CanEdit = False

    In your import script I propose to do the check here

    If elem.Columns("CCC_JobCodeType").CanEdit AndAlso
    DbVal.Compare(elem.GetRaw("CCC_JobCode"), resCCC_JobCode, ValType.String) <> 0 Then
    fullEntity.Value.PutValue("CCC_JobCode", resCCC_JobCode)
    End If
  • This is great. Thank you. I was staring at this portion of the script trying to figure out what to add when I saw your reply come in. I will give this a try today and will come back to let you know the result.
  • It worked beautifully. Thank you for your help!
  • Sorry to re-open this. I just realized that when I applied the above to the script, the other properties updated for the test Person, but now it does not update that field for any user even if CCC_JobCodeType is not set to "prohibit modification" for that Person.
  • I think I have found a solution... After realizing what I mentioned in my previous comment (property was no longer updating for any Person even with no prohibited properties), I looked into where the data is stored for 'Prohibit Modification' and discovered the QBMLock table. Below are the details on what I did. I'm relatively new to this, so I welcome any advice about any better or "cleaner" ways of doing it. 

    Solution

    If DbVal.Compare(elem.GetRaw("CCC_JobCodeType"), resCCC_JobCodeType, ValType.String) <> 0 Then
        'Get the Column UID for current column
    	Dim ColumnUID As String = Session.Source().GetSingleValue(Of String)(Query.From("DialogColumn").Where(f.AndRelation(f.Comparison("UID_DialogTable", "QER-T-Person", ValType.String), f.Comparison("ColumnName","CCC_JobCodeType", ValType.String))).Select("UID_DialogColumn"))
    	'Get the value for UID_Person
    	Dim PersonUID As String = elem.GetValue("UID_Person")
    	'Check that the column is not in QBMLock
    	If Not Session.Source().Exists("QBMLock", f.AndRelation(f.Comparison("UID_DialogColumn", ColumnUID, ValType.String, CompareOperator.Equal,FormatterOptions.NonUnicodeLiterals), f.Comparison("ObjectKeyOfRow",  "%" + PersonUID + "%", ValType.String, CompareOperator.Like, FormatterOptions.NonUnicodeLiterals)))
    		fullEntity.Value.PutValue("CCC_JobCodeType", resCCC_JobCodeType)
    	End If
    End If

     

    Functionality Tested

    • Confirmed changes are made to CCC_JobCodeType through import process when Prohibit Modification is FALSE for that property on a Person.
    • Confirmed changes are NOT made to CCC_JobCodeType through import process when Prohibit Modification is TRUE for that property on a Person.
    • Confirmed all other properties are updated for Person through import process when Prohibit Modification is true on CCC_JobCodeType.
  • I think the shortest version would be to use TryPutValue instead of PutValue.

    If DbVal.Compare(elem.GetRaw("CCC_JobCodeType"), resCCC_JobCodeType, ValType.String) <> 0 Then
        fullEntity.Value.TryPutValue("CCC_JobCodeType", resCCC_JobCodeType)
    End If
    

    If you want to create a log entry if the value couldn't applied, add an if to test for the result of TryPutValue to be different than ApplyResult.Applied.

  • Thank you for this. I will not be able to test this immediately, but I will return once I do with the results. This looks much cleaner and simpler. Your help is very much appreciated.