Dynamics CRM - Accessing Custom Product Option Value

*爱你&永不变心* 提交于 2019-11-28 14:16:21
James Wood

This function retrieves a dictionary of possible values localised to the current user. Taken from: CRM 2011 Programatically Finding the Values of Picklists, Optionsets, Statecode, Statuscode and Boolean (Two Options).

static Dictionary<String, int> GetNumericValues(IOrganizationService service, String entity, String attribute)
{
    RetrieveAttributeRequest request = new RetrieveAttributeRequest
    {
        EntityLogicalName = entity,
        LogicalName = attribute,
        RetrieveAsIfPublished = true
    };

    RetrieveAttributeResponse response = (RetrieveAttributeResponse)service.Execute(request);

    switch (response.AttributeMetadata.AttributeType)
    {
        case AttributeTypeCode.Picklist:
        case AttributeTypeCode.State:
        case AttributeTypeCode.Status:
            return ((EnumAttributeMetadata)response.AttributeMetadata).OptionSet.Options
                .ToDictionary(key => key.Label.UserLocalizedLabel.Label, option => option.Value.Value);

        case AttributeTypeCode.Boolean:
            Dictionary<String, int> values = new Dictionary<String, int>();

            BooleanOptionSetMetadata metaData = ((BooleanAttributeMetadata)response.AttributeMetadata).OptionSet;

            values[metaData.TrueOption.Label.UserLocalizedLabel.Label] = metaData.TrueOption.Value.Value;
            values[metaData.FalseOption.Label.UserLocalizedLabel.Label] = metaData.FalseOption.Value.Value;

            return values;

        default:
            throw new ArgumentOutOfRangeException();
    }
}

So you would then need to do something like:

Dictionary<String, int> values = GetNumericValues(proxy, "your_entity", "new_producttypesubcode");

if(values.ContainsKey("Trophy"))
{
    //Do something with the value
    OptionSetValue optionSetValue = values["Trophy"];
    int value = optionSetValue.Value;
}
Andy Meyers

Yes, that data is all stored in the metadata for an attribute (SDK article). You have to retrieve the entity metadata for the entity and then find the attribute in the list. Then cast that attribute to a PicklistAttributeMetadata object and it will contain a list of options. I would mention that typically retrieving Metadata from CRM is an expensive operation, so think about caching.

private static OptionSetMetadata RetrieveOptionSet(IOrganizationService orgService,
    string entityName, string attributeName)
{
    var entityResponse = (RetrieveEntityResponse)orgService.Execute(
        new RetrieveEntityRequest 
            { LogicalName = entityName, EntityFilters = EntityFilters.Attributes });

    var entityMetadata = entityResponse.EntityMetadata;

    for (int i = 0; i < entityMetadata.Attributes.Length; i++)
    {
        if (attributeName.Equals(entityMetadata.Attributes[i].LogicalName))
        {
            if (entityMetadata.Attributes[i].AttributeType.Value == 
                    AttributeTypeCode.Picklist)
            {
                var attributeMD = (PicklistAttributeMetadata)
                    entityMetadata.Attributes[i];

                return attributeMD.OptionSet;
            }
        }
    }

    return null;
}

Here is how to write the options to the console using the above call.

var optionSetMD = RetrieveOptionSet(orgService, "account", "accountcategorycode");
var options = optionSetMD.Options;

for (int i = 0; i < options.Count; i++)
{
    Console.WriteLine("Local Label: {0}.  Value: {1}",
        options[i].Label.UserLocalizedLabel.Label,
        options[i].Value.HasValue ? options[i].Value.Value.ToString() : "null");
}

I believe this works for global option set attributes as well, but if you know it is a global option set there is a different message for it that would probably a bit more efficient (SDK article).

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!