Mule Salesforce connector. Create Juntion Object using External IDs - salesforce

I have the following Objects and fields.
Object A: External Id (a_ext_id) and other fields
Object B: Extrernal Id (b_ext_id) and other fields
Custom Junction Object C: External id (c_ext_id) and fields a__c (lookup(a)), b__c (Master-Detail(b)) and Status__c
I would like to upsert records into Junction Object C without having to know the Salesforce Ids of Object A and Object B.
I just got it working with Partner WSDL.
Is there anyway to upsert in Mule without writing Java code?

External ID's can be used to achieve this. I would suggest use dataweave before the Salesforce connector and submit external id of the parent objects as shown below: (assuming payload have the external ID values)
{
c_ext_id: payload.cExt, // Value: C's external ID from payload
a__r: {
a_ext_id: payload.aExt // value: A's External ID from payload
},
b__r:{
b_ext_id: payload.bExt // value: B's External ID from payload
},
status__c: payload.status
}

Related

Insert to Parent and child custom object using external Id

I am trying to insert a record into a child custom object using the external id of the parent custom object. I am almost clear on how to setup the external id field in the parent object, but very confused with how to setup a foreign key in my child object. I am attaching the pics here which has details of the master and child custom objects. What I am i supposed to add to the child custom object to link its records to the parent object.
Also here is the code I got from another post in stackoverflow, but that didn't work in my case
enter image description heresumchans__City_Master__c city = new sumchans__City_Master__c(Name='[![enter image description here][1]][1]Vancouver',sumchans__PROVINCE__c = 'BC', sumchans__City_Name_Ext_Id__c = 'Vancouver');
insert city;
sumchans__City_Stat__c cityStat = new sumchans__City_Stat__c(Name = 'Vancouver', sumchans__ON_BILLINGS__c = 50, sumchans__City_Master__c=new sumchans__City_Master__c(sumchans__City_Name_Ext_Id__c='Vancouver'));
insert cityStat;
Ext. ids are meant to be used in integrations, Data Loader... They can be used in Apex too but the syntax looks bit funny. Use them in Apex if you must save on queries or want to go "dear salesforce, I don't remember if I saved this object already, I know unique identifier is 123, go figure it out yourself whether it needs insert or update".
If you insert parent and child in same transaction - just user the Id generated into parent record. If they're separate, a while ago you did this:
insert new sumchans__City_Master__c city = new sumchans__City_Master__c(Name=Vancouver',
sumchans__PROVINCE__c = 'BC',
sumchans__City_Name_Ext_Id__c = 'Vancouver'
);
Then later in another transaction you can do this without querying:
sumchans__City_Stat__c cityStat = new sumchans__City_Stat__c(Name = 'Vancouver',
sumchans__ON_BILLINGS__c = 50,
sumchans__City_Master__r = new sumchans__City_Master__c(
sumchans__City_Name_Ext_Id__c='Vancouver'
)
);
insert cityStat;
Note that I used __r instead of __c. __c would be your real foreign key, Id field, 15 or 18 characters. __r would be a reference to another object (with ext. id or query result for example), similar to writing SELECT FirstName, Email, Account.Name FROM Contact.
In Apex it has to be as a object referece (so either query or cheat with new keyword, just to create it in memory. You won't actually save that "parent"). In things like data loader you can map values bit like myCsvExtIdColumn -> sumchans__City_Master__r.sumchans__City_Name_Ext_Id__c
Create a lookup field instead. Because External ID field used to reference an ID from another external system.
If you want to relate the foreign key with and relational DBMS, you need to create a lookup relationship type field in the child object. There you need to assign the Parent Object in the Related To field.

how to assign value to lookup fields in salesforce

i have two objects KNDY4__Sales_Order__c and KNDY4__Bill_to__c.these two are linked through lookup relationship.i am trying to insert one order record as follows
`KNDY4__Sales_Order__c order=New KNDY4__Sales_Order__c();
order.KNDY4__Ship_to__c ='a14q0000001LnIeAAK';
order.KNDY4__Bill_to__r.Predicted_External_ID__c ='CN-0222741-Sold To';
order.KNDY4__Company__c ='a0l1N00000BQQKF';
Insert order;`
i am geting error as {"Object reference not set to an instance of an object."}.
how to assign values to lookup field.can anyone help me
When linking a record based on an external id, the relationship field needs to be set to an sObject with the external id, and not just the value of the id itself.
On line 3, since KNDY4__Bill_to__c is a lookup field to a custom object possibly named KNDY4__Customer__c, you should set the value of the lookup to an instance of that object, e.g.
order.KNDY4__Bill_to__r = new KNDY4__Customer__c(KNDY4__Predicted_External_ID__c ='CN-0222741-Sold To');

Facing issue while inserting lookup type record in salesforce: mule esb

I am facing issue while inserting record in salesforce.
Type of record is lookup(Account) and field name is site_id.I insert csv file record into salesforce. But because of this record(data type(lookup)) i can not insert record in salesforce. If I change type of record to Text than i can insert. But I need lookup(Account) type.
How is it possible ...please help me
following is my flow
<batch:job name="testsalesforceBatch1">
<batch:input>
<file:inbound-endpoint path="CustomFile" responseTimeout="10000" doc:name="File"/>
<data-mapper:transform config-ref="CSV_To_List_Report__c__1" doc:name="CSV To List<Report__c>"/>
</batch:input>
<batch:process-records>
<batch:step name="Batch_Step">
<batch:commit size="1000" doc:name="Batch Commit">
<sfdc:create-bulk config-ref="Salesforce" type="Report__c" doc:name="Salesforce">
<sfdc:objects ref="#[payload]"/>
</sfdc:create-bulk>
</batch:commit>
</batch:step>
</batch:process-records>
<batch:on-complete>
<logger message="#[payload.totalRecords]" level="INFO" doc:name="Logger"/>
</batch:on-complete>
</batch:job>
I got following error...
[SaveResult errors='{[1][Error fields='{XXXXXXX,}'
message='XXXXXX: id value of incorrect type: 000'
statusCode='MALFORMED_ID'
]
NOTE: 000 value is available in Account table
I got answer..how to insert lookup data type record in salesforce through mule.
Use recordId to store that value...
Thanks
For Salesforce Integrations there are two ways to insert/upsert/create fields with lookup values.
Way 1: Use the actual ID of the lookup target. So if you are going to lookup an Account, you first need to get the ID of the Account you are targeting, then use that ID in the field as a "String" in data mapper.
Way 2: Use a External ID on Account and upsert the new record referring to the external ID. This is a little more complicated but is very excellent way to not have to do two API calls.
In Datamapper then, you need to have Account be listed as an Element and not as an Attribute. This has to be done manually as Datamapper won't know to do this on its own.
Account (Element)
|-type (String) -> 'Account' *this is just a fixed string*
|-ExternalIdFieldName__c (String) -> external_id_from_datasource
Since Account is a standard SalesForce object it doesn't have a __c or __r after it, if it was a custom object and you are doing a lookup it changes a little bit.
Objects:
MyCustomAccount__c
External ID in above: AccountExternalId__c
Lookup field: AccountLookup__c (lookup to Account from Contact)
In Datamapper then you have:
AccountLookup__r (Element) *notice the __r instead of __c*
|- type (String) -> 'MyCustomAccount__c' *this is just a fixed string*
|- AccountExternalId__c (String) -> externalidfieldfromcsv

Pentaho salesforce upsert using externalID

I am trying to insert data in salesforce using upsert, for one field i am using the ExternalId field , i have tried many combinations but it fails...I get the error : the syntax should be object:externalId/lookupField
Any idea what is the exact syntax? Keep in mind i am inserting in table Account and the externalId field refers to Account also
object:externalId/lookupField is not very clear is it. There's a comment hidden away in the Pentaho code:
// We use an external key
// the structure should be like this :
// object:externalId/lookupField
// where
// object is the type of the object
// externalId is the name of the field in the object to resolve the value
// lookupField is the name of the field in the current object to update (is the "__r" version)
Lets say you're populating a Salesforce Object Foo__c, which has a Lookup field to Contact called Contact__c. The 'relationship name' for that lookup field would then be Contact__r.
On Contact lets say you have added an External ID called Legacy_Id__c and thats what you want to use when populating Foo__c.
What Pentaho would want in the Module Field column would then be:
Contact:Legacy_Id__c\Contact__r
The bit to the left of the slash is telling Pentaho which object/external id to map to. To the right of the slash, its telling Pentaho which lookup/relationship on Foo__c to fill in.

Elementary Apex Object IDs

Quick Question. In the below code, you can see that the for loop (which takes all of the records in newTimecards and puts them as a variable called timecard) and adds the Resource_c to the resourceIds set. I'm confused about how this object is considered an ID data type. When an object is made in Salesforce does it automatically have an ID made, so that it knows Resource_c ID can be added to a set? Note that within the Resource_c Object there is also a field called Resource_ID_c. Resource_c within Timecard_c is a Master-Detail data type. Resource_c is the parent of Timecard_c.
Now that I think about it, resourceIds.add(timecard.Resource_c), does that reference the relationship between the two objects and then searches through Resource_c and adds the ID field Resource_ID_c automactically since it's a unique field?
Thanks for your help.
public class TimecardManager {
public class TimecardException extends Exception {}
public static void handleTimecardChange(List<Timecard__c> oldTimecards,
List<Timecard__c> newTimecards) {
Set<ID> resourceIds = new Set<ID>();
for (Timecard__c timecard : newTimecards) {
resourceIds.add(timecard.Resource__c);
}
Every object instance (and that means EVERY, including factory ones) has a unique organization level ID, whose field name is always Id, is covered by Apex type ID and is a case-sensitive string of 15 characters that also has an 18 character case-insensitive representation. The first three characters are object prefix code (e.g. 500 for a Case) so all instances of the same object share the same prefix. You see these values all across SF (for example in https://na1.salesforce.com/02s7000000BW59L the 02s7000000BW59L in the URL is the ID). When an instance of the object is created using INSERT DML operation, the salesforce automatically assigns unique value based on the prefix and the next available transactional sub ID, it all happens transparently to you.
This is not to be confused with object Name field which is a field you define when you create an object and which can be auto-incremented and so on (e.g. MYOBJ-{00000}) and which can have more meaning to a user than a cryptic ID
When you create a lookup or master-detail relationship it is ID that is being used to link the two instances, not the Name. In the above example Resource__c seems to be that lookup field and it contains Id value of row's master.
What the code does is it enumerates all resources used in timelines and builds a set of their IDs, the purpose of which is most probably to be used via WHERE Id IN :resourceIds clause to load resource details from master table.
mmix's answer is a great overview to what an ID is and where it comes from. To answer what I think is your specific question:
Any time there is a reference from one object to another (like here, between Timecard_c and Resource_c), the field representing the reference will be an ID. So, the for loop that calls resourceIds.add(timecard.Resource__c) is just building up your set of ID's (those 15-character strings). The timecard.Resource__c doesn't look through the Resource__c table to find the ID, timecard.Resource__c is the ID.

Resources