From JSON to a Ruby Hash

How to convert JSON to a Ruby hash

What about the following snippet?

require 'json'
value = '{"val":"test","val1":"test1","val2":"test2"}'
puts JSON.parse(value) # => {"val"=>"test","val1"=>"test1","val2"=>"test2"}

How to convert JSON response to hash, and extract specific key and value

You can use select to extract the expected key and value.
Please refer ruby select.

def specific_currency(currency)
@response_body ||= RestClient.get(@weather).body
@hash_response = JSON.parse(@response_body)['rates'].select { |element| element.to_s == currency }
end

Convert JSON into a Hash

Solved my issues using:

object = self.as_json.with_indifferent_access
# => allowing me to use a symbol key instead of a string

ok_vals = object[:values][:ok].as_json.gsub(/\=\>/, ':')
# => allowing to change json string '{"val1"=>"val1", "val2"=>"val2"}' to '{"val1":"val1", "val2":"val2"}'
ok_vals = JSON.parse(ok_vals)
# => which transform json string to hash {val1: "val1", val2: "val2"}

Feel free to make any suggestions to this code. Thanks for the help.

How can I convert a string in my JSON file into a Ruby hash?

I think something like this would help:

def media_url
tweet = self.object
JSON.parse(tweet.media[0].gsub('=>', ':'))["media_url"]
end

You need to replace => with : in order for JSON.parse to work

Or

To get the complete hash you can use a more generic method like media:

def media
tweet = self.object
JSON.parse(tweet.media[0].gsub('=>', ':'))
end

How to convert JSON to a hash, search for and change a value

I understand your JSON may look like this:

"{\"features\":{\"additional-options\":true},\"values\":{\"lo-value\":34,\"hi-value\":554},\"persons\":[{\"name\":\"john\",\"member\":true,\"current\":false,\"sponsor\":\"pete\",\"profile\":\"\",\"credits\":[\"04\"],\"linked\":[\"philip\",\"guy\"],\"maptools\":[\"crossfit\",\"soccer\",\"running\"]},{\"name\":\"mary\",\"member\":true,\"current\":false,\"sponsor\":\"judy\",\"profile\":\"\",\"credits\":[\"all\"],\"activities\":[\"swimming\",\"cycling\",\"running\"]}],\"data_map\":[1122,3234]}"

I suggest using an OpenStruct to organize your data:

your_struct_name =  JSON.parse(yourJson, object_class: OpenStruct)

Then you get all the things you want. For the operations you show:

#change_key(hash, "features.additional-options", false)
your_struct_name.features['additional-options'] = false
#this one above you set in this hash-like manner because of the '-' in the middle of the key. Otherwise you could just do your_struct_name.features.additional_options = false

#del_from_array(hash, "persons.name=mary.activities", "cycling")
your_struct_name.persons.last.activities.delete('swimming')

# or selecting by name:
your_struct_name.persons.select {|person| person.name == 'mary' }.first.activities.delete('swimming')

#add_to_array(hash, "persons.name=mary.activities", "hockey")
your_struct_name.persons.last.activities << 'hockey'

#del_key(hash, "data_map")
your_struct_name.delete_field('data_map')

#del_key(hash, persons.name=john.profile)
...

#del_key(hash, persons.name=mary.credits)
...

Then, after you make your changes, you can use:

your_struct_name.to_h.to_json

You can also use the method as_json to get a structure very similar to what you showed on the question:

your_struct_name.as_json

OpenStruct is very nice to deal with data that has a changing structure. If you have data that can be "modeled", has a name you can call, has some attributes you can predict, and even methods you will use for this data, I suggest you to create a Class to describe this data, its properties and attributes (it can even inherit from OpenStruct). Then work inside this Class domain, creating a layer of abstraction. This way your code gets a lot more robust and readable. Don't forget to create automatic tests! It saves you a lot of time.

The way you organize and abstract your data, and specially the way you name entities are things that have high impact on code quality.

For further reading see: Object and ActiveData.

Parsing JSON list object to Ruby hash

A JSON Array of Objects becomes a Ruby Array of Hashes. These Hashes can then contain more Arrays and so on.

If you want to access the Hashes, you need to iterate through the Array. If you want to access the groups you need to iterate again.

scripts = JSON.parse(json)

# Iterate through each script
scripts.each { |script|
# Print the script's name.
puts "Script: #{script["name"]}"

# Iterate through the script's groups.
groups = script["groups"]
groups.each { |group|
# Print each group's name.
puts "Group: #{group["name"]}"
}
}

How to convert a ruby hash object to JSON?

One of the numerous niceties of Ruby is the possibility to extend existing classes with your own methods. That's called "class reopening" or monkey-patching (the meaning of the latter can vary, though).

So, take a look here:

car = {:make => "bmw", :year => "2003"}
# => {:make=>"bmw", :year=>"2003"}
car.to_json
# NoMethodError: undefined method `to_json' for {:make=>"bmw", :year=>"2003"}:Hash
# from (irb):11
# from /usr/bin/irb:12:in `<main>'
require 'json'
# => true
car.to_json
# => "{"make":"bmw","year":"2003"}"

As you can see, requiring json has magically brought method to_json to our Hash.

Convert JSON string to hash

It's most likely because this isn't valid JSON. Change your single quotes to double quotes, like so:

test = '[{"domain": "abc.com"}, {"domain": "def.com"}, {"domain": "ghi.com"}]'

An explanation can be found here, and you can validate your JSON here.

Ruby JSON parse changes Hash keys

In short, no. Think about it this way, storing symbols in JSON is the same as storing strings in JSON. So you cannot possibly distinguish between the two when it comes to parsing the JSON string. You can of course convert the string keys back into symbols, or in fact even build a class to interact with JSON which does this automagically, but I would recommend just using strings.

But, just for the sake of it, here are the answers to this question the previous times it's been asked:

what is the best way to convert a json formatted key value pair to ruby hash with symbol as key?

ActiveSupport::JSON decode hash losing symbols

Or perhaps a HashWithIndifferentAccess

from json to a ruby hash?

You want JSON.parse or JSON.load:

def load_user_lib( filename )
JSON.parse( IO.read(filename) )
end

The key here is to use IO.read as a simple way to load the JSON string from disk, so that it can be parsed. Or, if you have UTF-8 data in your file:

  my_object = JSON.parse( IO.read(filename, encoding:'utf-8') )

I've linked to the JSON documentation above, so you should go read that for more details. But in summary:

  • json = my_object.to_json — method on the specific object to create a JSON string.
  • json = JSON.generate(my_object) — create JSON string from object.
  • JSON.dump(my_object, someIO) — create a JSON string and write to a file.
  • my_object = JSON.parse(json) — create a Ruby object from a JSON string.
  • my_object = JSON.load(someIO) — create a Ruby object from a file.

Alternatively:

def load_user_lib( filename )
File.open( filename, "r" ) do |f|
JSON.load( f )
end
end

Note: I have used a "snake_case" name for the method corresponding to your "camelCase" saveUserLib as this is the Ruby convention.



Related Topics



Leave a reply



Submit