Revision 6d81475c

b/Makefile.am
11 11

  
12 12
ACLOCAL_AMFLAGS = -I autotools
13 13
DOCBOOK_WRAPPER = $(top_srcdir)/autotools/docbook-wrapper
14
BUILD_RAPI_RESOURCE_DOC = $(top_srcdir)/doc/build-rapi-resources-doc
15 14
REPLACE_VARS_SED = autotools/replace_vars.sed
16 15

  
17 16
hypervisordir = $(pkgpythondir)/hypervisor
......
45 44
CLEANFILES = \
46 45
	autotools/replace_vars.sed \
47 46
	devel/upload \
48
	doc/rapi-resources.gen \
49 47
	doc/examples/bash_completion \
50 48
	doc/examples/ganeti.initd \
51 49
	doc/examples/ganeti.cron \
......
114 112
	doc/hooks.rst \
115 113
	doc/iallocator.rst \
116 114
	doc/install.rst \
115
	doc/rapi.rst \
117 116
	doc/security.rst
118 117

  
119 118
dochtml = $(patsubst %.rst,%.html,$(docrst))
......
152 151
	devel/upload.in \
153 152
	$(docrst) \
154 153
	$(docdot) \
155
	doc/build-rapi-resources-doc \
156 154
	doc/examples/bash_completion.in \
157 155
	doc/examples/ganeti.initd.in \
158 156
	doc/examples/ganeti.cron.in \
......
224 222

  
225 223
TESTS_ENVIRONMENT = PYTHONPATH=.:$(top_builddir)
226 224

  
227
RAPI_RESOURCES = $(wildcard lib/rapi/*.py)
228

  
229 225
all-local: stamp-directories lib/_autoconf.py devel/upload \
230 226
	doc/examples/bash_completion \
231 227
	doc/examples/ganeti.initd doc/examples/ganeti.cron
......
248 244

  
249 245
doc/design-2.0.html: doc/design-2.0.rst doc/arch-2.0.png
250 246

  
251
doc/rapi.html: doc/rapi-resources.gen
252

  
253
doc/rapi-resources.gen: $(BUILD_RAPI_RESOURCE_DOC) $(RAPI_RESOURCES)
254
	PYTHONPATH=.:$(top_builddir) $(BUILD_RAPI_RESOURCE_DOC) > $@ || \
255
	  rm -f $@
256

  
257 247
man/%.7.in man/%.8.in: man/%.sgml man/footer.sgml $(DOCBOOK_WRAPPER)
258 248
	@test -n "$(DOCBOOK2MAN)" || { echo 'docbook2html' not found during configure; exit 1; }
259 249
	TMPDIR=`mktemp -d` && { \
......
281 271

  
282 272
man/footer.sgml $(TESTS): srclinks
283 273

  
284
$(TESTS) $(BUILD_RAPI_RESOURCE_DOC): ganeti lib/_autoconf.py
274
$(TESTS): ganeti lib/_autoconf.py
285 275

  
286 276
lib/_autoconf.py: Makefile stamp-directories
287 277
	set -e; \
/dev/null
1
#!/usr/bin/python
2
#
3

  
4
# Copyright (C) 2008 Google Inc.
5
#
6
# This program is free software; you can redistribute it and/or modify
7
# it under the terms of the GNU General Public License as published by
8
# the Free Software Foundation; either version 2 of the License, or
9
# (at your option) any later version.
10
#
11
# This program is distributed in the hope that it will be useful, but
12
# WITHOUT ANY WARRANTY; without even the implied warranty of
13
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
# General Public License for more details.
15
#
16
# You should have received a copy of the GNU General Public License
17
# along with this program; if not, write to the Free Software
18
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19
# 02110-1301, USA.
20

  
21
"""Script to generate documentation for remote API resources.
22

  
23
This is hard-coded to the section numbering we have in the master RST
24
document.
25

  
26
"""
27

  
28
import re
29
import cgi
30
import inspect
31

  
32
from ganeti.rapi import rlib2
33
from ganeti.rapi import connector
34

  
35

  
36
CHECKED_COMMANDS = ["GET", "POST", "PUT", "DELETE"]
37

  
38

  
39
def beautify(text):
40
  """A couple of small enhancements, epydoc-to-rst.
41

  
42
  """
43
  pairs = [
44
    ("@return:", "Returns:"),
45
    ]
46

  
47
  for old, new in pairs:
48
    text = text.replace(old, new)
49

  
50
  return text
51

  
52

  
53
def indent(text):
54
  """Returns a text block with all lines indented.
55

  
56
  """
57
  lines = text.splitlines()
58
  lines = ["  " + l for l in lines]
59
  return "\n".join(lines)
60

  
61

  
62
def main():
63
  # Get list of all resources
64
  all = list(connector.CONNECTOR.itervalues())
65

  
66
  # Sort rlib by URI
67
  all.sort(cmp=lambda a, b: cmp(a.DOC_URI, b.DOC_URI))
68

  
69
  print ".. Automatically generated, do not edit\n"
70

  
71
  for cls in all:
72
    title = cls.DOC_URI
73
    print "%s\n%s\n" % (title, "+" * len(title))
74

  
75
    # Class docstring
76
    description = inspect.getdoc(cls)
77
    if description:
78
      print "::\n"
79
      print indent(description.strip())
80
    print
81
    supported = [cmd for cmd in CHECKED_COMMANDS if hasattr(cls, cmd)]
82
    print "It supports the following commands: %s." % (", ".join(supported))
83
    print
84

  
85
    for cmd in CHECKED_COMMANDS:
86
      if not hasattr(cls, cmd):
87
        continue
88

  
89
      print "%s\n%s\n" % (cmd, "~" * len(cmd))
90

  
91
      # Get docstring
92
      text = inspect.getdoc(getattr(cls, cmd))
93
      if text:
94
        text = beautify(text)
95
        print "::\n"
96
        print indent(text)
97
        print
98

  
99

  
100
if __name__ == "__main__":
101
  main()
b/doc/rapi.rst
82 82
Resources
83 83
---------
84 84

  
85
.. include:: rapi-resources.gen
85
/
86
+
87

  
88
::
89

  
90
  / resource.
91

  
92
It supports the following commands: GET.
93

  
94
GET
95
~~~
96

  
97
::
98

  
99
  Show the list of mapped resources.
100

  
101
  Returns: a dictionary with 'name' and 'uri' keys for each of them.
102

  
103
/2
104
++
105

  
106
::
107

  
108
  /2 resource, the root of the version 2 API.
109

  
110
It supports the following commands: GET.
111

  
112
GET
113
~~~
114

  
115
::
116

  
117
  Show the list of mapped resources.
118

  
119
  Returns: a dictionary with 'name' and 'uri' keys for each of them.
120

  
121
/2/info
122
+++++++
123

  
124
::
125

  
126
  Cluster info.
127

  
128
It supports the following commands: GET.
129

  
130
GET
131
~~~
132

  
133
::
134

  
135
  Returns cluster information.
136

  
137
  Example::
138

  
139
  {
140
    "config_version": 2000000,
141
    "name": "cluster",
142
    "software_version": "2.0.0~beta2",
143
    "os_api_version": 10,
144
    "export_version": 0,
145
    "candidate_pool_size": 10,
146
    "enabled_hypervisors": [
147
      "fake"
148
    ],
149
    "hvparams": {
150
      "fake": {}
151
     },
152
    "default_hypervisor": "fake",
153
    "master": "node1.example.com",
154
    "architecture": [
155
      "64bit",
156
      "x86_64"
157
    ],
158
    "protocol_version": 20,
159
    "beparams": {
160
      "default": {
161
        "auto_balance": true,
162
        "vcpus": 1,
163
        "memory": 128
164
       }
165
      }
166
    }
167

  
168
/2/instances
169
++++++++++++
170

  
171
::
172

  
173
  /2/instances resource.
174

  
175
It supports the following commands: GET, POST.
176

  
177
GET
178
~~~
179

  
180
::
181

  
182
  Returns a list of all available instances.
183

  
184

  
185
  Example::
186

  
187
    [
188
      {
189
        "name": "web.example.com",
190
        "uri": "\/instances\/web.example.com"
191
      },
192
      {
193
        "name": "mail.example.com",
194
        "uri": "\/instances\/mail.example.com"
195
      }
196
    ]
197

  
198
  If the optional 'bulk' argument is provided and set to 'true'
199
  value (i.e '?bulk=1'), the output contains detailed
200
  information about instances as a list.
201

  
202
  Example::
203

  
204
    [
205
      {
206
         "status": "running",
207
         "disk_usage": 20480,
208
         "nic.bridges": [
209
           "xen-br0"
210
          ],
211
         "name": "web.example.com",
212
         "tags": ["tag1", "tag2"],
213
         "beparams": {
214
           "vcpus": 2,
215
           "memory": 512
216
         },
217
         "disk.sizes": [
218
             20480
219
         ],
220
         "pnode": "node1.example.com",
221
         "nic.macs": ["01:23:45:67:89:01"],
222
         "snodes": ["node2.example.com"],
223
         "disk_template": "drbd",
224
         "admin_state": true,
225
         "os": "debian-etch",
226
         "oper_state": true
227
      },
228
      ...
229
    ]
230

  
231
  Returns: a dictionary with 'name' and 'uri' keys for each of them.
232

  
233
POST
234
~~~~
235

  
236
::
237

  
238
  Create an instance.
239

  
240
  Returns: a job id
241

  
242
/2/instances/[instance_name]
243
++++++++++++++++++++++++++++
244

  
245
::
246

  
247
  /2/instances/[instance_name] resources.
248

  
249
It supports the following commands: GET, DELETE.
250

  
251
GET
252
~~~
253

  
254
::
255

  
256
  Send information about an instance.
257

  
258

  
259

  
260
DELETE
261
~~~~~~
262

  
263
::
264

  
265
  Delete an instance.
266

  
267

  
268

  
269
/2/instances/[instance_name]/reboot
270
+++++++++++++++++++++++++++++++++++
271

  
272
::
273

  
274
  /2/instances/[instance_name]/reboot resource.
275

  
276
  Implements an instance reboot.
277

  
278
It supports the following commands: POST.
279

  
280
POST
281
~~~~
282

  
283
::
284

  
285
  Reboot an instance.
286

  
287
  The URI takes type=[hard|soft|full] and
288
  ignore_secondaries=[False|True] parameters.
289

  
290
/2/instances/[instance_name]/shutdown
291
+++++++++++++++++++++++++++++++++++++
292

  
293
::
294

  
295
  /2/instances/[instance_name]/shutdown resource.
296

  
297
  Implements an instance shutdown.
298

  
299
It supports the following commands: PUT.
300

  
301
PUT
302
~~~
303

  
304
::
305

  
306
  Shutdown an instance.
307

  
308

  
309

  
310
/2/instances/[instance_name]/startup
311
++++++++++++++++++++++++++++++++++++
312

  
313
::
314

  
315
  /2/instances/[instance_name]/startup resource.
316

  
317
  Implements an instance startup.
318

  
319
It supports the following commands: PUT.
320

  
321
PUT
322
~~~
323

  
324
::
325

  
326
  Startup an instance.
327

  
328
  The URI takes force=[False|True] parameter to start the instance
329
  if even if secondary disks are failing.
330

  
331
/2/instances/[instance_name]/tags
332
+++++++++++++++++++++++++++++++++
333

  
334
::
335

  
336
  /2/instances/[instance_name]/tags resource.
337

  
338
  Manages per-instance tags.
339

  
340
It supports the following commands: GET, PUT, DELETE.
341

  
342
GET
343
~~~
344

  
345
::
346

  
347
  Returns a list of tags.
348

  
349
  Example: ["tag1", "tag2", "tag3"]
350

  
351
PUT
352
~~~
353

  
354
::
355

  
356
  Add a set of tags.
357

  
358
  The request as a list of strings should be PUT to this URI. And
359
  you'll have back a job id.
360

  
361
DELETE
362
~~~~~~
363

  
364
::
365

  
366
  Delete a tag.
367

  
368
  In order to delete a set of tags, the DELETE
369
  request should be addressed to URI like:
370
  /tags?tag=[tag]&tag=[tag]
371

  
372
/2/jobs
373
+++++++
374

  
375
::
376

  
377
  /2/jobs resource.
378

  
379
It supports the following commands: GET.
380

  
381
GET
382
~~~
383

  
384
::
385

  
386
  Returns a dictionary of jobs.
387

  
388
  Returns: a dictionary with jobs id and uri.
389

  
390
/2/jobs/[job_id]
391
++++++++++++++++
392

  
393
::
394

  
395
  /2/jobs/[job_id] resource.
396

  
397
It supports the following commands: GET, DELETE.
398

  
399
GET
400
~~~
401

  
402
::
403

  
404
  Returns a job status.
405

  
406
  Returns: a dictionary with job parameters.
407
      The result includes:
408
          - id: job ID as a number
409
          - status: current job status as a string
410
          - ops: involved OpCodes as a list of dictionaries for each
411
            opcodes in the job
412
          - opstatus: OpCodes status as a list
413
          - opresult: OpCodes results as a list of lists
414

  
415
DELETE
416
~~~~~~
417

  
418
::
419

  
420
  Cancel not-yet-started job.
421

  
422

  
423

  
424
/2/nodes
425
++++++++
426

  
427
::
428

  
429
  /2/nodes resource.
430

  
431
It supports the following commands: GET.
432

  
433
GET
434
~~~
435

  
436
::
437

  
438
  Returns a list of all nodes.
439

  
440
  Example::
441

  
442
    [
443
      {
444
        "id": "node1.example.com",
445
        "uri": "\/instances\/node1.example.com"
446
      },
447
      {
448
        "id": "node2.example.com",
449
        "uri": "\/instances\/node2.example.com"
450
      }
451
    ]
452

  
453
  If the optional 'bulk' argument is provided and set to 'true'
454
  value (i.e '?bulk=1'), the output contains detailed
455
  information about nodes as a list.
456

  
457
  Example::
458

  
459
    [
460
      {
461
        "pinst_cnt": 1,
462
        "mfree": 31280,
463
        "mtotal": 32763,
464
        "name": "www.example.com",
465
        "tags": [],
466
        "mnode": 512,
467
        "dtotal": 5246208,
468
        "sinst_cnt": 2,
469
        "dfree": 5171712,
470
        "offline": false
471
      },
472
      ...
473
    ]
474

  
475
  Returns: a dictionary with 'name' and 'uri' keys for each of them
476

  
477
/2/nodes/[node_name]/tags
478
+++++++++++++++++++++++++
479

  
480
::
481

  
482
  /2/nodes/[node_name]/tags resource.
483

  
484
  Manages per-node tags.
485

  
486
It supports the following commands: GET, PUT, DELETE.
487

  
488
GET
489
~~~
490

  
491
::
492

  
493
  Returns a list of tags.
494

  
495
  Example: ["tag1", "tag2", "tag3"]
496

  
497
PUT
498
~~~
499

  
500
::
501

  
502
  Add a set of tags.
503

  
504
  The request as a list of strings should be PUT to this URI. And
505
  you'll have back a job id.
506

  
507
DELETE
508
~~~~~~
509

  
510
::
511

  
512
  Delete a tag.
513

  
514
  In order to delete a set of tags, the DELETE
515
  request should be addressed to URI like:
516
  /tags?tag=[tag]&tag=[tag]
517

  
518
/2/os
519
+++++
520

  
521
::
522

  
523
  /2/os resource.
524

  
525
It supports the following commands: GET.
526

  
527
GET
528
~~~
529

  
530
::
531

  
532
  Return a list of all OSes.
533

  
534
  Can return error 500 in case of a problem.
535

  
536
  Example: ["debian-etch"]
537

  
538
/2/tags
539
+++++++
540

  
541
::
542

  
543
  /2/instances/tags resource.
544

  
545
  Manages cluster tags.
546

  
547
It supports the following commands: GET, PUT, DELETE.
548

  
549
GET
550
~~~
551

  
552
::
553

  
554
  Returns a list of tags.
555

  
556
  Example: ["tag1", "tag2", "tag3"]
557

  
558
PUT
559
~~~
560

  
561
::
562

  
563
  Add a set of tags.
564

  
565
  The request as a list of strings should be PUT to this URI. And
566
  you'll have back a job id.
567

  
568
DELETE
569
~~~~~~
570

  
571
::
572

  
573
  Delete a tag.
574

  
575
  In order to delete a set of tags, the DELETE
576
  request should be addressed to URI like:
577
  /tags?tag=[tag]&tag=[tag]
578

  
579
/nodes/[node_name]
580
++++++++++++++++++
581

  
582
::
583

  
584
  /2/nodes/[node_name] resources.
585

  
586
It supports the following commands: GET.
587

  
588
GET
589
~~~
590

  
591
::
592

  
593
  Send information about a node.
594

  
595

  
596

  
597
/version
598
++++++++
599

  
600
::
601

  
602
  /version resource.
603

  
604
  This resource should be used to determine the remote API version and
605
  to adapt clients accordingly.
606

  
607
It supports the following commands: GET.
608

  
609
GET
610
~~~
611

  
612
::
613

  
614
  Returns the remote API version.

Also available in: Unified diff