uni-app 云数据库file类型的字段设置为null后,无法更新覆盖

uni-app 云数据库file类型的字段设置为null后,无法更新覆盖

产品分类:
uniCloud/腾讯云

示例代码:

{
  "bsonType": "object",
  "permission": {
    "create": "'album_course_manage' in auth.permission",
    "delete": "'album_course_manage' in auth.permission",
    "read": true,
    "update": "'album_course_manage' in auth.permission"
  },
  "required": [
    "name",
    "media_file",
    "album_ids"
  ],
  "properties": {
    "_id": {
      "description": "存储文档 ID(商品 ID),系统自动生成"
    },
    "name": {
      "bsonType": "string",
      "description": "课程名称",
      "title": "课程名称",
      "trim": "both"
    },
    "desc": {
      "bsonType": "string",
      "description": "课程描述",
      "title": "课程描述",
      "trim": "both"
    },
    "course_length": {
      "bsonType": "string",
      "description": "课程时长",
      "title": "课程时长",
      "trim": "both"
    },
    "course_length_seconds": {
      "bsonType": "int",
      "description": "课程时长-秒",
      "title": "课程时长-秒",
      "defaultValue": 0
    },
    "play_times": {
      "bsonType": "int",
      "description": "播放次数",
      "title": "播放次数",
      "defaultValue": 0
    },
    "album_ids": {
      "bsonType": "array",
      "description": "所属专辑id列表",
      "title": "所属专辑",
      "foreignKey": "lz-album._id",
      "enum": {
        "collection": "lz-album",
        "field": "_id as value, name as text"
      }
    },
    "media_file": {
      "bsonType": "file",
      "description": "课程文件",
      "title": "课程文件",
      "permission": {
        "read": "'appGetCourse' in action || 'album_course_manage' in auth.permission"
      }
    },
    "video_file": {
      "bsonType": "file",
      "description": "课程视频文件",
      "title": "课程视频文件",
      "permission": {
        "read": "'appGetCourse' in action || 'album_course_manage' in auth.permission"
      }
    },
    "add_date": {
      "bsonType": "timestamp",
      "defaultValue": {
        "$env": "now"
      },
      "description": "上架时间"
    },
    "enable": {
      "bsonType": "bool",
      "description": "是否上架销售",
      "title": "启用",
      "defaultValue": false
    },
    "free": {
      "bsonType": "bool",
      "description": "是否为免费试听",
      "title": "免费试听",
      "defaultValue": false
    },
    "order": {
      "bsonType": "int",
      "title": "显示排序",
      "description": "排序",
      "defaultValue": 0
    }
  }
}
云数据库有这样一条记录,这条数据初始添加的时候,其中video_file为可选,初始设置为null
{
  "add_date": 1639536264900,
  "album_ids": [
    "859059a56197ae9a06da8c1d06cbc14d"
  ],
  "course_length": "00:00",
  "course_length_seconds": 0,
  "enable": true,
  "free": false,
  "media_file": {
    "extname": "mp3",
    "fileID": "cloud://tcb-qityvfnccrppizja0c5a4-594724.7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812/1639536261289_0.mp3",
    "name": "好妹妹 - 不说再见.mp3",
    "path": "https://7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812.tcb.qcloud.la/1639536261289_0.mp3",
    "size": 11967457,
    "url": "https://7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812.tcb.qcloud.la/1639536261289_0.mp3"
  },
  "name": "好妹妹 - 不说再见",
  "order": 2,
  "play_times": 0,
  "video_file": null
}
在前端调用update更新这条数据的时候,video_file字段通过file_picker选择了一个文件上传更新的时候,会报错导致这个字段无法更新
以下为提交的更新对象
{
  "name": "好妹妹 - 不说再见",
  "media_file": {
    "extname": "mp3",
    "name": "好妹妹 - 不说再见.mp3",
    "path": "https://7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812.tcb.qcloud.la/1639536261289_0.mp3",
    "size": 11967457,
    "fileID": "cloud://tcb-qityvfnccrppizja0c5a4-594724.7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812/1639536261289_0.mp3",
    "url": "https://7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812.tcb.qcloud.la/1639536261289_0.mp3"
  },
  "video_file": {
    "extname": "mp4",
    "fileType": "video",
    "name": "2.mp4",
    "path": "https://7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812.tcb.qcloud.la/1639537441518_0.mp4",
    "size": 8417062,
    "fileID": "cloud://tcb-qityvfnccrppizja0c5a4-594724.7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812/1639537441518_0.mp4",
    "url": "https://7463-tcb-qityvfnccrppizja0c5a4-594724-1308150812.tcb.qcloud.la/1639537441518_0.mp4"
  },
  "enable": true,
  "order": 2,
  "course_length": "00:00",
  "course_length_seconds": 0,
  "play_times": 0,
  "free": false,
  "album_ids": ["859059a56197ae9a06da8c1d06cbc14d"]
}
以下为报错信息
errCode: DATABASE_REQUEST_FAILED | errMsg: [FailedOperation] multiple write errors: [{write errors: [{Cannot create field 'extname' in element {video_file: null}}]}, {<nil>}]

操作步骤:

已在上面说明

预期结果:

可以正常更新覆盖null

实际结果:

报错无法更新这个字段

bug描述:

云数据库中类型为file的字段,添加记录后,初始设置为null以后,无法update


更多关于uni-app 云数据库file类型的字段设置为null后,无法更新覆盖的实战教程也可以访问 https://www.itying.com/category-93-b0.html

20 回复

jql已调整为自动过滤file类型字段null数据

更多关于uni-app 云数据库file类型的字段设置为null后,无法更新覆盖的实战教程也可以访问 https://www.itying.com/category-93-b0.html


2023.4.13问题还存在

你怎么用的?上面说的调整试jql对bsonType: file类型字段做的处理。如果你没有使用jql注意自己对复杂类型过滤null值

问题已了解,建议将删除的文件更新为一个空对象

空对象就是直接更新为{}吗,貌似也是不行

上传空对象{}会提示类型不符

回复 5***@qq.com: 看一下是前端校验的还是云端校验的

回复 5***@qq.com: 把空对象改成{url:’’}试试呢

回复 DCloud_uniCloud_WYQ: 这个问题最后是怎么解决的?我也遇到了这样的问题

如云库手动更新为{}可以,但是前端默认值设置为{}的话,无法提交,验证的结果是类型不符

此问题仍然存在。 一个带图片的集合,第一次不传图,保存, 第二次去补这个图片就上传不了。 云端报的错误

我的情况和题主一模一样,百度一圈也找不到解决方案! 当前时间:20220728 问题仍然存在! 希望官方能解决一下!

遇到相同问题 今天是2023年3月1日 手动设置可以设置为{},但前端更新成{}会报类型错误,无法设置。 设置为null可以,但后期将无法覆盖更新。

目前我的解决办法,大家可参考: 更新时设置为{url:’’}是可以的,这样相当于图片删除了。

单独设置一个变量存储v-model,比如 xxximg 在调用该字段值的地方加判断,如果res.result.data[0].img.url为空,则认为图片不存在。 如果不为空,则认为图片存在

这种bug都不给修复一下,这么久了。哎

回复 z***@126.com: {url:’’}也删除不了

同,问题还在 如果是 file 数组 会变成 [ null, { url:"" } ],一样报错

不仅仅是file类型 对象类型也是一样 测试的时候,因为字段值直接删除是无效的,只能改值,但是对象类型如果改成null就无法更新,现在2025年还是没修复吗

这是 uni-app 云数据库的一个已知问题。当 file 类型字段初始值为 null 时,直接更新为完整的 file 对象会报错,因为数据库无法在 null 值上创建子字段。

解决方案:

  1. 使用 db.command.set 操作符
const db = uniCloud.database()
db.collection('your-collection').doc('your-doc-id').update({
  video_file: db.command.set({
    extname: "mp4",
    fileType: "video",
    name: "2.mp4",
    path: "https://...",
    size: 8417062,
    fileID: "cloud://...",
    url: "https://..."
  })
})
  1. 先删除再设置(两步操作):
// 先设置为空对象
await db.collection('your-collection').doc('your-doc-id').update({
  video_file: {}
})

// 再更新为完整对象
await db.collection('your-collection').doc('your-doc-id').update({
  video_file: {
    extname: "mp4",
    // ... 其他字段
  }
})
回到顶部