티스토리 뷰

프로그래밍 공부/Ruby on Rails : Gem

Ruby on Rails : 띵동! 알람잼 [Gem : unread]

마음 따뜻한 개발자, 나른한 하루 2019. 11. 5. 21:18

해당 글은 https://blog.naver.com/kbs4674/221174702377 로 부터 게시글이 이전되었습니다.

 

띵동! 누군가가 제 게시물에 댓글을 달면 그 알림이 오면 참 좋겠죠!

이번에는 누군가 댓글을 달면 알람이 울리는 알람잼에 대해 같이 해보겠습니다! 

 

 참고 

1. Deivse Gem [클릭], act-as-commentable-with-threading(중첩댓글) [클릭] Gem을 활용한 기준으로 설명드립니다.

 

 

  • 알람잼 : unread

 참고  시작 전 제 댓글 방식은 다음 댓글방식을 이용했습니다. [참고 : 클릭]

위 댓글 방식을 기준으로 설명합니다.

 

1.  Gemfile  을 열어서 다음 내용을 추가합니다.

gem 'unread'

이어서 Gem을 설치합니다.

bundle install

 

2. 터미널에 다음 명령어를 입력해줍니다.

rails g unread:migration

 

3. Migrate 후, 다음 명령어를 입력해줘서 새로운 controller, model, db 파일을 생성합니다.

rails g controller new_notifications index show read_all
rails g model new_notification content link user:belongs_to

그리고 DB를 Migrate 해주세요.

rake db:migrate

 

4. 알림이 울릴 Comment의 controller로 이동 후, create 액션 내에 다음 내용을 추가해줍니다.

class CommentsController < ApplicationController
  ...
 
  def create
    ...
    
    respond_to do |format|
      if @comment.save
        make_child_comment
        format.html  { redirect_to("#{request.referrer}#comment#{@comment.id}", :notice => '댓글이 작성되었습니다.') }
        
        ## 댓글
        if (@comment.parent_id == nil && @comment.user_id != commentable.user_id)
          # 외부인이 댓글을 쓸 경우 => 글 작성자에게 알림
          if (@comment.user_id != commentable.user_id)
            @new_notification = NewNotification.create! user: commentable.user,
                                                    content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                    link: request.referrer
          end
        ## 대댓글 영역
        elsif (@comment.parent_id != nil && @comment.user_id != commentable.user_id)
          # 외부인이 대댓글을 작성 시 => 댓글 작성자에게 알림이 발송
          if (@comment.user_id != @comment.parent.user_id)
            @new_notification = NewNotification.create! user: @comment.parent.user,
                                                    content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                    link: request.referrer
          
          ## 대댓글 답변자 모두에게 => 알림 발송
          elsif (@comment.parent_id == @comment.parent.id)
            @comment.parent.children.each do |x|
              if (@comment.user_id != x.user_id && x.user_id != commentable.user_id) # 자기 자신에겐 알림 메세지가 안가게
                @new_notification5 = NewNotification.create! user: x.user,
                                                            content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                            link: request.referrer
              end
            end
          end
          
          # + 외부인이 대댓글을 작성 시 && 댓글 != 게시글 작성자 => 게시글 작성자에게 알림이 발송
          if (@comment.user_id != @comment.parent.user_id && @comment.parent.user_id != commentable.user_id)
            @new_notification = NewNotification.create! user: commentable.user,
                                                    content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                    link: request.referrer
 
          if (@comment.parent_id == @comment.parent.id)
            @comment.parent.children.each do |x|
              if (@comment.user_id != x.user_id && x.user_id != commentable.user_id) # 자기 자신에겐 알림 메세지가 안가게
                @new_notification5 = NewNotification.create! user: x.user,
                                                            content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                            link: request.referrer
              end
            end
          end
 
          # 댓글 != 게시글 작성자 && 댓글 != 대댓글 작성자 => 게시글 작성자에게 알림이 발송
          elsif (@comment.user_id != commentable.user_id && @comment.parent.user_id != commentable.user_id)
            @new_notification = NewNotification.create! user: commentable.user,
                                                    content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                    link: request.referrer
          end
          
        elsif (@comment.parent_id != nil && @comment.user_id == commentable.user_id && @comment.user_id != @comment.parent.user_id)
          # 댓글 == 게시글 작성자 && 댓글 != 대댓글 작성자 => 대댓글 작성자에게 알림이 발송
          @new_notification = NewNotification.create! user: @comment.parent.user,
                                                    content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                    link: request.referrer
          
                                                    
        elsif (@comment.parent_id != nil && @comment.parent_id == @comment.parent.id)
          @comment.parent.children.each do |x|
            if (@comment.user_id != x.user_id && @comment.user_id != x.parent.user_id )# 자기 자신에겐 알림 메세지가 안가게
              @new_notification5 = NewNotification.create! user: x.user,
                                                          content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                          link: request.referrer
            end
          end
        end
        
        if (@comment.parent_id != nil && @comment.user_id == commentable.user_id && @comment.user_id != @comment.parent.user_id)
          @comment.parent.children.each do |x|
            if (@comment.user_id != x.user_id || x.parent_id != x.parent.id )# 자기 자신에겐 알림 메세지가 안가게
              @new_notification5 = NewNotification.create! user: x.user,
                                                          content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                          link: request.referrer
            elsif (@comment.user_id != x.user_id && x.parent_id != x.parent.id )# 자기 자신에겐 알림 메세지가 안가게
              @new_notification5 = NewNotification.create! user: x.user,
                                                          content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                          link: request.referrer
            end
          end
        end
        
        if (@comment.parent_id != nil && @comment.user_id == commentable.user_id && @comment.user_id == @comment.parent.user_id)
          @comment.parent.children.each do |x|
            if (@comment.user_id != x.user_id || x.parent_id != x.parent.id )# 자기 자신에겐 알림 메세지가 안가게
              @new_notification5 = NewNotification.create! user: x.user,
                                                          content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                          link: request.referrer
            elsif (@comment.user_id != x.user_id && x.parent_id != x.parent.id )# 자기 자신에겐 알림 메세지가 안가게
              @new_notification5 = NewNotification.create! user: x.user,
                                                          content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                          link: request.referrer
            end
          end
        end
        
        if (@comment.parent_id != nil && @comment.parent.user_id == commentable.user_id)
          @comment.parent.children.each do |x|
            if (@comment.user_id != x.user_id && @comment.user_id != x.parent.user_id )# 자기 자신에겐 알림 메세지가 안가게
              @new_notification5 = NewNotification.create! user: x.user,
                                                          content: "#{current_user.email.truncate(15, omission: '...')} 님이 댓글을 다셨습니다.",
                                                          link: request.referrer
            end
          end
        end
        
        @comment.save
      else
        format.html  { redirect_to(request.referrer, :alert => '댓글 내용을 작성해주세요.') }
      end
    end
  end
 
  ...
end

 

5.  app/controllers/new_notification.rb  파일을 열고, 각 액션 별로 다음과 같이 내용을 넣어주세요.

class NewNotificationsController < ApplicationController
    def index
        @new_notifications = current_user.new_notifications.unread_by(current_user)
    end
    
    def show
        @new_notification = NewNotification.find(params[:id])
        @new_notification.mark_as_read! for: current_user
        redirect_to @new_notification.link
    end
      
    def read_all
        current_user.new_notifications.mark_as_read! :all, for: current_user
        redirect_back fallback_location: root_path
    end
end

 

6.  app/models/comment.rb  Model 파일로 이동 후, 모델 관계를 선언합니다.

class Comment < ApplicationRecord
    ...
    belongs_to :user
end

 

 

7.  app/models/user.rb  Model 파일로 이동 후, 아래와 같이 Gem 기능 연동 및 모델관계를 선언합니다.

class User < ApplicationRecord
  acts_as_reader
  has_many :new_notifications
end

 

8.  app/models/new_notification.rb  Model 파일로 이동 후, Gem 기능 설정 및 모델관계를 선언합니다.

class NewNotification < ApplicationRecord
    belongs_to :user
    acts_as_readable on: :created_at
end

 

9.  app/views/new_notifications  폴더 내에  _new_notification.html.erb  파일을 새로 만들어 준 후,

해당 파일 속에 다음 내용을 입력해줍니다.

<%= link_to new_notification.content, new_notification %>

 

10.  app/views/layouts/application.html.erb  파일로 이동 후, 적절한 위치에 알람 위치를 지정 후,

알림잼이 보여지게 하는 코드를 작성하면 되는데... 아래 코드는 아주 간단하게 view 코드를 짜봤습니다.

* 여러분들 스타일에 맞게 디자인을 다시 커스터마이징 해주세요.

## app/views/layouts/application.yml
<head>
...
<script>
function showHide(id) {
   var obj = document.getElementById(id);
   if (obj.style.display == 'none')
       obj.style.display = 'block';
   else
       obj.style.display = 'none';
}
</script>
...
</head>
## app/views/layouts/application.yml

<% if user_signed_in? %>
  <a onclick="showHide('info_html')" onfocus="this.blur()"><b>알림(<%= current_user.new_notifications.unread_by(current_user).count %>)</b></a>
  <div id="info_html" style="display:none; margin-top: 10px;">
    <%= render partial: "new_notifications/new_notification", collection: current_user.new_notifications.unread_by(current_user) %>
    <%= link_to '<b>모든 알림 지우기</b>'.html_safe, new_notifications_read_all_path %>
  </div>
<% end %>

 

 

11.  config/routes.rb  파일로 이동 후, 라우터 규칙을 추가해주세요.

## 알림 : 전체 삭제
get '/new_notifications/read_all' => 'new_notifications#read_all'

## 알림
resources :new_notifications

 

12. 서버를 껏다 킵니다.

 

 

13. 내가 작성한 게시글에 누군가 댓글을 달면 다음과 같이 결과를 보실 수 있습니다.

 

  • 참고/도움

1) L. G. S 형

2) unread Github [클릭]

 

루비온 레일즈 Ruby on Rails ROR

댓글
댓글쓰기 폼
공지사항
Total
37,626
Today
18
Yesterday
231
링크
«   2020/08   »
            1
2 3 4 5 6 7 8
9 10 11 12 13 14 15
16 17 18 19 20 21 22
23 24 25 26 27 28 29
30 31          
글 보관함