<?php defined('BASEPATH') OR exit('No direct script access allowed');

class TransCompare {

/*
	public function __construct() {
		parent::__construct();
	}
*/
	private static function key_compare_func($a, $b)
	{
		if (is_array($a)) $a = json_encode($a);
		if (is_array($b)) $b = json_encode($b);

		if ($a === $b)
		{
			return 0;
		}

		return ($a > $b) ? 1:-1;
	}

	public static function recursive_array_diff_assoc($array1, $array2)
	{
		$difference = [];

		foreach ($array1 as $key => $value) {
		    if (array_key_exists($key, $array2)) {
		        if (is_array($value) && is_array($array2[$key])) {
		            $new_diff = self::recursive_array_diff_assoc($value, $array2[$key]);
		            if (!empty($new_diff)) {
		                $difference[$key] = $new_diff;
		            }
		        } elseif ($value !== $array2[$key]) {
		            $difference[$key] = $value;
		        }
		    } else {
		        $difference[$key] = $value;
		    }
		}

		return $difference;
	}

	private static function my_array_diff_uassoc($arr1, $arr2)
	{
		return array_diff_uassoc($arr1, $arr2, [self::class, 'key_compare_func']);
	}

	public static function Compare($oldRecord,$newRecord,$transId)
	{
		$logData = array();
		$jsonData = array();
		$skipAddressCheck = false;

		if (!empty($oldRecord) && !empty($newRecord))
		{
			$diff_old = self::recursive_array_diff_assoc($oldRecord['trans'], $newRecord['trans']);
			$diff_new = self::recursive_array_diff_assoc($newRecord['trans'], $oldRecord['trans']);

			// $diff_old = array_diff_uassoc($oldRecord['trans'], $newRecord['trans'], [self::class, 'key_compare_func']);
			// $diff_new = array_diff_uassoc($newRecord['trans'], $oldRecord['trans'], [self::class, 'key_compare_func']);

			$translog = array_merge_recursive($diff_old, $diff_new);

			$tType = $newRecord['trans']['tType'];
			$jsonData['id'] = $oldRecord['trans']['id'];
			foreach ($translog as $key => $val)
			{
				if ($key == 'conId')
				{
					$skipAddressCheck = true;
				}
				$jsonData['Field'][$key]['O'] = $val[0]; 
				$jsonData['Field'][$key]['N'] = $val[1];
			}

			if (!empty($newRecord['payModes']))
			{
				
				self::mergeTransNoIdFields($oldRecord['payModes'], $newRecord['payModes'], $tType, 'PaymentModes', 'accId', $jsonData);
			}

			if (!empty($newRecord['payment']))
			{
				self::mergeTransArrayFields($oldRecord['payment'], $newRecord['payment'], $tType, 'TransPayment', 'tNo', $jsonData);
			}
			if (!empty($newRecord['attachments']))
			{
				self::mergeTransArrayFields($oldRecord['attachments'], $newRecord['attachments'], $tType, 'attachments', 'fileName', $jsonData);
			}
			/* Trans Items*/
			if (!empty($newRecord['transItems']))
			{
				self::mergeTransArrayFields($oldRecord['transItems'], $newRecord['transItems'], $tType, 'Items', 'id', $jsonData, !empty($oldRecord['itemAttr']) ? $oldRecord['itemAttr'] : null, !empty($newRecord['itemAttr']) ? $newRecord['itemAttr'] : null);
			}
			/* Journal*/
			if (!empty($newRecord['journal']))
			{
				self::mergeTransArrayFields($oldRecord['journal'], $newRecord['journal'], $tType, 'TransAccount', 'id', $jsonData);
			}
			if (!empty($newRecord['expenses']))
			{
				self::mergeTransArrayFields($oldRecord['expenses'], $newRecord['expenses'], $tType, 'Expense/Payment', 'id', $jsonData);
			}
			/* Trans Fields*/
			if (!empty($newRecord['transFields']))
			{
				self::mergeTransArrayFields($oldRecord['transFields'], $newRecord['transFields'], $tType, 'transFields', 'fName', $jsonData);
			}

			/* Trans address*/
			if (empty($skipAddressCheck))
			{
				$oldTransAddress = array();
				$newTransAddress = array();

				if (!empty($oldRecord['transAddr']))
				{
					$oldTransAddress = array_column($oldRecord['transAddr'], 'addrType');
				}

				if (!empty($newRecord['transAddr']))
				{
					$newTransAddress = array_column($newRecord['transAddr'], 'addrType');
				}

				$TransAddresskeys = array_unique(array_merge($oldTransAddress, $newTransAddress));
				$loopCnt = 0;

				foreach ($TransAddresskeys as $key => $val)
				{
					$nIndex = array_search($val, $newTransAddress);
					$oIndex = array_search($val, $oldTransAddress);

					if (is_numeric($nIndex) && is_numeric($oIndex) && $nIndex >= 0 && $oIndex >= 0)
					{
						$diff_old = self::recursive_array_diff_assoc($oldRecord['transAddr'][$oIndex], $newRecord['transAddr'][$nIndex]);
						$diff_new = self::recursive_array_diff_assoc($newRecord['transAddr'][$nIndex], $oldRecord['transAddr'][$oIndex]);

						// $diff_old = array_diff_uassoc($oldRecord['transAddr'][$oIndex], $newRecord['transAddr'][$nIndex], [self::class, 'key_compare_func']);
						// $diff_new = array_diff_uassoc($newRecord['transAddr'][$nIndex], $oldRecord['transAddr'][$oIndex], [self::class, 'key_compare_func']);

						if (!empty($diff_old) && !empty($diff_new))
						{
							$cusFieldlog = array_merge_recursive($diff_old, $diff_new);
							$jsonData['TransAddress'][$loopCnt]['Type'] = $val;
							$jsonData['TransAddress'][$loopCnt]['Action'] = 'M';
							foreach ($cusFieldlog as $ikey => $ival)
							{
								$jsonData['TransAddress'][$loopCnt]['Field'][$ikey]['O'] = $ival[0] ;
								$jsonData['TransAddress'][$loopCnt]['Field'][$ikey]['N'] = $ival[1] ;
							}
							$loopCnt++;
						}
					}
					else
					{
						$jsonData['TransAddress']['N'] = $newRecord['transAddr'];
						$jsonData['TransAddress']['O'] = $oldRecord['transAddr'];
					}
				}
			}
			$logData['trans'][] = $jsonData;
		}
		else if (!empty($oldRecord) && $oldRecord)
		{
			$jsonData['Action'] = 'D';
			$tType = $oldRecord['trans']['tType'];

			foreach ($oldRecord['trans'] as $key => $val)
			{
				if ($key != 'id' && !empty($val) && (!is_numeric($val) || (float)$val != 0))
				{
					$jsonData['Field'][$key] =  $val;
				}
			}

			if (!empty($oldRecord['transItems']))
			{
				foreach ($oldRecord['transItems'] as $key => $val)
				{
					$jsonData['Items'][$key]['ItemName'] = $val['ItemName'];
					foreach ($val as $tkey => $tval)
					{
						if ($tkey == 'itemAttrId' && !empty($tval) && $oldRecord['itemAttr'] && array_key_exists($tval, $oldRecord['itemAttr']))
						{
							$sep = '';
							$attributes = '';
							foreach($oldRecord['itemAttr'][$val['itemAttrId']] as $akey => $aval)
							{
								$attributes .= $sep .$aval;
								$sep = '|';
							}
							$jsonData['Items'][$key]['Field'][]['attribute'] = $attributes;
						}
						else if($tkey != 'id' && !empty($tval) && (!is_numeric($tval) || (float)$tval != 0))
						{
							$jsonData['Items'][$key]['Field'][][$tkey] = $tval;
						}
					}
				}
			}

			if (!empty($oldRecord['transAddr']))
			{
				foreach ($oldRecord['transAddr'] as $key => $val)
				{
					$jsonData['TransAddress'][$key]['Type'] = $val['addrType'];
					foreach ($val as $tkey => $tval)
					{
						if (!empty($tval) && (!is_numeric($tval) || (float)$tval != 0))
						{
							$jsonData['TransAddress'][$key]['Field'][][$tkey] = $tval;
						}
					}
				}
			}

			if (!empty($oldRecord['payModes']))
			{
				foreach ($oldRecord['payModes'] as $key => $val)
				{
					$accountType = ($tType =='PP' || $tType == 'PE') ? 'PaidfromAccount' : 'DepositAccount';
					$jsonData['PaymentModes'][$key ][$accountType] = $val['AccountName'];
					foreach ($val as $pkey => $pval)
					{
						if(!empty($pval) && $pkey != 'accId' && (!is_numeric($pval) || (float)$pval != 0))
						{
							$jsonData['PaymentModes'][$key ]['Field'][][$pkey] = $pval;
						}
					}
				}
			}

			if (!empty($oldRecord['transFields']))
			{
				$jsonData['Field']['customFields'] = $oldRecord['transFields'];
			}

			if (!empty($oldRecord['attachments']))
			{
				$jsonData['Field']['attachments'] = $oldRecord['attachments'];
			}

			if (!empty($oldRecord['journal']))
			{
				foreach ($oldRecord['journal'] as $key => $val)
				{
					$jsonData['TransAccount'][$key ]['Account'] = ($val['accCode'] == 'AR' || $val['accCode'] == 'AP') ? $val['Contact'] : $val['accName'];
					unset($val['id']);
					unset($val['accCode']);
					foreach ($val as $pkey => $pval)
					{
						if (!empty($pval) && (!is_numeric($pval) || (float)$pval != 0))
						{
							$jsonData['TransAccount'][$key ]['Field'][][$pkey] = $pval;
						}
					}
				}
			}

			if (!empty($oldRecord['expenses']))
			{
				foreach ($oldRecord['expenses'] as $key => $val)
				{
					$jsonData['Expense/Payment'][$key ]['Account'] = $val['id'];
					unset($val['id']);

					foreach ($val as $pkey => $pval)
					{
						if (!empty($pval) && (!is_numeric($pval) || (float)$pval != 0))
						{
							$jsonData['Expense/Payment'][$key ]['Field'][][$pkey] = $pval;
						}
					}
				}
			}

			$logData['trans'][] = $jsonData;
		}

		return $logData;
		// self::TransModel->updateTransLog( json_encode($logData,JSON_UNESCAPED_SLASHES),$transId,$action);
	}

	private static function mergeTransNoIdFields($oldData, $newData, $tType, $type, $field, &$jsonData)
	{
		$oldFieldids = array_column($oldData, $field);
		$newFieldids = array_column($newData, $field);

		$loopCnt = 0;

		$uniqueFieldKeys = array_unique(array_merge($oldFieldids, $newFieldids));

		foreach ($uniqueFieldKeys as $key => $val)
		{
			$nFieldIndexes = array_keys($newFieldids, $val);
			$oFieldIndexes = array_keys($oldFieldids, $val);

			$nindexCnt = sizeof($nFieldIndexes);
			$oindexCnt = sizeof($oFieldIndexes);

			$lcnt = ($nindexCnt<$oindexCnt) ? $oindexCnt : $nindexCnt;

			for($cnt=0;$cnt<$lcnt;$cnt++)
			{
				if(array_key_exists($cnt, $oFieldIndexes) && array_key_exists($cnt, $nFieldIndexes))
				{
					$diff_old = self::recursive_array_diff_assoc($oldData[$oFieldIndexes[$cnt]], $newData[$nFieldIndexes[$cnt]]);
					$diff_new = self::recursive_array_diff_assoc($newData[$nFieldIndexes[$cnt]], $oldData[$oFieldIndexes[$cnt]]);

					// $diff_old = array_diff_uassoc($oldData[$oFieldIndexes[$cnt]], $newData[$nFieldIndexes[$cnt]], [self::class, 'key_compare_func']);
					// $diff_new = array_diff_uassoc($newData[$nFieldIndexes[$cnt]], $oldData[$oFieldIndexes[$cnt]], [self::class, 'key_compare_func']);

					if(!empty($diff_old)&&!empty($diff_new))
					{
						$fieldlog = array_merge_recursive($diff_old, $diff_new);

						switch($type)
						{
							case 'PaymentModes':
								$accountType = ($tType == 'PP' || $tType == 'PE') ? 'PaidfromAccount' : 'DepositAccount';
								$jsonData[$type][$loopCnt][$accountType] = $newData[$nFieldIndexes[$cnt]]['AccountName'];
								$jsonData[$type][$loopCnt]['Action'] = 'M';

								foreach ($fieldlog as $ikey => $ival)
								{
									if( $ikey != 'accId')
									{
										$jsonData[$type][$loopCnt]['Field'][$ikey]['O'] = $ival[0];
										$jsonData[$type][$loopCnt]['Field'][$ikey]['N'] = $ival[1];
									}
								}
								$loopCnt++;
							break;
						}
					}
				}
				else if(array_key_exists($cnt, $oFieldIndexes))
				{
					$oIndex = $oFieldIndexes[$cnt];
					$oldData[$oIndex] = array_filter($oldData[$oIndex]);
					switch($type)
					{
						case 'PaymentModes':
							$accountType = ($tType =='PP' || $tType =='PE') ? 'PaidfromAccount' : 'DepositAccount';
							$jsonData[$type][$loopCnt][$accountType] = $oldData[$oIndex]['AccountName'];
							$jsonData[$type][$loopCnt]['Action'] = 'D';

							foreach ( $oldData[$oIndex] as $itkey => $itval)
							{
								if($itkey != 'accId' && !empty($itval) && (is_numeric($itval) && (float)$itval != 0))
								{
									$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
								}
							}

							$loopCnt++;
						break;
					
					}
				}
				else if (array_key_exists($cnt,$nFieldIndexes))
				{
					$nIndex = $nFieldIndexes[$cnt];
					$newData[$nIndex] = array_filter($newData[$nIndex]);
					switch($type)
					{
						case 'PaymentModes':
							$accountType = ($tType =='PP'||$tType =='PE') ? 'PaidfromAccount' : 'DepositAccount';
							$jsonData[$type][$loopCnt][$accountType] = $newData[$nIndex]['AccountName'];
							$jsonData[$type][$loopCnt]['Action'] = 'N';
							foreach ( $newData[$nIndex] as $itkey => $itval)
							{
								if($itkey!='accId' && !empty($itval) && (is_numeric($itval) && (float)$itval != 0))
								{
									$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
								}
							}
							$loopCnt++;
						break;
					}
				}
			}
		}
	}

	private static function mergeTransArrayFields($oldData, $newData, $tType, $type, $field, &$jsonData, $olditemAttr=array(), $newitemAttr=array())
	{
		$oldFieldids = array();
		$newFieldids = array();

		if(!empty($oldData) && $oldData != NULL )
		{
			$oldFieldids = array_column($oldData, $field);
		}

		if(!empty($newData) &&  $newData != NULL)
		{
			$newFieldids = array_column($newData, $field);
		}

		$loopCnt = 0;

		$uniqueFieldKeys = array_unique(array_merge($oldFieldids, $newFieldids));

		foreach ($uniqueFieldKeys as $key => $val)
		{
			$arOldAttr = array();
			$arNewAttr = array();
			$resArray = array();

			$nIndex = array_search($val,$newFieldids);
			$oIndex = array_search($val,$oldFieldids);

			if (is_numeric($nIndex) && is_numeric($oIndex) && $nIndex >=0 && $oIndex >=0)
			{
				$diff_old = self::recursive_array_diff_assoc($oldData[$oIndex], $newData[$nIndex]);
				$diff_new = self::recursive_array_diff_assoc($newData[$nIndex], $oldData[$oIndex]);

				// $diff_old = array_diff_uassoc($oldData[$oIndex], $newData[$nIndex],[self::class, 'key_compare_func']);
				// $diff_new = array_diff_uassoc($newData[$nIndex], $oldData[$oIndex],[self::class, 'key_compare_func']);

				if (!empty($diff_old) && !empty($diff_new))
				{
					$fieldlog = array_merge_recursive($diff_old, $diff_new);

					switch($type)
					{
						case 'transFields':
							foreach ($fieldlog as $ikey => $ival)
							{
								$fName = $oldData[$oIndex]['fName'];
								$jsonData['Field'][$fName ]['O'] = $ival[0];
								$jsonData['Field'][$fName ]['N'] = $ival[1];
							}
						break;
						case 'TransAccount':
							$jsonData[$type][$loopCnt]['Account'] = ($newData[$nIndex]['accCode']=='AR' || $newData[$nIndex]['accCode']=='AP') ? $newData[$nIndex]['Contact'] : $newData[$nIndex]['accName'];
							$jsonData[$type][$loopCnt]['Action'] = 'M';
							foreach ($fieldlog as $ikey => $ival)
							{
								$fName = $ikey;
								$jsonData[$type][$loopCnt]['Field'][$ikey]['O'] = $ival[0];
								$jsonData[$type][$loopCnt]['Field'][$ikey]['N'] = $ival[1];
							}
							$loopCnt++;
						break;
						case 'Expense/Payment':
							$jsonData[$type][$loopCnt]['Account'] = $newData[$nIndex]['id'];
							$jsonData[$type][$loopCnt]['Action'] = 'M';
							foreach ($fieldlog as $ikey => $ival)
							{
								$fName  = $ikey;
								$jsonData[$type][$loopCnt]['Field'][$ikey]['O'] = $ival[0];
								$jsonData[$type][$loopCnt]['Field'][$ikey]['N'] = $ival[1];
							}
							$loopCnt++;
						break;
						case 'TransPayment':
							$jsonData[$type][$loopCnt]['TransactionDesc'] = $newData[$nIndex]['TransactionDesc'];
							$jsonData[$type][$loopCnt]['Action'] = 'M';
							foreach ($fieldlog as $ikey => $ival)
							{
								$jsonData[$type][$loopCnt]['Field'][$ikey]['O'] = $ival[0];
								$jsonData[$type][$loopCnt]['Field'][$ikey]['N'] = $ival[1];
							}
							$loopCnt++;
						break;
						case 'Items':
							$jsonData[$type][$loopCnt]['TransItemId'] = $val;
							$jsonData[$type][$loopCnt]['ItemName'] = $newData[$nIndex]['ItemName'];
							$jsonData[$type][$loopCnt]['Action'] = 'M';
							foreach ($fieldlog as $ikey => $ival)
							{
								if ($ikey == 'itemAttrId')
								{
									continue;
								}
								$jsonData[$type][$loopCnt]['Field'][$ikey]['O'] = $ival[0] ;
								$jsonData[$type][$loopCnt]['Field'][$ikey]['N'] = $ival[1] ;
							}
							$arOldAttr = array();
							$arNewAttr = array();
							if(!empty($olditemAttr)&& !empty($olditemAttr[$oldData[$oIndex]['itemAttrId']]))
							{
								$arOldAttr = $olditemAttr[$oldData[$oIndex]['itemAttrId']];
							}
							if(!empty($newitemAttr)&& !empty($newitemAttr[$newData[$nIndex]['itemAttrId']]))
							{
								$arNewAttr = $newitemAttr[$newData[$nIndex]['itemAttrId']];
							}
							self::mergeTransFields($arOldAttr,$arNewAttr,1,'attribute',$resArray);
							if(!empty($resArray['Field']) && !empty($resArray['Field']['attribute']))
							{
								$jsonData[$type][$loopCnt]['Field']['attribute'] = $resArray['Field']['attribute'];
							}
							$loopCnt++;
						break;
						
						default:
							foreach ($fieldlog as $ikey => $ival)
							{
								$fName = $ikey;
								$jsonData['Field'][$fName ]['O'] = $ival[0];
								$jsonData['Field'][$fName ]['N'] = $ival[1];
							}
					}
				}
			}
			else if (is_numeric($nIndex) && $nIndex >=0)
			{
				$newData[$nIndex] = array_filter($newData[$nIndex]);
				$newData[$nIndex]['accCode'] = isset($newData[$nIndex]['accCode'])?$newData[$nIndex]['accCode']:'';
				switch($type)
				{
					case 'TransAccount':
						$jsonData[$type][$loopCnt]['Action'] = 'N';
						$jsonData[$type][$loopCnt]['Account'] = ($newData[$nIndex]['accCode']=='AR' || $newData[$nIndex]['accCode']=='AP') ? $newData[$nIndex]['Contact'] : $newData[$nIndex]['accName'];
						unset($newData[$nIndex]['id']);
						unset($newData[$nIndex]['accCode']);

						foreach ( $newData[$nIndex] as $itkey => $itval)
						{
							if(!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}
						$loopCnt++;
					break;
					case 'TransPayment':
						$jsonData[$type][$loopCnt]['TransactionDesc'] =  $newData[$nIndex]['TransactionDesc'];
						$jsonData[$type][$loopCnt]['Action'] = 'N';
						unset($newData[$nIndex]['tNo']);

						foreach ($newData[$nIndex] as $itkey => $itval)
						{
							if (!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}
						$loopCnt++;
					break;
					case 'Expense/Payment':
						$jsonData[$type][$loopCnt]['Account'] = $newData[$nIndex]['id'];
						$jsonData[$type][$loopCnt]['Action'] = 'N';

						unset($newData[$nIndex]['id']);
						foreach ( $newData[$nIndex] as $itkey => $itval)
						{
							if(!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}
						$loopCnt++;
					break;
					case 'Items':
						$jsonData[$type][$loopCnt]['TransItemId'] = $val;
						$jsonData[$type][$loopCnt]['ItemName'] = $newData[$nIndex]['ItemName'];
						$jsonData[$type][$loopCnt]['Action'] = 'N';
						if (!empty($newData[$nIndex]['itemAttrId']))
						{
							$itemAttrId = $newData[$nIndex]['itemAttrId'];
							unset($newData[$nIndex]['itemAttrId']);
						}

						unset($newData[$nIndex]['id']);
						unset($newData[$nIndex]['ItemName']);

						foreach ($newData[$nIndex] as $itkey => $itval)
						{
							if(!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}

						if (!empty($itemAttrId) && !empty($newitemAttr[$itemAttrId]))
						{
							$arNewAttr = $newitemAttr[$itemAttrId];
							self::mergeTransFields($arOldAttr,$arNewAttr,1,'attribute',$resArray);
						}

						if(!empty($resArray['Field']) && !empty($resArray['Field']['attribute']))
						{
							$jsonData[$type][$loopCnt]['Field'][]['attribute'] = $resArray['Field']['attribute'];
						}

						$loopCnt++;
					break;
					case 'transFields':
					default:
						$jsonData['Field'][$type]['N'][] = $newData[$nIndex];
					break;
				}
			}
			else if (is_numeric($oIndex) && $oIndex >= 0)
			{
				$oldData[$oIndex] = array_filter($oldData[$oIndex]);
				$oldData[$oIndex]['accCode'] = isset($oldData[$oIndex]['accCode'])?$oldData[$oIndex]['accCode']:'';
				switch($type)
				{
					case 'TransAccount':
						$jsonData[$type][$loopCnt]['Action'] = 'D';
						$jsonData[$type][$loopCnt]['Account'] = ($oldData[$oIndex]['accCode'] == 'AR' || $oldData[$oIndex]['accCode'] == 'AP') ? $oldData[$oIndex]['Contact'] : $oldData[$oIndex]['accName'];
						unset($oldData[$oIndex]['id']);
						unset($oldData[$oIndex]['accCode']);
						foreach ($oldData[$oIndex] as $itkey => $itval)
						{
							if (!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}
						$loopCnt++;
					break;
					case 'TransPayment':
						$jsonData[$type][$loopCnt]['TransactionDesc'] =  $oldData[$oIndex]['TransactionDesc'];
						$jsonData[$type][$loopCnt]['Action'] = 'D';
						unset($oldData[$oIndex]['tNo']);
						foreach ($oldData[$oIndex] as $itkey => $itval)
						{
							if(!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}
						$loopCnt++;
					break;
					case 'Expense/Payment':
						$jsonData[$type][$loopCnt]['Account'] =  $oldData[$oIndex]['id'];
						$jsonData[$type][$loopCnt]['Action'] = 'D';
						unset($oldData[$oIndex]['id']);
						foreach ( $oldData[$oIndex] as $itkey => $itval)
						{
							if(!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}
						$loopCnt++;
					break;
					case 'Items':
						$jsonData[$type][$loopCnt]['TransItemId'] = $val;
						$jsonData[$type][$loopCnt]['ItemName'] = $oldData[$oIndex]['ItemName'];
						$jsonData[$type][$loopCnt]['Action'] = 'D';
						if (!empty($oldData[$oIndex]['itemAttrId']))
						{
							$itemAttrId = $oldData[$oIndex]['itemAttrId'];
							unset($oldData[$oIndex]['itemAttrId']);
						}

						unset($oldData[$oIndex]['id']);
						unset($oldData[$oIndex]['ItemName']);

						foreach ($oldData[$oIndex] as $itkey => $itval)
						{
							if(!empty($itval) && (!is_numeric($itval) || (float)$itval != 0))
							{
								$jsonData[$type][$loopCnt]['Field'][][ $itkey] = $itval;
							}
						}

						if (!empty($itemAttrId) && !empty($olditemAttr[$itemAttrId]))
						{
							$arOldAttr = $olditemAttr[$itemAttrId];

							self::mergeTransFields($arOldAttr, $arNewAttr, 1, 'attribute', $resArray);
						}

						if(!empty($resArray['Field']) && !empty($resArray['Field']['attribute']))
						{
							$jsonData[$type][$loopCnt]['Field'][]['attribute'] = $resArray['Field']['attribute'];
						}

						$loopCnt++;
					break;
					case 'transFields':
					default:
						$jsonData['Field'][$type]['O'][] = $oldData[$oIndex];
					break;
				}
			}
		}
	}

	private static function mergeTransFields($oldData, $newData, $isStrFormat, $fieldType, &$jsonData)
	{
		$sep = '';
		if(!array_key_exists('Field',$jsonData)){
			$jsonData = ['Field'=>array()];
		}
		if(!empty($oldData) && !empty($newData))
		{
			$diff_old = self::recursive_array_diff_assoc($oldData, $newData);
			$diff_new = self::recursive_array_diff_assoc($newData, $oldData);

			// $diff_old = array_diff_uassoc($oldData, $newData,[self::class, 'key_compare_func']);
			// $diff_new = array_diff_uassoc($newData,$oldData,[self::class, 'key_compare_func']);

			if(!empty($diff_old) && !empty($diff_new))
			{
				$translog = array_merge_recursive($diff_old ,$diff_new );

				foreach ($translog as $ikey => $ival)
				{
					if($isStrFormat)
					{
						$jsonData['Field'][$fieldType]['O'] .= $sep.$ival[0];
						$jsonData['Field'][$fieldType]['N'] .= $sep.$ival[1] ;
						$sep = '|';
					}
					else
					{
						$jsonData['Field'][$ikey]['O'] = $ival[0] ;
						$jsonData['Field'][$ikey]['N'] = $ival[1] ;
					}
				}
			}
		}
		else if(!empty($oldData))
		{
			foreach ($oldData as $ikey => $ival)
			{
				if($isStrFormat && !empty($ival) && (!is_numeric($ival) || (float)$ival != 0))
				{
					if(array_key_exists($fieldType,$jsonData['Field'])){
						$jsonData['Field'][$fieldType] .= $sep . $ival;
					}else{
						$jsonData['Field'] = [$fieldType => $sep . $ival];
					}
					$sep = '|';
				}
				else if(!empty($ival) && (!is_numeric($ival) || (float)$ival != 0))
				{
					$jsonData['Field'][$ikey]['O'] = $ival;
					$jsonData['Field'][$ikey]['N'] = '';
				}
			}
		}
		else if(!empty($newData))
		{
			foreach ($newData as $ikey => $ival)
			{
				if ($isStrFormat && !empty($ival) && (!is_numeric($ival) || (float)$ival != 0))
				{
					if(array_key_exists($fieldType,$jsonData['Field'])){
						$jsonData['Field'][$fieldType] .= $sep . $ival;
					}else{
						$jsonData['Field'] = [$fieldType => $sep . $ival];
					}
					$sep = '|';
				}
				else if(!empty($ival) && (!is_numeric($ival) || (float)$ival != 0))
				{
					$jsonData['Field'][$ikey]['N'] = $ival;
					$jsonData['Field'][$ikey]['O'] = '';
				}
			}
		}
	}
}

