摘要:本教程提供了一个JSP示例以及如何将其与Salesforce REST API集成。 我们将逐步完成创建外部客户端以使用Force.com (同时使用HTTP(S)和JSON)管理您的数据的分步过程。

在此示例中,我将Mac OS X 10.9.2与Apache Tomcat 7服务器和Java 1.7一起使用。 Eclipse Java EE版是用于开发和测试的IDE。 本教程中给出的说明也应适用于其他平台的较小修改。

如果要访问本教程中的整个示例代码,则可以在以下位置访问它: github.com/seethaa/force_rest_example

所有代码已更新为可与httpclient 4.3库一起使用。

什么是REST?

REST代表表象小号泰特贸易交接,并且是无状态的客户端-服务器通信协议通过HTTP。

为什么以及何时在Java中为JSP使用REST API

REST API非常适合需要大量交互并使用同步通信来传输数据的浏览器应用程序。 Salesforce REST API为简单的Web服务提供了与Force.com进行交互的编程接口,并支持XML和JSON格式。 Salesforce REST API非常适合移动应用程序或动态网站,以在Web服务器上快速检索或更新记录。 虽然应为BulkAPI保留批量记录检索,但此轻量级的REST API可以用于常见服务器页面,这些页面涉及快速更新和频繁的用户交互,例如更新单个用户记录。

设置您的开发帐户和前提条件

您将需要以下内容:

  1. 转到https://developer.salesforce.com/signup并注册您的免费DE帐户。 就本示例而言,即使您已经有一个帐户,我也建议注册一个Developer Edition。 这样可以确保您在启用了最新功能的情况下获得干净的环境。
  2. Java应用程序服务器。 我在Mac OS X和Eclipse上使用Apache Tomcat 7作为IDE创建了我的数据库。 http://developer.salesforce.com/page/Force.com_IDE上还有一个免费的Eclipse插件,但本教程使用了原始的Eclipse设置。
  3. 使用http://tomcat.apache.org/tomcat-7.0-doc/ssl-howto.html在Tomcat服务器上配置SSL。 如果您在Eclipse中进行开发,请确保在Eclipse环境中的server.xml文件中添加连接器部分,例如:
    <Connector SSLEnabled="true" clientAuth="false" keystoreFile="/Users/seetha/.keystore" keystorePass="password" maxThreads="200" port="8443" protocol="HTTP/1.1" scheme="https" secure="true" sslProtocol="TLS"/>
  4. 将所需的jar文件添加到WebContent / WEBINF / lib。 您将需要commons-codec-1.6.jar , httpclient4.3.3.jar , httpcore-4.3.2.jar , commons-logging-1.1.3.jar和java-json.jar 。 对于Eclipse,我还必须确保所有jar都已添加到构建路径(右键单击Project→Build Path→配置构建路径→选择Libraries选项卡→单击Add Jars→从WEBINF / lib文件夹中选择Jar文件。

创建一个连接的应用程序

  1. 返回Force.com DE,通过控制台创建一个新的Connected App。 单击设置→构建→创建→应用程序。 向下滚动到“已连接的应用程序”部分,然后单击“新建”按钮。

    • 确保回调URL为http:// localhost:8080 / <your_app_context_path> / oauth / _callback

      (您可以通过返回Eclipse找到应用程序上下文路径:右键单击Project→Properties→Web Project Settings→Context root)

    • 选中“启用OAuth设置”复选框
    • 本教程所需的OAuth范围(请参见图1)是“访问和管理数据(api)”和“通过Web提供对数据的访问”(web),但是应根据您的要求更改这些范围。
    • 图1:创建新的连接的应用程序

  2. 复制ClientID和Client Secret(参见图2),因为这两个都将在下一步中使用。

    图2:具有用户密钥和机密的连接的应用程序示例

    认证方式

    需要将三个文件导入到您的JSP项目中,如下所示:

    index.html

    <!DOCTYPE html PUBLIC "­//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <meta http­equiv="Content­Type" content="text/html; charset=UTF­8">
    <title>REST/OAuth Example</title>
    </head>
    <body><script type="text/javascript"  language="javascript">if (location.protocol != "https:") {document.write("OAuth  will not work correctly from plain http. "+ "Please use an https URL.");} else {document.write("<a href=\"oauth\">Run Connected App demo via REST/OAuth.</a>");}</script>
    </body>
    </html>

    OAuthConnectedApp.java

    import java.io.IOException;
    import java.io.InputStream;
    import java.io.UnsupportedEncodingException;
    import java.net.URLEncoder;
    import java.util.ArrayList;
    import java.util.List;import javax.servlet.ServletException;
    import javax.servlet.annotation.WebInitParam;
    import javax.servlet.annotation.WebServlet;
    import javax.servlet.http.HttpServlet;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;import org.apache.http.Consts;
    import org.apache.http.HttpEntity;
    import org.apache.http.NameValuePair;
    import org.apache.http.client.entity.UrlEncodedFormEntity;
    import org.apache.http.client.methods.CloseableHttpResponse;
    import org.apache.http.client.methods.HttpPost;
    import org.apache.http.impl.client.CloseableHttpClient;
    import org.apache.http.impl.client.HttpClients;
    import org.apache.http.message.BasicNameValuePair;import org.json.JSONException;
    import org.json.JSONObject;
    import org.json.JSONTokener;@WebServlet(name  = "oauth", urlPatterns = { "/oauth/*", "/oauth" }, initParams = {
    // clientId is 'Consumer Key' in the Remote Access UI
    //**Update with your own Client ID
    @WebInitParam(name  = "clientId", value = "3MVG9JZ_r.QzrS7jzujCYrebr8kajDEcjXQLXnV9nGU6PaxOjuOi_n8EcUf0Ix9qqk1lYCa4_Jaq7mpqxi2YT"),
    // clientSecret is 'Consumer Secret' in the Remote Access UI
    //**Update with your own Client Secret
    @WebInitParam(name  = "clientSecret", value = "2307033558641049067"),
    // This must be identical to 'Callback URL' in the Remote Access UI
    //**Update with your own URI
    @WebInitParam(name  = "redirectUri", value = "http://localhost:8080/force_rest_example/oauth/_callback"),
    @WebInitParam(name  = "environment", value = "https://login.salesforce.com"), })/**
    * Servlet parameters
    * @author  seetha
    *
    */
    public class OAuthConnectedApp  extends HttpServlet {private static final long serialVersionUID = 1L;private static final String ACCESS_TOKEN = "ACCESS_TOKEN";private static final String INSTANCE_URL = "INSTANCE_URL";private String clientId = null;private String clientSecret = null;private String redirectUri = null;private String environment = null;private String authUrl = null;private String tokenUrl = null;public void init() throws ServletException {clientId = this.getInitParameter("clientId");clientSecret = this.getInitParameter("clientSecret");redirectUri = this.getInitParameter("redirectUri");environment = this.getInitParameter("environment");try {authUrl = environment+ "/services/oauth2/authorize?response_type=code&client_id="+ clientId + "&redirect_uri="+ URLEncoder.encode(redirectUri, "UTF­8");}catch (UnsupportedEncodingException e) {throw new ServletException(e);}tokenUrl = environment + "/services/oauth2/token";}protected void doGet(HttpServletRequest request, HttpServletResponse  response) throws ServletException, IOException {String accessToken = (String) request.getSession().getAttribute(ACCESS_TOKEN);//System.out.println("calling doget");if (accessToken == null) {String instanceUrl = null;if (request.getRequestURI().endsWith("oauth")) {// we need to send the user to authorizeresponse.sendRedirect(authUrl);return;}else {System.out.println("Auth successful ­ got callback");String code = request.getParameter("code");// Create an instance of HttpClient.CloseableHttpClient  httpclient = HttpClients.createDefault();try{// Create an instance of HttpPost.HttpPost httpost = new HttpPost(tokenUrl);// Adding all form parameters in a List of type NameValuePairList<NameValuePair>  nvps = new ArrayList<NameValuePair>();nvps.add(new BasicNameValuePair("code", code));nvps.add(new BasicNameValuePair("grant_type","authorization_code"));nvps.add(new BasicNameValuePair("client_id", clientId));nvps.add(new BasicNameValuePair("client_secret", clientSecret));nvps.add(new BasicNameValuePair("redirect_uri", redirectUri));httpost.setEntity(new  UrlEncodedFormEntity(nvps, Consts.UTF_8));// Execute the request.CloseableHttpResponse closeableresponse=httpclient.execute(httpost);System.out.println("Response Statusline:"+closeableresponse.getStatusLine());try {// Do the needful with entity.HttpEntity entity = closeableresponse.getEntity();InputStream rstream = entity.getContent();JSONObject authResponse = new JSONObject(new JSONTokener(rstream));accessToken = authResponse.getString("access_token");instanceUrl = authResponse.getString("instance_url");} catch (JSONException e) {// TODO Auto­generated catch block e.printStackTrace();e.printStackTrace();} finally {// Closing the responsecloseableresponse.close();}} finally {httpclient.close();}}// Set a session attribute so that other servlets can get the access tokenrequest.getSession().setAttribute(ACCESS_TOKEN, accessToken);// We also get the instance URL from the OAuth response, so set it in the session toorequest.getSession().setAttribute(INSTANCE_URL, instanceUrl);}response.sendRedirect(request.getContextPath() + "/ConnectedAppREST");}}

    ConnectedAppREST.java

    import java.io.IOException;
    import java.io.InputStream;
    import java.io.PrintWriter;
    import java.net.URISyntaxException;
    import java.util.Iterator;import javax.servlet.ServletException;
    import javax.servlet.annotation.WebServlet;
    import javax.servlet.http.HttpServlet;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;import org.apache.http.HttpEntity;
    import org.apache.http.HttpStatus;
    import org.apache.http.client.methods.CloseableHttpResponse;
    import org.apache.http.client.methods.HttpDelete;
    import org.apache.http.client.methods.HttpGet;
    import org.apache.http.client.methods.HttpPost;
    import org.apache.http.client.utils.URIBuilder;
    import org.apache.http.entity.ContentType;
    import org.apache.http.entity.StringEntity;
    import org.apache.http.impl.client.CloseableHttpClient;
    import org.apache.http.impl.client.HttpClients;import org.json.JSONArray;
    import org.json.JSONException;
    import org.json.JSONObject;
    import org.json.JSONTokener;@WebServlet(urlPatterns = { "/ConnectedAppREST"  })
    /**
    * Demo for Connect App/REST API
    * @author  seetha
    *
    */
    public class ConnectedAppREST  extends HttpServlet {private static final long serialVersionUID = 1L;private static final String ACCESS_TOKEN = "ACCESS_TOKEN";private static final String INSTANCE_URL = "INSTANCE_URL";private void showAccounts(String  instanceUrl, String accessToken,PrintWriter writer) throws ServletException, IOException {CloseableHttpClient  httpclient = HttpClients.createDefault();HttpGet httpGet = new HttpGet();//add key and valuehttpGet.addHeader("Authorization", "OAuth " + accessToken);try {URIBuilder builder = new URIBuilder(instanceUrl+ "/services/data/v30.0/query");builder.setParameter("q", "SELECT Name, Id from Account LIMIT 100");httpGet.setURI(builder.build());CloseableHttpResponse  closeableresponse = httpclient.execute(httpGet);System.out.println("Response Status line :" + closeableresponse.getStatusLine());if (closeableresponse.getStatusLine().getStatusCode() == HttpStatus.SC_OK) {// Now lets use the standard java json classes to work with the resultstry {// Do the needful with entity.HttpEntity entity = closeableresponse.getEntity();InputStream rstream = entity.getContent();JSONObject authResponse = new JSONObject(new JSONTokener(rstream));System.out.println("Query response: " + authResponse.toString(2));writer.write(authResponse.getInt("totalSize") + " record(s) returned\n\n");JSONArray results = authResponse.getJSONArray("records");for (int i = 0; i < results.length(); i++) {writer.write(results.getJSONObject(i).getString("Id")+ ", "+ results.getJSONObject(i).getString("Name")+ "\n");}writer.write("\n");}catch (JSONException e) {e.printStackTrace();throw new ServletException(e);}}} catch (URISyntaxException  e1) {// TODO Auto­generated catch blocke1.printStackTrace();} finally {httpclient.close();}}private String createAccount(String  name, String instanceUrl,String accessToken, PrintWriter writer) throws ServletException, IOException {String accountId = null;CloseableHttpClient  httpclient = HttpClients.createDefault();JSONObject account = new JSONObject();try {account.put("Name",  name);}catch (JSONException e) {e.printStackTrace();throw new ServletException(e);}HttpPost httpost = new HttpPost(instanceUrl+  "/services/data/v30.0/sobjects/Account/");httpost.addHeader("Authorization", "OAuth " + accessToken);StringEntity messageEntity = new StringEntity( account.toString(), ContentType.create("application/json"));httpost.setEntity(messageEntity);// Execute the request.CloseableHttpResponse  closeableresponse = httpclient.execute(httpost);System.out.println("Response Status line :" + closeableresponse.getStatusLine());try {writer.write("HTTP status " + closeableresponse.getStatusLine().getStatusCode() + " creating account\n\n");if (closeableresponse.getStatusLine().getStatusCode()  == HttpStatus.SC_CREATED) {try {// Do the needful with entity.HttpEntity entity = closeableresponse.getEntity();InputStream rstream = entity.getContent();JSONObject authResponse = new JSONObject(new JSONTokener(rstream));System.out.println("Create response: " + authResponse.toString(2));if (authResponse.getBoolean("success")) {accountId = authResponse.getString("id");writer.write("New record id " + accountId + "\n\n");}} catch (JSONException e) {e.printStackTrace();// throw new ServletException(e);}}}finally {httpclient.close();}return accountId;}private void showAccount(String  accountId, String instanceUrl,String accessToken, PrintWriter writer) throws ServletException, IOException {CloseableHttpClient  httpclient = HttpClients.createDefault();HttpGet httpGet = new HttpGet();//add key and valuehttpGet.addHeader("Authorization", "OAuth " + accessToken);try {URIBuilder builder = new URIBuilder(instanceUrl + "/services/data/v30.0/sobjects/Account/" + accountId);httpGet.setURI(builder.build());//httpclient.execute(httpGet);CloseableHttpResponse  closeableresponse = httpclient.execute(httpGet);System.out.println("Response Status line :" + closeableresponse.getStatusLine());if (closeableresponse.getStatusLine().getStatusCode()  == HttpStatus.SC_OK) {try {// Do the needful with entity.HttpEntity entity = closeableresponse.getEntity();InputStream rstream = entity.getContent();JSONObject authResponse = new JSONObject(new JSONTokener(rstream));System.out.println("Query response: " + authResponse.toString(2));writer.write("Account  content\n\n");Iterator iterator = authResponse.keys();while (iterator.hasNext()) {String key = (String) iterator.next();Object obj = authResponse.get(key);String value = null;if (obj instanceof String) {value = (String) obj;}writer.write(key + ":" + (value != null ? value : "") + "\n");}writer.write("\n");} catch (JSONException e) {e.printStackTrace();throw new ServletException(e);}}}catch (URISyntaxException  e1) {// TODO Auto­generated catch blocke1.printStackTrace();} finally {httpclient.close();}}private void updateAccount(String  accountId, String newName, String city, String instanceUrl, String accessToken, PrintWriter writer) throws ServletException, IOException {CloseableHttpClient  httpclient = HttpClients.createDefault();JSONObject update = new JSONObject();try {update.put("Name", newName);update.put("BillingCity", city);}catch (JSONException e) {e.printStackTrace();throw new ServletException(e);}HttpPost httpost = new HttpPost(instanceUrl + "/services/data/v30.0/sobjects/Account/" +accountId+"?_HttpMethod=PATCH");httpost.addHeader("Authorization", "OAuth " + accessToken);StringEntity messageEntity = new StringEntity( update.toString(), ContentType.create("application/json"));httpost.setEntity(messageEntity);// Execute the request.CloseableHttpResponse  closeableresponse = httpclient.execute(httpost); System.out.println("Response Status line :" + closeableresponse.getStatusLine());try {writer.write("HTTP status " + closeableresponse.getStatusLine().getStatusCode() + " updating account " + accountId + "\n\n");} finally {httpclient.close();}}private void deleteAccount(String  accountId, String instanceUrl, String accessToken, PrintWriter writer) throws IOException {CloseableHttpClient  httpclient = HttpClients.createDefault();HttpDelete delete = new HttpDelete(instanceUrl + "/services/data/v30.0/sobjects/Account/" + accountId);delete.setHeader("Authorization", "OAuth " + accessToken);// Execute the request.CloseableHttpResponse  closeableresponse = httpclient.execute(delete);System.out.println("Response Status line :" + closeableresponse.getStatusLine());try {writer.write("HTTP status " + closeableresponse.getStatusLine().getStatusCode() + " deleting account " + accountId + "\n\n");} finally {delete.releaseConnection();}}/*** @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse*      response)*/@Overrideprotected void doGet(HttpServletRequest request, HttpServletResponse  response) throws ServletException, IOException {PrintWriter writer = response.getWriter();String accessToken = (String) request.getSession().getAttribute( ACCESS_TOKEN);String instanceUrl = (String) request.getSession().getAttribute( INSTANCE_URL);if (accessToken == null) {writer.write("Error ­ no access token");return;}writer.write("We have an access token: " + accessToken + "\n" + "Using instance " + instanceUrl + "\n\n");showAccounts(instanceUrl, accessToken, writer);String accountId = createAccount("My New Org", instanceUrl, accessToken, writer);if (accountId == null) {System.out.println("Account ID null");}showAccount(accountId,  instanceUrl, accessToken, writer);showAccounts(instanceUrl, accessToken, writer);updateAccount(accountId, "My New Org, Inc", "San Francisco", instanceUrl, accessToken, writer);showAccount(accountId,  instanceUrl, accessToken, writer);deleteAccount(accountId, instanceUrl, accessToken, writer);showAccounts(instanceUrl, accessToken, writer);}}
  3. 更改OAuthConnectedApp.java以基于Connected App配置替换Client ID,Client Secret和Callback URI字段。
  4. 在Eclipse(请参见图3)中或从外部启动Tomcat服务器,并导航到https:// localhost:8443 / <your_app_context_path> /

    图3:在Eclipse中运行Tomcat服务器

    图4:检索对象屏幕

  5. 除非通过HTTPS,否则单击上面的链接(请参见图4)将不起作用,并且必须将SSL配置为Tomcat的端点。

    如果所有配置都正确完成,您应该会看到一个salesforce.com登录屏幕(请参见图5)。 继续并使用salesforce.com凭据登录以授权Web应用程序访问资源。

    图5:OAuth的Salesforce.com登录屏幕

  6. 登录将允许ConnectedAppREST演示执行创建,显示,更新和删除记录的方法(请参见图6)。

    图6:Connected App REST演示的输出

*提示和警告

  1. 确保您拥有一个Developer Edition(DE)帐户,因为Professional,Enterprise,Developer等之间存在细微差别。Developer版本是免费的,并且不会过期(除非一年后未使用)。
  2. OAuthConnectedApp.java中的回调URL必须与添加到连接的应用程序的URL相同。
  3. 如果收到HTTP 403错误,则表示正在访问您请求的资源“被禁止”。 检查您用来访问的用户名/帐户是否具有适当的权限。
  4. 确保index.html直接在WebContent目录下。

资源资源

有关全面的设置或资源,请访问: http : //developer.salesforce.com/en/mobile/resources

参考文献

  1. Force.com REST API开发人员指南 (PDF)
  2. 使用Force.com REST API

翻译自: https://www.javacodegeeks.com/2014/06/how-to-use-salesforce-rest-api-with-your-javaserver-pages.html

如何在JavaServer Pages中使用Salesforce REST API相关推荐

  1. javaserver_如何在JavaServer Pages中使用Salesforce REST API

    javaserver 摘要:本教程提供了一个JSP示例以及如何将其与Salesforce REST API集成. 我们将逐步完成创建外部客户端以使用Force.com (同时使用HTTP(S)和JSO ...

  2. 如何在Vue项目中引入ArcGIS JavaScript API​ 创建三维可视化地图(含vue项目创建教程)

    新手上路之在Vue项目中引入ArcGIS API​ 视频教程 B站搜索 X北辰北,感谢up主无私的教学~ B站地址:https://www.bilibili.com/video/BV18E411K7B ...

  3. 如何优雅又庶民地在Github Pages中上线Ghost博客系统

    序篇 笔者对于「想要拥有个人网站」这事儿,在过去几年总会偶尔灵光一现,心血来潮地买下几个月的轻应用服务器以及域名,然后兴高采烈地架设起来,更换各种博客主题,记录一些学习心得:然而,潮起之后马上潮落,有 ...

  4. 微软word开机自启动_如何在Microsoft Word中创建自定义封面

    微软word开机自启动 A great cover page draws in readers. If you use Microsoft Word, you're in luck, because ...

  5. 【ASP.NET教程-WP教程08】ASP.NET Web Pages - 文件-在ASP.NET Web Pages中处理文件和实现文件上传功能的介绍

    ASP.NET Web Pages - 文件处理与上传 在ASP.NET Web Pages开发中,文件处理和上传是常见的任务之一.文件处理涉及到多个方面,包括文件的读取.写入.复制.移动和删除等操作 ...

  6. 实例讲解如何在DB2 UDB中正确的监控死锁

    实例讲解如何在DB2 UDB中正确的监控死锁 aS,?Kr P   前言:这篇文章通过详细的实例阐述了如何在DB2 UDB 中监控死锁的发生.在DB2 UDB中有两种类型的监控器:快照监控器和事件监控 ...

  7. 如何在sqlite3连接中创建并调用自定义函数

    #!/user/bin/env python # @Time :2018/6/8 14:44 # @Author :PGIDYSQ #@File :CreateFunTest.py '''如何在sql ...

  8. Iar环境c语言调用汇编函数,如何在IAR EWARM中通过内联汇编程序在另一个模块中调用C函数?...

    我在硬故障处理程序中有一些程序集.程序集基本上是为了传递当前堆栈指针作为参数(在R0中).它看起来像这样...如何在IAR EWARM中通过内联汇编程序在另一个模块中调用C函数? __asm(&quo ...

  9. 学习如何在AutoCad土木工程中绘制建筑设计图

    学习如何在AutoCad中绘制建筑设计图从平面图到AutoCad土木工程中的整栋建筑 你会学到: 如何绘制房屋地图 如何绘制建筑设计 如何从AutoCad打印或出图 AutoCaD使用 AutoCaD ...

最新文章

  1. 用Php设置Iptables,如何使用CSF添加自定义iptables规则
  2. [K/3Cloud]进度条控件编程接口
  3. Python学习笔记:Day4 编写Model
  4. 1标志图片_这四种情况将不再扣分罚款!11月起,全国高速统一限速标志
  5. 跟我一起学.NetCore之日志(Log)模型核心
  6. 吵架后女生和男生的夜晚!所有男生都这样吗?
  7. 用 @Value(“${xxxx}“)注解从配置文件读取值的用法
  8. Windows Maven环境变量配置
  9. 【Antlr】Antlr重写输入流
  10. C语言排序方法-----二元选择排序法
  11. 【BZOJ5249】【九省联考2018】—IIIDX(线段树)
  12. 关于==和equals的探索
  13. 09. 斐波那契数列(C++版本)
  14. mybatis动态sql,条件判断详解示例
  15. 如何将txt文件转为EXCEL文件?
  16. fractal 分形维数 盒子维 纹理特征
  17. 电脑键盘指法的正确练习步骤
  18. php中的implode,php里implode是什么意思
  19. 期货市场倒挂什么意思(期货市场倒挂什么意思啊)
  20. RMAN Recipes 中对Flash Recovery Area的总结

热门文章

  1. JavaWeb前端之AJAX的初步学习
  2. 部署kafka kafka的service容器和zookeeper kafka客户端 Elasticsearch的客户端
  3. 登录系统 提示框_实物资产管理软件操作手册(职员和系统用户)
  4. sap wad_使用网真和WAD热部署Kubernetes
  5. cassandra可视化_容器化Spring Data Cassandra应用程序
  6. netflix 模式创新_创新设计模式:工厂模式
  7. 过滤器过滤特定的url_如何从过滤器中排除URL
  8. lagom的微服务框架_微服务有麻烦吗? Lagom在这里为您提供帮助。 试试吧!
  9. netbeans连接数据库_NetBeans Java EE技巧#1 –数据库中的实体类
  10. java8 streams_Java SE 8新功能介绍:使用Streams API处理集合