如何检查对象属性存在性并更新缺失项?及Ruby代码DRY重构
检查对象属性存在性与缺失属性更新 + 代码重构方案
嘿,咱们先拆解问题:首先聊聊怎么检查对象属性是否存在并更新缺失的,然后再一步步重构你的Rails代码,让它更符合DRY(Don't Repeat Yourself)原则,看起来更简洁清爽~
一、如何检查属性是否存在并更新缺失属性
对于Ruby on Rails的ActiveRecord对象来说:
- 检查属性是否存在:用
respond_to?(:属性名)就能判断对象是否拥有该属性(不过一般模型定义了数据库字段的话,属性肯定存在,更多场景是检查属性值是否缺失) - 检查属性值是否缺失:推荐用
blank?方法,它比empty?更通用——既能处理空字符串,也能处理nil、空数组等情况,避免出现nil.empty?的报错 - 更新缺失属性:可以先收集需要更新的属性到哈希里,再统一用
assign_attributes或update!批量赋值,减少重复代码
二、代码重构实现
你的原代码逻辑没问题,但重复了保存操作和提示信息输出,咱们把这些重复逻辑抽出来,优化后代码如下:
stock = Stock.find_or_initialize_by(ticker: ticker) # 收集需要更新的属性 update_attributes = {} update_attributes[:jse_link] = link if stock.new_record? || stock.jse_link.blank? update_attributes[:name] = name if stock.new_record? || stock.name.blank? update_attributes[:price] = price if stock.new_record? || !stock.price.eql?(price) # 只有当有属性需要更新时才执行保存和提示 if update_attributes.present? stock.assign_attributes(update_attributes) stock.save! # 动态生成提示信息,避免重复字符串 action = stock.new_record? ? "created" : "updated" message_parts = ["#{stock.ticker} #{action} successfully"] message_parts << "price: #{stock.price}" if update_attributes.key?(:price) message_parts << "name: #{stock.name}" if update_attributes.key?(:name) message_parts << "can be viewed at #{stock.jse_link}" if update_attributes.key?(:jse_link) puts message_parts.join(', ') + '.' end
三、重构亮点说明
- 集中管理更新条件:把所有需要更新的属性判断集中到
update_attributes哈希里,避免了多分支的重复逻辑 - 更安全的缺失判断:用
blank?替代empty?,兼容nil值场景,避免运行时错误 - 统一保存逻辑:不管是新建记录还是更新记录,都用
assign_attributes+save!处理,减少重复的保存代码 - 动态生成提示:根据实际更新的属性拼接提示信息,不用写多份几乎一样的
puts语句,符合DRY原则
内容的提问来源于stack exchange,提问作者marcamillion
相关产品推荐
相关产品推荐

