作为数据分析神器,Python、Tableau各有所长,Python 功能全而强大,Tableau可视化效果好。而把二者结合,将产生更为丰富的效果。
这里需要 Python 的第三方库 TabPy。启动 Tabpy 服务,在Tableau中连接此服务,则可以在Tableau中使用 Python 的各种函数功能。
TabPy 安装
与其他 Python 包的安装一样,直接 pip 安装即可。
1 |
pip install tabpy |
由于公司内网的限制,直接 pip 无法连接网络,增加代理即可安装成功!
1 |
pip install pytab --proxy="xxxx:xxx" |
TabPy 服务器启动
tabpy安装成功后,在python安装目录的tabpy文件夹(C:\ProgramData\Anaconda3\Lib\site-packages\tabpy_server\
)下回有 startup.bat 文件,双击打开,即可启动tabpy服务。
为以后使用方便,可使用os
将其写入到 Python 脚本中:
1 2 |
import os os.system(r"C:\ProgramData\Anaconda3\Lib\site-packages\tabpy_server\startup.bat") |
启动后,若输出以下结果,则说明 TabPy 服务启动成功!
1 2 3 |
Initializing TabPy... Done initializing TabPy. Web service listening on port 9004 |
Tableau 连接 TabPy 服务
tabpy服务启动成功后,保持窗口不要关闭,此时服务器处于等待Tableau连接的状态。
打开Tableau软件,依次点击菜单栏 帮助–设置和性能–管理外部服务连接,即可打开服务器连接设置。
由于我们搭建的 TabPy 服务是建立在本地计算机上,因此服务器填写为“http://localhost”,端口为“9004”(这是默认的端口),如下所示。【全程需要保持tabpy服务一直开启,不要关闭】
Pytab 自定义函数部署
连接 TabPy 服务后,可在 Tableau 中使用 Python 自带的各种函数。同样,我们可以设置自定义函数,然后部署到 TabPy 服务上。
例如,我们要定义 2 个列表相加的函数 add,如下:
1 2 3 4 |
import numpy as np def add(a,b): return np.add(np.array(a),np.array(b)).tolist() # 注意:由于要在tableau中使用函数的输出结果,需要有return值 |
在部署 add 函数之前,首先需要定义我们将要部署的服务器及端口
1 2 |
import tabpy_client client = tabpy_client.Client('http://localhost:9004') |
然后,使用 deploy 将函数部署到服务上。
1 |
client.deploy(name='add', obj=add, override=True) |
上述命令运行后则马上结束了,不像 TabPy 那样一直处于后台运行的状态。不要担心,此时只要 TapPy 服务未关闭,add 函数就已经部署成功啦~
TabPy 服务搭建及函数部署汇总
为简化服务启动及部署的步骤,可将所有函数汇总到一个 Python 脚本中,这样运行一次代码即可把所有工作准备好。
主要是分为几个模块:
- TabPy 启动函数
- 功能性函数自定义
- 已定义函数部署
- schedule 运行。由于 Tabpy 服务启动后需要在后台一直运行并保持不关闭,这里采用多线程与 Sleep 结合的方式,使服务启动后停顿一会再启动自定义函数的部署
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
import os import time from multiprocessing import Process import tabpy_client import numpy as np # 服务启动 def starts(): os.system(r"C:\ProgramData\Anaconda3\Lib\site-packages\tabpy_server\startup.bat") print('*'*30+'Succeed'+'*'*30) # 自定义函数 def add(a,b): return np.add(np.array(a),np.array(b)).tolist() # 函数部署 def clients(): client = tabpy_client.Client('http://localhost:9004') print('\n' + '*' * 50 + 'TabPy Deployment Succeeds' + '*' * 50 + '\n') client.deploy(name='add', obj=add, override=True) # Schedule脚本运行 if __name__ == '__main__': s = Process(target=starts) s.start() time.sleep(5) runs = Process(target=clients) runs.start() |
Tableau 调用 TabPy 服务
Tableau 主要通过在创建计算字段中使用 TabPy 服务中的函数,即由 input 通过python函数计算得到 output。代码样式如下:
1 2 3 |
SCRIPT_REAL("return tabpy.query('add',_arg1,_arg2)['response']",sum(1),sum(2)) # 注意,这里一定要有return值 # 其中 _arg1和_arg2指要输入的参数 |
上述代码在 Python 也可直接运行,我觉得可以用来验证函数是否定义正确
1 2 |
r = client.query('add',[1,2,3,4],[12,3,4,5])['response'] print(r) |
除了SCRIPT_REAL
外,还有SCRIPT_BOOL
,SCRIPT_INT
,SCRIPT_STR
等函数,对应输出不同的数据类型~
TabPy 一次性调用所有函数【2019/8/2/8 更新】
当自定义的函数较多时,需要依次重复写代码调用,可将所有的方法打包成 class,再利用inspect.getmembers
函数实现批量部署方法
1 2 3 4 5 6 7 8 9 |
def clients_startup(): client = tabpy_client.Client('http://localhost:9004') print('\n' + '*' * 50 + 'TabPy Deployment Succeeds' + '*' * 50 + '\n') m = myfunction() for name, function in inspect.getmembers(m): if name.startswith('f_'): client.deploy(name=name, obj=function, override=True) print('%s 方法部署成功!' % name) |
其中inspect.getmembers
会返回一个二维 list。第一个值是方法的 name,第二个值是方法本身(即方法函数)。再结合 startwith 方法,就可以把函数一次性部署完成~