Ringkasan : Untuk sekitar 1 juta pengguna aktif dan 150 juta aktivitas tersimpan, saya tetap sederhana:
- Gunakan basis data relasional untuk penyimpanan kegiatan unik (1 catatan per aktivitas / "hal yang terjadi") Buat catatan sekompleks yang Anda bisa. Struktur sehingga Anda dapat dengan cepat mengambil kumpulan kegiatan berdasarkan ID aktivitas atau dengan menggunakan satu set ID teman dengan batasan waktu.
- Publikasikan ID aktivitas ke Redis setiap kali catatan aktivitas dibuat, tambahkan ID ke daftar "aliran aktivitas" untuk setiap pengguna yang merupakan teman / pelanggan yang harus melihat aktivitas.
Query Redis untuk mendapatkan aliran aktivitas untuk setiap pengguna dan kemudian mengambil data terkait dari db sesuai kebutuhan. Kembali ke menanyakan db berdasarkan waktu jika pengguna perlu menelusuri jauh ke belakang (jika Anda bahkan menawarkan ini)
Saya menggunakan tabel MySQL lama yang biasa untuk menangani sekitar 15 juta kegiatan.
Itu terlihat seperti ini:
id
user_id (int)
activity_type (tinyint)
source_id (int)
parent_id (int)
parent_type (tinyint)
time (datetime but a smaller type like int would be better)
activity_type
memberi tahu saya jenis kegiatan, source_id
memberi tahu saya catatan yang terkait dengan kegiatan tersebut. Jadi jika jenis aktivitas berarti "tambah favorit" maka saya tahu bahwa source_id merujuk ke ID dari catatan favorit.
The parent_id
/ parent_type
berguna untuk aplikasi saya - mereka memberitahu saya apa aktivitas tersebut terkait dengan. Jika sebuah buku difavoritkan, maka parent_id / parent_type akan memberi tahu saya bahwa aktivitas tersebut berkaitan dengan buku (jenis) dengan kunci primer yang diberikan (id)
Saya mengindeks (user_id, time)
dan menanyakan aktivitas yang ada user_id IN (...friends...) AND time > some-cutoff-point
. Mengesampingkan id dan memilih indeks berkerumun yang berbeda mungkin merupakan ide yang baik - saya belum bereksperimen dengan itu.
Hal-hal yang cukup mendasar, tetapi bekerja, itu sederhana, dan mudah untuk bekerja seiring dengan perubahan kebutuhan Anda. Juga, jika Anda tidak menggunakan MySQL, Anda mungkin bisa melakukan lebih baik dalam hal indeks.
Untuk akses yang lebih cepat ke aktivitas terbaru, saya telah bereksperimen dengan Redis . Redis menyimpan semua data di dalam memori, sehingga Anda tidak dapat memasukkan semua aktivitas Anda di sana, tetapi Anda dapat menyimpan cukup banyak untuk sebagian besar layar yang paling populer di situs Anda. 100 terbaru untuk setiap pengguna atau sesuatu seperti itu. Dengan Redis dalam campuran, ini mungkin bekerja seperti ini:
- Buat catatan aktivitas MySQL Anda
- Untuk setiap teman pengguna yang membuat aktivitas, dorong ID ke daftar aktivitas mereka di Redis.
- Pangkas setiap daftar ke item X terakhir
Redis cepat dan menawarkan cara untuk menyalurkan perintah di satu koneksi - jadi mendorong aktivitas ke 1000 teman membutuhkan milidetik.
Untuk penjelasan lebih rinci tentang apa yang saya bicarakan, lihat contoh Twitter Redis: http://redis.io/topics/twitter-clone
Perbarui Februari 2011 Saya punya 50 juta aktivitas aktif saat ini dan saya belum mengubah apa pun. Satu hal yang menyenangkan tentang melakukan sesuatu yang mirip dengan ini adalah menggunakan baris kecil yang ringkas. Saya berencana membuat beberapa perubahan yang akan melibatkan lebih banyak aktivitas dan lebih banyak pertanyaan dari aktivitas itu dan saya pasti akan menggunakan Redis untuk menjaga hal-hal cepat. Saya menggunakan Redis di area lain dan itu benar-benar berfungsi dengan baik untuk beberapa jenis masalah.
Perbarui Juli 2014 Kami hingga sekitar 700 ribu pengguna aktif bulanan. Selama beberapa tahun terakhir, saya telah menggunakan Redis (seperti yang dijelaskan dalam daftar berpoin) untuk menyimpan 1000 ID aktivitas terakhir untuk setiap pengguna. Biasanya ada sekitar 100 juta catatan aktivitas dalam sistem dan mereka masih disimpan di MySQL dan tata letak masih sama. Catatan-catatan ini memungkinkan kami untuk pergi dengan memori Redis yang lebih sedikit, mereka berfungsi sebagai catatan data aktivitas, dan kami menggunakannya jika pengguna perlu halaman lebih jauh ke belakang pada waktunya untuk menemukan sesuatu.
Ini bukan solusi cerdas atau sangat menarik tetapi telah membantu saya dengan baik.