farcebook は、Rails フレームワークに基づいて構築された Facebook からインスピレーションを得たフルスタック Web アプリケーションです。 farcebook は、フロントエンド コンポーネントのレンダリングに PostgreSQL データベースと React を使用し、状態管理には Redux を使用します。
茶番ライブ
ユーザーがアカウントにサインアップすると、プロフィール ページが作成されます。各プロフィールには、プロフィール写真とカバー写真を保存するヘッダー、現在のユーザー情報をすべて表示する「紹介」セクション、ユーザーの最初の 9 人の友達を表示する「友達」セクション、およびユーザーが投稿したすべての投稿を表示するフィードが含まれます。ユーザーに投稿し、ユーザーのウォールに投稿します。
写真は AWS S3 バケットを使用してホストされ、 paperclip
gem を使用してアップロードされてデータベースに保存されます。
ユーザーは、 Post
およびComment
コンポーネントを通じて他のユーザーと情報を共有します。投稿は、別のユーザーのウォールに直接投稿することも、自分のウォールに投稿することもできます (投稿のreceiver_id
は自分のid
と同じです)。ユーザーは、各投稿と一緒に共有する画像をアップロードすることもできます。
投稿を作成すると、編集と削除の両方が可能になります。作成者はすべての投稿を編集および削除できますが、投稿の受信者は削除のみできます。
承認を示すために、ユーザーは投稿にLike
を選択できます。投稿には、受け取った「いいね!」の数だけでなく、「いいね!」をしたユーザーのリストも表示されます。
ユーザーは投稿にコメントを残すこともできます。コメントは作成された時期に基づいて順番に表示されます。コメントには他のコメントを返信することもでき、各コメントにはネストされたコメントがすべて表示されます。コメントは、オプションのparent_comment_id
を介して他のコメントに関連付けられます。
ユーザーは、投稿と同じ方法でコメントにLike
こともできます。これは、多態性関連付けを使用して 1 つのテーブルを使用して行われます。この関連付けでは、 likable_type
使用して、どのような種類のアイテムがいいねされているかを保存します。
ユーザーがウォールに投稿したり、投稿/コメントが「いいね!」されたりコメントされたときに、 Notification
が作成され、別のユーザーに送信されます。これは、どのアイテムが通知されているかを追跡する多態性関連付けを使用して再び実現されます。
ユーザーのナビゲーションバーには、新しい未確認の通知があるたびに表示される視覚的なインジケーターと、最近のすべての通知のリストを表示するドロップダウンがあります。各NotificationListItem
には、他のユーザーの名前と実行されたアクションが表示されるほか、クリックされた際の該当のアイテムへのリンクも表示されます。
ActiveRecord を使用した積極的な読み込みを利用して、データベース クエリを最適化し、パフォーマンスを向上させました。ユーザーのフィードを取得するとき、後で使用できるように、すべての関連情報も各投稿とともにクエリされます。
#posts_controller.rb
...
def feed
...
author_ids = @current_user . friend_ids + [ @current_user . id ]
@posts = Post . includes ( comments : [ { likes : :liker } , :child_comments ] , likes : :liker )
. where ( 'author_id IN (?) OR receiver_id = ?' , author_ids , @current_user . id )
. limit ( 10 )
. order ( updated_at : :desc )
. distinct
...
ユーザーを保護するために、コメントやウォールへの投稿の多くの機能は、ユーザー間の友情の裏で保護されています。これは、React の条件付きレンダリングを使用して行われ、現在のユーザーが投稿作成者の友人であるか、プロファイルの所有者であるか、または現在のユーザーが自分の投稿/プロファイルと対話しようとしているかどうかを確認します。
// post_show.jsx
// Showing comment form on Posts
...
{ ( areFriends || isCurrentUser ) &&
< CommentForm postId = { id } / >
}
...
// post_form.jsx
// Showing Post form on user profiles
...
render ( ) {
if ( ! currentProfileFriends . includes ( currentUserId ) ) {
return null
}
...