From 97c860c1c285c6dd189dbaa1eec6ee36a6482ff3 Mon Sep 17 00:00:00 2001
From: Kevin Kok Khah Whey <khahwhey.kok@3ds.com>
Date: 星期四, 12 十月 2023 19:19:37 +0800
Subject: [PATCH] Kevin: Modified logic of GlobalOTDTable.SetIsLinkedWithFinishedGoodAttributes method to fix some bugs.

---
 /dev/null                                                                                               |   91 -------------
 _Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDs.qbl                                             |    8 +
 _Main/BL/Type_Global_MappingProduct_MP/Attribute_IsLinkedWithFGCrossBusiness.qbl                        |    8 +
 _Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDsCrossBusiness.qbl                                |    8 +
 _Main/BL/Type_Global_MappingProduct_MP/Method_SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG.qbl |  167 +++++++++++++++++++++++
 _Main/BL/Type_Global_MappingOperation/Attribute_IsLinkedWithFGCrossBusiness.qbl                         |    8 +
 _Main/BL/Type_GlobalDTOTable/Method_SetIsLinkedWithFinishedGoodAttributes_DEBUG.qbl                     |   75 ++++++++++
 _Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMCountCrossBusiness.qbl                              |    8 +
 _Main/BL/Type_Global_MappingOperationBOM/Attribute_IsLinkedWithFGCrossBusiness.qbl                      |    8 +
 9 files changed, 290 insertions(+), 91 deletions(-)

diff --git a/_Main/BL/Type_GlobalDTOTable/Method_SetIsLinkedWithFinishedGoodAttributes.qbl b/_Main/BL/Type_GlobalDTOTable/Method_SetIsLinkedWithFinishedGoodAttributes.qbl
deleted file mode 100644
index 5a4ba17..0000000
--- a/_Main/BL/Type_GlobalDTOTable/Method_SetIsLinkedWithFinishedGoodAttributes.qbl
+++ /dev/null
@@ -1,45 +0,0 @@
-Quintiq file version 2.0
-#parent: #root
-Method SetIsLinkedWithFinishedGoodAttributes
-{
-  Description: 'Method to traverse the supply chain to determine if there are any products that are not used to produce finished goods.'
-  TextBody:
-  [*
-    // Reset IsLinkedWithFinishedGood
-    traverse( this, Global_MappingProduct_MP, instance )
-    {
-      instance.IsLinkedWithFinishedGood( false );
-    }
-    
-    traverse( this, Global_MappingOperation, instance )
-    {
-      instance.IsLinkedWithFinishedGood( false );
-    }
-    
-    traverse( this, Global_MappingOperationBOM, instance )
-    {
-      instance.IsLinkedWithFinishedGood( false );
-    }
-    
-    productspool := selectset( this, Global_MappingProduct_MP, product,
-                               product.ProductMajorType() <> "鎴愬搧" );
-    operationspool := this.Global_MappingOperation( relget );
-    operationbomspool := this.Global_MappingOperationBOM( relget );
-    
-    // Traverse each finished good and search for linked products/operations/lanes
-    traverse( this, Global_MappingProduct_MP, product,
-              product.ProductMajorType() = "鎴愬搧" )
-    {
-      uniquebomids := construct( Strings );
-      product.IsLinkedWithFinishedGood( false );
-      product.SetIsLinkedWithFinishedGoodAttributes_Recursive( 0, // depth
-                                                               100, // maxdepth
-                                                               productspool,
-                                                               operationspool,
-                                                               operationbomspool,
-                                                               uniquebomids );
-      uniquebomids := uniquebomids.Unique();
-      product.BOMCount( uniquebomids.Size() );
-    }
-  *]
-}
diff --git a/_Main/BL/Type_GlobalDTOTable/Method_SetIsLinkedWithFinishedGoodAttributes_DEBUG.qbl b/_Main/BL/Type_GlobalDTOTable/Method_SetIsLinkedWithFinishedGoodAttributes_DEBUG.qbl
new file mode 100644
index 0000000..09c33d2
--- /dev/null
+++ b/_Main/BL/Type_GlobalDTOTable/Method_SetIsLinkedWithFinishedGoodAttributes_DEBUG.qbl
@@ -0,0 +1,75 @@
+Quintiq file version 2.0
+#parent: #root
+Method SetIsLinkedWithFinishedGoodAttributes_DEBUG
+{
+  Description: 'Method to traverse the supply chain to determine if there are any products that are not used to produce finished goods.'
+  TextBody:
+  [*
+    // Reset IsLinkedWithFinishedGood
+    traverse( this, Global_MappingProduct_MP, instance )
+    {
+      instance.IsLinkedWithFinishedGood( false );
+      instance.BOMCount( 0 );
+      instance.BOMIDs( "" );
+      
+      instance.IsLinkedWithFGCrossBusiness( false );
+      instance.BOMCountCrossBusiness( 0 );
+      instance.BOMIDsCrossBusiness( "" );
+    }
+    
+    traverse( this, Global_MappingOperation, instance )
+    {
+      instance.IsLinkedWithFinishedGood( false );
+      instance.IsLinkedWithFGCrossBusiness( false );
+    }
+    
+    traverse( this, Global_MappingOperationBOM, instance )
+    {
+      instance.IsLinkedWithFinishedGood( false );
+      instance.IsLinkedWithFGCrossBusiness( false );
+    }
+    
+    finishedgoods := selectset( this, Global_MappingProduct_MP, product,
+                                product.ProductMajorType() = "鎴愬搧" );
+    numfinishedgoods := finishedgoods.Size();
+    index := 1;
+    
+    // Traverse each finished good and search for linked products/operations/lanes
+    traverse( finishedgoods, Elements, product )
+    {
+      if( not product.IsLinkedWithFinishedGood() )
+      {
+        info( "KKK", this.DefinitionName(), "SetIsLinkedWithFinishedGoodAttributes",
+              "| Processing Product:", product.ID(), "(", index, "/", numfinishedgoods, ")" );
+        uniquebomids := construct( Strings );
+        product.SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG( 0, // depth
+                                                                 100, // maxdepth
+                                                                 uniquebomids,
+                                                                 false // isallowcrossbusinesstype
+                                                               );
+        uniquebomids := uniquebomids.Difference( product.ID() ).Unique();
+        product.BOMCount( uniquebomids.Size() );
+        product.BOMIDs( uniquebomids.ToString( ";" ) );
+      }
+      
+      if( not product.IsLinkedWithFGCrossBusiness() )
+      {
+        info( "KKK", this.DefinitionName(), "SetIsLinkedWithFinishedGoodAttributes",
+              "| Processing Product (cross business type):", product.ID(), "(", index, "/", numfinishedgoods, ")" );
+        uniquebomidscrossbusiness := construct( Strings );
+        product.SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG( 0, // depth
+                                                                 100, // maxdepth
+                                                                 uniquebomidscrossbusiness,
+                                                                 true // isallowcrossbusinesstype
+                                                               );
+        uniquebomidscrossbusiness := uniquebomidscrossbusiness.Difference( product.ID() ).Unique();
+        product.BOMCountCrossBusiness( uniquebomidscrossbusiness.Size() );
+        product.BOMIDsCrossBusiness( uniquebomidscrossbusiness.ToString( ";" ) );
+      }
+      
+      index++;
+    }
+    
+    info( "KKK", this.DefinitionName(), "SetIsLinkedWithFinishedGoodAttributes", "| Ended." );
+  *]
+}
diff --git a/_Main/BL/Type_Global_MappingOperation/Attribute_IsLinkedWithFGCrossBusiness.qbl b/_Main/BL/Type_Global_MappingOperation/Attribute_IsLinkedWithFGCrossBusiness.qbl
new file mode 100644
index 0000000..5725fee
--- /dev/null
+++ b/_Main/BL/Type_Global_MappingOperation/Attribute_IsLinkedWithFGCrossBusiness.qbl
@@ -0,0 +1,8 @@
+Quintiq file version 2.0
+#parent: #root
+Attribute IsLinkedWithFGCrossBusiness
+{
+  #keys: '3[157968.0.1171600004][157968.0.1171600003][157968.0.1171600005]'
+  Description: 'Updated procedurally for checking whether this object is used to produce a finished good cross business type.'
+  ValueType: Boolean
+}
diff --git a/_Main/BL/Type_Global_MappingOperationBOM/Attribute_IsLinkedWithFGCrossBusiness.qbl b/_Main/BL/Type_Global_MappingOperationBOM/Attribute_IsLinkedWithFGCrossBusiness.qbl
new file mode 100644
index 0000000..b20b273
--- /dev/null
+++ b/_Main/BL/Type_Global_MappingOperationBOM/Attribute_IsLinkedWithFGCrossBusiness.qbl
@@ -0,0 +1,8 @@
+Quintiq file version 2.0
+#parent: #root
+Attribute IsLinkedWithFGCrossBusiness
+{
+  #keys: '3[157968.0.1171600022][157968.0.1171600021][157968.0.1171600023]'
+  Description: 'Updated procedurally for checking whether this object is used to produce a finished good cross business type.'
+  ValueType: Boolean
+}
diff --git a/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMCountCrossBusiness.qbl b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMCountCrossBusiness.qbl
new file mode 100644
index 0000000..e85ba06
--- /dev/null
+++ b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMCountCrossBusiness.qbl
@@ -0,0 +1,8 @@
+Quintiq file version 2.0
+#parent: #root
+Attribute BOMCountCrossBusiness
+{
+  #keys: '3[157968.0.1171600059][157968.0.1171600058][157968.0.1171600060]'
+  Description: 'Number of unique BOM used to produce this finished good cross business types.'
+  ValueType: Number
+}
diff --git a/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDs.qbl b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDs.qbl
new file mode 100644
index 0000000..d4dcf3a
--- /dev/null
+++ b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDs.qbl
@@ -0,0 +1,8 @@
+Quintiq file version 2.0
+#parent: #root
+Attribute BOMIDs
+{
+  #keys: '3[157968.0.1171600062][157968.0.1171600061][157968.0.1171600063]'
+  Description: 'Unique BOM IDs used to produce this finished good.'
+  ValueType: String
+}
diff --git a/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDsCrossBusiness.qbl b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDsCrossBusiness.qbl
new file mode 100644
index 0000000..e48b8de
--- /dev/null
+++ b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_BOMIDsCrossBusiness.qbl
@@ -0,0 +1,8 @@
+Quintiq file version 2.0
+#parent: #root
+Attribute BOMIDsCrossBusiness
+{
+  #keys: '3[157968.0.1171600056][157968.0.1171600055][157968.0.1171600057]'
+  Description: 'Unique BOM IDs used to produce this finished good cross business types.'
+  ValueType: String
+}
diff --git a/_Main/BL/Type_Global_MappingProduct_MP/Attribute_IsLinkedWithFGCrossBusiness.qbl b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_IsLinkedWithFGCrossBusiness.qbl
new file mode 100644
index 0000000..2e2ebdc
--- /dev/null
+++ b/_Main/BL/Type_Global_MappingProduct_MP/Attribute_IsLinkedWithFGCrossBusiness.qbl
@@ -0,0 +1,8 @@
+Quintiq file version 2.0
+#parent: #root
+Attribute IsLinkedWithFGCrossBusiness
+{
+  #keys: '3[157968.0.1171600039][157968.0.1171600038][157968.0.1171600040]'
+  Description: 'Updated procedurally for checking whether this object is used to produce a finished good cross business type.'
+  ValueType: Boolean
+}
diff --git a/_Main/BL/Type_Global_MappingProduct_MP/Method_SetIsLinkedWithFinishedGoodAttributes_Recursive.qbl b/_Main/BL/Type_Global_MappingProduct_MP/Method_SetIsLinkedWithFinishedGoodAttributes_Recursive.qbl
deleted file mode 100644
index f0425fa..0000000
--- a/_Main/BL/Type_Global_MappingProduct_MP/Method_SetIsLinkedWithFinishedGoodAttributes_Recursive.qbl
+++ /dev/null
@@ -1,91 +0,0 @@
-Quintiq file version 2.0
-#parent: #root
-Method SetIsLinkedWithFinishedGoodAttributes_Recursive (
-  Number depth,
-  Number maxdepth,
-  Global_MappingProduct_MPs productspool,
-  Global_MappingOperations operationspool,
-  Global_MappingOperationBOMs operationbomspool,
-  output Strings uniquebomids_o
-)
-{
-  Description: 'Method to traverse the supply chain recursively to determine if there are any products that are not used to produce finished goods.'
-  TextBody:
-  [*
-    if( not this.IsLinkedWithFinishedGood() )
-    {
-      if( this.ProductMajorType() <> "鎴愬搧" )
-      {
-        uniquebomids_o.Add( this.ID() );
-      }
-      
-      depth := depth + 1;
-      this.IsLinkedWithFinishedGood( true );
-      
-      if( depth <= maxdepth )
-      {
-        operations := selectset( operationspool, Elements, operation,
-                                 not operation.IsLinkedWithFinishedGood()
-                                 and operation.BusinessType() = this.BusinessType()
-                                 and operation.ProductID() = this.ID() );
-        operationspool.Remove( operations );
-        
-        traverse( operations, Elements, operation )
-        {
-          operation.IsLinkedWithFinishedGood( true );
-          
-          operationboms := selectset( operationbomspool, Elements, operationbom,
-                                      not operationbom.IsLinkedWithFinishedGood()
-                                      and operationbom.BusinessType() = operation.BusinessType()
-                                      and operationbom.OrganCode() = operation.OrganCode()
-                                      and operationbom.ProcessSection() = operation.ProcessSection()
-                                      and operationbom.ProductCode() = operation.ProductID() );
-          operationbomspool.Remove( operationboms );
-          
-          traverse( operationboms, Elements, operationbom )
-          {
-            operationbom.IsLinkedWithFinishedGood( true );
-            
-            componentproduct := Global_MappingProduct_MP::FindTypeIndexIDAndBusinessType( operationbom.ComponentCode(),
-                                                                                          operationbom.BusinessType() );
-            
-            if( guard( not componentproduct.IsLinkedWithFinishedGood(), false ) )
-            {
-              productspool.Remove( componentproduct );
-              componentproduct.SetIsLinkedWithFinishedGoodAttributes_Recursive( depth,
-                                                                                maxdepth,
-                                                                                productspool,
-                                                                                operationspool,
-                                                                                operationbomspool,
-                                                                                uniquebomids_o );
-            }
-            
-            if( operationbom.AlternativeMaterialCode() <> ""
-                and operationbom.AlternativeMaterialCode() <> operationbom.ComponentCode() )
-            {
-              alternativeproduct := Global_MappingProduct_MP::FindTypeIndexIDAndBusinessType( operationbom.AlternativeMaterialCode(),
-                                                                                              operationbom.BusinessType() );
-              
-              if( guard( not alternativeproduct.IsLinkedWithFinishedGood(), false ) )
-              {
-                productspool.Remove( alternativeproduct );
-                alternativeproduct.SetIsLinkedWithFinishedGoodAttributes_Recursive( depth,
-                                                                                    maxdepth,
-                                                                                    productspool,
-                                                                                    operationspool,
-                                                                                    operationbomspool,
-                                                                                    uniquebomids_o );
-              }
-            }
-          }
-        }
-      }
-      else
-      {
-        debuginfo( "Product:", this.ID(),
-                   "| BusinessType:", this.BusinessType(),
-                   "| Max depth reached, stop searching... (", depth, ")" );
-      }
-    }
-  *]
-}
diff --git a/_Main/BL/Type_Global_MappingProduct_MP/Method_SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG.qbl b/_Main/BL/Type_Global_MappingProduct_MP/Method_SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG.qbl
new file mode 100644
index 0000000..9dc5d75
--- /dev/null
+++ b/_Main/BL/Type_Global_MappingProduct_MP/Method_SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG.qbl
@@ -0,0 +1,167 @@
+Quintiq file version 2.0
+#parent: #root
+Method SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG (
+  Number depth,
+  Number maxdepth,
+  output Strings uniquebomids_o,
+  Boolean isallowcrossbusinesstype
+)
+{
+  Description: 'Method to traverse the supply chain recursively to determine if there are any products that are not used to produce finished goods.'
+  TextBody:
+  [*
+    info( 'KKK2', this.DefinitionName(), "SetIsLinkedWithFinishedGoodAttributes_Recursive",
+          "| Depth:", depth,
+          "| Product:", this.ID(),
+          "| BusinessType:", this.BusinessType(),
+          "| isallowcrossbusinesstype:", isallowcrossbusinesstype,
+          "| IsLinkedWithFGCrossBusiness:", this.IsLinkedWithFGCrossBusiness(),
+          "| IsLinkedWithFinishedGood:", this.IsLinkedWithFinishedGood() );
+    if( ifexpr( isallowcrossbusinesstype,
+                not this.IsLinkedWithFGCrossBusiness(),
+                not this.IsLinkedWithFinishedGood() ) )
+    {
+      depthlocal := depth + 1;
+      
+      if( uniquebomids_o.Find( this.ID() ) < 0 )
+      {
+        uniquebomids_o.Add( this.ID() );
+      }
+      
+      if( isallowcrossbusinesstype )
+      {
+        this.IsLinkedWithFGCrossBusiness( true );
+      }
+      else
+      {
+        this.IsLinkedWithFinishedGood( true );
+      }
+      
+      if( depthlocal <= maxdepth )
+      {
+        uniquebomids_local := construct( Strings );
+        operations := selectset( this.GlobalOTDTable(), Global_MappingOperation, operation,
+                                 ( isallowcrossbusinesstype
+                                   or operation.BusinessType() = this.BusinessType() )
+                                 and operation.ProductID() = this.ID() );
+        
+        traverse( operations, Elements, operation )
+        {
+          if( isallowcrossbusinesstype )
+          {
+            operation.IsLinkedWithFGCrossBusiness( true );
+          }
+          else
+          {
+            operation.IsLinkedWithFinishedGood( true );
+          }
+          
+          operationboms := selectset( this.GlobalOTDTable(), Global_MappingOperationBOM, operationbom,
+                                      operationbom.BusinessType() = operation.BusinessType()
+                                      and operationbom.OrganCode() = operation.OrganCode()
+                                      and operationbom.ProcessSection() = operation.ProcessSection()
+                                      and operationbom.ProductCode() = operation.ProductID() );
+          
+          traverse( operationboms, Elements, operationbom )
+          {
+            if( isallowcrossbusinesstype )
+            {
+              operationbom.IsLinkedWithFGCrossBusiness( true );
+            }
+            else
+            {
+              operationbom.IsLinkedWithFinishedGood( true );
+            }
+            
+            traverse( this.GlobalOTDTable(), Global_MappingProduct_MP, componentproduct,
+                      componentproduct.ID() = operationbom.ComponentCode()
+                      and ( isallowcrossbusinesstype
+                            or componentproduct.BusinessType() = operationbom.BusinessType() ) )
+            {
+              componentproduct.SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG( depthlocal,
+                                                                                maxdepth,
+                                                                                uniquebomids_local,
+                                                                                isallowcrossbusinesstype );
+            }
+            
+            if( operationbom.AlternativeMaterialCode() <> ""
+                and operationbom.AlternativeMaterialCode() <> operationbom.ComponentCode() )
+            {
+              traverse( this.GlobalOTDTable(), Global_MappingProduct_MP, alternativeproduct,
+                        alternativeproduct.ID() = operationbom.AlternativeMaterialCode()
+                        and ( isallowcrossbusinesstype
+                              or alternativeproduct.BusinessType() = operationbom.BusinessType() ) )
+              {
+                alternativeproduct.SetIsLinkedWithFinishedGoodAttributes_Recursive_DEBUG( depthlocal,
+                                                                                    maxdepth,
+                                                                                    uniquebomids_local,
+                                                                                    isallowcrossbusinesstype );
+              }
+            }
+            
+            info( 'KKK2', this.DefinitionName(), "SetIsLinkedWithFinishedGoodAttributes_Recursive",
+                  "| Depth:", depthlocal - 1,
+                  "| BusinessType:", operation.BusinessType(),
+                  "| OrganCode:", operation.OrganCode(),
+                  "| ProcessSection:", operation.ProcessSection(),
+                  "| ProductID:", operation.ProductID(),
+                  "| isallowcrossbusinesstype:", isallowcrossbusinesstype,
+                  "| IsLinkedWithFGCrossBusiness:", this.IsLinkedWithFGCrossBusiness(),
+                  "| IsLinkedWithFinishedGood:", this.IsLinkedWithFinishedGood(),
+                  "| UniqueBOMIDs:", uniquebomids_local.Unique().ToString( ";" ) );
+          }
+        }
+        
+        uniquebomids := uniquebomids_local.Unique().Difference( this.ID() );
+        
+        if( isallowcrossbusinesstype )
+        {
+          this.BOMCountCrossBusiness( uniquebomids.Size() );
+          this.BOMIDsCrossBusiness( uniquebomids.ToString( ";" ) );
+        }
+        else
+        {
+          this.BOMCount( uniquebomids.Size() );
+          this.BOMIDs( uniquebomids.ToString( ";" ) );
+        }
+        
+        traverse( uniquebomids, Elements, uniquebomid,
+                  uniquebomids_o.Find( uniquebomid ) < 0 )
+        {
+          uniquebomids_o.Add( uniquebomid );
+        }
+      }
+      else
+      {
+        debuginfo( "Product:", this.ID(),
+                   "| BusinessType:", this.BusinessType(),
+                   "| IsAllowCrossBusinessType:", isallowcrossbusinesstype,
+                   "| Max depth reached, stop searching... (", depth, ")" );
+      }
+    }
+    else
+    {
+      if( uniquebomids_o.Find( this.ID() ) < 0 )
+      {
+        uniquebomids_o.Add( this.ID() );
+      }
+      
+      uniquebomids := construct( Strings );
+                
+      if( isallowcrossbusinesstype )
+      {
+        uniquebomids := this.BOMIDsCrossBusiness().Tokenize( ";" );
+      }
+      else
+      {
+        uniquebomids := this.BOMIDs().Tokenize( ";" );
+      }
+      
+      traverse( uniquebomids, Elements, uniquebomid,
+                uniquebomids_o.Find( uniquebomid ) < 0 )
+      {
+        uniquebomids_o.Add( uniquebomid );
+      }
+    }
+  *]
+}

--
Gitblit v1.9.3