java中OSS的sts授權(quán)和直傳

首先钓辆,作為一個一年多碼農(nóng)經(jīng)驗(yàn)的我徐钠,這是第一次接觸oss瓷产。說起來也挺好不意思的锋边。畢竟上一份工作真的小外包。一些第三方調(diào)用等都已經(jīng)封裝好了的擅笔。而且都是小項目性誉,用到oss也就存存用戶頭像啊羽氮,用戶簡介里的照片啊等等的豁鲤。也不涉及什么需要保密的秽誊。所以大多數(shù)項目都是前端直接調(diào)用oss。壓根不經(jīng)過后端畅形。別管什么安全不安全的养距,起碼簡單方便開發(fā)快是真的诉探。

然后這幾天接觸oss日熬,只能說遇到了一些不能算是坑的坑。在這里吐槽一下肾胯,從老板指示說讓oss在后端授權(quán)前端才能調(diào)用開始竖席,我便開始上網(wǎng)查閱資料【炊牵看了看阿里的文檔毕荐,覺得也沒多么復(fù)雜,所以就沒放在心上艳馒。直到昨天真的打算把這個功能落實(shí)在代碼上了憎亚,于是跟老板問了oss的賬號和密碼。卻不料老板給發(fā)來一個文檔弄慰,其中各種圖片的保存路徑的劃分就不說了第美。最主要的賬號是參數(shù)的形式發(fā)給我的。其中包括AccessKeyID陆爽,AccessKeySecret什往,RoleArn,BucketName慌闭,Endpoint别威,TokenExpireTime躯舔。這五個。好的吧省古,興許人家阿里賬號上有著什么什么重要又私密的東西粥庄,給這些參數(shù)也ok吧。畢竟看官方文檔用到的數(shù)據(jù)也都在了豺妓。

好的飒赃,開始實(shí)踐!我有多信心滿滿最后進(jìn)坑摔得就有多慘科侈。按照阿里官方文檔搭demo载佳。然后我可能也是心大,直接就搭了臨時授權(quán)的demo臀栈。畢竟這也是一年多經(jīng)驗(yàn)帶來的自信蔫慧,覺得一個三方軟件的使用肯定不會做的多難。問題出就出在這了权薯。demo復(fù)制粘貼添添改改刪刪姑躲。。于是跑起來了~~~這里要介紹一些oss的知識:

oss的授權(quán)訪問分為兩種

使用STS進(jìn)行臨時授權(quán):

STS的優(yōu)勢如下:

您無需透露您的長期密鑰(AccessKey)給第三方應(yīng)用盟蚣,只需生成一個訪問令牌并將令牌交給第三方應(yīng)用黍析。您可以自定義這個令牌的訪問權(quán)限及有效期限。

您無需關(guān)心權(quán)限撤銷問題屎开,訪問令牌過期后自動失效阐枣。

使用簽名URL進(jìn)行臨時授權(quán):

生成簽名URL

您可以將生成的簽名URL提供給訪客進(jìn)行臨時訪問。生成簽名URL時奄抽,您可以指定URL的過期時間蔼两,來限制訪客的訪問時長。

官方文檔寫的很清楚逞度,不過寫的sts再好额划,架不住簽名url授權(quán)看起來比較眼熟,所以我選擇了使用簽名URL進(jìn)行臨時授權(quán)档泽;簽名url臨時授權(quán)是分請求的俊戳。get的url獲取最簡單:

// Endpoint以杭州為例,其它Region請按實(shí)際情況填寫馆匿。

String endpoint ="http://oss-cn-hangzhou.aliyuncs.com";

// 阿里云主賬號AccessKey擁有所有API的訪問權(quán)限抑胎,風(fēng)險很高。強(qiáng)烈建議您創(chuàng)建并使用RAM賬號進(jìn)行API訪問或日常運(yùn)維甜熔,請登錄 https://ram.console.aliyun.com 創(chuàng)建RAM賬號圆恤。

String accessKeyId ="<yourAccessKeyId>";//

String accessKeySecret ="<yourAccessKeySecret>";

String bucketName ="<yourBucketName>";

String objectName ="<yourObjectName>";//因?yàn)檫@個我當(dāng)時沒有太看明白,所以特意寫個注釋,萬一有和我一樣傻的呢盆昙。這個是你文件的名字羽历。因?yàn)間et是只能讀取,所以這里就是你想讓訪客讀取的那個文件名淡喜。在put里就是你想保存進(jìn)oss取的名字秕磷。

// 創(chuàng)建OSSClient實(shí)例。

OSSClient ossClient =newOSSClient(endpoint, accessKeyId, accessKeySecret);

// 設(shè)置URL過期時間為1小時炼团。

Date expiration =new Date(new Date().getTime() +3600*1000);

// 生成以GET方法訪問的簽名URL澎嚣,訪客可以直接通過瀏覽器訪問相關(guān)內(nèi)容。

URL url = ossClient.generatePresignedUrl(bucketName, objectName, expiration);

// 關(guān)閉OSSClient瘟芝。ossClient.shutdown();

但是其功能只是讓訪客可以直接通過瀏覽器訪問相關(guān)內(nèi)容易桃。因?yàn)槲覀円獙?shí)現(xiàn)的是前端存圖片,所以這個就pass掉了锌俱。不過只要按照要求配置是沒問題的∥钪#現(xiàn)在的我已經(jīng)做過demo了。一次跑通贸宏。

如果說親們運(yùn)行得到的url有問題的話造寝,可以把錯誤復(fù)制粘貼百度一下。幾乎都能查得到吭练。我記得阿里官方手冊也專門有一個對各種錯誤的解釋的頁面诫龙。

https://error-center.aliyun.com/status/product/Oss

然后繼續(xù)講我遇到的錯誤:

<Code>SignatureDoesNotMatch</Code>

? ? <Message>The request signature we calculated does not match the signature you provided. Check your key and signing method.</Message>

? ? <RequestId>5D16D23D1DE99D87A3686758</RequestId>

? ? <HostId>our-shanghai-cer.oss-cn-shanghai.aliyuncs.com</HostId>

? ? <OSSAccessKeyId>LTAIisi3C6MHfTux</OSSAccessKeyId>

? ? <SignatureProvided>+DaLfan2W/V+ZNJ/bOFECwT0jBY=</SignatureProvided>

? ? <StringToSign>GET

一直報這個錯,百度n次都說讓我檢查簽名和key之類的鲫咽。我也是復(fù)制粘貼手打签赃,因?yàn)榘俣壬虾芏嗾f是不是keyId上有空格啦什么的。但是各種沒用浑侥。問群里大神姊舵,問貼吧大佬晰绎。整整一下午到晚上八點(diǎn)多都在解決這個問題~~知道回家洗完澡還在想能是什么原因寓落。今早上班,在群里大佬的提點(diǎn)下開始懷疑老板給的參數(shù)(一開始是真的沒想到)荞下。于是做了一個最簡單的直傳demo伶选。ok,還是報錯尖昏。而且這次的報錯很明確仰税。

[ErrorCode]: AccessDenied

[RequestId]: 5D1724AA94911CA42A5668FD

[HostId]: our-shanghai-cer.oss-cn-shanghai.aliyuncs.com

[ResponseError]:

<?xml version="1.0" encoding="UTF-8"?>

<Error>

? <Code>AccessDenied</Code>

? <Message>The bucket you access does not belong to you.</Message>

? <RequestId>5D1724AA94911CA42A5668FD</RequestId>

? <HostId>our-shanghai-cer.oss-cn-shanghai.aliyuncs.com</HostId>

</Error>

看到這沒跑了~~就是老板給的參數(shù)是錯了,別管我心理多少頭草泥馬在奔跑了~反正我逝去的一天青春也沒多值錢抽诉。繼續(xù)往下搞的前提問到能用的參數(shù)啊陨簇,所以找老板要參數(shù)。問賬號是多少(因?yàn)槲覀兝习宀⒉皇羌夹g(shù)迹淌,只能說一知半解河绽,所以有點(diǎn)不敢信他的參數(shù)了)己单。結(jié)果過了n久,躊躇的給我發(fā)來了一個賬號和口令耙饰。我猜了一會兒試了一會兒最終登陸成功纹笼,是個阿里云的子賬號。ok吧苟跪,別管我心理舒服不舒服的廷痘,拿著人家工資呢。我自己去建立key然后保存secert件已。這回又搭起了demo笋额。再也不敢一次性做最終目的了。從直傳 開始測試篷扩,而且是一步一測試:

public class Demo {

private static final String ENDPOINT = "oss-cn-shanghai.aliyuncs.com";//根據(jù)你們自己的情況填寫

private static final String ACCESSKEYID = "你的keyId";

private static final String ACCESSKEYSECRET = "你的keySecert";

private static final String BUCKETNAME = "你的bucketName";

public static void main(String[] args) {

OSS ossClient = new OSSClient(ENDPOINT, ACCESSKEYID, ACCESSKEYSECRET);//創(chuàng)建一個oss連接對象

//判斷是否有此工作空間鳞陨,主要是我都對參數(shù)不信任了~~哎~~小心點(diǎn)不會錯

?if (!ossClient.doesBucketExist(BUCKETNAME)) {

System.out.println("沒有這個bucketName");

}else {

? // 上傳內(nèi)容到指定的存儲空間(bucketName)并保存為指定的文件名稱(objectName)。

? ? ? ? String content = "測試不過吃鍵盤";

//因?yàn)槲疫@里就是個demo瞻惋,所以隨便傳的字符串厦滤。別的格式不一樣的。官方手冊很清楚

? ? ? ? ossClient.putObject(BUCKETNAME, "測試1號", new ByteArrayInputStream(content.getBytes()));

? ? ? ? ossClient.shutdown();

}? ? ?}}

然后運(yùn)行后歼狼,我去oss里面查掏导,確實(shí)保存進(jìn)去了,松了一口氣的感覺羽峰√伺兀卡了我差不多一天半差點(diǎn)對自己喪失信心了。這個成功是信心的找回梅屉。然后也說句題外話值纱,有時候確實(shí)會因?yàn)槟涿罘堑脑蚓涂ㄒ欢螘r間。心態(tài)要好坯汤,別煩躁發(fā)怒虐唠,這是正常的。

直傳成功了繼續(xù)研究授權(quán)吧惰聂。因?yàn)樯罡衭rl的坑疆偿。。所以決定還是走大眾路線搓幌。杆故。sts授權(quán)吧。于是開始查sts授權(quán)的demo溉愁〈︻酰看了看官網(wǎng)的demo大體聊一下自己的理解。

sts就是通過oss官方加密生成一個臨時的key和密鑰。然后可以設(shè)置這個臨時密鑰的時間撤蟆。

第一步導(dǎo)包篙贸。sts專屬的兩個:

<dependency>

<groupId>com.aliyun</groupId>

<artifactId>aliyun-java-sdk-sts</artifactId>

<version>3.0.0</version>

</dependency>

<dependency>

<groupId>com.aliyun</groupId>

<artifactId>aliyun-java-sdk-core</artifactId>

<version>[4.4.2,5.0.0)</version>

</dependency>

注意下,我們用oss有時候直傳有時候只生成sts臨時密鑰枫疆。所以這個是不同的包的爵川。而且子賬號的授權(quán)也可能不一樣。而oss好多權(quán)限真的很惡心(這里要聲明一點(diǎn)息楔,上文提到的老板給的賬號不對就是這個原因寝贡。他給我的是生成sts的權(quán)限的賬號而我用來直傳和生成url。)值依。只能我我安全意識不夠強(qiáng)吧圃泡。反正我是只覺得麻煩。

言歸正傳愿险。如果想用來直傳需要引入另一個包

<dependency>

<groupId>com.aliyun.oss</groupId>

<artifactId>aliyun-sdk-oss</artifactId>

<version>2.8.3</version>

</dependency>

直傳和生成臨時url上文已經(jīng)講完了這里就不多話了颇蜡。繼續(xù)說怎么生成臨時sts。我直接上代碼:

public ResultBean getSTS() {

try {

// 構(gòu)造 default profile(參數(shù)留空辆亏,無需添加 region ID)

IClientProfile profile = DefaultProfile.getProfile("", accessKeyId, accessKeySecret);

// 用 profile 構(gòu)造 client

DefaultAcsClient client = new DefaultAcsClient(profile);

final AssumeRoleRequest request = new AssumeRoleRequest();

request.setSysEndpoint(endpoint);

request.setSysMethod(MethodType.POST);

request.setRoleArn(roleArn);

request.setRoleSessionName(roleSessionName);

request.setPolicy(policy); // Optional

final AssumeRoleResponse response = client.getAcsResponse(request);

return Tools.result(200, "獲取sts臨時憑證成功", response, true);

} catch (Exception e) {

LOG.info("Error Message: " + e.getMessage());

return Tools.result(500, "獲取sts臨時憑證失敗", null, false);

}

}

敲黑板說一下幾個參數(shù):

7绯印!扮叨!這里要敲黑板注意g拖摇!彻磁!注意endpoint這個參數(shù)0濉!就是"sts.aliyuncs.com"這個衷蜓。其實(shí)也可以換成別的累提。但是跟你所認(rèn)知的可能不一樣。都是以sts開頭的磁浇。官方文檔有斋陪。如果不愿意寫這個的親們可以自己去官網(wǎng)查你對應(yīng)的。

還要說一點(diǎn)roleSessionName這個參數(shù)扯夭。有的帖子上說可以不寫之類的鳍贾。但是我不知道是版本更新了還是咋的。反正現(xiàn)在的一定要寫的交洗。

?policy 這個參數(shù)是可以自定義。但是因?yàn)槲沂钦罩俜绞謨缘膁emo改的橡淑。所以這個也就沒改~~

protected static final Logger LOG = LoggerFactory.getLogger(OssUtil.class);

private final static String endpoint = "sts.aliyuncs.com";

private final static String accessKeyId = "我的keyId";

private final static String accessKeySecret = "i我的密鑰";

private final static String roleArn = "這個可以在控制臺查到";

private final static String roleSessionName = "這個也可以在控制臺查到";

private final static String policy = "{\n" + "? ? \"Version\": \"1\", \n" + "? ? \"Statement\": [\n" + "? ? ? ? {\n"

+ "? ? ? ? ? ? \"Action\": [\n" + "? ? ? ? ? ? ? ? \"oss:*\"\n" + "? ? ? ? ? ? ], \n"

+ "? ? ? ? ? ? \"Resource\": [\n" + "? ? ? ? ? ? ? ? \"acs:oss:*:*:*\" \n" + "? ? ? ? ? ? ], \n"

+ "? ? ? ? ? ? \"Effect\": \"Allow\"\n" + "? ? ? ? }\n" + "? ? ]\n" + "}";

為啥給分開了呢构拳。因?yàn)槲覄倓偺岬搅藱?quán)限問題。上面哪個只能生成sts臨時憑證。所以因?yàn)槲疫€要直傳置森。所以這是兩個子賬號斗埂。然后填寫上也沒啥特別的。

private final static String endpoint_upload = "oss-cn-shanghai.aliyuncs.com";

private final static String accessKeyId_upload = "我的keyid";

private final static String accessKeySecret_upload = "我的密鑰";

private final static String bucketName_upload = "our-shanghai-cer";

反正用了兩天的時間凫海。oss起碼暫時需要的功能都跑通了~~哎呛凶,不容易啊~~我感覺最大的坑就是各種權(quán)限~~~嘖嘖

好了好了有問題留言,歡迎糾錯~~
喏行贪,手打不易漾稀,大家動動小手分享轉(zhuǎn)發(fā)點(diǎn)贊評論啥的~~~~

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市建瘫,隨后出現(xiàn)的幾起案子崭捍,更是在濱河造成了極大的恐慌,老刑警劉巖啰脚,帶你破解...
    沈念sama閱讀 212,542評論 6 493
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件殷蛇,死亡現(xiàn)場離奇詭異,居然都是意外死亡橄浓,警方通過查閱死者的電腦和手機(jī)粒梦,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,596評論 3 385
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來荸实,“玉大人谍倦,你說我怎么就攤上這事±崂眨” “怎么了昼蛀?”我有些...
    開封第一講書人閱讀 158,021評論 0 348
  • 文/不壞的土叔 我叫張陵,是天一觀的道長圆存。 經(jīng)常有香客問我叼旋,道長,這世上最難降的妖魔是什么沦辙? 我笑而不...
    開封第一講書人閱讀 56,682評論 1 284
  • 正文 為了忘掉前任夫植,我火速辦了婚禮,結(jié)果婚禮上油讯,老公的妹妹穿的比我還像新娘详民。我一直安慰自己,他們只是感情好陌兑,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,792評論 6 386
  • 文/花漫 我一把揭開白布沈跨。 她就那樣靜靜地躺著,像睡著了一般兔综。 火紅的嫁衣襯著肌膚如雪饿凛。 梳的紋絲不亂的頭發(fā)上狞玛,一...
    開封第一講書人閱讀 49,985評論 1 291
  • 那天,我揣著相機(jī)與錄音涧窒,去河邊找鬼心肪。 笑死,一個胖子當(dāng)著我的面吹牛纠吴,可吹牛的內(nèi)容都是我干的硬鞍。 我是一名探鬼主播,決...
    沈念sama閱讀 39,107評論 3 410
  • 文/蒼蘭香墨 我猛地睜開眼戴已,長吁一口氣:“原來是場噩夢啊……” “哼固该!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起恭陡,我...
    開封第一講書人閱讀 37,845評論 0 268
  • 序言:老撾萬榮一對情侶失蹤蹬音,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后休玩,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體著淆,經(jīng)...
    沈念sama閱讀 44,299評論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,612評論 2 327
  • 正文 我和宋清朗相戀三年拴疤,在試婚紗的時候發(fā)現(xiàn)自己被綠了永部。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,747評論 1 341
  • 序言:一個原本活蹦亂跳的男人離奇死亡呐矾,死狀恐怖苔埋,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情蜒犯,我是刑警寧澤组橄,帶...
    沈念sama閱讀 34,441評論 4 333
  • 正文 年R本政府宣布,位于F島的核電站罚随,受9級特大地震影響玉工,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜淘菩,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 40,072評論 3 317
  • 文/蒙蒙 一遵班、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧潮改,春花似錦狭郑、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,828評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至趾疚,卻和暖如春缨历,著一層夾襖步出監(jiān)牢的瞬間以蕴,已是汗流浹背糙麦。 一陣腳步聲響...
    開封第一講書人閱讀 32,069評論 1 267
  • 我被黑心中介騙來泰國打工辛孵, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人赡磅。 一個月前我還...
    沈念sama閱讀 46,545評論 2 362
  • 正文 我出身青樓魄缚,卻偏偏與公主長得像,于是被迫代替她去往敵國和親焚廊。 傳聞我的和親對象是個殘疾皇子冶匹,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,658評論 2 350

推薦閱讀更多精彩內(nèi)容