【问题标题】:How to delete documents from Filetable?如何从 Filetable 中删除文档?
【发布时间】:2019-08-13 15:29:11
【问题描述】:

我正在尝试从 sql server 的文件表中删除一些文档。

这里我有一个表,我将所有附件的详细信息和文档存储在名为 Attchemnts 的 sql server 文件表中。

AttachmentDetails 表具有以下架构,

CREATE TABLE [dbo].[AttachmentDetails](
    [Id] [int] IDENTITY(1,1) NOT NULL PRIMARY KEY,
    [DocumentName] [nvarchar](max) NULL,
    [DocumentType] [nvarchar](max) NULL,
    [ModifiedDateTime] [datetime] NOT NULL,
    [CreatedDateTime] [datetime] NOT NULL,
    [CreatedBy] [nvarchar](254) NULL,
    [ModifiedBy] [nvarchar](254) NULL,
    [IsDeleted] [bit] NULL,
    )

每当我将任何文档上传到 File 表时,我都会根据表架构将该文档的详细信息插入到 AttchemntsDetails 表中。

这里我尝试了下面的解决方案

CREATE PROCEDURE [dbo].[DeleteFiles] 
AS
BEGIN
DELETE Attachments
FROM AttachmentDetails a
WHERE 
    DocumentType = 'video/mp4'  AND  DATEDIFF(day, a.CreatedDateTime, GETDATE())<11
end

此过程假设仅删除 10 天前的视频/mp4 文件,但它会从文件表中删除任何类型的文档。

【问题讨论】:

  • DELETE ... FROM ... WHERE ... 存储类型无关紧要
  • 此处发布的查询将导致随机删除,因为没有保证所有TOP 1 查询在没有ORDER BY 子句时将返回什么.你想做什么?编写一个正确的DELETE 查询比这个复杂的循环容易得多。
  • 我写了循环,因为我想检查表中每条记录的条件。
  • 这就是所有查询中的WHERE 子句的用途。 WHERE DocumentType = 'video/mp4' AND CreatedDateTime &lt; DATEADD(day,30,getdate()) 检查这两个条件的所有记录,只删除匹配的记录
  • BTW 发布表模式、数据样本和所需的输出。现在人们必须猜测这些表是什么。 ID 是两个表中的主键吗? Table1 是什么?

标签: sql-server stored-procedures filetable


【解决方案1】:

SQL 是一种基于集合的语言。对于每个基于光标/循环的脚本,都有一个更简单、更快的基于集合的解决方案。无论如何,编写此查询的方式会导致随机删除,因为无法保证所有这些 TOP 1 查询在没有 ORDER BY 子句的情况下会返回什么。

您似乎正在尝试删除所有超过 30 天的视频附件。看起来日期也存储在名为table1 的单独表中。如果您使用 FROM 子句,您可以编写一个 DELETE 语句,其行来自 JOIN,例如:

DELETE Attachments
FROM Attachments inner join table1 a on a.ID=Attachments.ID
WHERE 
    DocumentType = 'video/mp4' AND
    CreatedDateTime < DATEADD(day,-30,getdate())

编辑

原始查询包含DATEADD(day,30,getdate()),而它应该是DATEADD(day,-30,getdate())

示例

假设我们有这两个表:

create table attachments (ID int primary key,DocumentType nvarchar(100))

insert into attachments (ID,DocumentType)
values
(1,'video/mp4'),
(2,'audio/mp3'),
(3,'application/octet-stream'),
(4,'video/mp4')

create table table1 (ID int primary key, CreatedDateTime datetime)

insert into table1 (ID,CreatedDateTime)
values
(1,dateadd(day,-40,getdate())),
(2,dateadd(day,-40,getdate())),
(3,getdate()),
(4,getdate())

执行DELETE 查询只会删除 ID=1 的附件。查询

select *
from Attachments
```

Will return :

```
ID  DocumentType
2   audio/mp3
3   application/octet-stream
4   video/mp4
```

【讨论】:

  • 我尝试了上面的查询,并删除了文件表中的所有文档。
  • 如果所有个都符合条件,就会发生这种情况。如果所有附件都是超过 30 天的视频,它们将被删除。另一方面,如果ID 列被滥用并且例如table1.ID 不是唯一的,那么每个附件可能都有一个匹配的table1 记录。您没有提供有关表的任何信息,仅提供无效查询
  • 实际上只有2-3个video类型的文档,其余是图像,文本和doc文件。是的,我同意我没有提供表架构。
  • 糟糕,应该是-30,而不是30
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-08-14
  • 2015-08-31
  • 2011-09-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-03-10
相关资源
最近更新 更多