Задать вопрос
@AndreyBuyback
Разбираю Руби и Рельсы, учусь.

Как подгружать чат на страницу после загрузки страницы?

Есть страничка, в левой части обычный контент, в правой части чат. Хочу чтобы чат подгружался после загрузки страницы. Допустим хочу рендерить страничку с постами:
class PostsController < ApplicationController
    def index 
        @posts = Post.all
        @messages = Message.all # приходится тянуть в контроллер подгрузку сообщений из чата
        @message = Message.new # и новое сообщение для создания формы
    end
end

Или когда я буду рендерить страницу создания поста, мне опять придется тянуть сообщения чата в контроллер, и т.д. в каждый контроллер, что плохо. А если бы чат подгружался после загрузки или подгружался один раз при подключении пользователя к Action Cable, а затем обновлялся только с помощью него, было бы здорово.
Пишу на Ruby On Rails, использую Turbolinks, Stimulus и Action Cable для чата. Что можно придумать?
  • Вопрос задан
  • 131 просмотр
Подписаться 1 Средний Комментировать
Решения вопроса 2
nikolaokonesh
@nikolaokonesh
Не курю не пью
Вот довольно простой метод, так к примеру набросок, использовал setTimeout() для загрузки комментариев:
show.html.erb
<div class="d-block" id="comments-show-columns">
            <div id="open_comments" class="mt-4">
              <div data-controller="comments">
                Загрузка комментариев...
                <%= link_to url_for(open: 'true'), class: 'hidden', remote: true, data: {target: "comments.opencomment"} do %>
                <% end %>
              </div>
            </div>
          </div>


show.js.erb
<% if params[:open] %>
  var opening = document.querySelector("#open_comments")
  var pagin = document.querySelector("#comments-show-paginator")

  pagin.classList.toggle("hidden")
  opening.innerHTML = ('<%=j render(partial: "comments/comment", collection: @comments, locals: {full: true}, continue_thread: 10) %>')
<% end %>


app/javascript/controllers/comments_controller.js
import { Controller } from "stimulus";

export default class extends Controller {
  static targets = ["opencomment"]

  connect() {
    setTimeout(() => this.opencommentTarget.click(), 500 )
  }

}


Так же используйте data-turbolinks-permanent чтобы визуально чат не загружался вновь при рендеринге страницы и так же айди open_comments должен содержать id страницы типа open_comments_<%= post.id %>.
Может есть способы другие то было бы интересно посмотреть.
Ответ написан
@AndreyBuyback Автор вопроса
Разбираю Руби и Рельсы, учусь.
В общем траблы были у меня в представлениях. Немного изменил код, удалил ChatController и представления для него за ненадобностью. Вызываю рендер через MessageController и добавил представление чата в `views/messages/_chat.html.erb`.

def render_message
      @message = Message.new
      @messages = Message.all
      MessagesController.render partial: 'messages/chat', locals: { message: @message, messages: @messages }
end


Соответственно вьюха `messages/chat.html.erb`

<div id="chat-wrapper">
    <div class="chat-messages" data-target="chat.messages">
        <%= render partial: 'messages/message', collection: messages, as: :message %>
    </div>
    <div class="chat-message-form">
        <%= render partial: 'messages/form', locals: { message: message } %>
    </div>
</div>


Все, теперь все работает, всем спасибо) Варианты реализаций, в ответе Nikola Okonesh и в комментарии к этому ответу.
Ответ написан
Комментировать
Пригласить эксперта
Ответы на вопрос 1
alfss
@alfss
https://career.habr.com/alfss
Напишите чат на JS. Предоставьте для него API.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы