前言
在PowerBI中,数据的实时展示是一个很常见的场景,根据不同的需求会有不同的方案,但一般都会允许一定的数据延迟,以减轻数据源的负载。对于那些需要真正实时展示一些时间敏感型数据的场景,可以使用具有实时流式处理功能的流数据集或推送数据集来实现。那么本篇文章介绍的就是推送数据集的应用。
推送数据集的数据可以永久保存,适用于实时性要求高且需要对历史数据进行分析的场景。因为推送数据集可以永久保存数据,因此可以使用它的数据来创建报表,但报表里的内容无法实时更新,不过可以将报表里的内容固定到仪表板中,固定到仪表板中的内容则可以实时更新。另外需要注意,将整个报表页面固定到仪表板是不能实时更新的。
由于可以把报表的内容固定到仪表板,且支持实时刷新,因此推送数据集可以实现更复杂的二次计算或聚合计算,并且支持更多的图表类型。
使用推送数据集所创建的仪表板的效果如下图所示:
推送数据集的创建与数据推送
推送数据集的创建、数据的推送以及表结构的修改或度量值的创建等,都需要借助PowerBI的REST API,以下是API接口的说明:
创建推送数据集:
Url: https://api.powerbi.com/v1.0/myorg/groups/{工作区ID}/datasets
Method:POST
Request Header:
Authorization: Token //需要注册Azure应用才能获取
Content-Type: application/json
Request Body:
{
"name": "推送数据集的名称",
"defaultMode": "Push",
"tables": [
{
"name": "要在数据集中创建的表的名称",
"columns": [
{
"name": "表的字段名称1",
"dataType": "数据类型1"
},
{
"name": "表的字段名称2",
"dataType": "数据类型2"
},
...
],
"measures":[
{
"name": "度量值的名称1",
"expression": "度量值的表达式1",
"formatString": "度量值的数据格式1"
},
{
"name": "度量值的名称2",
"expression": "度量值的表达式2",
"formatString": "度量值的数据格式2"
},
...
]
},
...
],
"relationships":[
{
"name":"ToTable->FromTable",
"crossFilteringBehavior":"OneDirection",
"fromColumn":"多端表的字段名称",
"fromTable":"多端表的表名",
"toColumn":"一端表的字段名称",
"toTable":"一端表的表名"
},
...
]
}
Python代码示例:
import requests
import os
token = '获取方式请参考我的另一篇文章:Azure应用注册与访问令牌获取'
groupId = '工作区ID'
url = f'https://api.powerbi.com/v1.0/myorg/groups/{groupId}/datasets'
datasetInfo = {
"name": 'push dataset test',
"defaultMode": "Push",
"tables": [
{
"name": "客户表",
"columns": [
{
"name": "姓名",
"dataType": "string"
},
{
"name": "年龄",
"dataType": "double"
}
],
"measures":[
{
"name": "度量值-行数",
"expression": "COUNTROWS('客户表')",
"formatString":"0.00"
},
{
"name": "度量值-行数2",
"expression": "COUNTROWS('销售表')",
"formatString":"0.00"
}
]
},
{
"name": "销售表",
"columns": [
{
"name": "客户姓名",
"dataType": "string"
},
{
"name": "产品名称",
"dataType": "string"
},
{
"name": "销售梳理",
"dataType": "double"
}
]
}
],
"relationships":[
{
"name":"客户表->销售表",
"crossFilteringBehavior":"OneDirection",
"fromColumn":"客户姓名",
"fromTable":"销售表",
"toColumn":"姓名",
"toTable":"客户表"
}
]
}
createDataset = requests.post(url,headers={'authorization':token},json=datasetInfo,timeout=(5,10))
print(createDataset.text)
os.system('pause')
往推送数据集里推送数据:
Url: https://api.powerbi.com/v1.0/myorg/groups/{工作区ID}/datasets/{推送数据集ID}/tables/{推送数据集中的表的名称}/rows
Method:POST
Request Header:
Authorization: Token //需要注册Azure应用才能获取
Content-Type: application/json
Request Body:
{
"rows": [
{
"字段1": "对应字段的值",
"字段2": "对应字段的值",
"字段3": "对应字段的值",
...
},
{
"字段1": "对应字段的值",
"字段2": "对应字段的值",
"字段3": "对应字段的值",
...
},
...
]
}
Python代码示例:
import requests
import os
token = '获取方式请参考我的另一篇文章:Azure应用注册与访问令牌获取'
groupId = '工作区ID'
datasetId = '数据集ID'
tableName = '客户表'
url = f'https://api.powerbi.com/v1.0/myorg/groups/{groupId}/datasets/{datasetId}/tables/{tableName}/rows'
for i in range(1000):
requestBody ={
"rows": [
{
"姓名": f"test{i}",
"年龄": random.random()
}
]
}
insertData = requests.post(url,headers={'authorization':token},json=requestBody,timeout=(5,10))
time.sleep(1)
os.system('pause')
修改表结构或创建度量值:
Url: https://api.powerbi.com/v1.0/myorg/groups/{工作区ID}/datasets/{推送数据集ID}/tables/{推送数据集中的表的名称}
Method:PUT
Request Header:
Authorization: Token //需要注册Azure应用才能获取
Content-Type: application/json
Request Body:
{
"name": "推送数据集中的表的新名称",
"columns": [
{
"name": "新的字段名称1",
"dataType": "数据类型1"
},
{
"name": "新的字段名称2",
"dataType": "数据类型2"
},
...
],
"measures":[
{
"name": "度量值的名称1",
"expression": "度量值的表达式1",
"formatString": "度量值的数据格式1"
},
{
"name": "度量值的名称2",
"expression": "度量值的表达式2",
"formatString": "度量值的数据格式2"
},
...
]
}
Python代码示例:
import requests
import os
token = '获取方式请参考我的另一篇文章:Azure应用注册与访问令牌获取'
groupId = '工作区ID'
datasetId = '数据集ID'
tableName = '产品表'
url = f'https://api.powerbi.com/v1.0/myorg/groups/{groupId}/datasets/{datasetId}/tables/{tableName}'
requestBody = {
"name": "产品表",
"columns": [
{
"name": "产品名称",
"dataType": "string"
},
{
"name": "产品类别",
"dataType": "string"
}
],
"measures":[
{
"name": "度量值-行数",
"expression": "COUNTROWS('产品表')",
"formatString":"0.00"
},
{
"name": "度量值-行数2",
"expression": "COUNTROWS('产品表')",
"formatString":"0.00"
}
]
}
alterTable = requests.put(url,headers={'authorization':token},json=requestBody,timeout=(5,10))
print(alterTable.text)
os.system('pause')
以上API接口的描述并不是全部,省略了部分不常用的参数,详细内容请查阅官方文档:
Push Datasets – Datasets PostDatasetInGroup
Push Datasets – Datasets PostRowsInGroup
Push Datasets – Datasets PutTableInGroup
注意事项:
1、在调用REST API时需要先获取到Token,即需要先获取访问令牌,关于获取访问令牌的具体步骤与原理,请参考我的另一篇文章:Azure应用注册与访问令牌获取,并从该文章末尾处复制给出的现成代码,然后填写相关参数即可。注意:需要给Azure应用授予PowerBI Services的Dataset.ReadWrite.All权限。
2、工作区ID与数据集ID可以从浏览器上方地址栏处获取这两个ID,具体如下图所示:
3、在获取访问令牌时,若选择使用服务主体模式,则必须在PowerBI Service的门户管理中打开服务主体API访问的功能,若只使用主用户模式,则不用打开该功能。
4、获取访问令牌时无论是使用主用户模式还是服务主体模式,都需要给相应的主用户或服务主体授予工作区的访问权限。具体的权限级别视情况而定,比如刷新报表就需要参与者或以上权限,如果是共享报表那就需要成员或以上权限,因此建议授予成员或管理员权限是比较好的。给工作区添加权限时,如果添加的是服务主体,则使用Azure应用的名称进行搜索并添加;如果添加的是主用户,则使用主用户的名称或邮箱进行搜索并添加。
使用推送数据集创建实时更新的仪表板
进入到数据集详细页面,然后找到创建空白报表按钮,如下图所示:
然后编辑报表的内容,需要注意,报表的内容是无法实时更新的。
然后通过固定按钮,将需要展示的视觉对象固定到仪表板中,如下图所示:
最后,即可得到实时更新的仪表板,如下图所示:
总结
推送数据集的创建与修改都需要通过REST API来进行,具有一定的使用门槛。但与流数据集相比,推送数据集的数据可以永久保存,而且可以定义关系与创建度量值,因此可以在报表中创建更多类型的图表,并可以进行更复杂的计算。