- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我是 Azure 以及共享点与 Java 集成的新手。
我正在尝试将 Java 与 Sharepoint 集成。 Sharepoint-Office 365 可在 Azure ADFS 中使用。我需要编写一个 Java 程序来进行身份验证,然后使用 Sharepoint 提供的 RESTful API 访问文件。 Azure 正在使用 WS-Federation 身份验证过程。我一直在尝试寻找可以帮助我使用 WS-F 身份验证然后访问文件的代码。我找不到任何有用的 Material 。
基本身份验证不起作用,我也没有参与过 WS-F 身份验证。所以不知道从哪里开始。我还使用了Office-365-sdk执行此操作,但无法执行此操作,因为它使用与我的应用程序不相关的客户端 ID 和其他属性。例如,不需要客户端 ID,因为共享点已经可用。
我得到了this link也是如此,但是缺少一些方法,并且它没有解释用于实现的库。请指导我实现这一点。
最佳答案
这是来自 article 的代码您提到的:
package com.waveaccess.someproject.commons.service;
import com.waveaccess.someproject.commons.config.Const;
import com.waveaccess.someproject.commons.config.properties.SharePointProperties;
import com.waveaccess.someproject.commons.service.exceptions.SharePointAuthenticationException;
import com.waveaccess.someproject.commons.service.exceptions.SharePointSignInException;
import com.google.common.base.Joiner;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.json.JSONException;
import org.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.RequestEntity;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.RestTemplate;
import org.springframework.xml.transform.StringSource;
import org.springframework.xml.xpath.XPathExpression;
import org.w3c.dom.Document;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerException;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMResult;
import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
/**
* @author Maksim Kanev
*/
@Service
public class SharePointServiceCached {
private static final Logger log = LoggerFactory.getLogger(SharePointServiceCached.class);
@Autowired
private RestTemplate restTemplate;
@Autowired
private SharePointProperties sharePointProperties;
@Autowired
private XPathExpression xPathExpression;
@Cacheable(Const.CACHE_NAME_TOKEN)
public String receiveSecurityToken(Long executionDateTime) throws TransformerException, URISyntaxException {
RequestEntity<String> requestEntity = new RequestEntity<>(buildSecurityTokenRequestEnvelope(), HttpMethod.POST, new URI(sharePointProperties.getEndpoint() + "/extSTS.srf"));
ResponseEntity<String> responseEntity = restTemplate.exchange(requestEntity, String.class);
DOMResult result = new DOMResult();
Transformer transformer = TransformerFactory.newInstance().newTransformer();
transformer.transform(new StringSource(responseEntity.getBody()), result);
Document definitionDocument = (Document) result.getNode();
String securityToken = xPathExpression.evaluateAsString(definitionDocument);
if (StringUtils.isBlank(securityToken)) {
throw new SharePointAuthenticationException("Unable to authenticate: empty token");
}
log.debug("Microsoft Online respond with Token: {}", securityToken);
return securityToken;
}
private String buildSecurityTokenRequestEnvelope() {
String envelopeTemplate = "<s:Envelope xmlns:s=\"http://www.w3.org/2003/05/soap-envelope\" xmlns:a=\"http://www.w3.org/2005/08/addressing\" xmlns:u=\"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd\"> <s:Header> <a:Action s:mustUnderstand=\"1\">http://schemas.xmlsoap.org/ws/2005/02/trust/RST/Issue</a:Action> <a:ReplyTo> <a:Address>http://www.w3.org/2005/08/addressing/anonymous</a:Address> </a:ReplyTo> <a:To s:mustUnderstand=\"1\">https://login.microsoftonline.com/extSTS.srf</a:To> <o:Security s:mustUnderstand=\"1\" xmlns:o=\"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd\"> <o:UsernameToken> <o:Username>%s</o:Username> <o:Password>%s</o:Password> </o:UsernameToken> </o:Security> </s:Header><s:Body><t:RequestSecurityToken xmlns:t=\"http://schemas.xmlsoap.org/ws/2005/02/trust\"><wsp:AppliesTo xmlns:wsp=\"http://schemas.xmlsoap.org/ws/2004/09/policy\"><a:EndpointReference><a:Address>" + sharePointProperties.getEndpoint() + "</a:Address></a:EndpointReference></wsp:AppliesTo><t:KeyType>http://schemas.xmlsoap.org/ws/2005/05/identity/NoProofKey</t:KeyType> <t:RequestType>http://schemas.xmlsoap.org/ws/2005/02/trust/Issue</t:RequestType> <t:TokenType>urn:oasis:names:tc:SAML:1.0:assertion</t:TokenType></t:RequestSecurityToken></s:Body></s:Envelope>";
return String.format(envelopeTemplate, sharePointProperties.getUsername(), sharePointProperties.getPassword());
}
@Cacheable(Const.CACHE_NAME_COOKIE)
public List<String> getSignInCookies(String securityToken) throws TransformerException, URISyntaxException {
RequestEntity<String> requestEntity = new RequestEntity<>(securityToken, HttpMethod.POST, new URI(sharePointProperties.getEndpoint() + "/_forms/default.aspx?wa=wsignin1.0"));
ResponseEntity<String> responseEntity = restTemplate.exchange(requestEntity, String.class);
HttpHeaders headers = responseEntity.getHeaders();
List<String> cookies = headers.get("Set-Cookie");
if (CollectionUtils.isEmpty(cookies)) {
throw new SharePointSignInException("Unable to sign in: no cookies returned in response");
}
log.debug("SharePoint respond with cookies: {}", Joiner.on(", ").join(cookies));
return cookies;
}
public String getFormDigestValue(List<String> cookies) throws IOException, URISyntaxException, TransformerException, JSONException {
MultiValueMap<String, String> headers = new LinkedMultiValueMap<>();
headers.add("Cookie", Joiner.on(';').join(cookies));
headers.add("Accept", "application/json;odata=verbose");
headers.add("X-ClientService-ClientTag", "SDK-JAVA");
RequestEntity<String> requestEntity = new RequestEntity<>(headers, HttpMethod.POST, new URI(sharePointProperties.getEndpoint() + "/_api/contextinfo"));
ResponseEntity<String> responseEntity = restTemplate.exchange(requestEntity, String.class);
JSONObject json = new JSONObject(responseEntity.getBody());
return json.getJSONObject("d")
.getJSONObject("GetContextWebInformation")
.getString("FormDigestValue");
}
public Long parseExecutionDateTime(Date dateTime) {
if (dateTime == null)
return null;
final Calendar cal = Calendar.getInstance();
cal.setTime(dateTime);
cal.set(Calendar.HOUR_OF_DAY, 0);
cal.set(Calendar.MINUTE, 0);
cal.set(Calendar.SECOND, 0);
cal.set(Calendar.MILLISECOND, 0);
return cal.getTime().getTime();
}
}
应按如下方式调用此服务的方法:
package com.waveaccess.someproject.commons.service;
import com.google.common.base.Joiner;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpMethod;
import org.springframework.http.RequestEntity;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.RestTemplate;
import java.net.URI;
import java.util.Date;
import java.util.List;
/**
* @author Maksim Kanev
*/
@Service
public class SharePointService {
private static final Logger log = LoggerFactory.getLogger(SharePointService.class);
@Autowired
private SharePointServiceCached serviceCached;
@Autowired
private RestTemplate restTemplate;
public String performHttpRequest(HttpMethod method, String path) throws Exception {
Long executionDateTime = serviceCached.parseExecutionDateTime(new Date());
String securityToken = serviceCached.receiveSecurityToken(executionDateTime);
List<String> cookies = serviceCached.getSignInCookies(securityToken);
MultiValueMap<String, String> headers = new LinkedMultiValueMap<>();
headers.add("Cookie", Joiner.on(';').join(cookies));
RequestEntity<String> requestEntity = new RequestEntity<>(headers, method, new URI(path));
ResponseEntity<String> responseEntity = restTemplate.exchange(requestEntity, String.class);
String responseBody = responseEntity.getBody();
log.debug(responseBody);
return responseBody;
}
public String performHttpRequest(String path, String json, boolean isUpdate, boolean isWithDigest) throws Exception {
Long executionDateTime = serviceCached.parseExecutionDateTime(new Date());
String securityToken = serviceCached.receiveSecurityToken(executionDateTime);
List<String> cookies = serviceCached.getSignInCookies(securityToken);
String formDigestValue = serviceCached.getFormDigestValue(cookies);
MultiValueMap<String, String> headers = new LinkedMultiValueMap<>();
headers.add("Cookie", Joiner.on(';').join(cookies));
headers.add("Content-type", "application/json;odata=verbose");
if (isWithDigest) {
headers.add("X-RequestDigest", formDigestValue);
}
if (isUpdate) {
headers.add("X-HTTP-Method", "MERGE");
headers.add("IF-MATCH", "*");
}
RequestEntity<String> requestEntity = new RequestEntity<>(json, headers, HttpMethod.POST, new URI(path));
ResponseEntity<String> responseEntity = restTemplate.exchange(requestEntity, String.class);
String responseBody = responseEntity.getBody();
log.debug(responseBody);
return responseBody;
}
public String attachFile(String path, byte[] file) throws Exception {
Long executionDateTime = serviceCached.parseExecutionDateTime(new Date());
String securityToken = serviceCached.receiveSecurityToken(executionDateTime);
List<String> cookies = serviceCached.getSignInCookies(securityToken);
String formDigestValue = serviceCached.getFormDigestValue(cookies);
MultiValueMap<String, String> headers = new LinkedMultiValueMap<>();
headers.add("Cookie", Joiner.on(';').join(cookies));
headers.add("X-RequestDigest", formDigestValue);
headers.add("content-length", String.valueOf(file.length));
RequestEntity<byte[]> requestEntity = new RequestEntity<>(file, headers, HttpMethod.POST, new URI(path));
ResponseEntity<String> responseEntity = restTemplate.exchange(requestEntity, String.class);
String responseBody = responseEntity.getBody();
log.debug(responseBody);
return responseBody;
}
}
XPathExpressionFactoryBean的配置:
package com.waveaccess.someproject.commons.config;
import com.waveaccess.someproject.commons.config.properties.SharePointProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.xml.xpath.XPathExpressionFactoryBean;
import java.util.HashMap;
import java.util.Map;
/**
* @author Maksim Kanev
*/
@Configuration
@EnableConfigurationProperties({SharePointProperties.class})
public class SharePointConfiguration {
@Bean
public XPathExpressionFactoryBean securityTokenExpressionFactoryBean() {
XPathExpressionFactoryBean xPathExpressionFactoryBean = new XPathExpressionFactoryBean();
xPathExpressionFactoryBean.setExpression("/S:Envelope/S:Body/wst:RequestSecurityTokenResponse/wst:RequestedSecurityToken/wsse:BinarySecurityToken");
Map<String, String> namespaces = new HashMap<>();
namespaces.put("S", "http://www.w3.org/2003/05/soap-envelope");
namespaces.put("wsse", "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd");
namespaces.put("wsu", "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd");
namespaces.put("wsa", "http://www.w3.org/2005/08/addressing");
namespaces.put("wst", "http://schemas.xmlsoap.org/ws/2005/02/trust");
xPathExpressionFactoryBean.setNamespaces(namespaces);
return xPathExpressionFactoryBean;
}
}
最后是SharePointProperties
:
package com.waveaccess.someproject.commons.config.properties;
import org.springframework.boot.context.properties.ConfigurationProperties;
/**
* @author Maksim Kanev
*/
@ConfigurationProperties("sharepoint")
public class SharePointProperties {
private String username;
private String password;
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
关于java - 使用 Java 访问 Azure 中的 Office 365(sharepoint REST api),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40601341/
我对 Office Scripts 和 Office Lab 感到困惑。 两者都可以在 Excel 中运行 javascript,但似乎无法在它们中共享代码。 对于 Office 脚本,一些代码如 f
如果我们加载一个引用 office.js 的网页在 Office 客户端之外,我们会收到警告:Office.js is loaded outside of Office client . 这些信息很有
我试图找到一种将 Outlook 插件发布到办公商店的方法。但我发现我们只能发布 Office 应用程序,而不能发布 Office 商店的加载项。因此我想知道 Office 应用程序和 Office
我想使用 Ooxml 以编程方式自定义“Heading1”和“Heading2”样式通过 office.js Visual Studio 代码中的库。我已经搜索过谷歌和许多文档,但仍然没有得到任何内容
我想使用 Microsoft.Office.Interop.Excel 从 XLS 文件中提取一些数据。我安装了 Visual Studio 2010 和 Office 开发人员工具。但是,我在 va
最近,Microsoft 推出了 Office 插件架构,该架构允许开发远程托管并在 Office 内的 IFrame 中运行的插件。我读了很多文章,试图了解这个架构是否是 VSTO 的替代品,或者它
我开发了一个将数据导入 Microsoft Excel 的应用程序。 我使用 VS2005 + .NET 2.0,并且我的计算机上安装了 Microsoft Office 2007 (Office 1
是否有推荐的方法(包、框架等)来设置 Office 加载项的自动化端到端测试。我对测试的所有搜索都导致侧加载应用程序和手动测试。 例如:https://dev.office.com/docs/add-
我们正在为 Excel 和 Word 开发 javascript Office 插件。我们的用户将使用 Office Desktop 和 Office Online。 当用户在加载项中创建新记录时,我
我在电子表格上有一个表格,我想删除所有现有数据。我使用下面的代码,除非表格已经是空的。 // Get the row count let rowCount = table.getRangeBetwee
所以我正在尝试开始开发 Office 365 加载项(以前的 Office 应用程序),我想知道 Office 在呈现您的应用程序时使用什么浏览器或浏览器引擎。我尝试使用 JavaScript 的 n
我正在寻找一些关于在 网上商店 上托管我们当前托管应用程序的更新版本的信息。 我的查询是,我们现有版本的应用程序说的 list 文件 版本。 1.0 托管在网上商店指向源位置(天蓝色 网站)说 mya
在我们的组织中,我们构建了一个 Office 加载项。现在我们想在我们的加载项中添加打印功能。谁能帮助我如何使用 Office javascript API 添加打印功能。 最佳答案 Office.J
我有兴趣了解有关 Microsoft Office Communicator 的更多信息IM 客户端,以及它如何确定您的存在(即您是在计算机旁还是不在)。任何人都可以向我指出解释这一点的教程或 API
问题: 我有两个电子表格,每个电子表格都有不同的用途,但包含一个特定的数据,这两个电子表格中的数据需要相同。这条数据(其中一列)在电子表格 A 中更新,但也需要在电子表格 B 中更新。 目标: 以某种
可在此处获得office.js的正式版本: https://appsforoffice.microsoft.com/lib/1/hosted/office.js 它在代码中包含以下几行: window
不久前我有了一个发现。只需按照以下步骤操作: 在 Office 2003 中创建一个 .doc/.xls/.ppt 文件。在其中保留一些测试数据并关闭该文件。现在重命名该文件以将其文件扩展名更改为随机
姓名:来自:file:///D:/Samples/TestUpdatedVersion/bin/Debug/TestUpdatedVersion.vsto 无法安装自定义,因为当前已安装另一个版本并且
已结束。此问题正在寻求书籍、工具、软件库等的推荐。它不满足Stack Overflow guidelines 。目前不接受答案。 我们不允许提出寻求书籍、工具、软件库等推荐的问题。您可以编辑问题,以便
我对使用 Office 2007 在 2007 之前的二进制格式(.doc、.xls、.ppt)和新的 Office Open XML 格式(.docx、.xlsx、.pptx)之间进行转换很感兴趣
我是一名优秀的程序员,十分优秀!