rails控制器中的字符串替换或类似解决方案

rails string substitution or similar solution in controller

我正在为所有 50 个州的用户构建一个网站。我们需要为每个用户显示特定于他们情况的信息,例如,他们在该状态下完成的事件数。每个状态的视图(部分)显示特定于状态的信息,因此依赖于特定于状态的模型中的特定于状态的计算。我们想做类似的事情:

@#{user.state} = #{user.state.capitalize}.new(current_user)

在 users_controller 而不是

@illinois = Illinois.new(current_user) if (@user.state == 'illinois')
.... [and the remaining 49 states]
@wisconsin = Wisconsin.new(current_user) if (@user.state == 'wisconsin')

触发 Illinois.rb 模型,然后由

驱动 users_controller 中定义的视图
def user_state_view
  @user = current_user
  @events = Event.all
  @illinois = Illinois.new(current_user) if (@user.state == 'illinois')
end

我正在努力寻找更好的方法来执行此操作/重构它。谢谢!

如果可以的话,我会避免动态定义实例变量。它可以用 instance_variable_set 来完成,但这是不必要的。您没有理由需要将变量定义为 @illinois 而不是 @user_state 或类似的东西。这是一种方法。

先做一个状态的静态列表:

def states
  %{wisconsin arkansas new_york etc}
end

然后创建一个字典,将这些状态映射到它们的 classes:

def state_classes
  states.reduce({}) do |memo, state|
    memo[state] = state.camelize.constantize
    memo
  end
end
# = { 'illinois' => Illinois, 'wisconsin' => Wisconsin, 'new_york' => NewYork, etc }

您 hard-code 某处的状态标识符列表很重要,因为将任意值传递给 contantize 不是一个好习惯。

然后实例化正确的 class 就轻而易举了:

@user_state = state_classes[@user.state].new(current_user)

肯定有其他方法可以做到这一点(例如,可以将其添加到模型层)