在Redshift UDF中导入用户定义的库

4

我正在尝试在Redshift中的用户定义的Python函数中导入一个库。

我已经创建了一个名为nltk的库,如下所示:

[CREATE OR REPLACE LIBRARY nltk LANGUAGE plpythonu FROM 's3://nltk.zip' CREDENTIALS 'aws_access_key_id=*****;aws_secret_access_key=****';]

一旦创建,我尝试将它作为一个函数导入:

CREATE  OR REPLACE FUNCTION f_function (sentence varchar)
    RETURNS VARCHAR STABLE AS $$
    from nltk import tokenize
    token = nltk.word_tokenize(sentence)
    return token $$ LANGUAGE plpythonu;

tokenize是nltk库中的一个子目录。

但是当我尝试在表格上调用函数时,出现了以下错误:

SELECT f_function(text) from table_txt;

我遇到了以下错误:

亚马逊无效操作:ImportError: No module named nltk。请查看svl_udf_log以获取更多信息
详细信息:
-----------------------------------------------
错误: ImportError: No module named nltk。请查看svl_udf_log以获取更多信息
代码: 10000
上下文: UDF
查询: 69145
位置: udf_client.cpp:298
进程: query0_21 [pid=3165]

请问有谁能帮我找出问题所在?

你在Redshift中使用过nltk吗? - Sahil Desai
2个回答

1
首先,您的Python代码存在一个明显的问题:您从未导入nltk,然后调用nltk.word_tokenize
其次,在下载了nltk包之后,您需要压缩包内部的模块文件夹,并将此zip上传到RedShift。
nltk-X.Y.zip
├─ setup.py
├─ requirements.txt
├─ nltk <- This is the folder that should be zipped and uploaded to S3
...  ├─ __init__.py
     ├─ tokenize.py

RedShift 只能导入模块 -- 你的根目录应该有一个 __init__.py 文件。http://docs.aws.amazon.com/redshift/latest/dg/udf-python-language-support.html


1

我仍然在上述指示中挣扎,所以当我最终找到它时,我想分享一下我是如何让它正常工作的。

首先,创建你的库:

create or replace library stem 
language plpythonu 
from 's3://[Your Bucket Here]/stem.zip' 
credentials 'aws_access_key_id=[aws key];aws_secret_access_key=[aws secret key]';

这是我编辑过的Stemming nltk zip库(我引入了兼容性以使其自包含),然后将其上传到S3:https://drive.google.com/file/d/0BzNI6AJdNrJCVThoSXVHY1NyUGM/view?usp=sharing。为了使用它,我必须编辑init.py库以引用上面创建的Redshift UDF库("Stem")。接着我在Redshift中创建了我的Python UDF函数:
create or replace function f_lancaster_stem (text varchar)
returns varchar 
immutable as $$
    from stem import LancasterStemmer
    st = LancasterStemmer()
    return st.stem(text)
$$ LANGUAGE plpythonu;

那么只需调用UDF!

select f_lancaster_stem('resting') from dual;

1
我不明白你为了让init.py工作所做的步骤。 - ScottieB

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接