Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sqlite/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Database design 如何在SQLite3中为一个资源管理两个闭包表_Database Design_Sqlite - Fatal编程技术网

Database design 如何在SQLite3中为一个资源管理两个闭包表

Database design 如何在SQLite3中为一个资源管理两个闭包表,database-design,sqlite,Database Design,Sqlite,我希望这不是太具体了。我觉得这是一次学习的经历 在高层,我正在编写一个到sqlite3数据库的JSON:API接口,用于存储用户评论。有了JSON:API,可以在包含的部分列出一个简单的资源列表,每个资源都提供了一个关系,它可以指向其他注释。使用闭包表来表示注释线程和注释类似乎很自然 我从以下几点开始: CREATE TABLE comments ( id INTEGER PRIMARY KEY, author TEXT, body TEXT, created_at DATE,

我希望这不是太具体了。我觉得这是一次学习的经历

在高层,我正在编写一个到sqlite3数据库的JSON:API接口,用于存储用户评论。有了JSON:API,可以在
包含的
部分列出一个简单的资源列表,每个资源都提供了一个
关系
,它可以指向其他注释。使用闭包表来表示注释线程和注释类似乎很自然

我从以下几点开始:

CREATE TABLE comments (
  id INTEGER PRIMARY KEY,
  author TEXT,
  body TEXT,
  created_at DATE,
  email TEXT,
  href TEXT,
  ip_address TEXT,
  post_id TEXT
);

CREATE TABLE comment_threads (
  parent_id INTEGER NOT NULL,
  child_id INTEGER NOT NULL,
  PRIMARY KEY (parent_id, child_id)
);

CREATE TABLE comment_likes (
  comment_id INTEGER NOT NULL,
  ip_address TEXT NOT NULL,
  PRIMARY KEY (comment_id, ip_address)
);
我的想法是,我可以通过
post\u id
选择注释,然后从
comment\u thread
表中获取注释,并构建一个注释的平面列表,将其放入JSON:API输出的
included
部分

令人担忧的是,这意味着许多SQL查询和手动重建注释的关系。我担心的是,对每个资源执行多个SQL查询似乎有点幼稚

如何在一条(或更少)SQL语句中执行此操作

我已经能够通过以下评论实现这一点:

SELECT c.id,c.author,c.body,c.created_at,c.href,c.post_id,
       COUNT(cl.comment_id) AS likes
FROM comments AS c
JOIN comment_likes AS cl ON c.id == cl.comment_id
WHERE c.post_id == 'test'
ORDER BY c.created_at ASC;
但我不确定如何将其扩展,使表格看起来像:

| id | author | body            | created_at | href | post_id | likes | comments   |
|====|========|=================|============|======|=========|=======|============|
|  1 | Bob    | test comment    | 1990-12-17 |      | test    |     1 | array(2,3) |
|  2 | Jane   | test comment 2  | 1990-12-18 |      |         |     0 | array()    |
|  3 | Jill   | test comment 3  | 1990-12-19 |      |         |     0 | array(4,5) |
|  4 | Bortus | test comment 4  | 1990-12-20 |      |         |     2 | array()    |
|  5 | John   | test comment 5  | 1990-12-21 |      |         |     0 | array()    |
这可能吗

样本数据
这在一条语句中很容易做到——您只需要在所选的值中使用两个相关的子查询来计算like count和child comment list列

注意:由于要将其转换为JSON,下面使用扩展名为comments列使用JSON数组来保存步骤。如果您的sqlite安装程序没有使用该功能进行编译,您可以使用执行类似的操作

产生

id          author      body          created_at  href        post_id     likes       comments  
----------  ----------  ------------  ----------  ----------  ----------  ----------  ----------
1           Bob         test comment  1990-12-17              test        1           [2,3]     
2           Jane        test comment  1990-12-18                          0           []        
3           Jill        test comment  1990-12-19                          0           [4,5]     
4           Bortus      test comment  1990-12-20                          2           []        
5           John        test comment  1990-12-21                          0           []        
6           Spock       test comment  1990-12-22              test2       2           [7]       
7           Jim         test comment  1990-12-23                          0           [8]       
8           Beverly     test comment  1990-12-24                          1           [9]       
9           Stacy       test comment  1990-12-25                          0           [10]      
10          Alice       test comment  1990-12-26                          0           []       

编辑:如果您只想要一条带有特定
post\u id
及其回复线程的评论,而不是每条评论,请发挥作用:

WITH one_thread AS
 (SELECT id, author, body, created_at, href, post_id FROM comments WHERE post_id = 'test'
  UNION ALL
  SELECT c.id, c.author, c.body, c.created_at, c.href, c.post_id
  FROM one_thread AS o
  JOIN comment_threads AS t ON o.id = t.parent_id
  JOIN comments AS c ON t.child_id = c.id)
SELECT id, author, body, created_at, href, post_id
     , (SELECT count(*) FROM comment_likes AS l WHERE c.id = l.comment_id) AS likes
     , (SELECT json_group_array(t.child_id) FROM comment_threads AS t WHERE c.id = t.parent_id) AS comments
FROM one_thread AS c
ORDER BY created_at;
这正好

id          author      body          created_at  href        post_id     likes       comments  
----------  ----------  ------------  ----------  ----------  ----------  ----------  ----------
1           Bob         test comment  1990-12-17              test        1           [2,3]     
2           Jane        test comment  1990-12-18                          0           []        
3           Jill        test comment  1990-12-19                          0           [4,5]     
4           Bortus      test comment  1990-12-20                          2           []        
5           John        test comment  1990-12-21                          0           []  

您是否可以提供样本数据来填充表(作为insert语句以便于复制和粘贴),以获得所需的输出?@Shawn sample data已添加。
WITH one_thread AS
 (SELECT id, author, body, created_at, href, post_id FROM comments WHERE post_id = 'test'
  UNION ALL
  SELECT c.id, c.author, c.body, c.created_at, c.href, c.post_id
  FROM one_thread AS o
  JOIN comment_threads AS t ON o.id = t.parent_id
  JOIN comments AS c ON t.child_id = c.id)
SELECT id, author, body, created_at, href, post_id
     , (SELECT count(*) FROM comment_likes AS l WHERE c.id = l.comment_id) AS likes
     , (SELECT json_group_array(t.child_id) FROM comment_threads AS t WHERE c.id = t.parent_id) AS comments
FROM one_thread AS c
ORDER BY created_at;
id          author      body          created_at  href        post_id     likes       comments  
----------  ----------  ------------  ----------  ----------  ----------  ----------  ----------
1           Bob         test comment  1990-12-17              test        1           [2,3]     
2           Jane        test comment  1990-12-18                          0           []        
3           Jill        test comment  1990-12-19                          0           [4,5]     
4           Bortus      test comment  1990-12-20                          2           []        
5           John        test comment  1990-12-21                          0           []