【问题标题】:Salesforce Apex - Populating an object from SOQL querySalesforce Apex - 从 SOQL 查询填充对象
【发布时间】:2013-04-12 11:20:55
【问题描述】:

我有一个简单的 SOQL 查询,它返回与联系人和 CampaignMember 相关的信息。我正在尝试使用 SOQL 查询的结果填充自定义对象。但是在加载 Visualforce 页面时出现以下错误:

CampaignMember 的无效字段campaign.name

列出campaignMembers = [从CampaignMember中选择campaign.name、contact.id、contact.firstname、contact.lastname、status、campaignId,其中contactId = '003U000000U0eNq'和campaigns中的campaignId];

for (整数 i = 0; i 

我已经在开发者控制台中单独运行了 SOQL 查询,并且查询成功。为什么我不能从 for 循环中的 SOQL 查询中提取活动名称?

【问题讨论】:

    标签: salesforce apex-code soql


    【解决方案1】:

    您看到的错误是因为您应该将其写为campaignMembers[i].Campaign.Name。或者,如果您坚持使用 getter 语法,campaignMembers[i].getSobject('Campaign').get('Name')

    您需要包装器对象(或任何 CampaignMemberResult 是什么)有什么特殊原因吗? 我有一种奇怪的感觉,你编写了太多代码来实现简单的事情;)campaignMembers[i].Campaign.Name 的语法也意味着你不必对字符串使用强制转换。


    另外 - 如果您需要知道“此联系人发生在哪些广告系列中”,您有两种方法:

    平坦

    select contact.id,contact.firstname, contact.lastname, 
        campaignid, campaign.name, 
        status 
    from CampaignMember 
    where contactId = '003U000000U0eNq'
    

    子查询

    从联系人向下到活动成员的相关列表,然后到活动以获取他们的姓名

    SELECT Id, FirstName, LastName,
        (SELECT CampaignId, Campaign.Name FROM CampaignMembers)
    FROM Contact WHERE Id = '003U000000U0eNq'
    

    示例如何在 visualforce 中直接使用“平面”结果(不带CampaignMemberResult):

    顶点:

    public List<CampaignMember> flatMembers {get;set;} // insert dick joke here
    
    flatMembers = [select contact.id,contact.firstname, contact.lastname, 
        campaignid, campaign.name, 
        status 
    from CampaignMember 
    where contactId = '003U000000U0eNq'];
    

    音频:

    <apex:pageBlockTable value="{!flatMembers}" var="cm">
        <apex:column value="{!cm.Contact.LastName}" />
        <apex:column value="{!cm.Status}" />
        <apex:column value="{!cm.Campaign.Name}" />
    

    编辑

    我的最终目标是在联系人上显示 Visualforce 页面 记录显示所有活动的列表,每个活动旁边都有一个复选框 指示联系人是否为成员。

    您确实意识到它可以很快变成一张很长的桌子吗?也许对活动进行一些过滤(如果您想阅读一些高级的东西 - 检查“StandardSetController”的文档)。此外,我很确定有一些方法可以从活动报告中将联系人/潜在客户添加到活动中 - 也许开箱即用的东西可以节省您的时间并且更易于维护......

    但代码解决方案将非常简单,从帮助包装类开始:

    public class CampaignWrapper{
        public Boolean selected {get;set;}
        public Campaign c {get; private set;}
        public CampaignWrapper(Campaign c){
            this.c = c;
            selected = !c.CampaignMembers.isEmpty();
        }
    }
    

    然后查询并构建包装器列表:

    List<CampaignWrapper> wrappers = new List<CampaignWrapper>();
    for(Campaign c : [SELECT Id, Name, (SELECT Id FROM CampaignMember WHERE ContactId = '...')
        FROM Campaign
        LIMIT 1000]){
        wrappers.add(new CampaignMember(c));
    }
    

    你应该准备好了;)如果它只是为了显示 - 你甚至可能不需要包装类(visualforce 表达式中的一些技巧可能或者使用Map&lt;Campaign, Boolean&gt; 甚至......

    1000 条记录是传递给 Visualforce 的集合的限制(如果您的页面是只读的,则为 10K)。过去 - 分页,很可能与上述 StandardSetController 一起使用。

    【讨论】:

    • 感谢 eyecream,我认为您认为我为简单的事情编写了太多代码是正确的。我的最终目标是在联系人记录上显示一个 Visualforce 页面,该页面显示所有活动的列表,每个活动旁边都有一个复选框,指示联系人是否是成员。使用上面的示例进行一些调整,我认为这应该是可能的?
    • 感谢 eyecream,像往常一样,您的回答很有见地!
    • 嗨,eyescream,我已经更新了我的控制器以使用您在上面编辑时描述的模式。如果我们从 wrappers.add(new CampaignMember(c)) 添加新的 CampaignMembers,我必须更新该行;到 wrappers.add(new CampaignMember(Campaign=c));因为我有一个编译错误。但是,我现在有以下与包装类相关的编译错误:不兼容的元素类型 SOBJECT:CampaignMember 用于 CampaignMailingGroupController.CampaignWrapper 的集合。我的包装类位于我的主控制器类中,这是正确的吗?
    • 我很惊讶你不得不使用像Campaign=c 这样奇怪的东西。我的意思是这就像说Integer=5,它甚至可以编译吗?您可以使用更大的代码 sn-p 来编辑您的问题吗?两个包装类定义。以及用于填充列表的查询...
    • 虽然我写的时候很奇怪,但是编译好了??无论如何,我已经看到了我的方式的错误并恢复了改变。我现在添加 (new Campaign(c));到包装器列表,结果正是我所追求的!再次感谢您的帮助。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多