Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How Does ReactJS Handles Rails Active Record Associations

I'm iterating over a user's post items. I can lists the items but not their profile based on my relationship:

Post Model:

belongs_to :user

Profile Model:

belongs_to :user

User Model:

has_many :posts
has_one :profile

PostsController:

class PostsController < ApplicationController
  respond_to :json

  before_action :set_post, only: [:show, :edit, :update, :destroy]
  before_action :only_current_user, except:[:show, :interest]

  # GET /posts
  # GET /posts.json
  def index
    @user = User.friendly.find( params[:user_id] )
  end
  [...]
end

Index page controller:

class PagesController < ApplicationController

    respond_to :json

    def index
        @users = User.all
        @posts = Post.all.order("created_at DESC")
    end
   [...]
end

Without JS, I get the values with:

<% @posts.each do |s| %>
 <%= s.user.profile.business_name %>
 <%= s.post_type %>
 <%= s.<all others> %>
<% end %>

Now with React, I can use the react-rails gem for this:

var Posts = React.createClass({

  render: function() {

    var createItem = (p) => (

    <div className="row">
      {p.post_type}
      {p.foobar}
      {p.user.name} //this does not work
    </div>

    );

    return (
      <div className="panel">
        {this.props.posts.map(createItem)}
      </div>
    );

  }
});

Index.html.erb:

<%= react_component('Posts', { posts: @posts } %>

I thought I had the answer but this just spits out all the users when I only want the user with associated post:

<%= react_component('Posts', { posts: @posts,
                               users: @users } %>

Then I'd add the props in the js but that's not what I want.

There seem to be a clue in my console that I'm trying to figure out:

"Warning: Each child in an array or iterator should have a unique "key" prop. Check the render method of Posts.

like image 589
Sylar Avatar asked Oct 20 '15 06:10

Sylar


People also ask

How does React work with Rails?

There are two ways to use React with Ruby on Rails. The first is to build two separate, standalone apps, with the React app on a different repository and communicating with the backend via an API. This can simply be achieved by creating both apps separately using Create React App and the Rails CLI.

What is Active Record association?

This association indicates that each instance of the model has zero or more instances of another model. For example, in an application containing authors and books, the author model could be declared like this: class Author < ApplicationRecord has_many :books end Copy.

How connect React and Rails?

First, you need to add the gem to your gemfile by running the command gem 'react-rails' and install the gem by running bundle install and react-rails installation script: rails g react:install . These actions will create a directory for the components and manifest file, and add them to the application. js file.


1 Answers

I don't think the warning has anything to do with the issue but just to get rid of it you can add the key prop in the React component like this:

var Posts = React.createClass({

  render: function() {

    var createItem = (p) => (

    <div className="row" key={p.id}>
      {p.post_type}
      {p.foobar}
      {p.user.name} //this does not work
    </div>

    );

    return (
      <div className="panel">
        {this.props.posts.map(createItem)}
      </div>
    );

  }
});

As for the real issue, please try changing the assignment of @posts to something like @posts = Post.all.includes(:user).as_json(include: { user: { only: [:name] } })

My guess is that you are just querying the posts. By default as_json (the method called when you return json data) does not include associations, therefore you won't get anything on the react side.

like image 117
nbermudezs Avatar answered Sep 29 '22 14:09

nbermudezs