Can anyone break this code down for me and explain how this can be done in classic Rails way with callbacks(if any) and methods?
class SearchController < ApplicationController
expose :search_result, -> { SearchService.new(search_params).call }
def search_params
params.permit(:q, :scope)
end
end
class SearchController < ApplicationController
def index
#search_result = SearchService.new(search_params).call
end
def search_params
params.permit(:q, :scope)
end
end
expose :search_result, -> { SearchService.new(search_params).call } creates a variable #search_result
Related
I am trying to pass stored_products from shopify into a Rails app but keep getting a home controller error at https://f588240c.ngrok.io/ i have made updates, with no luck and restarted the server a number of times with no luck.
Any help would be welcomed. Heres the code
class Api::V1::HomeController < ShopifyApp::AuthenticatedController
def index
#products = ShopifyAPI::Product.find(:all, params: { limit: 10 })
#products.each do |product|
StoredProduct.where(shopify_id: product.id)
.first_or_create do |stored_product|
stored_product.shopify_id = product.id
stored_product.shopify_title = product.title
stored_product.shopify_handle = product.handle
stored_product.shopify_image_url = product.image.src
stored_product.shop_id = #shop.id
stored_product.save
product.images.each do |image|
ProductImage.where(shopify_id: image.id)
.first_or_create do |product_image|
product_image.image_url = image.src
product_image.stored_product_id = stored_product_id
product_image.shopify_id = image.id
end
end
end
end
#stored_products = StoredProduct.belongs_to_shop(#shop.id)
end
end
From the authenticated controller
private
def set_shop
#shop = Shop.find_by(id: session[:shopify])
set_locale
end
from the store_products.rb file
class StoredProduct < ApplicationRecord
belongs_to :shop
has_many :product_images
scope :belongs_to_shop, -> shop_id { where(shop_id: shop_id) }
end
For this specific issue/code tutorial, the private set_shop method should be set like follows:
def set_shop
#shop = Shop.find_by(id: session[:shop_id])
set_locale
end
The other answer has params instead of session
The problem is that #shop is nil. The error message says it cannot call the method .id on NilClass.
In the image I can see that you have a shop_id in the params so you might just need to change your code here:
def set_shop
#shop = Shop.find_by(id: params[:shop_id])
set_locale
end
But that depends on your code, so please double check.
I have a controller which calls a class method from a model. However, I got undefined method 'where' for Jira:Class.
controller:
module Api
module V1
class JiraController < ApplicationController
def index
jira = Jira.where()
jira_stat = JiraStat.new(jira)
render json: [
{
t('jira.api.status') => jira_stat.status,
t('jira.api.number_of_jiras') => jira_stat.jira_total
}
]
end
end
end
end
model:
# frozen_string_literal: true
require 'active_model'
class Jira
include ActiveModel::Model
include JiraKit
attr_accessor :status, :jira
def self.where(status_name = 'all')
if status_name == 'all'
jiras = JiraKit.where.jira_issues(status: ['open', 'submitted', 'in
progress', 'in review', 'closed'])
elsif
jiras = JiraKit.where.jira_issues(status: [status_name])
end
new(#status = status_name, #jira = jiras)
end
end
I think I have used self keyword. But I don't know why I can't access that method. If I create an instance of Jira model, I am able to access that method.
i have class HomeController
class HomeController < ApplicationController
def event_one
Req = **endpoint.connection**
res = req.body**(json format)**
#events = res
end
def event_two
#events
end
end
Can i use one instance variable(#events) which got response from endpoint in event_one method,from another event_two method.
try using this DRY code:
class HomeController < ApplicationController
before_action :set_events, only: [:event_one, :event_two]
def event_one
#your code here
# for example puts #events
end
def event_two
#your code here
# for example puts #events
end
private
def set_events
req = **endpoint.connection**
res = req.body**(json format)**
#events = res
end
end
you can achieve use a private method to set evnets
class HomeController < ApplicationController
def event_one
set_events
end
def event_two
set_events
end
private
def set_events
Req = **endpoint.connection**
res = req.body**(json format)**
#events = res
end
end
You can also call this method using filter of you want to set for every action of this controller.
Hope this will help!
In apps/models/concerns/deactivable.rb
module Deactivatable
extend ActiveSupport::Concern
included do
scope :alive, -> { where(:deactivated_at => nil) }
end
def deactivate(t = Time.current)
update_attribute(:deactivated_at,t)
end
def activate
update_attribute(:deactivated_at,nil)
end
def deactivated?
deactivated_at.present?
end
end
This is being included in 2 models, app/models/activity_rules/activity_detection_rule.rb and app/models/concerns/generic_campaign.rb.
There are 2 more models which contain the same methods with different attribute name.
In redeemable.rb,
class Redeemable < ActiveRecord::Base
scope :alive, -> { where("(deactivation_date is null) and (expiry_date is null or expiry_date >= ?)",Date.today) }
def deactivate(t = Time.current)
update_attribute(:deactivation_date,t)
end
def reactivate
update_attribute(:deactivation_date,nil)
end
def deactivated?
deactivation_date.present?
end
end
and in surprise_set.rb
scope :alive, -> { where("deactivation_date is null") }
with the same 3 methods as redeemable.rb.
How to use Deactivable concern to DRY up the other two models?
You could return the attribute that indicates the time of deactivation from a class method. You can provide a default implementation in your concern and override in the class that includes the concern if you need to:
module Deactivatable
extend ActiveSupport::Concern
included do
scope :alive, -> { where(deactive_attr => nil) }
def self.deactive_attr
:deactivated_at
end
end
def deactivate(t = Time.current)
update_attribute(self.class.deactive_attr, t)
end
def activate
update_attribute(self.class.deactive_attr, nil)
end
def deactivated?
self.send(self.class.deactive_attr).present?
end
end
Then, in classes where you want to provide a different attribute you can add a class method:
include Deactivatable
def self.deactive_attr
:deactivation_date
end
You could also DRY up your alive scope a bit by allowing the class that includes the concern to define the conditions for 'aliveness'. In the concern you can define the default
scope :alive, -> { where(self.active_conditions) }
def self.active_conditions
{ self.deactive_attr => nil }
end
You can then provide a different implementation of active_conditions in the class itself:
self self.active_conditions
["(deactivation_date is null) and
(expiry_date is null or expiry_date >= ?)", Date.today]
end
I have a filter shared between some controllers, which is primarily declared as private in ApplicationController. This method sets find and pagination conditions for controllers.
class ApplicationController < ActionController::Base
...
protected # or private
# Define parametros de busca
def set_find_opts(klass)
#filter = params[:f].to_i || nil
#order = klass.set_order params[:o]
#opts = { :page => params[:page] }
#opts[:order] = #order if #order
end
...
end
class Admin::UsersController < AdminController
...
before_filter(:only => :index) {|c| c.set_find_opts User }
...
end
I'm getting this error:
1) Error:
test_should_get_index(Admin::UsersControllerTest):
NoMethodError: protected method `set_find_opts' called for #<Admin::UsersControl
ler:0x848f3ac>
app/controllers/admin/users_controller.rb:4
functional/admin/users_controller_test.rb:9:in `test_should_get_index'
Why it happens?
You can't send private/protected messages with an explicit receiver (object.protected_method) like you are doing in your block. You can try c.send(:set_find_opts, User) or c.instance_eval { set_find_opts(User) }.