在Ruby中读取json并设置变量以在另一个类中使用
这里需要读取一个json文件,并从一个类生成变量,然后在另一个类中使用它们。到目前为止,我得到的是 helper.rb在Ruby中读取json并设置变量以在另一个类中使用,ruby,json,Ruby,Json,这里需要读取一个json文件,并从一个类生成变量,然后在另一个类中使用它们。到目前为止,我得到的是 helper.rb class MAGEINSTALLER_Helper #note nonrelated items removed require 'fileutils' #REFACTOR THIS LATER def load_settings() require 'json' file = File.open("script
class MAGEINSTALLER_Helper
#note nonrelated items removed
require 'fileutils'
#REFACTOR THIS LATER
def load_settings()
require 'json'
file = File.open("scripts/installer_settings.json", "rb")
contents = file.read
file.close
#note this should be changed for a better content check.. ie:valid json
#so it's a hack for now
if contents.length > 5
begin
parsed = JSON.parse(contents)
rescue SystemCallError
puts "must redo the settings file"
else
puts parsed['bs_mode']
parsed.each do |key, value|
puts "#{key}=>#{value}"
instance_variable_set("@" + key, value) #better way?
end
end
else
puts "must redo the settings file"
end
end
#a method to provide feedback simply
def download(from,to)
puts "completed download for #{from}\n"
end
end
在Pre_start.rb文件中调用
class Pre_start
#note nonrelated items removed
def initialize(params=nil)
puts 'World'
mi_h = MAGEINSTALLER_Helper.new
mi_h.load_settings()
bs_MAGEversion=instance_variable_get("@bs_MAGEversion") #doesn't seem to work
file="www/depo/newfile-#{bs_MAGEversion}.tar.gz"
if !File.exist?(file)
mi_h.download("http://www.dom.com/#{bs_MAGEversion}/file-#{bs_MAGEversion}.tar.gz",file)
else
puts "mage package exists"
end
end
end
josn文件是有效的json,并且是一个简单的对象(注意,这里有更多的只是显示相关的)
我需要json设置文件的原因是,我需要从bash脚本和后来的php脚本中提取设置。此文件是用于传递每个共享和需要匹配的设置的公共线程
现在,我得到了一个空字符串作为值。在工作代码中,我们一直在做类似的事情。问题和解决方案是在代码的主级别正确使用变量和范围。我们使用YAML,您使用的是JSON,但想法是一样的 通常我们在主代码中定义一个常量,如
CONFIG
,我们将YAML加载到该常量中,然后该常量在我们需要的所有代码中都可用。对于您而言,请改用JSON:
require 'json'
require_relative 'helper'
CONFIG = JSON.load_file('path/to/json')
此时,顶级代码和“helper.rb”代码都可以使用CONFIG
作为另一种方法,只需将JSON加载到任一文件中即可。加载时间可以忽略不计,并且仍然是相同的数据
由于JSON数据在程序运行时应该是静态的,所以可以在常量中使用它。仅当数据因代码的实例而异时,将其存储在实例变量中才有意义,这在从JSON或YAML类型文件加载数据时没有意义
另外,请注意,我使用的是来自JSON类的方法。不要使用繁杂的程序将JSON复制到实例变量中
例如,剥离代码:
require 'fileutils'
require 'json'
CONTENTS = JSON.load_file('scripts/installer_settings.json')
class MAGEINSTALLER_Helper
def download(from,to)
puts "completed download for #{from}\n"
end
end
CONFIG
可以在任何一个文件中初始化/加载,只需在需要访问内容之前从顶层执行即可
记住,Ruby从第一个文件的顶部开始执行它,然后向下读取。当遇到def
、class
和module
块之外的代码时,会执行这些代码,因此Ruby一看到这些代码就会进行CONFIG
初始化。如果在您开始调用方法和创建类实例之前发生这种情况,那么您的代码将很高兴。在这一行:
bs_MAGEversion=instance_variable_get("@bs_MAGEversion") #doesn't seem to work
mi_h.load_settings()
实例_变量_get未从存储值的mi_h对象中检索。按照您的使用方式,该行相当于:
bs_MAGEversion=@bs_MAGEversion
将其更改为mi_h.instance_variable_get会起作用。它也将是难看的红宝石。但我觉得这不是你想要的。如果我读对了,您需要这一行:
bs_MAGEversion=instance_variable_get("@bs_MAGEversion") #doesn't seem to work
mi_h.load_settings()
在预启动对象中填充@bs_MAGEversion和@bs_模式。Ruby不是那样工作的。最接近您在这里寻找的东西可能是mixin,如下所述:
实例变量集
正在MAGEINSTALLER\u Helper
类中创建变量。这就是您无法访问这些变量的原因
您可以将其重构为一个模块,如下所示:
require 'fileutils'
require 'json'
module MAGEINSTALLER_Helper
#note nonrelated items removed
#REFACTOR THIS LATER
def load_settings()
content = begin
JSON.load_file('scripts/installer_settings.json')
rescue
puts 'must redo the settings file'
{} # return an empty Hash object
end
parsed.each {|key, value| instance_variable_set("@#{key}", value)}
end
#a method to provide feedback simply
def download(from,to)
puts "completed download for #{from}\n"
end
end
class PreStart
include MAGEINSTALLER_Helper
#note nonrelated items removed
def initialize(params=nil)
puts 'World'
load_settings # The method is available inside the class
file="www/depo/newfile-#{@bs_MAGEversion}.tar.gz"
if !File.exist?(file)
download("http://www.dom.com/#{@bs_MAGEversion}/file-#{@bs_MAGEversion}.tar.gz",file)
else
puts "mage package exists"
end
end
end
我对其进行了一点重构,使其更具红色风格。我想我会遵循这一点,但还是有点混乱。您的意思是,在最上面的整个文件中放置CONFIG
,因此当我通过帮助程序加载它时,它将可用于所有类?对ruby来说还是个新手,所以我还是会拿到我的霸王牌。这就是我的票,我喜欢它的发展方向。那么这更像是红宝石风格?传统知识