linode-incandescent 0.6.2.SNAPSHOT

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,2 @@
1
+ coverage/
2
+ pkg/
data/CHANGELOG ADDED
@@ -0,0 +1,2 @@
1
+
2
+ * 2009/08/04 - Initial commit.
data/MIT-LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2009, Rick Bradley
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README ADDED
@@ -0,0 +1,140 @@
1
+ Linode Ruby API
2
+
3
+ INSTALLATION:
4
+
5
+ Make sure gemcutter.org is in your gem sources list, then:
6
+
7
+ % sudo gem install linode
8
+
9
+ To run tests you will need both rspec and mocha installed.
10
+
11
+ RUNNING:
12
+
13
+ Consult the Linode API guide here: http://www.linode.com/api/autodoc.cfm
14
+ You will need to get an API key (check your account profile).
15
+
16
+ Here is an annoyingly exhaustive IRB session where I play around with the API:
17
+
18
+ irb> require 'rubygems'
19
+ irb> require 'linode'
20
+ irb> api_key = 'TOPSECRETAPIKEY'
21
+ irb> l = Linode.new(:api_key => api_key)
22
+ => #<Linode:0x100e03c @api_key="TOPSECRETAPIKEY">
23
+
24
+ irb> result = l.test.echo(:foo => 'bar', :baz => 'xyzzy')
25
+ => #<OpenStruct baz="xyzzy", foo="bar">
26
+ irb> result.foo
27
+ => "bar"
28
+ irb> result.baz
29
+ => "xyzzy"
30
+
31
+ irb> result = l.avail.datacenters
32
+ => [#<OpenStruct datacenterid=2, location="Dallas, TX, USA">, #<OpenStruct datacenterid=3, location="Fremont, CA, USA">, #<OpenStruct datacenterid=4, location="Atlanta, GA, USA">, #<OpenStruct datacenterid=6, location="Newark, NJ, USA">]
33
+ irb> s = _
34
+ => [#<OpenStruct datacenterid=2, location="Dallas, TX, USA">, #<OpenStruct datacenterid=3, location="Fremont, CA, USA">, #<OpenStruct datacenterid=4, location="Atlanta, GA, USA">, #<OpenStruct datacenterid=6, location="Newark, NJ, USA">]
35
+ irb> result.first
36
+ => #<OpenStruct datacenterid=2, location="Dallas, TX, USA">
37
+ irb> result.first.location
38
+ => "Dallas, TX, USA"
39
+ irb> l.avail.datacenters.collect {|i| i.location }
40
+ => ["Dallas, TX, USA", "Fremont, CA, USA", "Atlanta, GA, USA", "Newark, NJ, USA"]
41
+ irb> l.avail.datacenters.collect {|i| i.datacenterid }
42
+ => [2, 3, 4, 6]
43
+
44
+ irb> l.user.getapikey(:username => 'me', :password => 'SECKRIT')
45
+ => #<OpenStruct api_key="TOPSECRETAPIKEY", username="me">
46
+ irb> l.user.getapikey(:username => 'me', :password => 'SECKRIT').api_key
47
+ => "TOPSECRETAPIKEY"
48
+ irb> l.user.getapikey(:username => 'me', :password => 'SECKRIT').username
49
+ => "me"
50
+
51
+ irb> l.avail.kernels
52
+ => [#<OpenStruct isxen=1, label="2.6.16.38-x86_64-linode2", kernelid=85>, #<OpenStruct isxen=1, label="2.6.18.8-domU-linode7", kernelid=81>, #<OpenStruct isxen=1, label="2.6.18.8-linode10", kernelid=89>, #<OpenStruct isxen=1, label="2.6.18.8-linode16", kernelid=98>, #<OpenStruct isxen=1, label="2.6.18.8-x86_64-linode1", kernelid=86>, #<OpenStruct isxen=1, label="2.6.24.4-linode8", kernelid=84>, #<OpenStruct isxen=1, label="2.6.25-linode9", kernelid=88>, #<OpenStruct isxen=1, label="2.6.25.10-linode12", kernelid=90>, #<OpenStruct isxen=1, label="2.6.26-linode13", kernelid=91>, #<OpenStruct isxen=1, label="2.6.27.4-linode14", kernelid=93>, #<OpenStruct isxen=1, label="2.6.27.4-x86_64-linode3", kernelid=94>, #<OpenStruct isxen=1, label="2.6.28-linode15", kernelid=96>, #<OpenStruct isxen=1, label="2.6.28-x86_64-linode4", kernelid=97>, #<OpenStruct isxen=1, label="2.6.28.3-linode17", kernelid=99>, #<OpenStruct isxen=1, label="2.6.28.3-x86_64-linode5", kernelid=100>, #<OpenStruct isxen=1, label="2.6.29-linode18", kernelid=101>, #<OpenStruct isxen=1, label="2.6.29-x86_64-linode6", kernelid=102>, #<OpenStruct isxen=1, label="Latest 2.6 Series (2.6.18.8-linode16)", kernelid=60>, #<OpenStruct isxen=1, label="pv-grub-x86_32", kernelid=92>, #<OpenStruct isxen=1, label="pv-grub-x86_64", kernelid=95>, #<OpenStruct isxen=1, label="Recovery - Finnix (kernel)", kernelid=61>]
53
+ irb> l.avail.kernels.size
54
+ => 21
55
+ irb> l.avail.kernels.first
56
+ => #<OpenStruct isxen=1, label="2.6.16.38-x86_64-linode2", kernelid=85>
57
+ irb> l.avail.kernels.first.label
58
+ => "2.6.16.38-x86_64-linode2"
59
+
60
+ irb> l.avail.linodeplans
61
+ => [#<OpenStruct ram=360, label="Linode 360", avail={"6"=>26, "2"=>57, "3"=>20, "4"=>39}, price=19.95, planid=1, xfer=200, disk=16>, #<OpenStruct ram=540, label="Linode 540", avail={"6"=>11, "2"=>38, "3"=>14, "4"=>28}, price=29.95, planid=2, xfer=300, disk=24>, #<OpenStruct ram=720, label="Linode 720", avail={"6"=>13, "2"=>27, "3"=>18, "4"=>30}, price=39.95, planid=3, xfer=400, disk=32>, #<OpenStruct ram=1080, label="Linode 1080", avail={"6"=>18, "2"=>7, "3"=>9, "4"=>4}, price=59.95, planid=4, xfer=600, disk=48>, #<OpenStruct ram=1440, label="Linode 1440", avail={"6"=>14, "2"=>5, "3"=>7, "4"=>3}, price=79.95, planid=5, xfer=800, disk=64>, #<OpenStruct ram=2880, label="Linode 2880", avail={"6"=>3, "2"=>3, "3"=>3, "4"=>3}, price=159.95, planid=6, xfer=1600, disk=128>, #<OpenStruct ram=5760, label="Linode 5760", avail={"6"=>5, "2"=>6, "3"=>5, "4"=>5}, price=319.95, planid=7, xfer=2000, disk=256>, #<OpenStruct ram=8640, label="Linode 8640", avail={"6"=>5, "2"=>6, "3"=>5, "4"=>5}, price=479.95, planid=8, xfer=2000, disk=384>, #<OpenStruct ram=11520, label="Linode 11520", avail={"6"=>5, "2"=>6, "3"=>5, "4"=>5}, price=639.95, planid=9, xfer=2000, disk=512>, #<OpenStruct ram=14400, label="Linode 14400", avail={"6"=>5, "2"=>6, "3"=>5, "4"=>5}, price=799.95, planid=10, xfer=2000, disk=640>]
62
+ irb> l.avail.linodeplans.size
63
+ => 10
64
+ irb> l.avail.linodeplans.first
65
+ => #<OpenStruct ram=360, label="Linode 360", avail={"6"=>26, "2"=>57, "3"=>20, "4"=>39}, price=19.95, planid=1, xfer=200, disk=16>
66
+ irb> l.avail.linodeplans.first.avail
67
+ => {"6"=>26, "2"=>57, "3"=>20, "4"=>39}
68
+
69
+ irb> l.avail.distributions
70
+ => [#<OpenStruct label="Arch Linux 2007.08", minimagesize=436, create_dt="2007-10-24 00:00:00.0", is64bit=0, distributionid=38>, #<OpenStruct label="Centos 5.0", minimagesize=594, create_dt="2007-04-27 00:00:00.0", is64bit=0, distributionid=32>, #<OpenStruct label="Centos 5.2", minimagesize=950, create_dt="2008-11-30 00:00:00.0", is64bit=0, distributionid=46>, #<OpenStruct label="Centos 5.2 64bit", minimagesize=980, create_dt="2008-11-30 00:00:00.0", is64bit=1, distributionid=47>, #<OpenStruct label="Debian 4.0", minimagesize=200, create_dt="2007-04-18 00:00:00.0", is64bit=0, distributionid=28>, #<OpenStruct label="Debian 4.0 64bit", minimagesize=220, create_dt="2008-12-02 00:00:00.0", is64bit=1, distributionid=48>, #<OpenStruct label="Debian 5.0", minimagesize=200, create_dt="2009-02-19 00:00:00.0", is64bit=0, distributionid=50>, #<OpenStruct label="Debian 5.0 64bit", minimagesize=300, create_dt="2009-02-19 00:00:00.0", is64bit=1, distributionid=51>, #<OpenStruct label="Fedora 8", minimagesize=740, create_dt="2007-11-09 00:00:00.0", is64bit=0, distributionid=40>, #<OpenStruct label="Fedora 9", minimagesize=1175, create_dt="2008-06-09 15:15:21.0", is64bit=0, distributionid=43>, #<OpenStruct label="Gentoo 2007.0", minimagesize=1800, create_dt="2007-08-29 00:00:00.0", is64bit=0, distributionid=35>, #<OpenStruct label="Gentoo 2008.0", minimagesize=1500, create_dt="2009-03-20 00:00:00.0", is64bit=0, distributionid=52>, #<OpenStruct label="Gentoo 2008.0 64bit", minimagesize=2500, create_dt="2009-04-04 00:00:00.0", is64bit=1, distributionid=53>, #<OpenStruct label="OpenSUSE 11.0", minimagesize=850, create_dt="2008-08-21 08:32:16.0", is64bit=0, distributionid=44>, #<OpenStruct label="Slackware 12.0", minimagesize=315, create_dt="2007-07-16 00:00:00.0", is64bit=0, distributionid=34>, #<OpenStruct label="Slackware 12.2", minimagesize=500, create_dt="2009-04-04 00:00:00.0", is64bit=0, distributionid=54>, #<OpenStruct label="Ubuntu 8.04 LTS", minimagesize=400, create_dt="2008-04-23 15:11:29.0", is64bit=0, distributionid=41>, #<OpenStruct label="Ubuntu 8.04 LTS 64bit", minimagesize=350, create_dt="2008-06-03 12:51:11.0", is64bit=1, distributionid=42>, #<OpenStruct label="Ubuntu 8.10", minimagesize=220, create_dt="2008-10-30 23:23:03.0", is64bit=0, distributionid=45>, #<OpenStruct label="Ubuntu 8.10 64bit", minimagesize=230, create_dt="2008-12-02 00:00:00.0", is64bit=1, distributionid=49>, #<OpenStruct label="Ubuntu 9.04", minimagesize=350, create_dt="2009-04-23 00:00:00.0", is64bit=0, distributionid=55>, #<OpenStruct label="Ubuntu 9.04 64bit", minimagesize=350, create_dt="2009-04-23 00:00:00.0", is64bit=1, distributionid=56>]
71
+ irb> l.avail.distributions.size
72
+ => 22
73
+ irb> l.avail.distributions.first
74
+ => #<OpenStruct label="Arch Linux 2007.08", minimagesize=436, create_dt="2007-10-24 00:00:00.0", is64bit=0, distributionid=38>
75
+ irb> l.avail.distributions.first.label
76
+ => "Arch Linux 2007.08"
77
+
78
+ irb> l.domain.resource.list
79
+ RuntimeError: Error completing request [domain.resource.list] @ [https://api.linode.com/] with data [{}]: ERRORCODE6ERRORMESSAGEDOMAINID is required but was not passed in
80
+ from ./lib/linode.rb:31:in `send_request'
81
+ from ./lib/linode.rb:13:in `list'
82
+ from (irb):3
83
+ irb> l.domain.resource.list(:DomainId => '1')
84
+ RuntimeError: Error completing request [domain.resource.list] @ [https://api.linode.com/] with data [{:DomainId=>"1"}]: ERRORCODE5ERRORMESSAGEObject not found
85
+ from ./lib/linode.rb:31:in `send_request'
86
+ from ./lib/linode.rb:13:in `list'
87
+ from (irb):5
88
+ irb> l.domain.resource.list(:DomainId => '1', :ResourceId => '2')
89
+ RuntimeError: Error completing request [domain.resource.list] @ [https://api.linode.com/] with data [{:DomainId=>"1", :ResourceId=>"2"}]: ERRORCODE5ERRORMESSAGEObject not found
90
+ from ./lib/linode.rb:31:in `send_request'
91
+ from ./lib/linode.rb:13:in `list'
92
+ from (irb):7
93
+
94
+ irb> l.linode
95
+ => #<Linode::Linode:0x10056e4 @api_url="https://api.linode.com/", @api_key="TOPSECRETAPIKEY">
96
+ irb> l.linode.list
97
+ => [#<OpenStruct datacenterid=6, lpm_displaygroup="", totalxfer=600, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="byggvir", totalram=1080, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=12446, totalhd=49152, alert_bwin_enabled=1, alert_bwout_enabled=1>, #<OpenStruct datacenterid=4, lpm_displaygroup="", totalxfer=200, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="bragi", totalram=360, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=15418, totalhd=16384, alert_bwin_enabled=1, alert_bwout_enabled=1>, #<OpenStruct datacenterid=2, lpm_displaygroup="", totalxfer=200, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="nerthus", totalram=360, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=15419, totalhd=16384, alert_bwin_enabled=1, alert_bwout_enabled=1>, #<OpenStruct datacenterid=3, lpm_displaygroup="", totalxfer=200, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday=0, status=1, alert_cpu_enabled=1, label="hoenir", totalram=360, backupwindow=0, alert_diskio_threshold=500, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=24405, totalhd=16384, alert_bwin_enabled=1, alert_bwout_enabled=1>]
98
+ irb> l.linode.list.size
99
+ => 4
100
+ irb> l.linode.list.first
101
+ => #<OpenStruct datacenterid=6, lpm_displaygroup="", totalxfer=600, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="byggvir", totalram=1080, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=12446, totalhd=49152, alert_bwin_enabled=1, alert_bwout_enabled=1>
102
+ irb> l.linode.list.first.datacenterid
103
+ => 6
104
+ irb> l.linode.list.first.label
105
+ => "byggvir"
106
+
107
+ irb(main):003:0* l.linode.config.list
108
+ RuntimeError: Error completing request [linode.config.list] @ [https://api.linode.com/] with data [{}]: ERRORCODE6ERRORMESSAGELINODEID is required but was not passed in
109
+ from ./lib/linode.rb:45:in `send_request'
110
+ from ./lib/linode.rb:13:in `list'
111
+ from (irb):3
112
+ irb> l.linode.list
113
+ => [#<OpenStruct datacenterid=6, lpm_displaygroup="", totalxfer=600, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="byggvir", totalram=1080, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=12446, totalhd=49152, alert_bwin_enabled=1, alert_bwout_enabled=1>, #<OpenStruct datacenterid=4, lpm_displaygroup="", totalxfer=200, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="bragi", totalram=360, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=15418, totalhd=16384, alert_bwin_enabled=1, alert_bwout_enabled=1>, #<OpenStruct datacenterid=2, lpm_displaygroup="", totalxfer=200, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="nerthus", totalram=360, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=15419, totalhd=16384, alert_bwin_enabled=1, alert_bwout_enabled=1>, #<OpenStruct datacenterid=3, lpm_displaygroup="", totalxfer=200, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday=0, status=1, alert_cpu_enabled=1, label="hoenir", totalram=360, backupwindow=0, alert_diskio_threshold=500, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=24405, totalhd=16384, alert_bwin_enabled=1, alert_bwout_enabled=1>]
114
+ irb> l.linode.list.first
115
+ => #<OpenStruct datacenterid=6, lpm_displaygroup="", totalxfer=600, alert_bwquota_enabled=1, alert_diskio_enabled=1, watchdog=1, alert_cpu_threshold=90, alert_bwout_threshold=5, backupsenabled=0, backupweeklyday="", status=1, alert_cpu_enabled=1, label="byggvir", totalram=1080, backupwindow=0, alert_diskio_threshold=300, alert_bwin_threshold=5, alert_bwquota_threshold=80, linodeid=12446, totalhd=49152, alert_bwin_enabled=1, alert_bwout_enabled=1>
116
+ irb> l.linode.list.first.linodeid
117
+ => 12446
118
+ irb> l.linode.config.list(:LinodeId => 12446)
119
+ => [#<OpenStruct helper_disableupdatedb=1, ramlimit=0, kernelid=60, helper_depmod=1, rootdevicecustom="", disklist="79850,79851,79854,,,,,,", label="byggvir", runlevel="default", rootdevicero=true, configid=43615, rootdevicenum=1, linodeid=12446, helper_libtls=false, helper_xen=1, comments="">]
120
+ irb> l.linode.config.list(:LinodeId => 12446).first.disklist
121
+ => "79850,79851,79854,,,,,,"
122
+
123
+ irb> l.linode.job.list
124
+ RuntimeError: Error completing request [linode.job.list] @ [https://api.linode.com/] with data [{}]: ERRORCODE6ERRORMESSAGELINODEID is required but was not passed in
125
+ from ./lib/linode.rb:45:in `send_request'
126
+ from ./lib/linode.rb:13:in `list'
127
+ from (irb):7
128
+ irb> l.linode.job.list(:LinodeId => 12446)
129
+ => [#<OpenStruct action="linode.boot", jobid=1241724, duration=8, host_finish_dt="2009-07-14 17:07:29.0", host_message="", linodeid=12446, host_success=1, host_start_dt="2009-07-14 17:07:21.0", entered_dt="2009-07-14 17:06:25.0", label="System Boot - byggvir">, #<OpenStruct action="linode.shutdown", jobid=1241723, duration=14, host_finish_dt="2009-07-14 17:07:20.0", host_message="", linodeid=12446, host_success=1, host_start_dt="2009-07-14 17:07:06.0", entered_dt="2009-07-14 17:06:25.0", label="System Shutdown">, #<OpenStruct action="linode.boot", jobid=1182441, duration=0, host_finish_dt="2009-06-10 04:27:49.0", host_message="Linode already running", linodeid=12446, host_success=0, host_start_dt="2009-06-10 04:27:49.0", entered_dt="2009-06-10 04:26:05.0", label="Lassie initiated boot">, #<OpenStruct action="linode.boot", jobid=1182436, duration=8, host_finish_dt="2009-06-10 04:27:49.0", host_message="", linodeid=12446, host_success=1, host_start_dt="2009-06-10 04:27:41.0", entered_dt="1974-01-04 00:00:00.0", label="Host initiated restart">, #<OpenStruct action="linode.boot", jobid=1182273, duration=0, host_finish_dt="2009-06-10 03:02:31.0", host_message="Linode already running", linodeid=12446, host_success=0, host_start_dt="2009-06-10 03:02:31.0", entered_dt="2009-06-10 02:59:49.0", label="Lassie initiated boot">, #<OpenStruct action="linode.boot", jobid=1182268, duration=8, host_finish_dt="2009-06-10 03:02:31.0", host_message="", linodeid=12446, host_success=1, host_start_dt="2009-06-10 03:02:23.0", entered_dt="1974-01-04 00:00:00.0", label="Host initiated restart">, #<OpenStruct action="linode.boot", jobid=1182150, duration=1, host_finish_dt="2009-06-10 01:28:40.0", host_message="Linode already running", linodeid=12446, host_success=0, host_start_dt="2009-06-10 01:28:39.0", entered_dt="2009-06-10 01:26:55.0", label="Lassie initiated boot">, #<OpenStruct action="linode.boot", jobid=1182145, duration=8, host_finish_dt="2009-06-10 01:28:39.0", host_message="", linodeid=12446, host_success=1, host_start_dt="2009-06-10 01:28:31.0", entered_dt="1974-01-04 00:00:00.0", label="Host initiated restart">]
130
+ irb> l.linode.job.list(:LinodeId => 12446).size
131
+ => 8
132
+
133
+ irb> l.linode.ip.list
134
+ RuntimeError: Error completing request [linode.ip.list] @ [https://api.linode.com/] with data [{}]: ERRORCODE6ERRORMESSAGELINODEID is required but was not passed in
135
+ from ./lib/linode.rb:45:in `send_request'
136
+ from ./lib/linode.rb:13:in `list'
137
+ from (irb):10
138
+ irb> l.linode.ip.list(:LinodeId => 12446)
139
+ => [#<OpenStruct rdns_name="byggvir.websages.com", ipaddressid=12286, linodeid=12446, ispublic=1, ipaddress="209.123.234.161">, #<OpenStruct rdns_name="li101-51.members.linode.com", ipaddressid=23981, linodeid=12446, ispublic=1, ipaddress="97.107.140.51">]
140
+ irb> ^D@ Wed Aug 05 01:50:52 rick@Yer-Moms-Computer
data/Rakefile ADDED
@@ -0,0 +1,31 @@
1
+ require 'rake'
2
+ require 'rake/testtask'
3
+ require 'rake/rdoctask'
4
+ require 'rspec/core/rake_task'
5
+
6
+ desc 'Default: run specs.'
7
+ task :default => :spec
8
+
9
+ desc 'Test the linode library.'
10
+ RSpec::Core::RakeTask.new('spec') do |t|
11
+ t.pattern = 'spec/**/*_spec.rb'
12
+ end
13
+
14
+ desc 'Test the linode library.'
15
+ task :test => :spec
16
+
17
+ begin
18
+ require 'jeweler'
19
+ Jeweler::Tasks.new do |gemspec|
20
+ gemspec.name = "linode"
21
+ gemspec.summary = "a Ruby wrapper for the Linode API"
22
+ gemspec.description = "This is a wrapper around Linode's automation facilities."
23
+ gemspec.email = "rick@rickbradley.com"
24
+ gemspec.homepage = "http://github.com/rick/linode"
25
+ gemspec.authors = ["Rick Bradley"]
26
+ gemspec.add_dependency('httparty', '>= 0.4.4')
27
+ end
28
+ Jeweler::GemcutterTasks.new
29
+ rescue LoadError
30
+ end
31
+
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.6.2
data/lib/linode.rb ADDED
@@ -0,0 +1,102 @@
1
+ require 'rubygems'
2
+ require 'ostruct'
3
+ require 'httparty'
4
+
5
+ class Linode
6
+ attr_reader :api_key
7
+
8
+ def self.has_method(*actions)
9
+ actions.each do |action|
10
+ define_method(action.to_sym) do |*data|
11
+ data = data.shift if data
12
+ data ||= {}
13
+ send_request(self.class.name.downcase.sub(/^linode::/, '').gsub(/::/, '.') + ".#{action}", data)
14
+ end
15
+ end
16
+ end
17
+
18
+ def self.has_unauthenticated_method(*actions)
19
+ actions.each do |action|
20
+ define_method(action.to_sym) do |*data|
21
+ data = data.shift if data
22
+ data ||= {}
23
+ send_unauthenticated_request(self.class.name.downcase.sub(/^linode::/, '').gsub(/::/, '.') + ".#{action}", data)
24
+ end
25
+ end
26
+ end
27
+
28
+ def self.has_namespace(*namespaces)
29
+ namespaces.each do |namespace|
30
+ define_method(namespace.to_sym) do ||
31
+ lookup = instance_variable_get("@#{namespace}")
32
+ return lookup if lookup
33
+ subclass = self.class.const_get(namespace.to_s.capitalize).new(:api_key => api_key, :api_url => api_url)
34
+ instance_variable_set("@#{namespace}", subclass)
35
+ subclass
36
+ end
37
+ end
38
+ end
39
+
40
+ has_namespace :test, :avail, :user, :domain, :linode
41
+
42
+ def initialize(args)
43
+ if args.include?(:api_key)
44
+ @api_key = args[:api_key]
45
+ @api_url = args[:api_url] if args[:api_url]
46
+ elsif args.include?(:username) and args.include?(:password)
47
+ @api_url = args[:api_url] if args[:api_url]
48
+ result = send_unauthenticated_request("user.getapikey", { :username => args[:username], :password => args[:password] })
49
+ @api_key = result.api_key
50
+ else
51
+ raise ArgumentError, "Either :api_key, or both :username and :password, are required"
52
+ end
53
+ end
54
+
55
+ def api_url
56
+ @api_url || 'https://api.linode.com/'
57
+ end
58
+
59
+ def send_request(action, data)
60
+ data.delete_if {|k,v| [:api_key ].include?(k) }
61
+ send_unauthenticated_request(action, { :api_key => api_key }.merge(data))
62
+ end
63
+
64
+ def send_unauthenticated_request(action, data)
65
+ data.delete_if {|k,v| [ :api_action, :api_responseFormat].include?(k) }
66
+ result = Crack::JSON.parse(HTTParty.get(api_url, :query => { :api_action => action, :api_responseFormat => 'json' }.merge(data)))
67
+ raise "Errors completing request [#{action}] @ [#{api_url}] with data [#{data.inspect}]:\n#{error_message(result, action)}" if error?(result)
68
+ reformat_response(result)
69
+ end
70
+
71
+
72
+ protected
73
+
74
+ def error?(response)
75
+ response and response["ERRORARRAY"] and ! response["ERRORARRAY"].empty?
76
+ end
77
+
78
+ def error_message(response, action)
79
+ response["ERRORARRAY"].collect { |err|
80
+ " - Error \##{err["ERRORCODE"]} - #{err["ERRORMESSAGE"]}. (Please consult http://www.linode.com/api/autodoc.cfm?method=#{action})"
81
+ }.join("\n")
82
+ end
83
+
84
+ def reformat_response(response)
85
+ result = response['DATA']
86
+ return result.collect {|item| convert_item(item) } if result.class == Array
87
+ return result unless result.respond_to?(:keys)
88
+ convert_item(result)
89
+ end
90
+
91
+ def convert_item(item)
92
+ item.keys.each do |k|
93
+ item[k.downcase] = item[k]
94
+ item.delete(k) if k != k.downcase
95
+ end
96
+ ::OpenStruct.new(item)
97
+ end
98
+ end
99
+
100
+ # include all Linode API namespace classes
101
+ Dir[File.expand_path(File.dirname(__FILE__) + '/linode/*.rb')].each {|f| require f }
102
+ Dir[File.expand_path(File.dirname(__FILE__) + '/linode/**/*.rb')].each {|f| require f }
@@ -0,0 +1,3 @@
1
+ class Linode::Avail < Linode
2
+ has_method :datacenters, :kernels, :linodeplans, :distributions, :stackscripts
3
+ end
@@ -0,0 +1,4 @@
1
+ class Linode::Domain < Linode
2
+ has_namespace :resource
3
+ has_method :update, :create, :list, :delete
4
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::Domain::Resource < Linode
2
+ has_method :create, :delete, :update, :list
3
+ end
@@ -0,0 +1,4 @@
1
+ class Linode::Linode < Linode
2
+ has_namespace :config, :disk, :ip, :job
3
+ has_method :update, :create, :list, :shutdown, :boot, :delete, :reboot
4
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::Linode::Config < Linode
2
+ has_method :create, :delete, :update, :list
3
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::Linode::Disk < Linode
2
+ has_method :update, :create, :list, :createfromdistribution, :createfromstackscript, :duplicate, :delete, :resize
3
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::Linode::Ip < Linode
2
+ has_method :list
3
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::Linode::Job < Linode
2
+ has_method :list
3
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::Stackscript < Linode
2
+ has_method :update, :create, :list, :delete
3
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::Test < Linode
2
+ has_method :echo
3
+ end
@@ -0,0 +1,3 @@
1
+ class Linode::User < Linode
2
+ has_unauthenticated_method :getapikey
3
+ end
data/linode.gemspec ADDED
@@ -0,0 +1,87 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{linode}
8
+ s.version = "0.6.2"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["Rick Bradley"]
12
+ s.date = %q{2010-08-03}
13
+ s.description = %q{This is a wrapper around Linode's automation facilities.}
14
+ s.email = %q{rick@rickbradley.com}
15
+ s.extra_rdoc_files = [
16
+ "README"
17
+ ]
18
+ s.files = [
19
+ ".gitignore",
20
+ "CHANGELOG",
21
+ "MIT-LICENSE",
22
+ "README",
23
+ "Rakefile",
24
+ "VERSION",
25
+ "lib/linode.rb",
26
+ "lib/linode/avail.rb",
27
+ "lib/linode/domain.rb",
28
+ "lib/linode/domain/resource.rb",
29
+ "lib/linode/linode.rb",
30
+ "lib/linode/linode/config.rb",
31
+ "lib/linode/linode/disk.rb",
32
+ "lib/linode/linode/ip.rb",
33
+ "lib/linode/linode/job.rb",
34
+ "lib/linode/stackscript.rb",
35
+ "lib/linode/test.rb",
36
+ "lib/linode/user.rb",
37
+ "linode.gemspec",
38
+ "spec/linode/avail_spec.rb",
39
+ "spec/linode/domain/resource_spec.rb",
40
+ "spec/linode/domain_spec.rb",
41
+ "spec/linode/linode/config_spec.rb",
42
+ "spec/linode/linode/disk_spec.rb",
43
+ "spec/linode/linode/ip_spec.rb",
44
+ "spec/linode/linode/job_spec.rb",
45
+ "spec/linode/linode_spec.rb",
46
+ "spec/linode/stackscript_spec.rb",
47
+ "spec/linode/test_spec.rb",
48
+ "spec/linode/user_spec.rb",
49
+ "spec/linode_spec.rb",
50
+ "spec/spec.opts",
51
+ "spec/spec_helper.rb"
52
+ ]
53
+ s.homepage = %q{http://github.com/rick/linode}
54
+ s.rdoc_options = ["--charset=UTF-8"]
55
+ s.require_paths = ["lib"]
56
+ s.rubygems_version = %q{1.3.7}
57
+ s.summary = %q{a Ruby wrapper for the Linode API}
58
+ s.test_files = [
59
+ "spec/linode/avail_spec.rb",
60
+ "spec/linode/domain/resource_spec.rb",
61
+ "spec/linode/domain_spec.rb",
62
+ "spec/linode/linode/config_spec.rb",
63
+ "spec/linode/linode/disk_spec.rb",
64
+ "spec/linode/linode/ip_spec.rb",
65
+ "spec/linode/linode/job_spec.rb",
66
+ "spec/linode/linode_spec.rb",
67
+ "spec/linode/stackscript_spec.rb",
68
+ "spec/linode/test_spec.rb",
69
+ "spec/linode/user_spec.rb",
70
+ "spec/linode_spec.rb",
71
+ "spec/spec_helper.rb"
72
+ ]
73
+
74
+ if s.respond_to? :specification_version then
75
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
76
+ s.specification_version = 3
77
+
78
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
79
+ s.add_runtime_dependency(%q<httparty>, [">= 0.4.4"])
80
+ else
81
+ s.add_dependency(%q<httparty>, [">= 0.4.4"])
82
+ end
83
+ else
84
+ s.add_dependency(%q<httparty>, [">= 0.4.4"])
85
+ end
86
+ end
87
+