为什么新创建的扩展字段值(在联系人屏幕中创建)没有从(客户位置屏幕到联系人屏幕)正确默认?

Why newly created extension field value (created in Contacts screen) not defaulting correctly from (Customer location screen to Contacts screen)?

我在联系人屏幕(位置 id --- int)和客户位置屏幕中创建了一个新的扩展字段,当我点击“+”按钮时它应该重定向到联系人屏幕和 headersession“客户和位置 ID”应该是默认的,但位置 ID 不是默认的。

这是 img 示例:

这是我写的代码:

    public PXDBAction<Location> addContact;
    [PXUIField(DisplayName = Messages.AddContact)]
    [PXButton(ImageKey = PX.Web.UI.Sprite.Main.DataEntry)]
    public virtual void AddContact()
    {

        var row = Base.Location.Current;
        if (row == null || row.BAccountID == null) return;

        ContactExt extension = PXCache<Contact>.GetExtension<ContactExt>(Base.Contact.Current); //Base.Contact.Current

        ContactMaint graph = PXGraph.CreateInstance<ContactMaint>();
        graph.Clear();

        Location get = Base.Location.Current;
        Contact retbatch = graph.Contact.Insert(new Contact());

        retbatch.BAccountID = get.BAccountID;
        extension.UsrLocationCD = get.LocationID;

        if (!Base.IsContractBasedAPI)
            PXRedirectHelper.TryRedirect(graph, PXRedirectHelper.WindowMode.NewWindow);

        graph.Save.Press();
    }

新建扩展字段逻辑:

public class ContactExt : PXCacheExtension<PX.Objects.CR.Contact> /*, IBqlTable*/
{

    #region UsrLocationCD
    [PXDBInt()]
    [PXUIField(DisplayName = "Location ID")]

    [PXSelector(
      typeof(Search<Location.locationID, Where<Location.bAccountID,
           Equal<Current<Contact.bAccountID>>>>),
        SubstituteKey = typeof(Location.locationCD), ValidateValue = false)]

    public virtual int? UsrLocationCD { get; set; }
    public abstract class usrLocationCD : PX.Data.BQL.BqlInt.Field<usrLocationCD> { }
    #endregion

}

这是断点 img:

类似的功能应该出现在“机会”屏幕中

图片示例:

这是类似的代码(机会屏幕):

    public PXDBAction<Location> addOpportunity;
    [PXUIField(DisplayName = Messages.AddNewOpportunity)]
    [PXButton(ImageKey = PX.Web.UI.Sprite.Main.AddNew)]
    public virtual void AddOpportunity()
    {
        var row = CurrentBAccount.Current;
        if (row == null || row.BAccountID == null) return;


        OpportunityMaint graph = PXGraph.CreateInstance<OpportunityMaint>();
        graph.Clear();

        Location get = Base.Location.Current;
        CROpportunity retbatch = graph.Opportunity.Insert(new CROpportunity());

        retbatch.BAccountID = get.BAccountID;
        retbatch.LocationID = get.LocationID;

        if (!Base.IsContractBasedAPI)
            PXRedirectHelper.TryRedirect(graph, PXRedirectHelper.WindowMode.NewWindow);

        graph.Save.Press();
    } 

这是断点 img:

“机会”屏幕中的功能正常

“联系人屏幕”逻辑哪里出错了 以及如何克服这个问题?

我是这个acumatica的新手。

类似于

一般来说,您实际上并没有更新缓存(与数据库同步的底层数据对象)。从信息层的角度思考:

  • 数据库是商店数据的实际存储库
  • 缓存是数据库数据在内存中的工作副本。这就是我们使用的,最常见的“视图”(public PXSelect<> MyView;)通常定义在图表的顶部。
  • 内存中的工作对象是我们计算需要的值的地方。

Acumatica 通过 PXGraph 自然地将数据库中的数据检索到缓存对象中,以进行标准的 CRUD 操作。您将数据 (MyView.Insert(myData);) 添加到缓存并更新缓存中的数据 (MyView.Update(myData);),但在您保存 (Persist) 之前不会将其推送到数据库。当你检索一个扩展时(数据库的额外字段 table 在 DAC 扩展中定义)那么你在内存中只有一个对象(ContactExt contactExt = contact.GetExtenstion();)这是一样的使用 Contact contact = Contacts.Current();

时的概念

一旦您从数据库中检索数据,它就在缓存中。当您将数据“添加到数据库”时,您实际上是在使用内存(缓存)中的对象,直到您持久化该数据。当你操作数据时(extension.UsrLocationCD = get.LocationID;)然后内存中的对象被更新,但不是实际的缓存(当你按下保存时它会被持久化到数据库)。

要将更新的数据推送到您的工作对象 (extension.UsrLocationCD = get.LocationID;) 中,您需要将其推送到缓存中。这是通过多种方式完成的。在这种情况下,我只对视图使用更新。

graph.Contact.Update(extension);

您还可以使用:

graph.Caches[typeof(Contact)].Update(extension); 

最终,您需要保留数据,这已在代码示例的底部使用 graph.Save.Press();.[=14= 完成]

您的视图代码已更新:

public PXDBAction<Location> addContact;
[PXUIField(DisplayName = Messages.AddContact)]
[PXButton(ImageKey = PX.Web.UI.Sprite.Main.DataEntry)]
public virtual void AddContact()
{

    var row = Base.Location.Current;
    if (row == null || row.BAccountID == null) return;

    ContactExt extension = PXCache<Contact>.GetExtension<ContactExt>(Base.Contact.Current); //Base.Contact.Current

    ContactMaint graph = PXGraph.CreateInstance<ContactMaint>();
    graph.Clear();

    Location get = Base.Location.Current;
    Contact retbatch = graph.Contact.Insert(new Contact());

    retbatch.BAccountID = get.BAccountID;
    extension.UsrLocationCD = get.LocationID;

    // Update the cache
    graph.Contact.Update(extension);

    if (!Base.IsContractBasedAPI)
        PXRedirectHelper.TryRedirect(graph, PXRedirectHelper.WindowMode.NewWindow);

    graph.Save.Press();
}

小修改(调用扩展字段)帮助我在联系人屏幕上设置了默认值。

    public PXDBAction<Location> addContact;
    [PXUIField(DisplayName = Messages.AddContact)]
    [PXButton(ImageKey = PX.Web.UI.Sprite.Main.DataEntry)]
    public virtual void AddContact()
    {
        var row = Base.Location.Current;
        if (row == null || row.BAccountID == null) return;

        ContactMaint graph = PXGraph.CreateInstance<ContactMaint>();
        graph.Clear();

        Location get = Base.Location.Current;
        Contact retbatch = graph.Contact.Insert(new Contact());

//这是我改的扩展字段调用

        ContactExt extension = retbatch.GetExtension<ContactExt>();

        retbatch.BAccountID = get.BAccountID;
        extension.UsrLocationCD = get.LocationID;

//我更新到图缓存

        graph.Contact.Cache.Update(retbatch);

        if (!Base.IsContractBasedAPI)
            PXRedirectHelper.TryRedirect(graph, 
          PXRedirectHelper.WindowMode.NewWindow);
     }

Working after modify the code