Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 30 additions & 3 deletions src/main/java/com/force/api/ForceApi.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
import com.force.api.http.HttpRequest;
import com.force.api.http.HttpResponse;

import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.core.JsonGenerationException;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.JsonMappingException;
Expand Down Expand Up @@ -416,11 +415,39 @@ public DescribeSObject describeSObject(String sobject) {
throw new ResourceException(e);
}
}


/**
* Create nested objects
* ex: https://developer.salesforce.com/docs/atlas.en-us.api_rest.meta/api_rest/dome_composite_sobject_tree_create.htm
*
* @param nestedRecordRequest Nested recursive object to be included
* @return NestedResponse
*/
public NestedResponse insertNestedObjects(NestedRecordRequest nestedRecordRequest){

try {
return jsonMapper.readValue(
apiRequest(
new HttpRequest()
.url(uriBase() + "/composite/tree/" + nestedRecordRequest.getObjectApiName() )
.method("POST")
.header("Accept", "application/json")
.header("Content-Type", "application/json")
.content(jsonMapper.writeValueAsBytes(nestedRecordRequest))
)
.getStream(),
NestedResponse.class);

} catch (IOException e) {
throw new ResourceException(e);
}

}

private final String uriBase() {
return(session.getApiEndpoint()+"/services/data/"+config.getApiVersionString());
}

private final HttpResponse apiRequest(HttpRequest req) {
req.setAuthorization("Bearer "+session.getAccessToken());
req.setRequestTimeout(this.config.getRequestTimeout());
Expand Down
62 changes: 62 additions & 0 deletions src/main/java/com/force/api/NestedRecord.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
package com.force.api;

import com.fasterxml.jackson.annotation.JsonAnyGetter;
import com.fasterxml.jackson.annotation.JsonAnySetter;
import com.fasterxml.jackson.annotation.JsonProperty;

import java.util.Map;

public class NestedRecord {

@JsonProperty(value = "attributes")
protected Attribute attribute;

private Map<String, NestedRecordRequest> innerNestedRecordsByType;

@JsonAnyGetter
public Map<String, NestedRecordRequest> getInnerNestedRecordsByType() {
return innerNestedRecordsByType;
}

@JsonAnySetter
public void setInnerNestedRecordsByType(Map<String, NestedRecordRequest> innerNestedRecordsByType) {
this.innerNestedRecordsByType = innerNestedRecordsByType;
}

public Attribute getAttribute() {
return attribute;
}

public void setAttribute(Attribute attribute) {
this.attribute = attribute;
}

public class Attribute{

private String type;
private String referenceId;

public Attribute() { }

public Attribute(String type, String referenceId){
this.type = type;
this.referenceId = referenceId;
}

public String getReferenceId() {
return referenceId;
}

public void setReferenceId(String referenceId) {
this.referenceId = referenceId;
}

public String getType() {
return type;
}

public void setType(String type) {
this.type = type;
}
}
}
48 changes: 48 additions & 0 deletions src/main/java/com/force/api/NestedRecordRequest.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
package com.force.api;

import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonProperty;

import java.util.ArrayList;
import java.util.List;

public class NestedRecordRequest<T extends NestedRecord> {

@JsonProperty(value = "records")
private List<T> records;

@JsonIgnore
private String objectApiName;

/**
*
* @param objectApiName Object API Name ex: Account, CustomObject__c
*/
public NestedRecordRequest(String objectApiName){
this.records = new ArrayList<T>();
this.objectApiName = objectApiName;
}

public NestedRecordRequest(String objectApiName, List<T> records){
this.records = records;
this.objectApiName = objectApiName;
}

public NestedRecordRequest(String objectApiName, T t){
this.records = new ArrayList<T>();
this.records.add(t);
this.objectApiName = objectApiName;
}

public String getObjectApiName() {
return objectApiName;
}

public List<T> getRecords() {
return records;
}

public void setRecords(List<T> records) {
this.records = records;
}
}
70 changes: 70 additions & 0 deletions src/main/java/com/force/api/NestedResponse.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
package com.force.api;

import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonProperty;

import java.util.List;

@JsonIgnoreProperties(ignoreUnknown=true)
public class NestedResponse {

public NestedResponse(){}

@JsonCreator
public NestedResponse(@JsonProperty("hasErrors") boolean hasErrors, @JsonProperty("results") List<Result> results){
this.hasErrors = hasErrors;
this.results = results;
}

@JsonProperty("hasErrors") private boolean hasErrors;
@JsonProperty("results") private List<Result> results;

public boolean getHasErrors() {
return hasErrors;
}

public void setHasErrors(boolean hasErrors) {
this.hasErrors = hasErrors;
}

public List<Result> getResults() {
return results;
}

public void setResults(List<Result> results) {
this.results = results;
}

@JsonIgnoreProperties(ignoreUnknown=true)
static class Result{

public Result(){ }

@JsonCreator
public Result(@JsonProperty("referenceId") String referenceId, @JsonProperty("id") String id){

this.referenceId = referenceId;
this.id = id;
}

@JsonProperty("referenceId") private String referenceId;
@JsonProperty("id") private String id;

public String getReferenceId() {
return referenceId;
}

public void setReferenceId(String referenceId) {
this.referenceId = referenceId;
}

public String getId() {
return id;
}

public void setId(String id) {
this.id = id;
}
}
}
2 changes: 1 addition & 1 deletion src/main/java/com/force/api/http/HttpRequest.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ static public HttpRequest formPost() {
public enum ResponseFormat { STREAM, BYTE, STRING };

ResponseFormat responseFormat = ResponseFormat.STREAM;

byte[] contentBytes;
InputStream contentStream;

Expand Down
42 changes: 42 additions & 0 deletions src/test/java/com/force/api/NestedAccount.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
package com.force.api;

import com.fasterxml.jackson.annotation.JsonProperty;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class NestedAccount extends NestedRecord {

@JsonProperty(value = "Name")
private String name;

public NestedAccount(String refId){

this.attribute = new Attribute("Account", refId);
}

public String getName() {
return name;
}

public void setName(String name) {
this.name = name;
}

public void setContacts(List<NestedContact> contacts){

Map<String, NestedRecordRequest> innerNestedRecordsByType = getInnerNestedRecordsByType();
if(innerNestedRecordsByType == null)
innerNestedRecordsByType = new HashMap<String, NestedRecordRequest>();

NestedRecordRequest innerContacts = innerNestedRecordsByType.get("Contacts");
if(innerContacts == null)
innerContacts = new NestedRecordRequest("Account");

innerContacts.setRecords(contacts);
innerNestedRecordsByType.put("Contacts", innerContacts);
setInnerNestedRecordsByType(innerNestedRecordsByType);

}
}
33 changes: 33 additions & 0 deletions src/test/java/com/force/api/NestedContact.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
package com.force.api;

import com.fasterxml.jackson.annotation.JsonProperty;

public class NestedContact extends NestedRecord {

@JsonProperty(value = "LastName")
private String lastName;

@JsonProperty(value = "Email")
private String email;

public NestedContact(String refId){

this.attribute = new NestedRecord.Attribute("Contact", refId);
}

public String getLastName() {
return lastName;
}

public void setLastName(String lastName) {
this.lastName = lastName;
}

public String getEmail() {
return email;
}

public void setEmail(String email) {
this.email = email;
}
}
61 changes: 61 additions & 0 deletions src/test/java/com/force/api/NestedRecordTest.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
package com.force.api;

import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.junit.Test;

import java.util.ArrayList;
import java.util.List;

import static org.junit.Assert.assertTrue;

public class NestedRecordTest {

static ForceApi api = new ForceApi(new ApiConfig()
.setUsername(Fixture.get("username"))
.setPassword(Fixture.get("password"))
.setClientId(Fixture.get("clientId"))
.setClientSecret(Fixture.get("clientSecret")));

@Test
public void testInsert(){

ObjectMapper mapper = new ObjectMapper();
mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);

NestedAccount acc = new NestedAccount("acc2");
acc.setName("Acc 3");

NestedContact con1 = new NestedContact("con1");
con1.setLastName("Con1");
con1.setEmail("con1@nestedrecord.com");

NestedContact con2 = new NestedContact("con2");
con2.setLastName("Con2");
con2.setEmail("con2@nestedrecord.com");

List<NestedContact> contacts = new ArrayList<NestedContact>();
contacts.add(con1);
contacts.add(con2);

acc.setContacts(contacts);

NestedContact con3 = new NestedContact("con3");
con3.setLastName("Con3");
con3.setEmail("con3@nestedrecord.com");

NestedRecordRequest<NestedRecord> nestedRequest = new NestedRecordRequest<NestedRecord>("Account");
nestedRequest.getRecords().add(acc);

try {
System.out.println( mapper.writeValueAsString(nestedRequest) );
} catch (JsonProcessingException e) {
e.printStackTrace();
}

NestedResponse response = api.insertNestedObjects(nestedRequest);
assertTrue(response != null);
}

}