閱讀651 返回首頁    go 阿裏雲 go 技術社區[雲棲]


MaxCompute如何實現跨項目授權

實際的企業使用場景裏,可能需要把不同項目裏的數據、函數、計算資源等一起使用。那如何實現這種跨項目的使用呢,本文用實際例子來說明下。

準備

  • 項目空間:grant_from,需要授權的數據、函數、資源都在這個項目裏
  • 項目空間:grant_to,被授權的用戶需要在這個項目裏執行計算。
  • 用戶:aliyun$xxxx@aliyun.com,grant_from項目的project owner,後續的授權操作是這個賬號執行的。
  • 用戶:ram$xxxx@aliyun.com:chuanxue2,通過在大數據開發套件裏授權了grant_to項目的開發角色,現在在使用grant_to項目進行計算的時候,需要用到grant_from項目裏的數據、函數和資源。
  • 表:dual,在grant_from和grant_to裏都有的一張表,裏麵就一條數據,用於測試UDF用的。
  • 表:grant_from.wc_in,grant_from項目裏的一張表。需要授權給ram$xxxx@aliyun.com:chuanxue2,讓他在grant_to裏做計算的時候也能用到。
  • 函數:getPersonName,在grant_from裏的待授權函數
  • 資源resource_file.txt、和其他一些jar包是在grant_from裏的資源文件。

授權

需要添加用戶並做表對賬號的授權。授權後被授權賬號可以跨項目引用。

-- 以下操作是在grant_from裏由aliyun$xxxx@aliyun.com執行的
-- add user隻需要添加一次就夠了。以前添加過了就可以跳過
odps@ grant_from>add user RAM$xxxx@aliyun.com:chuanxue2;
-- 如果隻是SQL查詢,隻要給Select權限就夠了。不過使用MapReduce作為輸入表的話,還需要Describe 權限。這裏一並授權了。
odps@ grant_from>grant Select,Describe on table wc_in to user RAM$xxxx@aliyun.com:chuanxue2;

使用

可以在SQL裏,使用ProjectName.TableName使用這張表,比如

---以下操作是由RAM$xxxx@aliyun.com:chuanxue2在grant_to裏操作
odps@ grant_to>select * from grant_from.wc_in;

而在MapReduce/Graph裏,就以MapReduce為例,可以把代碼寫成

    InputUtils.addTable(TableInfo.builder().projectName("grant_from").tableName("wc_in").build(), job);
    OutputUtils.addTable(TableInfo.builder().tableName("wc_out").build(), job);

其他的一切使用方法都和使用本項目內的表的用法一樣,這裏不再贅言。

函數

授權

比如grant_from裏有個解析json字符串的內容的一個UDF,現在希望讓RAM$xxxx@aliyun.com:chuanxue2在grant_to裏也能用起來。
先看看這個UDF,aliyun$xxxx@aliyun.com在grant_from裏是怎麼用的:

odps@ grant_from>select getPersonName('{"id":100,"name":"chuanxue","age":11}') from dual;
+-----+
| _c0 |
+-----+
| chuanxue |
+-----+

授權之前,需要確定這個函數都涉及了什麼資源文件

odps@ grant_from>desc function  getPersonName;
Name                                    getPersonName
Owner                                   ALIYUN$xxxx@aliyun.com
Created Time                            2017-05-26 13:31:33
Class                                   odps.test.GetPersonName
Resources                               grant_from/resources/getPersonName.jar,grant_from/resources/gson-2.2.4.jar

所以授權的步驟包括:

--add user還是如前麵提到,隻需要添加一次,如果已經添加過可以不添加
odps@ grant_from>add user RAM$xxxx@aliyun.com:chuanxue2;

-- 授權函數
odps@ grant_from>grant read on function getPersonName to user RAM$xxxx@aliyun.com:chuanxue2;
OK
odps@ grant_from>grant read on resource getPersonName.jar to user RAM$xxxx@aliyun.com:chuanxue2;
OK
odps@ grant_from>grant read on resource gson-2.2.4.jar to user RAM$xxxx@aliyun.com:chuanxue2;
OK

使用

被授權後, RAM$xxxx@aliyun.com:chuanxue2就可以在grant_to這個項目裏使用到被授權的函數了。通過ProjectName:FunctionName可以很方便的引用這個函數。

-- 這個操作由被授權的子賬號在grant_to裏執行

odps@ grant_to>select grant_from:getPersonName('{"id":100,"name":"chuanxue","age":11}') from dual;
+-----+
| _c0 |
+-----+
| chuanxue |
+-----+

資源

命令行引用

需要資源的授權的場景比較少。不過比如說剛才的那個函數,也可以隻把資源授權給對方,讓對方自己創建一個函數。
資源文件的授權和前麵函數的授權方式一樣,不再重複,創建函數的方法和調用可以參考:

-- 在grant_to裏創建一個函數getPersonName2,使用的資源都是來自之前被授權的grant_from裏的getPersonName.jar和gson-2.2.4.jar
odps@ grant_to>create function getPersonName2 as odps.test.GetPersonName using grant_from/resources/getPersonName.jar,grant_from/re
sources/gson-2.2.4.jar;

-- 創建好了後的調用就正常調用了。dual表也是grant_to裏的dual表。
odps@ grant_to>select getPersonName2('{"id":100,"name":"chuanxue","age":11}') from dual;

而在mapreduce裏引用其他項目的jar包,也是一樣。先在grant_from裏做授權

-- cx_word_count2.jar其實就是cx_word_count.jar改了文件名,然後傳到grant_from作跨項目引用的。
odps@ grant_from>add jar C:\Users\chuanxue\Desktop\cx_word_count2.jar -f;
OK: Resource 'cx_word_count2.jar' have been updated.
odps@ grant_from>grant read on resource cx_word_count2.jar to user RAM$cloudtecengr@aliyun.com:chuanxue2;
OK

授權結束後,RAM$xxxx@aliyun.com:chuanxue2就可以在grant_to裏使用這個jar包

odps@ grant_to>jar -resources grant_from/resources/cx_word_count2.jar -classpath C:\Users\chuanxue\Desktop\cx_word_count2.jar odps.test.WordCount;

Java代碼裏讀取資源

還有一種場景,就是如何在代碼裏跨項目讀資源文件。一般本項目裏的資源文件的讀取方法是(參考這裏)

            byte[] buffer = new byte[1024];
            int bytesRead = 0;

            String filename = context.getJobConf().get("import.filename");
            bufferedInput = context.readResourceFileAsStream(filename);

            while ((bytesRead = bufferedInput.read(buffer)) != -1) {
              String chunk = new String(buffer, 0, bytesRead);
              importdata.append(chunk);
            }

在命令行裏的調用方式是:

odps@ grant_to>jar -resources grant_from/resources/cx_word_count3.jar,grant_from/resources/resource_file.txt -classpath C:\Users\chuanxue\Desktop\cx_word_count3.jar odps.test.WordCount;

在代碼裏,還是用

        String filename = "resource_file.txt";
        bufferedInput = context.readResourceFileAsStream(filename);

也就是說,是在jar命令裏告知任務使用的資源是來自其他項目的,到了MapReduce的Java代碼裏,所有的用法照舊,不需要特別指定資源的項目。

最後更新:2017-05-26 16:01:03

  上一篇:go  自適應網站怎麼做好些?
  下一篇:go  WannaCry後,今天的成都雲棲大會說了什麼