簡體   English   中英

SQL還是NoSQL搜索?

[英]SQL or NoSQL search?

讓我們假設我有一個擁有一定數量用戶且具有以下三個鮮明特征的網站:

1)用戶是網絡的一部分。 (該站點包含多個網絡。)

2)用戶是一定數量的其他站點成員的“聯系人”。

3)用戶上傳的個人文檔可能會與某些聯系人(其他聯系人除外)共享。

這樣,基於每個用戶的網絡,聯系人以及已與該用戶共享的其他文檔,用戶的文檔搜索是唯一的。 解決此問題的可能方法是什么?我需要為每個用戶的每次搜索附加一個長長的唯一SQL查詢嗎? 我目前正在將MySQL用作數據庫-使用它是否足夠,還是我需要在這里轉向NoSQL選項以維持類似的非過濾搜索的性能?

我想到了一些問題來幫助回答這個問題:

  1. 您認為普通用戶可以訪問多少個文件? 網絡中的許多文檔將共享給所有人看嗎?
  2. 用戶將如何找到文檔以及文檔的外觀如何? 他們將只能通過共享它的聯系人進行搜索嗎? 通過簡單的標題匹配? 他們將能夠對文檔內容進行全文搜索嗎?

根據這兩個問題的答案,關系系統可以正常工作,我想這是更好的選擇,因為您已經在使用MySql。 我認為您可以通過一些非常合理的查詢為關系系統中的單個用戶找到文檔。

這是潛在的裸露架構

User
--all users in the system
UserId int
NetworkId int (Not sure if this is a 1 to many relationship)

Document
--all documents in the system
DocumentId int
UserId int -- the author
Name varchar 
StatusId -- perhaps a flag to indicate whether it is public or not, e.g. shared with everyone in the same network or shared with all contacts

UserDocumentLink
--Linking between a document and the contacts a user has shared the document with
DocumentId
ContactId

UserContact
--A link between a user and all of their contacts
ContactId -- PK identity to represent a link between two users
UserId -- User who owns the contact
ContactUserId --The contact user

這是一個潛在的“搜索”查詢:

--documents owned by me
SELECT DocumentId
from Document where UserId = @userId

UNION

--documents shared with me explicitly
SELECT DocumentId
From UserContact uc
InnerJoin UserDocumentLink ucl on uc.ContactId = ucl.ContactId
Where 
uc.ContactUserId = @userId

UNION

--documents shared with me via some public status, using a keyword filter
Select DocumentId
From Document d 
inner join User u on d.UserId = u.UserId
where 
u.NetworkId = @userNetworkId
and d.status in ()
and d.Name like '%' + @keyword + '%'

我認為對模式設計可能更具影響力的要求是您的問題中未提到的要求-用戶將如何搜索文檔? 我們在這里談論什么樣的文件? MySql不是全文搜索的好選擇。

而是取決於您“一定數量”的用戶的意思。 如果您的意思是數以萬計,那么幾乎可以采用任何解決方案來充分發揮作用。 如果您的意思是數百萬,那么NoSQL解決方案可能會更便宜,更輕松地擴展。

我懷疑可以使用更通用的SQL查詢,而不是為每個用戶使用唯一的SQL查詢,例如,選擇屬於知道當前用戶的用戶的文檔,這些文檔被標記為與當前用戶共享,並且與搜索字符串匹配。

可以使用非規范化(在NoSQL方法中很常見)來提高性能。

但是,圖形數據庫(如Peter Neubauer所建議的)可能與文檔存儲(CouchDB,MongoDB或Cassandra)結合使用,可以很好地解決此類問題,並且可以很好地擴展。

我將看一下一些NOSQL解決方案,用於此互連的數據集,可能是Neo4j (圖形數據庫)。 通過Cypher進行查詢甚至非常簡單,因此您可以返回表格結果。

正如其他人指出的那樣,必須考慮用戶數量和請求頻率(流量)。 另外,冗余有多重要? 人們同時處理相同文檔的可能性有多大? 大多數文檔是否僅創建一次並分發用於“只讀”目的?

與這種特定情況下的rdbms相比,NoSQL可以以一種更輕松的方式幫助您擴展和獲得冗余。 我假設您有時希望在文檔上啟用標記等。

現在,我想知道是否有任何特定原因導致您不為此而使用現成的文檔管理和CMS系統? 我確信這是有充分理由的,但是也許所有這些選擇也值得一看。

我希望這有幫助。 祝好運!

  • 在這種情況下,非規范化將為您提供更好的讀取搜索性能。
  • 不要規范用戶,將頻繁加入的實體(如所有者和文本)保留在一個表中
  • 例如,在文本表上將所有者的名稱保留為FK,在文本表上保留其名稱並減少連接數,則可以自由使用sql。

正如您為小型社交網絡項目所建議的那樣,我已經在MySQL中使用長而獨特的查詢來管理此問題。 如今,我建議使用solr並將權限信息保留為每個文檔上可互換關鍵字的非規范化數組。 假設每個網絡都有一個唯一的可識別代碼(即100N-20000N),類似於用戶和特殊權限授予。 您可以存儲一組許可密鑰,例如“ 5515N 43243N 2342N 603U 203PG 44321PG”,並在搜索時將其視為關鍵字。

我將用一個簡單的業務流程解決方案來解決它,這將導致一個簡單的數據模式,一個簡單的查詢以及性能和可伸縮性:

  • 每個用戶都有一個文檔列表...期限。
  • 實際上,此列表是對文檔表中文檔的引用的列表(帶有所有者/安全信息...)
  • 與其他用戶共享文檔時,此文檔引用會添加到用戶的文檔列表中(如果需要,請標記為共享的文檔),然后將用戶添加到文檔安全列表中(例如,權限級別)。

sql查詢獲取文檔很簡單:從userdocument中選擇documentid,其中userid = @ userid

通過對文檔表的聯接,適當的索引和sql調整,它將與所有需要的信息一起運行,並且運行速度很快。

我希望我能很好地理解您的嘗試。

-<  = one to many
>-< = many to many (will require link table)
Network -< user -< documents >-< contact(user)
            v
            |
            ^
      contacts(user,user)

這是關系性的,除非您擁有十億用戶,否則我認為沒有理由使用NoSQL

網絡(除非您可以屬於多個網絡)是用戶的屬性

聯系人將在鏈接表user_contact(user,user)中保留

documents(doc_id,user_id)
user(user_id)
contacts(user_id,c_user_id) with foreign keys on users
document_contact(doc_id,c_user_id) where a trigger constrains the c_user_id

那么您將獲得所有文檔所有者和訂閱者(​​聯系人)的視圖

CREATE OR REPLACE VIEW user_docs AS 
     SELECT d.user_id, d.doc_id, 'owner' AS role
       FROM documents d
     JOIN users u ON d.user_id = u.user_id
UNION 
     SELECT c.user_id, d.doc_id, 'subscriber' AS role
       FROM documents d
     JOIN contacts c ON d.user_id = c.c_user_id;

然后,您可以根據文檔聯系人過濾視圖,

select * from user_docs ud 
where 
(ud.role = 'originator'
or
ud.doc_id in (select doc_id from document_contact dc where ud.doc_id = dc.doc_id)
) and ud.user_id = 'me'

在全文搜索方面,我會權衡即時性和性能。

我會在單獨的線程上創建用戶組合和文檔的哈希表,通常在用戶關聯更改時由異步調用觸發。

然后,我查詢哈希值+其他搜索條件。 這將消除對可能導致鎖定的末尾長SQL的需要。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM