目录
- 一、备注
- 二、工具类
- 三、对象存储放在内网,如何实现外网访问
一、备注
1、ObjectBasicInfo、ObjectDetailInfo、ResultBody这三个类可自行替换或者去掉
二、工具类
package com.xxx.util;import com.amazonaws.HttpMethod;
import com.amazonaws.auth.AWSStaticCredentialsProvider;
import com.amazonaws.auth.BasicAWSCredentials;
import com.amazonaws.client.builder.AwsClientBuilder;
import com.amazonaws.services.s3.AmazonS3;
import com.amazonaws.services.s3.AmazonS3ClientBuilder;
import com.amazonaws.services.s3.model.*;
import com.xxx.entity.huarun.ObjectBasicInfo;
import com.xxx.entity.huarun.ObjectDetailInfo;
import com.xxx.entity.huarun.ResultBody;
import com.hitachivantara.common.util.DatetimeFormat;
import com.hitachivantara.core.http.Protocol;
import com.hitachivantara.core.http.client.ClientConfiguration;
import com.hitachivantara.hcp.build.HCPClientBuilder;
import com.hitachivantara.hcp.build.HCPNamespaceClientBuilder;
import com.hitachivantara.hcp.common.auth.LocalCredentials;
import com.hitachivantara.hcp.standard.api.HCPNamespace;
import com.hitachivantara.hcp.standard.api.event.ListObjectHandler;
import com.hitachivantara.hcp.standard.define.NextAction;
import com.hitachivantara.hcp.standard.model.HCPObject;
import com.hitachivantara.hcp.standard.model.HCPObjectSummary;
import com.hitachivantara.hcp.standard.model.request.impl.CopyObjectRequest;
import com.hitachivantara.hcp.standard.model.request.impl.ListObjectRequest;
import com.obs.services.ObsClient;
import com.obs.services.model.HeaderResponse;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.conn.ssl.NoopHostnameVerifier;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.conn.ssl.TrustStrategy;
import org.apache.http.ssl.SSLContextBuilder;
import org.springframework.web.multipart.MultipartFile;import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import javax.net.ssl.HttpsURLConnection;
import javax.net.ssl.SSLContext;
import java.io.*;
import java.net.URL;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.*;/*** 华润对象存储(OBS)-工具类** @author hcs* @date 2023/6/20 17:03*/
@Slf4j
public class HuaRunOBSUtil {/*** 文件外链过期时间,7天*/private static long expire = 7 * 24 * 60 * 60;/*** 文件外链访问端口*/private static String port = "";private static RedisUtil redisUtil = SpringUtil.getBean(RedisUtil.class);private static String bucketName;private static String ak;private static String sk;private static String endPoint;private static String targetDomainName;private static String replaceDomainName;/*** OBS操作客户端*/private static HCPNamespace obsClient = null;/*** 上传、下载文件时使用以下对象** 解决报错:Received fatal alert: protocol_version** 华润对象存储的服务器支持TLSv1.2(使用tcpdump命令抓包看到的)*/private static AmazonS3 S3APIClient;//private static AmazonS3 hs3Client;/*** OBS操作客户端Map,key=bucketName,value=客户端*/private static Map<String, HCPNamespace> obsClientMap = new HashMap<>();private static final String SEPARATOR = "/";public HuaRunOBSUtil(String bucketName, String ak, String sk, String endPoint, String port) {HuaRunOBSUtil.bucketName = bucketName;HuaRunOBSUtil.ak = ak;HuaRunOBSUtil.sk = sk;HuaRunOBSUtil.endPoint = endPoint;if (StringUtils.isNotBlank(port)) {HuaRunOBSUtil.port = ":" + port;}createObsClientInstance();S3APIClient = getInstance(endPoint, ak, sk, "S3SignerType", getHttpProtocol(endPoint));}public static String getBucketName() {return bucketName;}public static String getAk() {return ak;}public static String getSk() {return sk;}public static String getEndPoint() {return endPoint;}public static synchronized AmazonS3 getInstance(String endpoint, String ak, String sk,String signature, String protocol) {synchronized (AmazonS3.class) {if (null == S3APIClient) {S3APIClient = getHCPCSS3Client(endpoint, ak, sk, signature, protocol);}}return S3APIClient;}/*** 获取亚马逊S3客户端** @param endpoint* @param ak* @param sk* @param signature S3SignerType - 表示V2* AWSS3V4SignerType - 表示V4* @param protocol* @return*/private static AmazonS3 getHCPCSS3Client(String endpoint, String ak, String sk, String signature, String protocol) {log.info("开始\t创建S3客户端");com.amazonaws.ClientConfiguration clientConfig = new com.amazonaws.ClientConfiguration();//使用HTTP或HTTPS协议if (protocol.toUpperCase().equals("HTTP")) {clientConfig.setProtocol(com.amazonaws.Protocol.HTTP);} else {clientConfig.setProtocol(com.amazonaws.Protocol.HTTPS);try {SSLContextBuilder builder = new SSLContextBuilder();builder.loadTrustMaterial(null, new TrustStrategy() {public boolean isTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {return true;}});SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(builder.build(),/*** 仅指定TLSv1.2协议,解决报错:Received fatal alert: protocol_version** 如果加上其他版本的协议,有可能会报错:Received fatal alert: protocol_version** 例如指定为TLSv1.1,使用tcpdump命令抓包时如果发现TLSv1.2,则该次交互时失败的*/new String[]{"TLSv1.2"},// For Java 1.7 , 1.8//new String[]{"SSLv3", "TLSv1", "TLSv1.1", "TLSv1.2"},// For Java1.6-1.7//new String[] { "TLSv1" },new String[]{"TLS_RSA_WITH_AES_128_CBC_SHA"},NoopHostnameVerifier.INSTANCE);clientConfig.getApacheHttpClientConfig().setSslSocketFactory(sslsf);} catch (Exception e) {log.error("创建S3客户端出现异常:" + e.getMessage(), e);}}//连接池的连接数clientConfig.setMaxConnections(50);//V2签名 或 V4签名//S3SignerType - 表示V2//AWSS3V4SignerType - 表示V4clientConfig.setSignerOverride(signature);AmazonS3 client = AmazonS3ClientBuilder.standard().withClientConfiguration(clientConfig)/*** 以下配置为false:外链格式:存储桶.endpoint/目录/文件名* 以下配置为true:外链格式:endpoint/存储桶/目录/文件名*///.withPathStyleAccessEnabled(true).withEndpointConfiguration(new com.amazonaws.client.builder.AwsClientBuilder.EndpointConfiguration(endpoint, null)).withCredentials(new AWSStaticCredentialsProvider(new BasicAWSCredentials(ak, sk))).build();log.info("成功\t创建S3客户端");return client;}/*** 获取OBS操作客户端** @return*/private static void createObsClientInstance() {try {if (obsClient == null) {synchronized (ObsClient.class) {if (obsClient == null) {log.info("createObsClientInstance--->bucketName={},ak={},sk={},endPoint={}", bucketName, ak, sk, endPoint);ClientConfiguration clientConfig = new ClientConfiguration();String httpProtocol = getHttpProtocol(endPoint);clientConfig.setProtocol(httpProtocol.equalsIgnoreCase(Protocol.HTTPS.toString()) ? Protocol.HTTPS : Protocol.HTTP);HCPNamespaceClientBuilder builder = HCPClientBuilder.defaultHCPClient();obsClient = builder.withClientConfiguration(clientConfig).withCredentials(new LocalCredentials(ak, sk))// 去除http协议.withEndpoint(endPoint.replace(getHttpProtocol(endPoint) + "://", "")).withNamespace(bucketName).bulid();obsClientMap.put(bucketName, obsClient);}}}} catch (Exception e) {log.error("连接华润对象存储服务器异常:" + e.getMessage(), e);}}/*** 获取上传文件的基础路径** @return url*/public static String getBasisUrl() {//实示例:http协议 + 存储桶名称 + . + endPoint + port + /String basisUrl = getHttpProtocol(endPoint) + "://" + bucketName + "." + endPoint.replace(getHttpProtocol(endPoint) + "://", "") + (StringUtils.isNotBlank(port) ? port + SEPARATOR : "");log.info("getBasisUrl--->" + basisUrl);basisUrl = replaceDomainName(basisUrl);return basisUrl;}/*** 获取上传文件的基础路径** @param bucketName* @return*/public static String getBasisUrl(String bucketName) {//实示例:http协议 + 存储桶名称 + . + endPoint + port + /String basisUrl = getHttpProtocol(endPoint) + "://" + bucketName + "." + endPoint.replace(getHttpProtocol(endPoint) + "://", "") + (StringUtils.isNotBlank(port) ? port + SEPARATOR : "");log.info("getBasisUrl2--->" + basisUrl);basisUrl = replaceDomainName(basisUrl);return basisUrl;}/*** 根据url地址获取存储桶名称** @param url* @return*/public static String getBucketNameByUrl(String url) {if (StringUtils.isNotBlank(url) && StringUtils.isNotBlank(getHttpProtocol(endPoint))&& url.contains(endPoint.replace(getHttpProtocol(endPoint) + "://", ""))) {String str = url.replace(getHttpProtocol(endPoint) + "://", "");return str.substring(0, str.indexOf("."));} else {// 华润只会使用一个存储桶(访问外链替换了域名导致不支持多个存储桶),这里直接返回log.info("getBucketNameByUrl--->返回默认存储桶" + HuaRunOBSUtil.bucketName);return HuaRunOBSUtil.bucketName;}}/*** 获取区域** @param endPoint* @return*/public static String getRegion(String endPoint) {String substring = endPoint.substring(endPoint.indexOf(".") + 1);return substring.substring(0, substring.indexOf("."));}/*** 获取http协议** @param endPoint* @return*/public static String getHttpProtocol(String endPoint) {return endPoint.substring(0, endPoint.indexOf(":"));}/*** 创建存储桶(不确定以下方式是否有用)** @param bucketName* @return*/public static void createBucket(String bucketName, String endPoint) {try {log.info("createBucket.bucketName--->" + bucketName);log.info("createBucket.endPoint--->" + endPoint);if (!headBucket(bucketName)) {ClientConfiguration clientConfig = new ClientConfiguration();String httpProtocol = getHttpProtocol(endPoint);clientConfig.setProtocol(httpProtocol.equalsIgnoreCase(Protocol.HTTPS.toString()) ? Protocol.HTTPS : Protocol.HTTP);HCPNamespaceClientBuilder builder = HCPClientBuilder.defaultHCPClient();HCPNamespace obsClient = builder.withClientConfiguration(clientConfig).withCredentials(new LocalCredentials(ak, sk))// 去除http协议.withEndpoint(endPoint.replace(getHttpProtocol(endPoint) + "://", "")).withNamespace(bucketName).bulid();obsClientMap.put(bucketName, obsClient);}} catch (Exception e) {log.error("createBucket出现异常:" + e.getMessage(), e);}}/*** 创建存储桶** @param bucketName* @return*/public static void createBucket(String bucketName) {try {log.info("createBucket.bucketName--->" + bucketName);if (!headBucket(bucketName)) {S3APIClient.createBucket(bucketName);}} catch (Exception e) {log.error("createBucket出现异常:" + e.getMessage(), e);}}/*** 删除存储桶** @param bucketName* @return*/public static void deleteBucket(String bucketName) {S3APIClient.deleteBucket(bucketName);}/*** 判断存储桶是否存在** @param bucketName* @return*/public static boolean headBucket(String bucketName) {try {return obsClient.doesNamespacesExist(bucketName);} catch (Exception e) {log.error("headBucket出现异常:" + e.getMessage(), e);}return false;}/*** 上传字符** @param bucketName* @param objectName* @param content* @return*/public static ResultBody putObjectByStr(String bucketName, String objectName, String content) {log.info("putObjectByStr--->bucketName={},objectName={},content={}", bucketName, objectName, content);if (StringUtils.isBlank(content)) {return null;}//重新构建objectNameobjectName = buildObjectName(objectName);String errorMsg = "";for (int i = 0; i < 3; i++) {try {S3APIClient.putObject(bucketName, objectName, content);return ResultBody.success(new ObjectBasicInfo("putObjectByStr", objectName));} catch (Exception e) {log.error("putObjectByStr出现异常:" + e.getMessage(), e);errorMsg = e.getMessage();}}return ResultBody.failure(errorMsg);}/*** 上传输入流** @param bucketName* @param objectName* @param inputStream* @return*/public static ResultBody putObjectByInput(String bucketName, String objectName, InputStream inputStream) {log.info("putObjectByInput--->bucketName={},objectName={}", bucketName, objectName);//重新构建objectNameobjectName = buildObjectName(objectName);String errorMsg = "";ObjectMetadata metadata = new ObjectMetadata();for (int i = 0; i < 3; i++) {try {metadata.setContentLength(inputStream.available());S3APIClient.putObject(bucketName, objectName, inputStream, metadata);return ResultBody.success(new ObjectBasicInfo("inputStream", objectName));} catch (Exception e) {log.error("第" + (i + 1) + "次putObjectByInput出现异常:" + e.getMessage(), e);errorMsg = e.getMessage();}}return ResultBody.failure(errorMsg);}/*** 上传文件输入流** @param bucketName* @param objectName* @param fileInputStream* @return*/public static ResultBody putObjectByFileInput(String bucketName, String objectName, FileInputStream fileInputStream) {log.info("putObjectByFileInput--->bucketName={},objectName={}", bucketName, objectName);return putObjectByInput(bucketName, objectName, fileInputStream);}/*** 通过MultipartFile,上传文件** @param bucketName* @param objectName* @param media* @return*/public static ResultBody putObjectByMultipartFile(String bucketName, String objectName, MultipartFile media) throws IOException {log.info("putObjectByMultipartFile--->bucketName={},objectName={}", bucketName, objectName);return putObjectByInput(bucketName, objectName, media.getInputStream());}/*** 上传本地文件** @param bucketName* @param objectName* @param file* @return*/public static ResultBody putObjectByFile(String bucketName, String objectName, File file) {log.info("putObjectByFile--->bucketName={},objectName={}", bucketName, objectName);//重新构建objectNameobjectName = buildObjectName(objectName);String errorMsg = "";for (int i = 0; i < 3; i++) {try {S3APIClient.putObject(bucketName, objectName, file);return ResultBody.success(new ObjectBasicInfo(file.getName(), objectName));} catch (Exception e) {log.error("第" + (i + 1) + "次putObjectByFile出现异常:" + e.getMessage(), e);errorMsg = e.getMessage();}}return ResultBody.failure(errorMsg);}/*** 下载文件到本地** @param bucketName* @param objectName* @param filePath* @return*/public static boolean downloadObject(String bucketName, String objectName, String filePath) throws Exception {log.info("downloadObject--->bucketName={},objectName={},filePath={}", bucketName, objectName, filePath);if (StringUtils.isBlank(filePath)) {return false;}//重新构建objectNameobjectName = buildObjectName(objectName);filePath = filePath.replace("\\", SEPARATOR);InputStream input = null;FileOutputStream fileOutputStream = null;try {S3Object obsObject = null;for (int i = 0; i < 3; i++) {try {// 获取对象obsObject = S3APIClient.getObject(bucketName, objectName);break;} catch (Exception e) {log.error("第" + (i + 1) + "次downloadObject出现异常:" + e.getMessage(), e);}}// 读取对象内容input = obsObject.getObjectContent();if (input == null) {return false;}//获取文件夹路径if (filePath.contains(SEPARATOR)) {String dir = filePath.substring(0, filePath.lastIndexOf(SEPARATOR));File difFile = new File(dir);if (!difFile.exists()) {//创建文件夹boolean mkdirs = difFile.mkdirs();}}File file = new File(filePath);fileOutputStream = new FileOutputStream(file);byte[] b = new byte[1024];int len;while ((len = input.read(b)) != -1) {fileOutputStream.write(b, 0, len);}return true;} finally {if (fileOutputStream != null) {fileOutputStream.close();}if (input != null) {input.close();}}}/*** 获取文件内容** @param bucketName* @param objectName* @return*/public static String getObjectContent(String bucketName, String objectName) throws IOException {log.info("getObjectContent--->bucketName={},objectName={}", bucketName, objectName);//重新构建objectNameobjectName = buildObjectName(objectName);InputStream input = null;ByteArrayOutputStream bos = new ByteArrayOutputStream();try {for (int i = 0; i < 3; i++) {try {// 读取对象内容input = S3APIClient.getObject(bucketName, objectName).getObjectContent();break;} catch (Exception e) {log.error("第" + (i + 1) + "次getObjectContent出现异常:" + e.getMessage(), e);}}byte[] b = new byte[1024];int len;while ((len = input.read(b)) != -1) {bos.write(b, 0, len);}return new String(bos.toByteArray());} catch (Exception e) {log.error("getObjectContent出现异常:" + e.getMessage(), e);} finally {bos.close();if (input != null) {input.close();}}return null;}/*** 获取文件输入流** @param bucketName* @param objectName* @return*/public static InputStream getObject(String bucketName, String objectName) {log.info("getObject--->bucketName={},objectName={}", bucketName, objectName);//重新构建objectNameobjectName = buildObjectName(objectName);for (int i = 0; i < 3; i++) {try {S3Object object = S3APIClient.getObject(bucketName, objectName);return object.getObjectContent();} catch (Exception e) {log.error("第" + (i + 1) + "次getObject出现异常:" + e.getMessage(), e);}}return null;}/*** 列举指定目录的全部对象** @param bucketName* @param directoryPath* @return*/public static ResultBody listAllObjects(String bucketName, String directoryPath) {log.info("listAllObjects--->bucketName={},directoryPath={}", bucketName, directoryPath);List<ObjectDetailInfo> objList = new ArrayList<>();try {HCPNamespace obsClient = obsClientMap.get(bucketName);ListObjectRequest request = new ListObjectRequest(directoryPath).withRecursiveDirectory(true);obsClient.listObjects(request, new ListObjectHandler() {@Overridepublic NextAction foundObject(HCPObjectSummary obj) {ObjectDetailInfo objInfo = new ObjectDetailInfo(obj.getName(),obj.getKey(),obj.getSize(),obj.getType(),DatetimeFormat.ISO8601_DATE_FORMAT.format(new Date(obj.getChangeTime())),obj.getContentHash());objList.add(objInfo);return null;}});} catch (Exception e) {log.error("listAllObjects出现异常:" + e.getMessage(), e);return ResultBody.failure(e.getMessage());}return ResultBody.success(objList);}/*** 删除单个对象** @param bucketName* @param objectName* @return*/public static ResultBody deleteObject(String bucketName, String objectName) {log.info("deleteObject--->bucketName={},objectName={}", bucketName, objectName);//重新构建objectNameobjectName = buildObjectName(objectName);try {HCPNamespace obsClient = obsClientMap.get(bucketName);obsClient.deleteObject(bucketName, objectName);return ResultBody.success();} catch (Exception e) {log.error("deleteObject出现异常:" + e.getMessage(), e);return ResultBody.failure(e.getMessage());}}/*** 复制对象** @param sourceBucketName* @param sourceObjectName* @param destBucketName* @param destObjectName* @return*/public static boolean copyObject(String sourceBucketName, String sourceObjectName,String destBucketName, String destObjectName) {log.info("deleteObject--->sourceBucketName={},sourceObjectName={},destBucketName={},destObjectName={}", bucketName, sourceObjectName, destBucketName, destObjectName);CopyObjectRequest copyObjectRequest = new CopyObjectRequest();copyObjectRequest.withSourceNamespace(sourceBucketName);copyObjectRequest.withSourceKey(sourceObjectName);copyObjectRequest.withTargetNamespace(destBucketName);copyObjectRequest.withTargetKey(destObjectName);try {obsClient.copyObject(copyObjectRequest);return true;} catch (Exception e) {log.error("copyObject出现异常:" + e.getMessage(), e);}return false;}/*** 判断对象是否存在** @param bucketName* @param objectName* @return*/public static boolean doesObjectExist(String bucketName, String objectName) {log.info("deleteObject--->bucketName={},objectName={}", bucketName, objectName);//重新构建objectNameobjectName = buildObjectName(objectName);try {HCPNamespace obsClient = obsClientMap.get(bucketName);return obsClient.doesObjectExist(objectName);} catch (Exception e) {log.error("doesObjectExist出现异常:" + e.getMessage(), e);}return false;}/*** 获取文件外链** @param bucketName* @param objectName* @param expires 单位:秒(s)* @return*/public static String getSignedUrl(String bucketName, String objectName, Long expires) {log.info("getSignedUrl--->bucketName={},objectName={},expires={}", bucketName, objectName, expires);//重新构建objectNameobjectName = buildObjectName(objectName);Date expiration = new Date(System.currentTimeMillis() + (expires * 1000));try {//String e = endPoint.replace(getHttpProtocol(endPoint) + "://", "");//AmazonS3 hs3Client = newS3Client(e, ak, sk);// 生成预签名时间URL url = S3APIClient.generatePresignedUrl(new GeneratePresignedUrlRequest(bucketName, objectName).withExpiration(expiration).withMethod(HttpMethod.GET));String s = url.toString();log.info("这个是api生成的url------------------------------------>" + s);// 由于api返回的是http,这里自行替换为endpoint使用的协议s = s.replace(getHttpProtocol(s) + "://", getHttpProtocol(endPoint) + "://");log.info("替换协议后url------>" + s);s = replaceDomainName(s);return s;} catch (Exception e) {log.error("getSignedUrl出现异常:" + e.getMessage(), e);}return null;}/*** 获取文件外链-url有效时间默认7天** @param bucketName* @param objectName* @return*/public static String getSignedUrl(String bucketName, String objectName) {return getSignedUrl(bucketName, objectName, expire);}/*** 重新构建objectName** @param objectName*/private static String buildObjectName(String objectName) {if (StringUtils.isBlank(objectName)) {return objectName;}//去除开头的/objectName = objectName.startsWith("/") ? objectName.substring(1) : objectName;//去除?后边的参数objectName = objectName.contains("?") ? objectName.substring(0, objectName.indexOf("?")) : objectName;return objectName;}/*** 传入文件访问外链,返回objectName** @param url* @return*/public static String getObjectNameByUrl(String url) {if (StringUtils.isBlank(url)) {return url;}try {url = URLDecoder.decode(url, "UTF-8");} catch (Exception e) {log.error("getObjectNameByUrl获取文件外链失败:" + e.getMessage(), e);}if (url.contains(getBasisUrl())) {// 去除基础路径url = url.replace(getBasisUrl(), "");// 去除?后边的参数url = url.contains("?") ? url.substring(0, url.indexOf("?")) : url;}return url;}/*** 获取华润OBS文件外链** @param redisKey* @param objectName* @return* @throws Exception*/public static String getOBSFileUrl(String redisKey, String objectName) throws Exception {if (StringUtils.isBlank(objectName) || StringUtils.isBlank(redisKey) || OBSUtil.httpRegex(objectName)) {return "";}objectName = URLDecoder.decode(objectName, "UTF-8");//重新构建objectNameobjectName = buildObjectName(objectName);Object o = redisUtil.get(redisKey);String url = o == null ? null : o.toString();if (StringUtils.isNotBlank(url)) {return url;} else {//重新获取urlString signedUrl = getSignedUrl(getBucketName(), objectName, expire);//保存访问url,有效期为6天redisUtil.set(redisKey, signedUrl, 6 * 24 * 60 * 60);return signedUrl;}}/*** 从指定存储桶获取华润OBS文件外链** @param redisKey* @param objectName* @param bucketName* @return* @throws Exception*/public static String getOBSFileUrl(String redisKey, String objectName, String bucketName) throws Exception {if (StringUtils.isBlank(objectName) || StringUtils.isBlank(redisKey) || StringUtils.isBlank(bucketName)) {return "";}//重新构建objectNameobjectName = buildObjectName(objectName);Object o = redisUtil.get(redisKey);String url = o == null ? null : o.toString();if (StringUtils.isNotBlank(url)) {return url;} else {//重新获取urlString signedUrl = getSignedUrl(bucketName, objectName, expire);//保存访问url,有效期为6天redisUtil.set(redisKey, signedUrl, 6 * 24 * 60 * 60);return signedUrl;}}/*** 保存华润OBS文件外链至redis** @param redisKey* @param url* @return*/public static boolean setOBSFileUrl(String redisKey, String url) {Object o = redisUtil.get(redisKey);if (o != null) {String value = o.toString();//只保存新的外链,解决url重复保存导致redis保存的是过期外链的问题if (!value.equals(url)) {//保存访问url,有效期为6天return redisUtil.set(redisKey, url, 6 * 24 * 60 * 60);}} else {//保存访问url,有效期为6天return redisUtil.set(redisKey, url, 6 * 24 * 60 * 60);}return true;}/*** 删除华润OBS文件外链** @param redisKey*/public static void delOBSFileUrl(String redisKey) {//删除访问urlredisUtil.del(redisKey);}/*** 替换域名** @param url* @return*/private static String replaceDomainName(String url){if (StringUtils.isNotBlank(replaceDomainName) && StringUtils.isNotBlank(targetDomainName)) {url = url.replace(targetDomainName, replaceDomainName);log.info("替换域名后url------>" + url);}return url;}public static void setTargetDomainName(String targetDomainName) {HuaRunOBSUtil.targetDomainName = targetDomainName;}public static void setReplaceDomainName(String replaceDomainName) {HuaRunOBSUtil.replaceDomainName = replaceDomainName;}
}
三、对象存储放在内网,如何实现外网访问
如果对象存储是放在内网的,可以按照以下示例配置ngin代理
nginx配置请参考:https://app.rwork.crc.com.cn/docs/dock9zVHp5WcpLYNKfjo5ACbU8g
结合代码中的targetDomainName
、replaceDomainName
可实现外网访问