Forum Discussion

GraemeLM's avatar
GraemeLM
Trusted Partner
5 months ago
Solved

Custom selector field working in one tenant, but errors in second tenant

I have a custom field working as expected in Tenant 1, but in other tenants it errors.

Publishing was performed using the Publish to Multiple Tenants button.

 

POOrder.CustomField is a selector showing a filtered list of Non-Stock Items belonging to a specific CUSTOMCLASS Item Class.

 

In Tenant 1, where the customisation was published from (to all tenants):
The selector correctly displays the list of items in the CUSTOMCLASS Item Class, allows selection in the custom field, and saves the Purchase Order without error.

 

In Tenant 2, the same custom field correctly displays the list of items (different items in this tenant, but still belonging to the matching named CUSTOMCLASS Item Class), allows selection in the custom field, but on save give this error: 'CustomField' cannot be found in the system.

 

Here is the DAC Extension:

  public class POOrderExt : PXCacheExtension<PX.Objects.PO.POOrder>
  {
    #region CustomField
    [PXDBString(50)]
    [PXUIField(DisplayName="Custom Field")]
    [PXSelector(
      typeof(Search<PX.Objects.IN.InventoryItem.inventoryCD
          , Where<PX.Objects.IN.InventoryItem.itemClassID, Equal<customfieldItemClassIdConstant>>>),
      typeof(PX.Objects.IN.InventoryItem.inventoryCD),
      typeof(PX.Objects.IN.InventoryItem.descr),
      DescriptionField=typeof(PX.Objects.IN.InventoryItem.descr))]
    public string CustomField { get; set; }
    public abstract class customField : IBqlField { }
    public class customfieldItemClassIdConstant : PX.Data.BQL.BqlInt.Constant<customfieldItemClassIdConstant>
    {
        public customfieldItemClassIdConstant()
            : base(FindCustomFieldItemClassID("CUSTOMCLASS")) { }
        
        public static int FindCustomFieldItemClassID(string itemClassCD)
        {
            PXResult<INItemClass> result = PXSelect<INItemClass,
                Where<INItemClass.itemClassCD, Equal<Required<INItemClass.itemClassCD>>>>
                .SelectWindowed(new PXGraph(), 0, 1, itemClassCD);
    
             if(result == null) return 0;

            INItemClass customfieldItemClass = result.GetItem<INItemClass>();
            if(customfieldItemClass == null)
            {
              return 0;
            }
            else
            {
              return customfieldItemClass?.ItemClassID ?? 0;
            }
        }
    }
    #endregion

 

I cant work out why it would work in one tenant, and not the others as the fields and selector is behaving as it should in all tenants, but the save of the selection is erroring, even though the database column is shared by all tenants.

  • Changed approach and used a different method to define the Item Class. Instead of using a constant in the code, created a custom checkbox on the Item Class, to flag it as the relevant class for the selector to show items of that class.

     

    Item Class DAC Extension:

    public class INItemClassExt : PXCacheExtension<PX.Objects.IN.INItemClass>
    {
      #region CustomItemClassFlag
      [PXDBBool]
      [PXUIField(DisplayName="Custom Item Class Flag")]
      public virtual Boolean? CustomItemClassFlag { get; set; }
      public abstract class customItemClassFlag : PX.Data.BQL.BqlBool.Field<customItemClassFlag> { }
      #endregion
    )


    Purchase Order DAC Extension:

    public class POOrderExt : PXCacheExtension<PX.Objects.PO.POOrder>
    {
    
      #region CustomField
      [PXDBString(50)]
      [PXUIField(DisplayName = "Custom Field")]
      [PXSelector(
          typeof(Search2<InventoryItem.inventoryCD,
              InnerJoin<INItemClass, On<InventoryItem.itemClassID, Equal<INItemClass.itemClassID>>>,
              Where<INItemClassExt.customItemClassFlag, Equal<True>>>),
          typeof(InventoryItem.inventoryCD),
          typeof(InventoryItem.descr),
          SubstituteKey = typeof(InventoryItem.inventoryCD),
          DescriptionField = typeof(InventoryItem.descr))]
      public string CustomField { get; set; }
      public abstract class customField : IBqlField { }
      #endregion
    )

     

3 Replies

  • Will_H's avatar
    Will_H
    MYOB Moderator

    Hi GraemeLM ,

    It shouldn't be the case, as you say the database column should exist in all DBs, but can you try republishing to multiple tenants with the "Run SQL Scripts" option ticked?

    If the customisation was trying to add any specific configuraiton information at a database level then the scripts only runnin for the primary tenant might explain it?

     

    Otherwise, I just almost linked you to your own StackOverflow post, so you're ahead of me on this one. 

    • GraemeLM's avatar
      GraemeLM
      Trusted Partner

      Thanks for reviewing this Will_H 

       

      Yes I've run what feels like a million republishes using all the options and multi-tenant settings to ensure all database scripts and changes have been actioned everywhere they should. 

       

  • GraemeLM's avatar
    GraemeLM
    Trusted Partner

    Changed approach and used a different method to define the Item Class. Instead of using a constant in the code, created a custom checkbox on the Item Class, to flag it as the relevant class for the selector to show items of that class.

     

    Item Class DAC Extension:

    public class INItemClassExt : PXCacheExtension<PX.Objects.IN.INItemClass>
    {
      #region CustomItemClassFlag
      [PXDBBool]
      [PXUIField(DisplayName="Custom Item Class Flag")]
      public virtual Boolean? CustomItemClassFlag { get; set; }
      public abstract class customItemClassFlag : PX.Data.BQL.BqlBool.Field<customItemClassFlag> { }
      #endregion
    )


    Purchase Order DAC Extension:

    public class POOrderExt : PXCacheExtension<PX.Objects.PO.POOrder>
    {
    
      #region CustomField
      [PXDBString(50)]
      [PXUIField(DisplayName = "Custom Field")]
      [PXSelector(
          typeof(Search2<InventoryItem.inventoryCD,
              InnerJoin<INItemClass, On<InventoryItem.itemClassID, Equal<INItemClass.itemClassID>>>,
              Where<INItemClassExt.customItemClassFlag, Equal<True>>>),
          typeof(InventoryItem.inventoryCD),
          typeof(InventoryItem.descr),
          SubstituteKey = typeof(InventoryItem.inventoryCD),
          DescriptionField = typeof(InventoryItem.descr))]
      public string CustomField { get; set; }
      public abstract class customField : IBqlField { }
      #endregion
    )