TL; DR:
Essi utilizzano un'architettura stack con grafici cache per tutto sopra il fondo MySQL del loro stack.
Risposta lunga:
Ho fatto qualche ricerca su questo me stesso perché ero curioso come gestire la loro enorme quantità di dati e di ricerca in un modo rapido. Ho visto persone che si lamentano gli script di social network su misura diventando lento quando la base di utenti cresce. Dopo che ho fatto un po 'me stesso benchmarking con solo 10k utenti e 2,5 milioni di amici connessioni - nemmeno provano a preoccuparsi di permessi di gruppo e simpatie e post muro - si è scoperto in fretta che questo approccio è viziata. Così ho trascorso qualche tempo la ricerca sul web su come farlo meglio e sono imbattuto in questo articolo ufficiale di Facebook:
Ho davvero vi consiglio di guardare la presentazione del primo link qui sopra prima di continuare a leggere. E 'probabilmente la migliore spiegazione di come FB lavora dietro le quinte si possono trovare.
Il video e articolo ti dice alcune cose:
- Stanno usando MySQL per lo fondo del loro stack
- Sopra lo SQL DB è lo strato Tao, che contiene almeno due livelli di cache e utilizza grafici per descrivere le connessioni.
- Non ho trovato nulla su ciò che software / DB quello realmente utilizzato per i loro grafici memorizzati nella cache
Diamo uno sguardo a questo, amici in comune sono in alto a sinistra:

Bene, questo è un grafico. :) E non ti dice come costruire in SQL, ci sono diversi modi per farlo, ma questo sito ha una buona quantità di approcci diversi. Attenzione: Si consideri che un DB relazionale è quello che è: E 'pensato per memorizzare i dati normalizzati, non una struttura grafico. Così non si esibirà buono come un database grafico specializzato.
Considera anche che si deve fare query più complesse che amici di amici, per esempio quando si desidera filtrare tutti i luoghi intorno a un dato di coordinate che tu ei tuoi amici di amici come. Un grafico è la soluzione perfetta qui.
Non posso dirvi come costruire in modo che esso deve svolgere bene ma richiede chiaramente un po 'di tentativi ed errori e benchmarking.
Qui è la mia deludente prova per solo reperti amici degli amici:
DB Schema:
CREATE TABLE IF NOT EXISTS `friends` (
`id` int(11) NOT NULL,
`user_id` int(11) NOT NULL,
`friend_id` int(11) NOT NULL
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8;
Amici di amici di query:
(
select friend_id
from friends
where user_id = 1
) union (
select distinct ff.friend_id
from
friends f
join friends ff on ff.user_id = f.friend_id
where f.user_id = 1
)
Consiglio vivamente di creare alcuni dati di esempio con almeno 10k record utente e ognuno di loro che hanno amici in comune almeno 250 e quindi eseguire la query. Sulla mia macchina (4770k i7, SSD, 16 GB di RAM) il risultato è stato ~ 0,18 secondi per quella query. Forse può essere ottimizzato, io non sono un genio DB (suggerimenti sono i benvenuti). Tuttavia, se questo scale lineari sei già a 1,8 secondi per appena 100k utenti, 18 secondi per 1 milione di utenti.
Questo potrebbe ancora suonare OKish per ~ 100k utenti, ma considerare che solo amici recuperati di amici e non ha fatto alcun query più complessa come " me visualizzare solo i messaggi di amici di amici + fare il check permesso se mi è permesso o non consentito per vedere alcuni di loro + fare una query sub per controllare se mi piaceva nessuno di loro ". Si vuole lasciare che il DB fare il controllo su se v'è piaciuto un post già o no o si dovrà fare nel codice. Considera anche che questa non è l'unica domanda che si esegue e che tu abbia più di utente attivo al tempo stesso su un sito più o meno popolari.
Credo che la mia risposta risponde alla domanda di come Facebook progettato il loro rapporto amici molto bene, ma mi dispiace che io non posso dirvi come implementare in modo che funzionerà veloce. L'implementazione di un social network è facile, ma fare in modo che si comporta bene, non è chiaramente - IMHO.
Ho iniziato a sperimentare con OrientDB a fare il grafico-query e la mappatura miei bordi al DB SQL sottostante. Se mai avere fatto scriverò un articolo su di esso.