|
@@ -10,11 +10,13 @@ import com.aliyuncs.profile.IClientProfile;
|
|
|
import com.aliyuncs.sts.model.v20150401.AssumeRoleRequest;
|
|
|
import com.aliyuncs.sts.model.v20150401.AssumeRoleResponse;
|
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
|
+import org.springframework.beans.factory.annotation.Value;
|
|
|
import org.springframework.data.redis.core.StringRedisTemplate;
|
|
|
import org.springframework.data.redis.core.ValueOperations;
|
|
|
import org.springframework.stereotype.Service;
|
|
|
|
|
|
import java.net.URL;
|
|
|
+import java.text.SimpleDateFormat;
|
|
|
import java.util.Date;
|
|
|
import java.util.concurrent.TimeUnit;
|
|
|
|
|
@@ -27,19 +29,76 @@ public class AliStsOssAuth {
|
|
|
@Autowired
|
|
|
private StringRedisTemplate stringRedisTemplate;
|
|
|
|
|
|
- private String accessKeyIdTemp = null;
|
|
|
- private String accessKeySecretTemp = null;
|
|
|
- private String securityTokenTemp = null;
|
|
|
-//
|
|
|
-// public AliStsOssAuth(StringRedisTemplate stringRedisTemplate) {
|
|
|
-// this.stringRedisTemplate = stringRedisTemplate;
|
|
|
-// }
|
|
|
-
|
|
|
+ //是否开启oss资源的临时授权
|
|
|
+ @Value("${oss.auth.enable}")
|
|
|
+ private int auth_enable;
|
|
|
// 目前只有"cn-hangzhou"这个region可用, 不要使用填写其他region的值
|
|
|
- public final String REGION_CN_HANGZHOU = "cn-hangzhou";
|
|
|
+ @Value("${oss.auth.REGION_CN_HANGZHOU}")
|
|
|
+ private String REGION_CN_HANGZHOU;
|
|
|
// 当前 STS API 版本
|
|
|
- public final String STS_API_VERSION = "2015-04-01";
|
|
|
- public AssumeRoleResponse assumeRole(String accessKeyId, String accessKeySecret,
|
|
|
+ @Value("${oss.auth.STS_API_VERSION}")
|
|
|
+ private String STS_API_VERSION;
|
|
|
+ // 只有 RAM用户(子账号)才能调用 AssumeRole 接口
|
|
|
+ // 阿里云主账号的AccessKeys不能用于发起AssumeRole请求
|
|
|
+ // 请首先在RAM控制台创建一个RAM用户,并为这个用户创建AccessKeys
|
|
|
+ @Value("${oss.auth.accessKeyId}")
|
|
|
+ private String accessKeyId;
|
|
|
+ @Value("${oss.auth.accessKeySecret}")
|
|
|
+ private String accessKeySecret;
|
|
|
+ // AssumeRole API 请求参数: RoleArn, RoleSessionName, Policy, and DurationSeconds
|
|
|
+ // RoleArn 需要在 RAM 控制台上获取
|
|
|
+ @Value("${oss.auth.roleArn}")
|
|
|
+ private String roleArn;
|
|
|
+ // RoleSessionName 是临时Token的会话名称,自己指定用于标识你的用户,主要用于审计,或者用于区分Token颁发给谁
|
|
|
+ // 但是注意RoleSessionName的长度和规则,不要有空格,只能有'-' '_' 字母和数字等字符
|
|
|
+ // 具体规则请参考API文档中的格式要求
|
|
|
+ private String roleSessionName = "yifang_oss_audio";
|
|
|
+ // 如何定制你的policy?
|
|
|
+ private String policy = "{\n" +
|
|
|
+ " \"Statement\": [\n" +
|
|
|
+ " {\n" +
|
|
|
+ " \"Action\": \"oss:*\",\n" +
|
|
|
+ " \"Effect\": \"Allow\",\n" +
|
|
|
+ " \"Resource\": \"*\"\n" +
|
|
|
+ " }\n" +
|
|
|
+ " ],\n" +
|
|
|
+ " \"Version\": \"1\"\n" +
|
|
|
+ "}";
|
|
|
+
|
|
|
+ //原始完整路径:http://efunaudio.oss-cn-beijing.aliyuncs.com/audio/001/00103035/00103035018.mp3
|
|
|
+ //endpoint,如"oss-cn-beijing.aliyuncs.com"
|
|
|
+ @Value("${oss.auth.endpoint}")
|
|
|
+ private String endpoint;
|
|
|
+ //bucket名称,如"efunaudio"
|
|
|
+ @Value("${oss.auth.bucketName}")
|
|
|
+ String bucketName;
|
|
|
+ //url授权链接的过期时间
|
|
|
+ @Value("${oss.auth.url_expiration}")
|
|
|
+ long urlExpiration;
|
|
|
+// //url的可以,如"audio/001/00103035/00103035018.mp3"
|
|
|
+// String key = "audio/001/00103035/00103035018.mp3";
|
|
|
+
|
|
|
+ private String accessKeyIdRole = null;
|
|
|
+ private String accessKeySecretRole = null;
|
|
|
+ private String securityTokenRole = null;
|
|
|
+
|
|
|
+ private final String accessKeyIdRoleSession = "OSS_AUTH_accessKeyIdRole";
|
|
|
+ private final String accessKeySecretRoleSession = "OSS_AUTH_accessKeySecretRole";
|
|
|
+ private final String securityTokenRoleSession = "OSS_AUTH_securityTokenRole";
|
|
|
+ private final String urlAuthSession = "OSS_AUTH_URL_";
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 向阿里申请下一步操作的token
|
|
|
+ * @param accessKeyId
|
|
|
+ * @param accessKeySecret
|
|
|
+ * @param roleArn
|
|
|
+ * @param roleSessionName
|
|
|
+ * @param policy
|
|
|
+ * @param protocolType
|
|
|
+ * @return AssumeRoleResponse
|
|
|
+ * @throws ClientException
|
|
|
+ */
|
|
|
+ private AssumeRoleResponse assumeRole(String accessKeyId, String accessKeySecret,
|
|
|
String roleArn, String roleSessionName, String policy,
|
|
|
ProtocolType protocolType) throws ClientException {
|
|
|
try {
|
|
@@ -62,42 +121,35 @@ public class AliStsOssAuth {
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- public void Auth(){
|
|
|
- // 只有 RAM用户(子账号)才能调用 AssumeRole 接口
|
|
|
- // 阿里云主账号的AccessKeys不能用于发起AssumeRole请求
|
|
|
- // 请首先在RAM控制台创建一个RAM用户,并为这个用户创建AccessKeys
|
|
|
- String accessKeyId = "LTAIwHeZreDzNDtR";
|
|
|
- String accessKeySecret = "gCTp82PM7B8liUrNlHqfLTQQTKLSAe";
|
|
|
- // AssumeRole API 请求参数: RoleArn, RoleSessionName, Policy, and DurationSeconds
|
|
|
- // RoleArn 需要在 RAM 控制台上获取
|
|
|
- String roleArn = "acs:ram::30370391:role/audioauth";
|
|
|
- // RoleSessionName 是临时Token的会话名称,自己指定用于标识你的用户,主要用于审计,或者用于区分Token颁发给谁
|
|
|
- // 但是注意RoleSessionName的长度和规则,不要有空格,只能有'-' '_' 字母和数字等字符
|
|
|
- // 具体规则请参考API文档中的格式要求
|
|
|
- String roleSessionName = "alice-001";
|
|
|
- // 如何定制你的policy?
|
|
|
- String policy = "{\n" +
|
|
|
- " \"Statement\": [\n" +
|
|
|
- " {\n" +
|
|
|
- " \"Action\": \"oss:*\",\n" +
|
|
|
- " \"Effect\": \"Allow\",\n" +
|
|
|
- " \"Resource\": \"*\"\n" +
|
|
|
- " }\n" +
|
|
|
- " ],\n" +
|
|
|
- " \"Version\": \"1\"\n" +
|
|
|
- "}";
|
|
|
+ /**
|
|
|
+ * 对oss的资源url进行临时访问授权
|
|
|
+ * @param url
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ public String AuthUrl(String url){
|
|
|
+ if(auth_enable<1){
|
|
|
+ return url;
|
|
|
+ }
|
|
|
+ String[] arr = url.split(endpoint+"/");
|
|
|
+ if(arr==null || arr.length<2){
|
|
|
+ System.out.println("fail to split url");
|
|
|
+ return url;
|
|
|
+ }
|
|
|
+ String key = arr[1];
|
|
|
// 此处必须为 HTTPS
|
|
|
ProtocolType protocolType = ProtocolType.HTTPS;
|
|
|
try {
|
|
|
- stringRedisTemplate.opsForValue().set("aaa", "111");
|
|
|
- System.out.println(stringRedisTemplate.opsForValue().get("aaa"));
|
|
|
ValueOperations valueOperations = stringRedisTemplate.opsForValue();
|
|
|
- if(valueOperations.get("accessKeyIdTemp")!=null
|
|
|
- && valueOperations.get("accessKeySecretTemp")!=null
|
|
|
- && valueOperations.get("securityTokenTemp")!=null ){
|
|
|
- accessKeyIdTemp = valueOperations.get("accessKeyIdTemp").toString();
|
|
|
- accessKeySecretTemp = valueOperations.get("accessKeySecretTemp").toString();
|
|
|
- securityTokenTemp = valueOperations.get("securityTokenTemp").toString();
|
|
|
+ if(valueOperations.get(urlAuthSession+key)!=null){
|
|
|
+ url = valueOperations.get(urlAuthSession+key).toString();
|
|
|
+ return url;
|
|
|
+ }
|
|
|
+ if(valueOperations.get(accessKeyIdRoleSession)!=null
|
|
|
+ && valueOperations.get(accessKeySecretRoleSession)!=null
|
|
|
+ && valueOperations.get(securityTokenRoleSession)!=null ){
|
|
|
+ accessKeyIdRole = valueOperations.get(accessKeyIdRoleSession).toString();
|
|
|
+ accessKeySecretRole = valueOperations.get(accessKeySecretRoleSession).toString();
|
|
|
+ securityTokenRole = valueOperations.get(securityTokenRoleSession).toString();
|
|
|
}else{
|
|
|
AssumeRoleResponse response = assumeRole(accessKeyId, accessKeySecret,
|
|
|
roleArn, roleSessionName, policy, protocolType);
|
|
@@ -107,25 +159,26 @@ public class AliStsOssAuth {
|
|
|
System.out.println("Access Key Secret: " + response.getCredentials().getAccessKeySecret());
|
|
|
System.out.println("Security Token: " + response.getCredentials().getSecurityToken());
|
|
|
|
|
|
- accessKeyIdTemp = response.getCredentials().getAccessKeyId();
|
|
|
- accessKeySecretTemp = response.getCredentials().getAccessKeySecret();
|
|
|
- securityTokenTemp = response.getCredentials().getSecurityToken();
|
|
|
+ SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'");
|
|
|
+ Date dateExp = sdf.parse(response.getCredentials().getExpiration());
|
|
|
+ long expiration = dateExp.getTime() + 8*3600*1000;
|
|
|
+ long curTime = new Date().getTime();
|
|
|
+ accessKeyIdRole = response.getCredentials().getAccessKeyId();
|
|
|
+ accessKeySecretRole = response.getCredentials().getAccessKeySecret();
|
|
|
+ securityTokenRole = response.getCredentials().getSecurityToken();
|
|
|
|
|
|
- valueOperations.set("accessKeyIdTemp", accessKeyIdTemp, 20L, TimeUnit.SECONDS);
|
|
|
- valueOperations.set("accessKeySecretTemp", accessKeySecretTemp, 20L, TimeUnit.SECONDS);
|
|
|
- valueOperations.set("securityTokenTemp", securityTokenTemp, 20L, TimeUnit.SECONDS);
|
|
|
+ valueOperations.set(accessKeyIdRoleSession, accessKeyIdRole, expiration-curTime, TimeUnit.MILLISECONDS);
|
|
|
+ valueOperations.set(accessKeySecretRoleSession, accessKeySecretRole, expiration-curTime, TimeUnit.MILLISECONDS);
|
|
|
+ valueOperations.set(securityTokenRoleSession, securityTokenRole, expiration-curTime, TimeUnit.MILLISECONDS);
|
|
|
}
|
|
|
|
|
|
- //原始完整路径:http://efunaudio.oss-cn-beijing.aliyuncs.com/audio/001/00103035/00103035018.mp3
|
|
|
- String endpoint = "oss-cn-beijing.aliyuncs.com";
|
|
|
- OSSClient client = new OSSClient(endpoint, accessKeyIdTemp, accessKeySecretTemp, securityTokenTemp);
|
|
|
- String bucketName = "efunaudio";
|
|
|
- String key = "audio/001/00103035/00103035018.mp3";
|
|
|
// 设置URL过期时间为1小时
|
|
|
- Date expiration = new Date(new Date().getTime() + 3600 * 1000);
|
|
|
+ Date expiration = new Date(new Date().getTime() + urlExpiration * 1000);
|
|
|
// 生成URL
|
|
|
- URL url = client.generatePresignedUrl(bucketName, key, expiration);
|
|
|
- System.out.println(url.toString());
|
|
|
+ OSSClient client = new OSSClient(endpoint, accessKeyIdRole, accessKeySecretRole, securityTokenRole);
|
|
|
+ URL urlAuth = client.generatePresignedUrl(bucketName, key, expiration);
|
|
|
+ url = urlAuth.toString();
|
|
|
+ valueOperations.set(urlAuthSession+key, url, urlExpiration, TimeUnit.SECONDS);
|
|
|
} catch (ClientException e) {
|
|
|
System.out.println("Failed to get a token.");
|
|
|
System.out.println("Error code: " + e.getErrCode());
|
|
@@ -133,5 +186,6 @@ public class AliStsOssAuth {
|
|
|
} catch (Exception e){
|
|
|
System.out.println("Error message: " + e.getMessage());
|
|
|
}
|
|
|
+ return url;
|
|
|
}
|
|
|
}
|