Last active
July 18, 2016 09:35
-
-
Save m-basov/e6e739148c023d06f2a552d937d58606 to your computer and use it in GitHub Desktop.
Convert old VSU config to new
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# rubocop:disable Metrics/LineLength | |
require 'json' | |
require 'optparse' | |
# Parse CLI options | |
options = {} | |
OptionParser.new do |opts| | |
opts.banner = "Usage: ruby converter.rb [options]. \n | |
If arguments are not provided will try to convert files in current directory." | |
opts.on('-f', '--file=path', 'Convert file and replace it content') { |f| options[:file] = f } | |
opts.on('-s', '--string=string', 'Convert string and output to stdout') { |s| options[:string] = s } | |
opts.on('-d', '--dir=path', 'Convert all files at given directory and replace it content') { |d| options[:dir] = d } | |
end.parse! | |
# String helpers | |
# underscrore("email-field") #=> "email_field" | |
def underscore(str = '') | |
new_string = str.gsub('::', '/') | |
new_string.gsub!(/([A-Z\d]+)([A-Z][a-z])/, '\1_\2') | |
new_string.gsub!(/([a-z\d])([A-Z])/, '\1_\2') | |
new_string.gsub!(/[[:space:]]|\-/, '\1_\2') | |
new_string.downcase! | |
new_string | |
end | |
# titleize("padding-bottom") #=> "Padding Bottom" | |
def titleize(str = '') | |
underscore(str).split('_').map(&:capitalize).join(' ') | |
end | |
# Convert old configs format to new one | |
class ConfigConverter | |
def initialize(hash) | |
fields = hash['content'] | |
styles = hash['styles'] | |
@styles = styles.map { |style| create_section(style, fields) } | |
end | |
def to_json | |
JSON.pretty_generate(Hash[@styles]) | |
end | |
private | |
def create_section(style, fields = []) | |
section_key = underscore(style['key']) | |
[section_key, { | |
name: style['name'], | |
screen: style.fetch('screen', 'cta'), | |
fields: create_fields(fields, style['related-fields'] || [style['key']]), | |
styles: create_styles(style['data'], section_key) | |
}] | |
end | |
def create_fields(fields, keys) | |
map = fields.map do |field| | |
next unless keys.include?(field['key']) | |
[underscore(field['key']), { | |
name: field['name'], | |
val: field['value'] | |
}] | |
end.compact | |
Hash[map] | |
end | |
def create_styles(styles, section_key = nil) | |
map = styles.map do |style| | |
[style['key'], { | |
name: titleize(style['key'].sub(/^\:/, '')), | |
val: style['value'] | |
}] | |
end | |
map.concat add_missing_styles(section_key) | |
# Convert array to hash | |
Hash[map] | |
end | |
def add_missing_styles(section_key) | |
case section_key | |
when 'general' | |
[ | |
['background-image', { | |
name: 'Form Background Image', | |
val: 'none' | |
}] | |
] | |
else | |
[] | |
end | |
end | |
end | |
# Convert give files and replace it's content with new config | |
def convert_files!(files) | |
files.each do |file| | |
content = File.read(file) | |
json = JSON.parse(content) | |
File.open(file, 'w') { |f| f.write(ConfigConverter.new(json).to_json) } | |
end | |
end | |
# Convert given JSON string and output to stdio | |
def convert_string!(string) | |
puts ConfigConverter.new(JSON.parse(string)).to_json | |
end | |
# Choose command | |
convert_files!([File.expand_path(options[:file])]) unless options[:file].nil? | |
convert_string!(options[:string]) unless options[:string].nil? | |
convert_files!(Dir["#{options[:dir]}/**/*.json"]) unless options[:dir].nil? | |
convert_files!(Dir["#{Dir.pwd}/**/*.json"]) if options.empty? |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# rubocop:disable Metrics/LineLength | |
require 'json' | |
require 'optparse' | |
# Parse CLI options | |
options = {} | |
OptionParser.new do |opts| | |
opts.banner = 'Usage: ruby updater.rb [options].' | |
opts.on('-d', '--dir=path', 'Path to directory with configs, by default is pwd') { |d| options[:dir] = d } | |
opts.on('-t', '--type=form-type', 'Form type in format trigger/template. Ex: hero/1') { |t| options[:type] = t } | |
opts.on('-s', '--str=config-string', 'Config to need updates') { |s| options[:str] = s } | |
end.parse! | |
# Hash deep merge | |
def deep_merge(current_hash, other_hash) | |
result_hash = current_hash.clone | |
current_hash.each_pair do |current_key, current_value| | |
other_value = other_hash[current_key] | |
result_hash[current_key] = if other_value.is_a?(Hash) && current_value.is_a?(Hash) | |
deep_merge(current_value, other_value) | |
else | |
other_value || current_value | |
end | |
end | |
result_hash | |
end | |
# Update old config to new one | |
class ConfigUpdater | |
def initialize(old_conf, new_conf) | |
@conf = update_config(old_conf, new_conf) | |
end | |
def to_json | |
JSON.pretty_generate(@conf) | |
end | |
private | |
def update_config(old_conf, new_conf) | |
old_hash = JSON.parse(old_conf) | |
new_hash = JSON.parse(new_conf) | |
deep_merge(new_hash, old_hash) | |
end | |
end | |
def process_config!(opts = {}) | |
dir = opts[:dir] || Dir.pwd | |
type = opts[:type] | |
str = opts[:str] | |
file = File.read(File.join(dir, "#{type}.json")) | |
updater = ConfigUpdater.new(str, file) | |
puts updater.to_json | |
end | |
process_config!(options) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment