mediawiki-gateway 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (47) hide show
  1. data/.gitignore +3 -0
  2. data/README +12 -0
  3. data/Rakefile +40 -0
  4. data/VERSION +1 -0
  5. data/config/hosts.yml +17 -0
  6. data/doc/classes/MediaWiki.html +189 -0
  7. data/doc/classes/MediaWiki/Config.html +269 -0
  8. data/doc/classes/MediaWiki/Gateway.html +952 -0
  9. data/doc/created.rid +1 -0
  10. data/doc/files/README_txt.html +117 -0
  11. data/doc/files/media_wiki/config_rb.html +108 -0
  12. data/doc/files/media_wiki/gateway_rb.html +113 -0
  13. data/doc/files/media_wiki/utils_rb.html +101 -0
  14. data/doc/files/script/create_page_rb.html +115 -0
  15. data/doc/files/script/delete_book_rb.html +108 -0
  16. data/doc/files/script/export_xml_rb.html +114 -0
  17. data/doc/files/script/get_page_rb.html +114 -0
  18. data/doc/files/script/import_xml_rb.html +114 -0
  19. data/doc/files/script/undelete_page_rb.html +101 -0
  20. data/doc/files/script/upload_commons_rb.html +109 -0
  21. data/doc/files/script/upload_file_rb.html +115 -0
  22. data/doc/fr_class_index.html +29 -0
  23. data/doc/fr_file_index.html +38 -0
  24. data/doc/fr_method_index.html +49 -0
  25. data/doc/index.html +24 -0
  26. data/doc/rdoc-style.css +208 -0
  27. data/lib/media_wiki.rb +3 -0
  28. data/lib/media_wiki/config.rb +69 -0
  29. data/lib/media_wiki/gateway.rb +307 -0
  30. data/lib/media_wiki/utils.rb +18 -0
  31. data/mediawiki-gateway.gemspec +88 -0
  32. data/script/create_page.rb +14 -0
  33. data/script/delete_book.rb +14 -0
  34. data/script/export_xml.rb +14 -0
  35. data/script/get_page.rb +12 -0
  36. data/script/import_xml.rb +14 -0
  37. data/script/run_fake_media_wiki.rb +8 -0
  38. data/script/undelete_page.rb +15 -0
  39. data/script/upload_commons.rb +42 -0
  40. data/script/upload_file.rb +14 -0
  41. data/spec/fake_media_wiki/api_pages.rb +131 -0
  42. data/spec/fake_media_wiki/app.rb +262 -0
  43. data/spec/fake_media_wiki/query_handling.rb +112 -0
  44. data/spec/gateway_spec.old +535 -0
  45. data/spec/gateway_spec.rb +653 -0
  46. data/spec/import-test-data.xml +68 -0
  47. metadata +115 -0
@@ -0,0 +1,653 @@
1
+ require 'active_support'
2
+ require 'rr'
3
+ require 'sham_rack'
4
+
5
+ require 'media_wiki/gateway'
6
+ require 'spec/fake_media_wiki/app'
7
+
8
+ $fake_media_wiki = FakeMediaWiki::App.new
9
+ ShamRack.mount($fake_media_wiki, 'dummy-wiki.example')
10
+
11
+ describe MediaWiki::Gateway do
12
+
13
+ before do
14
+ @gateway = MediaWiki::Gateway.new('http://dummy-wiki.example/w/api.php')
15
+ $fake_media_wiki.reset
16
+ end
17
+
18
+ describe '.wiki_to_uri' do
19
+
20
+ it "should underscore spaces" do
21
+ MediaWiki.wiki_to_uri('getting there').should == 'getting_there'
22
+ end
23
+
24
+ it "should escape ampersands" do
25
+ MediaWiki.wiki_to_uri('getting there & away').should == 'getting_there_%26_away'
26
+ end
27
+
28
+ it "should escape UTF-8" do
29
+ MediaWiki.wiki_to_uri('Phở').should == 'Ph%E1%BB%9F'
30
+ end
31
+
32
+ it "should escape each path component but leave slashes untouched" do
33
+ MediaWiki.wiki_to_uri('Phở/B&r/B z').should == 'Ph%E1%BB%9F/B%26r/B_z'
34
+ end
35
+
36
+ it "should pass through nil" do
37
+ MediaWiki.wiki_to_uri(nil).should == nil
38
+ end
39
+
40
+ end
41
+
42
+ describe '#login' do
43
+
44
+ describe "with a valid username & password" do
45
+
46
+ before do
47
+ @gateway.login('atlasmw', 'wombat')
48
+ end
49
+
50
+ it "should login successfully with the default domain" do
51
+ $fake_media_wiki.logged_in('atlasmw').should == true
52
+ end
53
+
54
+ end
55
+
56
+ describe "with a valid username, password and domain" do
57
+
58
+ before do
59
+ @gateway.login('ldapuser', 'ldappass', 'ldapdomain')
60
+ end
61
+
62
+ it "should login successfully" do
63
+ $fake_media_wiki.logged_in('ldapuser').should == true
64
+ end
65
+
66
+ end
67
+
68
+ describe "with an non-existent username" do
69
+
70
+ it "should raise an error" do
71
+ lambda do
72
+ @gateway.login('bogususer', 'sekrit')
73
+ end.should raise_error(StandardError)
74
+ end
75
+
76
+ end
77
+
78
+ describe "with an incorrect password" do
79
+
80
+ it "should raise an error" do
81
+ lambda do
82
+ @gateway.login('atlasmw', 'sekrit')
83
+ end.should raise_error(StandardError)
84
+ end
85
+
86
+ end
87
+
88
+ describe "with an incorrect domain" do
89
+
90
+ it "should raise an error" do
91
+ lambda do
92
+ @gateway.login('atlasmw', 'wombat', 'bogusdomain')
93
+ end.should raise_error(StandardError)
94
+ end
95
+
96
+ end
97
+
98
+ end
99
+
100
+ describe "#get_token" do
101
+
102
+ describe "when not logged in" do
103
+
104
+ describe "requesting an edit token" do
105
+
106
+ before do
107
+ @token = @gateway.send(:get_token, 'edit', 'Main Page')
108
+ end
109
+
110
+ it "should return a blank token" do
111
+ @token.should_not == nil
112
+ @token.should == "+\\"
113
+ end
114
+
115
+ end
116
+
117
+ describe "requesting an import token" do
118
+
119
+ it "should raise an error" do
120
+ lambda do
121
+ @gateway.send(:get_token, 'import', 'Main Page')
122
+ end.should raise_error(StandardError)
123
+ end
124
+
125
+ end
126
+
127
+ end
128
+
129
+ describe "when logged in as admin user" do
130
+
131
+ before do
132
+ @gateway.login('atlasmw', 'wombat')
133
+ end
134
+
135
+ describe "requesting an edit token for a single page" do
136
+
137
+ before do
138
+ @token = @gateway.send(:get_token, 'edit', 'Main Page')
139
+ end
140
+
141
+ it "should return a token" do
142
+ @token.should_not == nil
143
+ @token.should_not == "+\\"
144
+ end
145
+
146
+ end
147
+
148
+ describe "requesting an edit token for multiple pages" do
149
+
150
+ before do
151
+ @token = @gateway.send(:get_token, 'edit', "Main Page|Another Page")
152
+ end
153
+
154
+ it "should return a token" do
155
+ @token.should_not == nil
156
+ @token.should_not == "+\\"
157
+ end
158
+
159
+ end
160
+
161
+ describe "requesting an import token" do
162
+
163
+ before do
164
+ @token = @gateway.send(:get_token, 'import', 'Main Page')
165
+ end
166
+
167
+ it "should return a token" do
168
+ @token.should_not == nil
169
+ @token.should_not == "+\\"
170
+ end
171
+
172
+ end
173
+
174
+ end
175
+
176
+ end
177
+
178
+ describe "#get" do
179
+
180
+ describe "for an existing wiki page" do
181
+
182
+ it "returns raw page content" do
183
+ @gateway.get("Main Page").should == "Content"
184
+ end
185
+
186
+ end
187
+
188
+ describe "for a missing wiki page" do
189
+
190
+ it "returns nil" do
191
+ @gateway.get("page/missing").should be_nil
192
+ end
193
+
194
+ end
195
+
196
+ describe "for root (/)" do
197
+
198
+ it "returns nil" do
199
+ @gateway.get("").should be_nil
200
+ end
201
+
202
+ end
203
+
204
+ end
205
+
206
+ describe "#render" do
207
+
208
+ describe "for an existing wiki page" do
209
+
210
+ before do
211
+ @pages = @gateway.render('Main Page')
212
+ end
213
+
214
+ it "should return the page content" do
215
+ expected = "Sample <B>HTML</B> content"
216
+ @pages.to_s.should == expected
217
+ end
218
+ end
219
+
220
+ describe "for a missing wiki page" do
221
+
222
+ before do
223
+ @pages = @gateway.render('Invalidpage')
224
+ end
225
+
226
+ it "should return nil" do
227
+ @pages.should == nil
228
+ end
229
+
230
+ end
231
+
232
+ end
233
+
234
+ describe "#create" do
235
+
236
+ before do
237
+ @gateway.login('atlasmw', 'wombat')
238
+ end
239
+
240
+ describe "when creating a new page" do
241
+
242
+ before do
243
+ @page = @gateway.create("A New Page", "Some content")
244
+ end
245
+
246
+ it "should create the page" do
247
+ expected = <<-XML
248
+ <api>
249
+ <edit new='' result='Success' pageid='5' title='A New Page' oldrevid='0' newrevid='5'/>
250
+ </api>
251
+ XML
252
+ Hash.from_xml(@page.to_s).should == Hash.from_xml(expected)
253
+ end
254
+
255
+ end
256
+
257
+ describe "when creating a page that already exists" do
258
+
259
+ before do
260
+ $fake_media_wiki.reset
261
+ end
262
+
263
+ describe "and the 'overwrite' option is set" do
264
+
265
+ before do
266
+ @new_page = @gateway.create("Main Page", "Some new content", :summary => "The summary", :overwrite => true)
267
+ end
268
+
269
+ it "should overwrite the existing page" do
270
+ expected = <<-XML
271
+ <api>
272
+ <edit result='Success' pageid='5' title='Main Page' oldrevid='1' newrevid='5'/>
273
+ </api>
274
+ XML
275
+ Hash.from_xml(@new_page.to_s).should == Hash.from_xml(expected)
276
+ end
277
+
278
+ end
279
+
280
+ describe "and the 'overwrite' option is not set" do
281
+
282
+ it "should raise an error" do
283
+ lambda do
284
+ @gateway.create("Main Page", "Some new content")
285
+ end.should raise_error(StandardError)
286
+ end
287
+
288
+ end
289
+
290
+ end
291
+
292
+ end
293
+
294
+ describe "#upload" do
295
+
296
+ before do
297
+ @gateway.login('atlasmw', 'wombat')
298
+ end
299
+
300
+ describe "when uploading a new file" do
301
+
302
+ before do
303
+ pending "stubbing broken in mysterious ways"
304
+ stub(File).new(anything) { "SAMPLEIMAGEDATA" }
305
+ @page = @gateway.upload("some/path/sample_image.jpg")
306
+ end
307
+
308
+ it "should open the file" do
309
+ File.should have_received.new("some/path/sample_image.jpg")
310
+ end
311
+
312
+ it "should upload the file" do
313
+ expected = <<-XML
314
+ <api>
315
+ <upload result="Success" filename="sample_image.jpg"/>
316
+ </api>
317
+ XML
318
+ Hash.from_xml(@page.to_s).should == Hash.from_xml(expected)
319
+ end
320
+
321
+ end
322
+
323
+ end
324
+
325
+ describe "#delete" do
326
+
327
+ describe "when logged in as admin" do
328
+
329
+ describe "and the page exists" do
330
+ def delete_response
331
+ <<-XML
332
+ <api>
333
+ <delete title='Deletable Page' reason='Default reason'/>
334
+ </api>
335
+ XML
336
+ end
337
+
338
+ before do
339
+ @gateway.login("atlasmw", "wombat")
340
+
341
+ create("Deletable Page", "Some content")
342
+ @page = @gateway.delete("Deletable Page")
343
+ end
344
+
345
+ it "should delete the page" do
346
+ Hash.from_xml(@page.to_s) == Hash.from_xml(delete_response)
347
+ end
348
+ end
349
+
350
+ describe "and the page does not exist" do
351
+
352
+ before do
353
+ @gateway.login("atlasmw", "wombat")
354
+ end
355
+
356
+ it "should raise an error" do
357
+ lambda do
358
+ @gateway.delete("Missing Page")
359
+ end.should raise_error(StandardError)
360
+ end
361
+ end
362
+ end
363
+
364
+ describe "when not logged in" do
365
+
366
+ before do
367
+ create("Deletable Page", "Some content")
368
+ end
369
+
370
+ it "should raise an error" do
371
+ lambda do
372
+ @gateway.delete("Deletable Page")
373
+ end.should raise_error(StandardError)
374
+ end
375
+
376
+ end
377
+
378
+ end
379
+
380
+ describe "#undelete" do
381
+
382
+ describe "when logged in as admin" do
383
+ before do
384
+ $fake_media_wiki.reset
385
+ @gateway.login("atlasmw", "wombat")
386
+ end
387
+
388
+ describe "and the page no longer exists" do
389
+ before do
390
+ @revs = @gateway.undelete("Sandbox:Undeleted")
391
+ end
392
+
393
+ it "should recreate the given page" do
394
+ @gateway.list("Sandbox:Undeleted").should == [ "Sandbox:Undeleted" ]
395
+ end
396
+
397
+ it "should report one undeleted revision" do
398
+ @revs.should == 1
399
+ end
400
+ end
401
+
402
+ describe "but the page exists" do
403
+ before do
404
+ @revs = @gateway.undelete("Main Page")
405
+ end
406
+
407
+ it "should report zero undeleted revisions" do
408
+ @revs.should == 0
409
+ end
410
+ end
411
+ end
412
+
413
+ describe "when not logged in" do
414
+
415
+ it "should raise an error" do
416
+ lambda do
417
+ @gateway.undelete("Undeletable Page")
418
+ end.should raise_error(StandardError)
419
+ end
420
+
421
+ end
422
+
423
+ end
424
+
425
+ describe "#list" do
426
+
427
+ before do
428
+ $fake_media_wiki.reset
429
+ end
430
+
431
+ describe "with an empty key" do
432
+
433
+ before do
434
+ @list = @gateway.list("")
435
+ end
436
+
437
+ it "should list all pages" do
438
+ @list.sort.should == [ "Book:Italy", "Level/Level/Index", "Main 2", "Main Page" ]
439
+ end
440
+
441
+ end
442
+
443
+ describe "with a namespace as the key" do
444
+
445
+ before do
446
+ @list = @gateway.list("Book:")
447
+ end
448
+
449
+ it "should list all pages in the namespace" do
450
+ @list.should == [ "Book:Italy" ]
451
+ end
452
+
453
+ end
454
+
455
+ describe "with a partial title as the key" do
456
+
457
+ before do
458
+ @list = @gateway.list("Main")
459
+ end
460
+
461
+ it "should list all pages in the main namespace that start with key" do
462
+ @list.sort.should == [ "Main 2", "Main Page" ]
463
+ end
464
+
465
+ end
466
+
467
+ end
468
+
469
+ describe "#search" do
470
+
471
+ before do
472
+ $fake_media_wiki.reset
473
+ @gateway.create("Search Test", "Foo KEY Blah")
474
+ @gateway.create("Search Test 2", "Zomp KEY Zorg")
475
+ @gateway.create("Book:Search Test", "Bar KEY Baz")
476
+ @gateway.create("Sandbox:Search Test", "Evil KEY Evil")
477
+ end
478
+
479
+ describe "with an empty key" do
480
+
481
+ it "should raise an error" do
482
+ lambda do
483
+ @gateway.search("")
484
+ end.should raise_error(StandardError)
485
+ end
486
+
487
+ end
488
+
489
+ describe "with a valid key and no namespaces" do
490
+
491
+ before do
492
+ @search = @gateway.search("KEY")
493
+ end
494
+
495
+ it "should list all matching pages in the main namespace" do
496
+ @search.should == [ "Search Test", "Search Test 2" ]
497
+ end
498
+
499
+ end
500
+
501
+ describe "with a valid key and a namespace string" do
502
+
503
+ before do
504
+ @search = @gateway.search("KEY", "Book")
505
+ end
506
+
507
+ it "should list all matching pages in the specified namespaces" do
508
+ @search.should == [ "Book:Search Test" ]
509
+ end
510
+
511
+ end
512
+
513
+ describe "with a valid key and a namespace array" do
514
+
515
+ before do
516
+ @search = @gateway.search("KEY", ["Book", "Sandbox"])
517
+ end
518
+
519
+ it "should list all matching pages in the specified namespaces" do
520
+ @search.should == [ "Sandbox:Search Test", "Book:Search Test" ]
521
+ end
522
+
523
+ end
524
+
525
+ end
526
+
527
+ describe "#namespaces_by_prefix" do
528
+
529
+ before do
530
+ $fake_media_wiki.reset
531
+ @namespaces = @gateway.namespaces_by_prefix
532
+ end
533
+
534
+ it "should list all namespaces" do
535
+ @namespaces.should == { "" => 0, "Book" => 100, "Sandbox" => 200}
536
+ end
537
+
538
+ end
539
+
540
+ describe "#semantic_query" do
541
+
542
+ before do
543
+ @response = @gateway.semantic_query('[[place::123]]', ['mainlabel=Page'])
544
+ end
545
+
546
+ it "should return an HTML string" do
547
+ @response.should == "Sample <B>HTML</B> content"
548
+ end
549
+
550
+ end
551
+
552
+ describe "#import" do
553
+
554
+ def import_file
555
+ File.dirname(__FILE__) + "/import-test-data.xml"
556
+ end
557
+
558
+ describe "when not logged in" do
559
+
560
+ it "should raise an error" do
561
+ lambda do
562
+ @gateway.import(import_file)
563
+ end.should raise_error(StandardError)
564
+ end
565
+
566
+ end
567
+
568
+ describe "when logged in as admin" do
569
+
570
+ def import_response
571
+ <<-XML
572
+ <api>
573
+ <import>
574
+ <page title='Main Page' ns='0' revisions='0'/>
575
+ <page title='Template:Header' ns='10' revisions='1'/>
576
+ </import>
577
+ </api>
578
+ XML
579
+ end
580
+
581
+ before do
582
+ @gateway.login("atlasmw", "wombat")
583
+ @page = @gateway.import(import_file)
584
+ end
585
+
586
+ it "should import content" do
587
+ Hash.from_xml(@page.to_s) == Hash.from_xml(import_response)
588
+ end
589
+
590
+ end
591
+
592
+ end
593
+
594
+ describe "#export" do
595
+
596
+ def export_response
597
+ <<-XML
598
+ <mediawiki>
599
+ <page>
600
+ <title>Main Page</title>
601
+ <id>1</id>
602
+ <revision>
603
+ <id>1</id>
604
+ <text>Content</text>
605
+ </revision>
606
+ </page>
607
+ </mediawiki>
608
+ XML
609
+ end
610
+
611
+ before do
612
+ @page = @gateway.export("Main Page")
613
+ end
614
+
615
+ it "should return export data for the page" do
616
+ Hash.from_xml(@page.to_s).should == Hash.from_xml(export_response)
617
+ end
618
+
619
+ end
620
+
621
+ describe "#namespaces_by_prefix" do
622
+
623
+ before do
624
+ $fake_media_wiki.reset
625
+ @namespaces = @gateway.send :namespaces_by_prefix
626
+ end
627
+
628
+ it "should list all namespaces" do
629
+ @namespaces.should == { "" => 0, "Book" => 100, "Sandbox" => 200}
630
+ end
631
+
632
+ end
633
+
634
+ describe "#extensions" do
635
+
636
+ before do
637
+ $fake_media_wiki.reset
638
+ @extensions = @gateway.extensions
639
+ end
640
+
641
+ it "should list all extensions" do
642
+ @extensions.should == { "FooExtension" => "r1", "BarExtension" => "r2" }
643
+ end
644
+
645
+ end
646
+
647
+ def create(title, content, options={})
648
+ form_data = {'action' => 'edit', 'title' => title, 'text' => content, 'summary' => (options[:summary] || ""), 'token' => @gateway.send(:get_token, 'edit', title)}
649
+ form_data['createonly'] = "" unless options[:overwrite]
650
+ @gateway.send(:make_api_request, form_data)
651
+ end
652
+
653
+ end