メモ: クラス更新
SFDC Tooling API を使って SFDC に Apex クラスを更新する例。
public static boolean updateApexClass(final ToolingConnection toolingConnection, final String classId, final String classBody, final StringBuffer sbufErrorMsg) throws ConnectionException, InterruptedException { String containerId = null; { // create metadata container. final MetadataContainer metaContainer = new MetadataContainer(); metaContainer.setName("MyMetadataContainer" + System.currentTimeMillis()); final MetadataContainer[] metaContainers = { metaContainer }; final SaveResult[] saveResults = toolingConnection.create(metaContainers); if (saveResults[0].isSuccess() == false) { sbufErrorMsg.append( "fail to create MetadataContainer: reason: " + saveResults[0].getErrors()[0].getMessage()); return false; } containerId = saveResults[0].getId(); } { // update class body. final ApexClassMember aClassMember = new ApexClassMember(); aClassMember.setContentEntityId(classId); aClassMember.setBody(classBody); aClassMember.setMetadataContainerId(containerId); final ApexClassMember[] aClassMembers = { aClassMember }; final SaveResult[] saveResults = toolingConnection.create(aClassMembers); if (saveResults[0].isSuccess() == false) { sbufErrorMsg .append("fail to create Class Member: reason: " + saveResults[0].getErrors()[0].getMessage()); return false; } } String requestId = null; { final ContainerAsyncRequest request = new ContainerAsyncRequest(); request.setIsCheckOnly(false); request.setMetadataContainerId(containerId); final ContainerAsyncRequest[] requests = { request }; final SaveResult[] saveResults = toolingConnection.create(requests); if (saveResults[0].isSuccess() == false) { sbufErrorMsg.append("fail to create ContainerAsyncRequest object: reason: " + saveResults[0].getErrors()[0].getMessage() + "\n"); return false; } requestId = saveResults[0].getId(); } { final String soql = "select Id, State, DeployDetails, ErrorMsg from ContainerAsyncRequest where id = '" + requestId + "'"; String requestState = null; for (;; Thread.sleep(2000)) { final QueryResult queryResult = toolingConnection.query(soql); if (queryResult.getSize() <= 0) { sbufErrorMsg.append("fail to run async request"); return false; } final ContainerAsyncRequest asyncRequest = (ContainerAsyncRequest) queryResult.getRecords()[0]; requestState = asyncRequest.getState().toLowerCase(); if (requestState.equals("queued") == false) { if (asyncRequest.getDeployDetails().getComponentFailures().length > 0) { sbufErrorMsg.append(asyncRequest.getDeployDetails().getComponentFailures()[0].getProblem()); sbufErrorMsg.append("\n"); } System.out.println(); break; } System.out.print('.'); } switch (requestState) { case "completed": // success. break; default: sbufErrorMsg.append("fail to update class: " + requestState); return false; } } return true; }