飞书API 2-3:如何使用 API 创建数据表,解放人工?

一、引入

作为飞书多维表的深度使用者,经常需要将一些数据库的数据同步到多维表上,在数据写入之前,一般需要新建数据表和字段。当通过网页端界面新建字段时,如果字段少,还能接受手动一个个创建,不过一旦字段比较多,操作起来特别繁琐,机械地重复着,有点怀疑人生。

这种情况下,急需一个更加自动化的方式来解决!这不,飞书官方便提供了这样的 API 方便我们快速建数据表和字段。
注:数据表和多维表不是同个东西,多维表包含数据表,一个多维表中可以创建多个数据表,和 Excel 的逻辑差不多,多维表类比 Excel 文件,数据表类比 Sheet 表,区别参考如下:
image.png

本文就来探讨下如何通过飞书的 API 在多维表中创建数据表并插入数据,主要包含三方面:

  • 创建数据表
  • 对表的列进行增减等操作

二、创建数据表

2.1 多维表权限问题

注意:如果多维表不是通过应用创建,需要添加权限。

添加权限的方法也很简单,打开多维表,然后在右上角有三个横向的点,点击它,在调出的窗口中选择更多>添加文档应用。
image.png

在弹出的界面输入应用名称进行搜索,选中应用,配置编辑或管理权限,点击添加即可。
image.png

2.2 建数据表 API 调试

💡API 文档:新建一个数据表
获得权限之后,才能使用应用操作多维表。
创建数据表,至少需要三个配置项:数据表名称、视图名称、一个列。可查看示例值:

{
  "table": {
    "name": "数据表名称",
    "default_view_name": "默认的表格视图",
    "fields": [
      {
        "field_name": "多行文本",
        "type": 1
      }
    ]
  }
}

打开 API 调试台,需要输入 app_token 和 请求体。
如何获取 app_token?

  • 如果是通过 API 创建多维表,可以通过响应体提取到 app_token,响应体的结构如下。这种情况下,可以通过response.json().get('data').get('app').get('app_token')获取,或者参考 飞书 API 2-2 直接调用函数cre_bitable()获取。

image.png

  • 如果是针对已经创建好的多维表,查看地址栏获取

image.png

请求体可以使用默认的示例值,输入 app_token 和请求体之后,开始调试。
image.png

请求成功之后,会返回默认的视图 ID 和数据表的 ID,结果参考如下:
image.png

查看多维表,新建了一个名叫“数据表名称”的数据表,有一个默认视图叫默认的表示视图,该表有一列,叫多行文本。
image.png

三、字段操作

如果对现有的多维表的字段结构不满意,可以对数据表的字段进行新增、删除、更新操作。
对数据表进行字段操作都需要传递“app_token”和“table_id”。不同接口还有一些别的要求,新增字段需要传递请求体、更新字段需要传递“field_id”和请求体、删除字段需要传递“field_id”。
下文都通过上面创建的数据表来操作,所以 app_token 和 table_id 都是一样的,只讨论额外需要的参数。

3.1 新增字段

💡API 文档:新增字段
新增字段的请求体比较简单,一个字段名和字段类型即可,示例值如下:

{
    "field_name":"多行文本",
    "type":1
}

类型“1”表示1:多行文本,在前面 飞书API(5)中介绍 28 种数据类型的时候,介绍过该类型包含了三种子类型:多行文本、条码和 Email。默认是使用第一个,如果要使用后面的值类型,需要传递“ui_type”参数。

数据类型编码数据类型中文描述数据类型对应英文描述
1多行文本、条码Text,Barcode
1Email邮箱Email

比如,我要创建一个 条码,可使用以下请求体

{
    "field_name":"条码",
    "type":1,
    "ui_type":"Barcode"
}

成功之后,可以看到响应体会有相关字段的返回说明
image.png

一个 bug:虽然 Email 也是类型“1”,但是指定:“ui_type”:“Email” 之后,并不能成功创建 Email 类型的字段
image.png

在多维表上面显示和返回一致,是一个文本类型,而不是 Email。
image.png

3.2 更新字段

💡API 文档:更新字段
创建不了 Email,通过更新试试能不能处理。
相比新增字段,更新字段需要多传递一个参数:field_id,从新增的响应体可以了解到,邮箱字段的 field_id 是“fldhROhC0C”。请求体和新增字段时一致,发起调试请求后,报错了:DataNotChange(数据无变更)。说明更新字段也无法更改为“Email”类型。
image.png

那么如果要使用“Email”字段,就只能通过界面进行创建或修改,下面展示修改的的方法,创建直接点击添加字段选择“Email”即可。
image.png

换个需求:将第一个字段多行文本修改为自增数字的序号,多行文本字段的“field_id”为“fldvonP6L8”,请求体如下:

{
    "field_name":"序号",
    "type":1005,
    "ui_type":"AutoNumber"
}

调试结果如下,修改成功
image.png

查看多维表,已更新过来。
image.png

如果不知道“field_id”,怎么办?
调用列出字段的 API,填入“app_token”和“table_id”两个参数即可发起调试,查看对应数据表的字段信息。(💡API 文档:列出字段
image.png

3.3 删除字段

💡API 文档:删除字段
把条码字段删除。把“field_id”参数填写之后发起调试,便可以把条码字段删除。
image.png

查看多维表,已删除条码字段。
image.png

3.4 字段说明

飞书的字段类型有两个级别,主字段类型(“type”)和 ui 类型(“ui_type”)。
前面说到飞书共有 28 种数据类型,这个是指字段的 ui 类型(“ui_type”),主字段类型(“type”)是23种类型,多行文本、条码、邮箱这三类 ui 类型统一为多行文本类型,数字、进度、货币、评分这四类 ui 类型统一为数字类型。
能通过接口创建的字段类型如下:

  • “type”类型支持:1,2,3,4,5,7,11,13,15,17,18,20,21,22,23,1001,1002,1003,1004,1005。
  • “ui_type”类型支持:Text,Barcode,Number,Progress,Currency,Rating,SingleSelect,MultiSelect,DateTime,Checkbox,User,GroupChat,Phone,Url,Attachment,SingleLink,Formula,DuplexLink,Location,CreatedTime,ModifiedTime,CreatedUser,ModifiedUser,AutoNumber。

换个说法,不支持以下 4 种字段类型通过 API 创建:邮箱、查找引用、流程、按钮。
虽然其他的支持接口创建,但是有一些需要加上字段属性(“property”):进度、货币、评分、单向关联、双向关联。

  • 进度:需要在“property”中指定格式
  • 货币:需要在“property”中指定格式和货币类型
  • 评分:需要在“property”中指定格式和大小值
  • 单向关联:需要在“property”中指定引用的目标表和选择类型(单选/双选)
  • 双向关联:需要在“property”中指定引用的目标表和选择类型(单选/双选)和目标表的字段名

注意:公式如果没有传递“property”参数指定计算公式,是一个空公式。更多信息科参考:字段编辑指南

在创建数据表时,可以传递以下请求体,创建一个包含所有支持通过 API 创建的字段的数据表。
特别注意单向关联和双向关联中的“property”的“table_id”的值需要修改为你的多维表下的其他数据表的“table_id”,如果没有,需要去掉该字段,否则将创建失败。

{
  "table": {
    "name": "所有支持类型字段的数据表",
    "default_view_name": "一个视图",
    "fields": [
      {"field_name": "自动编号","type": 1005,"ui_type": "AutoNumber"},
      {"field_name": "多行文本","type": 1,"ui_type": "Text"},
      {"field_name": "条码","type": 1,"ui_type": "Barcode"},
      {"field_name": "数字","type": 2,"ui_type": "Number"},
      {"field_name": "进度","type": 2,"ui_type": "Progress",
          "property": {"formatter": "0.00%","min": 0.1,"max": 4,"range_customize": true}
          },
      {"field_name": "货币","type": 2,"ui_type": "Currency",
          "property": {"formatter": "0.0", "currency_code": "CNY" }
          },
      {"field_name": "评分","type": 2,"ui_type": "Rating",
          "property": {"formatter": "0", "min": 0, "max": 5, "rating": {"symbol": "star" }}
          },
      {"field_name": "单选","type": 3,"ui_type": "SingleSelect"},
      {"field_name": "多选","type": 4,"ui_type": "MultiSelect"},
      {"field_name": "日期","type": 5,"ui_type": "DateTime"},
      {"field_name": "复选框","type": 7,"ui_type": "Checkbox"},
      {"field_name": "人员","type": 11,"ui_type": "User"},
      {"field_name": "电话号码","type": 13,"ui_type": "Phone"},
      {"field_name": "超链接","type": 15,"ui_type": "Url"},
      {"field_name": "附件","type": 17,"ui_type": "Attachment"},
      {"field_name": "单向关联","type": 18,"ui_type": "SingleLink",
          "property": {"multiple": true,"table_id": "tblwZPx4ezszTIEh" }  
          },
      {"field_name": "公式","type": 20,"ui_type": "Formula"},
      {"field_name": "双向关联","type": 21,"ui_type": "DuplexLink",
          "property": {"multiple": false,"table_id": "tblwZPx4ezszTIEh","back_field_name": "双向关联-自动生成" }
          },
      {"field_name": "地理位置","type": 22,"ui_type": "Location"},
      {"field_name": "群组","type": 23,"ui_type": "GroupChat"},
      {"field_name": "创建时间","type": 1001,"ui_type": "CreatedTime"},
      {"field_name": "最后更新时间","type": 1002,"ui_type": "ModifiedTime"},
      {"field_name": "创建人","type": 1003,"ui_type": "CreatedUser"},
      {"field_name": "修改人","type": 1004,"ui_type": "ModifiedUser"}
    ]
  }
}

四、小结

本文探讨了如何通过 API 接口创建飞书多维表的数据表,在字段比较多的时候,方便快速创建表,而不需要在 UI 界面机械操作。基本步骤如下:

  • 授权:给应用开通多维表的写权限;
  • API 建表:梳理字段并调用 API 接口建表。

同时,探讨了字段的新增、更新和删除,以及介绍了多维表所有字段类型的特性。

  • 字段新增:需要“app_token”、“table_id”、字段名及数据类型;
  • 字段更新:需要“app_token”、“table_id”、“field_id”、新字段名及数据类型;
  • 字段删除:需要“app_token”、“table_id”和“field_id”。

最后,28 种字段类型的梳理如下:

序号typeui_type中文描述API 支持说明
11Text多行文本支持
21Barcode条码支持
31Email邮箱不支持
42Number数字支持
52Progress进度支持需要 property
62Currency货币支持需要 property
72Rating评分支持需要 property
83SingleSelect单选支持
94MultiSelect多选支持
105DateTime日期支持
117Checkbox复选框支持
1211User人员支持
1313Phone电话号码支持
1415Url超链接支持
1517Attachment附件支持
1618SingleLink单向关联支持需要 property
1719Lookup查找引用不支持
1820Formula公式支持空公式
1921DuplexLink双向关联支持需要 property
2022Location地理位置支持
2123GroupChat群组支持
2224Stage流程不支持
231001CreatedTime创建时间支持
241002ModifiedTime最后更新时间支持
251003CreatedUser创建人支持
261004ModifiedUser修改人支持
271005AutoNumber自动编号支持
283001Button按钮不支持



附录:代码小结


import requests
import json

def cre_data_sheet(access_token,app_token,request_body):
    url = f"https://open.feishu.cn/open-apis/bitable/v1/apps/{app_token}/tables"
    payload = json.dumps(request_body)
    
    headers = {
        'Content-Type': 'application/json',
        'Authorization': f'Bearer {access_token}'
    }

    payload = json.dumps(request_body)
    
    response = requests.request("POST", url, headers=headers, data=payload)
    code = response.json()['code']
    if code == 0:
        table_id = response.json().get("data").get("table_id")
        tb_name = request_body["table"]["name"]
        print(f"成功新建数据表:{tb_name},数据表的 table_id 为:{table_id}。关联函数:cre_data_sheet。")
        return table_id
    else:
        msg = response.json().get("msg")
        raise f"新建数据表失败,失败信息:{msg}。关联函数:cre_data_sheet。"

def add_field(access_token,app_token,table_id,request_body):
    url = f"https://open.feishu.cn/open-apis/bitable/v1/apps/{app_token}/tables/{table_id}/fields"
    payload = json.dumps(request_body)
    
    headers = {
        'Content-Type': 'application/json',
        'Authorization': f'Bearer {access_token}'
    }
    
    response = requests.request("POST", url, headers=headers, data=payload)
    code = response.json()['code']
    if code == 0:
        field_id = response.json().get("data").get("field").get("field_id")
        field_name = request_body["field_name"]
        print(f"成功新增字段:{field_name},该字段的 field_id 为:{field_id}。关联函数:add_field。")
        return table_id
    else:
        msg = response.json().get("msg")
        raise f"新增字段失败,失败信息:{msg}。关联函数:add_field。"

def update_field(access_token,app_token,table_id,field_id,request_body):
    url = f"https://open.feishu.cn/open-apis/bitable/v1/apps/{app_token}/tables/{table_id}/fields/{field_id}"
    payload = json.dumps(request_body)
    
    headers = {
        'Content-Type': 'application/json',
        'Authorization': f'Bearer {access_token}'
    }
    
    response = requests.request("PUT", url, headers=headers, data=payload)
    code = response.json()['code']
    if code == 0:
        field_id = response.json().get("data").get("field").get("field_id")
        field_name = request_body["field_name"]
        print(f"成功更新字段:{field_name}。关联函数:update_field。")
        return table_id
    else:
        msg = response.json().get("msg")
        raise f"更新字段失败,失败信息:{msg}。关联函数:update_field。"

def del_field(access_token,app_token,table_id,field_id):    
    url = f"https://open.feishu.cn/open-apis/bitable/v1/apps/{app_token}/tables/{table_id}/fields/{field_id}"
    
    headers = {
        'Content-Type': 'application/json',
        'Authorization': f'Bearer {access_token}'
    }
    
    response = requests.request("DELETE", url, headers=headers)
    code = response.json()['code']
    if code == 0:
        field_id = response.json().get("data").get("field_id")
        field_name = request_body["field_name"]
        print(f"成功删除字段:{field_name}。关联函数:del_field。")
        return table_id
    else:
        msg = response.json().get("msg")
        raise f"删除字段失败,失败信息:{msg}。关联函数:del_field。"

def get_tenant_access_token(app_id, app_secret):
    url = "https://open.feishu.cn/open-apis/auth/v3/tenant_access_token/internal"
    payload = json.dumps({
        "app_id": app_id,
        "app_secret": app_secret
    })
    headers = {'Content-Type': 'application/json'}
    response = requests.request("POST", url, headers=headers, data=payload)
    tenant_access_token = response.json()['tenant_access_token']
    print(f'成功获取tenant_access_token:{tenant_access_token}。关联函数:get_table_params。')
    return tenant_access_token

def main(request_body):
    app_id = 'your_app_id'
    app_secret = 'your_app_secret'
    app_token = 'your_app_token'
    request_body = {
      "table": {
        "name": "数据表名称",
        "default_view_name": "默认的表格视图",
        "fields": [
          {
            "field_name": "多行文本",
            "type": 1
          }
        ]
      }
    }
    access_token = get_tenant_access_token(app_id, app_secret)
    table_id = cre_data_sheet(access_token,app_token,request_body)

    # # 新增字段
    # request_body = {
    # 	"field_name": "条码",
    # 	"type": 1,
    # 	"ui_type": "Barcode"
    # }
    # add_field(access_token,app_token,table_id,request_body)

    # # 更新字段
    # request_body = {
    #     "field_name":"序号",
    #     "type":1005,
    #     "ui_type":"AutoNumber"
    # }
    # field_id = "your_field_id"
    # update_field(access_token,app_token,table_id,field_id,request_body)

    # # 删除字段
    # field_id = "your_field_id"
    # del_field(access_token,app_token,table_id,field_id)
    
if __name__ == '__main__':    
    main()
  • 4
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Xin学数据

为你点亮一盏灯,愿你前进无阻。

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值