I wanted to be able to backup the whole application in plain-text
database-indepent format. This turned out to be surprisingly easy
with YAML, though I did have to implement some hacks. I am including
pruned implementation below as FYI and to get some feedback. In
particular, having a more general solution for YAMLizing/unYAMLizing
many-to-many relationships in Active Record itself would be nice.
For reference entity relationships are:
customers (one-to-many) sites
sites (many-to-many) circuits
Gleb
def export_all
all_objects = {}
all_objects[''customers''] = Customer.find_all
all_objects[''sites''] = Site.find_all
all_objects[''circuits''] = Circuit.find_all.each {
|circuit|
# hack to transport many-to-many data
circuit.sites # populates @sites member
}
result = all_objects.to_yaml
result.gsub!(/\n/, "\r\n") # TODO: general functionality for
line endings
send_string_as_file(result, :filename => "app_backup.txt",
:type => ''text/plain'')
end
def import_all
text_to_import = @params["import"]["text"]
all_objects = YAML.load(text_to_import)
@customers = all_objects[''customers'']
@customers.each { |customer|
customer.instance_variable_set "@new_record", true
customer.save
}
@sites = all_objects[''sites'']
@sites.each { |site|
site.instance_variable_set "@new_record", true
site.save
}
@circuits = all_objects[''circuits'']
@circuits.each { |circuit|
circuit.instance_variable_set "@new_record", true
sites = circuit.sites # save for the future
circuit.save
# now update with child sites
circuit = Circuit.find(circuit.id)
circuit.add_sites(sites)
circuit.save
}
end
def destroy_all
Customer.destroy_all
Circuit.destroy_all
Site.destroy_all
redirect_to :action => "index"
end
Sample of the file:
---
devices:
- !ruby/object:Device
attributes:
name: MRI-123-4
site_id: "1"
platform: ''''
id: "2"
description: ''''
ipx_internal_network: ''''
ip_address: 10.1.1.2
ipx_network_name: ''''
- !ruby/object:Device
attributes:
name: ''''
site_id: "1"
platform: Netware 5.1
id: "3"
description: phone system
ipx_internal_network: ''''
ip_address: 10.1.1.3
ipx_network_name: "68"
circuits:
- !ruby/object:Circuit
attributes:
name: Global Inc. Buffalo Grove POS to Toolshed FT1
router_port: ''''
router: ''''
id: 8
line_type: FT1
sites:
- !ruby/object:Site
attributes:
name: Buffalo Grove Toolshed
subnet_id: "0"
id: "7"
customer_id: "2"
- !ruby/object:Site
attributes:
name: Buffalo Grove POS
subnet_id: "0"
id: "8"
customer_id: "2"
sites:
- !ruby/object:Site
attributes:
name: Mundelein HQ
subnet_id: "0"
id: "11"
customer_id: "5"
- !ruby/object:Site
attributes:
name: Niles
subnet_id: "0"
id: "10"
customer_id: "2"