Created
May 23, 2019 10:41
-
-
Save sfcure/4f2c15b3ae4c335e4a74e4dcdfb6afb6 to your computer and use it in GitHub Desktop.
Dependent Picklist Based on Record Types
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<aura:component implements="force:appHostable,flexipage:availableForAllPageTypes,flexipage:availableForRecordHome,force:hasRecordId,forceCommunity:availableForAllPageTypes,force:lightningQuickAction" | |
access="global" | |
controller="DependentPicklistController"> | |
<!-- Event Handlers --> | |
<aura:handler name="init" value="this" action="{!c.doInit}"/> | |
<!-- Attributes--> | |
<aura:attribute name="listControllingValues" type="list" default="[]" description="to store controller field values"/> | |
<aura:attribute name="listDependingValues" type="list" default="['--- None ---']" description="to store dependent field values"/> | |
<aura:attribute name="depnedentFieldMap" type="map" description="map to store dependent values with controlling value"/> | |
<aura:attribute name="bDisabledDependentFld" type="boolean" default="true"/> | |
<aura:attribute name="objDetail" type="Contact" default="{'sobjectType' : 'Contact'}"/> | |
<aura:attribute name="recordTypeName" type="String" default="" description="store field API name of Controller field"/> | |
<aura:attribute name="dependingFieldAPI" type="string" default="LightningApps__Country__c" description="store field API name of dependent field"/> | |
<!--Controller Field--> | |
<lightning:layoutItem size="4" padding="around-small"> | |
<lightning:select name="controllerFld" | |
label="Continent" | |
value="{!v.objDetail.LightningApps__Continent__c}" | |
onchange="{!c.onControllerFieldChange}"> | |
<aura:iteration items="{!v.listControllingValues}" var="val"> | |
<option value="{!val}">{!val}</option> | |
</aura:iteration> | |
</lightning:select> | |
</lightning:layoutItem> | |
<!--Dependent Field--> | |
<lightning:layoutItem size="4" padding="around-small"> | |
<lightning:select name="dependentFld" | |
label="Country" | |
value="{!v.objDetail.LightningApps__Country__c}" | |
disabled="{!v.bDisabledDependentFld}"> | |
<aura:iteration items="{!v.listDependingValues}" var="val"> | |
<option value="{!val}">{!val}</option> | |
</aura:iteration> | |
</lightning:select> | |
</lightning:layoutItem> | |
</aura:component> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class DependentPicklistController { | |
@AuraEnabled | |
public static Map<String,List<String>> getPicklistValues( String objectName, string fieldName, string recordTypeName ) { | |
System.debug( 'objectName : ' + objectName ); | |
System.debug( 'fieldName : ' + fieldName ); | |
System.debug( 'recordTypeName : ' + recordTypeName ); | |
if(String.isBlank( objectName) || String.isBlank(fieldName)){ | |
return null; | |
} | |
String recordTypeId; | |
if( !String.isBlank( recordTypeName ) ){ | |
recordTypeId = Schema.getGlobalDescribe().get( objectName ).getDescribe().getRecordTypeInfosByDeveloperName().get( recordTypeName ).getRecordTypeId(); | |
} | |
if( recordTypeId == null || recordTypeId == '' ){ | |
recordTypeId = Schema.getGlobalDescribe().get( objectName ).getDescribe().getRecordTypeInfosByDeveloperName().get( 'Master' ).getRecordTypeId(); | |
} | |
Map<String, List<String>> mapPicklistValues = new Map<String, List<String>>(); | |
mapPicklistValues = getValues( objectName, recordTypeId, fieldName ); | |
return mapPicklistValues; | |
} | |
public static Map<String, List<String>> getValues(String objectType, String recordTypeId, String fieldName) { | |
// Create the endpoint dynamically for your og | |
String Endpoint = URL.getSalesforceBaseUrl().toExternalForm(); | |
endpoint += '/services/data/v45.0'; | |
endpoint += '/ui-api/object-info/' + objectType + '/picklist-values/' + recordTypeId + '/' + fieldName; | |
EncodingUtil.urlEncode(endpoint,'UTF-8'); | |
// Call the API in order to get the values | |
HttpRequest req = new HttpRequest(); | |
// Since, we can not use the UserInfo.getSessionId() method here, I am using a Visualforce page in order | |
// to extract the session id which we can use for making API calls | |
req.setHeader('Authorization', 'OAuth ' + getSessionIdFromVFPage(Page.SessionId)); | |
req.setHeader('Accept', 'application/json '); | |
req.setHeader('Content-Type', 'application/json'); | |
req.setEndpoint(endpoint); | |
req.setMethod('GET'); | |
Http http = new Http(); | |
HTTPResponse res = http.send(req); | |
Map<String, String> result = new Map<String,String>(); | |
Map<String, List<String>> mapControllingWithDependentList = new Map<String,List<String>>(); | |
Map<Object, String> mapControllingValueWithIndex = new Map<Object,String>(); | |
Map<String, List<String>> mapPicklistValues = new Map<String,List<String>>(); | |
// Parse the response and build the dependent and controlling picklist values map | |
if( res.getStatus() == 'OK' && res.getStatusCode() == 200 ) { | |
Map<String,Object> root = (Map<String,Object>) JSON.deserializeUntyped( res.getBody() ); | |
System.debug( ' Response Body : ' + res.getBody() ); | |
// Get all the controlling values from response | |
if( root.containsKey('controllerValues') ) { | |
Map<String, Object> controllingValues = (Map<String, Object>) root.get( 'controllerValues' ); | |
// Map of all the controlling values with their index | |
for( String cValue: controllingValues.keySet() ) { | |
mapControllingValueWithIndex.put( controllingValues.get(cValue), cValue ); | |
} | |
} | |
System.debug('mapControllingValueWithIndex : ' + JSON.serializePretty( mapControllingValueWithIndex ) ); | |
if( !root.containsKey( 'values' ) ){ | |
return mapControllingWithDependentList; | |
} | |
// Get all the dependent values from the response returned with the Validfor attribute | |
// Each bit in the bitmap indicates whether this dependent picklist value is "valid for" a corresponding controlling field value | |
// The value in the validFor member is a Base64-encoded bitmap. | |
List<Object> pValues = (List<Object>) root.get( 'values' ); | |
for(Object pValue : pValues) { | |
Map<String,Object> pValueMap = (Map<String,Object>)pValue; | |
result.put( (String) pValueMap.get('value'), (String) pValueMap.get('label') ); | |
for(Object validfor : (List<Object>)pValueMap.get('validFor')) { | |
//Map the dependent Values List with their Controlling Value | |
if( mapControllingValueWithIndex.containsKey( validfor ) ) { | |
if( !mapControllingWithDependentList.containsKey( mapControllingValueWithIndex.get( validfor ) ) ) { | |
mapControllingWithDependentList.put( mapControllingValueWithIndex.get( validfor ), new List<String>() ); | |
} | |
mapControllingWithDependentList.get( mapControllingValueWithIndex.get( validfor ) ).add( (String) pValueMap.get( 'label' ) ); | |
} | |
} | |
} | |
System.debug( 'mapControllingWithDependentList : ' + JSON.serializePretty( mapControllingWithDependentList ) ); | |
//Map all the controlling values | |
for( String controllingFields : mapControllingValueWithIndex.Values() ){ | |
//Map controllingFields which has no dependent values associated to it | |
if( !mapPicklistValues.containsKey( controllingFields ) ) { | |
mapPicklistValues.put(controllingFields,new List<String>()); | |
} | |
//Map controllingFields which has dependent values associated to it | |
if(mapPicklistValues.containsKey( controllingFields ) && | |
mapControllingWithDependentList.containsKey( controllingFields ) ) { | |
mapPicklistValues.get( controllingFields ).addAll( mapControllingWithDependentList.get( controllingFields ) ); | |
} | |
} | |
} | |
else{ | |
System.debug( 'mapPicklistValues : ' + JSON.serializePretty( mapPicklistValues ) ); | |
} | |
//Return the Map of Controlling fields with the List of Dependent fields on the basis of Record Types | |
System.debug( 'mapPicklistValues : ' + JSON.serializePretty( mapPicklistValues ) ); | |
return mapPicklistValues; | |
} | |
public static String getSessionIdFromVFPage( PageReference visualforcePage ) { | |
if( !Test.isRunningTest() ) { | |
String sessionId = visualforcePage.getContent().toString(); | |
return sessionId; | |
} | |
return UserInfo.getSessionId(); | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
({ | |
doInit : function(component, event, helper) { | |
// get the fields API name and pass it to helper function | |
var recordTypeName = component.get("v.controllingFieldAPI"); | |
var dependingFieldAPI = component.get("v.dependingFieldAPI"); | |
var objDetails = component.get("v.objDetail"); | |
// call the helper function | |
helper.fetchPicklistValues(component, objDetails, recordTypeName, dependingFieldAPI ); | |
}, | |
onControllerFieldChange: function(component, event, helper) { | |
// get selected controller field value | |
var selectedControllerValue = event.getSource().get("v.value"); | |
var depnedentFieldMap = component.get("v.depnedentFieldMap"); | |
if ( selectedControllerValue != '--- None ---' ) { | |
let dependentFieldOptions = depnedentFieldMap[selectedControllerValue]; | |
if( dependentFieldOptions.length > 0 ) { | |
component.set("v.bDisabledDependentFld" , false); | |
helper.fetchDepValues( component, dependentFieldOptions ); | |
} | |
else{ | |
component.set("v.bDisabledDependentFld" , true); | |
component.set("v.listDependingValues", ['--- None ---']); | |
} | |
} | |
else { | |
component.set("v.listDependingValues", ['--- None ---']); | |
component.set("v.bDisabledDependentFld" , true); | |
} | |
}, | |
}) |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
({ | |
fetchPicklistValues: function( component, objDetails, recordTypeName, dependentField) { | |
console.log('*********'); | |
// call the server side function | |
var action = component.get("c.getPicklistValues"); | |
// pass paramerters [object definition , contrller field name , record type name] - | |
// to server side function | |
action.setParams({ | |
"objectName" : objDetails.sobjectType, | |
"fieldName": dependentField, | |
"recordTypeName": recordTypeName | |
}); | |
//set callback | |
action.setCallback(this, function(response) { | |
if (response.getState() == "SUCCESS") { | |
// Returned a map | |
let responseObj = response.getReturnValue(); | |
console.log(responseObj); | |
// Set the attribute with returned response | |
component.set( "v.depnedentFieldMap", responseObj ); | |
// Prepare a list of controlling values | |
let controllerFieldValues = []; | |
for (var cValue in responseObj ) { | |
controllerFieldValues.push( cValue ); | |
} | |
if ( controllerFieldValues.length > 0) { | |
controllerFieldValues.unshift('--- None ---'); | |
} | |
// set the controllerFieldValues variable values to continent(controller picklist field) | |
component.set("v.listControllingValues", controllerFieldValues); | |
} | |
else{ | |
alert('Something went wrong..'); | |
} | |
}); | |
$A.enqueueAction(action); | |
}, | |
fetchDepValues: function( component, dependentFieldOptions ) { | |
// create a empty array var for store dependent picklist values for controller field | |
let dependentFields = []; | |
dependentFields.push('--- None ---'); | |
for ( let i = 0; i < dependentFieldOptions.length; i++ ) { | |
dependentFields.push( dependentFieldOptions[i] ); | |
} | |
component.set( "v.listDependingValues", dependentFields ); | |
}, | |
}) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment