gf-Soks 1.0.4

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 (120) hide show
  1. data/LICENSE.txt +66 -0
  2. data/README.txt +64 -0
  3. data/bin/soks-create-wiki.rb +193 -0
  4. data/contrib/diff/lcs.rb +1105 -0
  5. data/contrib/diff/lcs/array.rb +21 -0
  6. data/contrib/diff/lcs/block.rb +51 -0
  7. data/contrib/diff/lcs/callbacks.rb +322 -0
  8. data/contrib/diff/lcs/change.rb +169 -0
  9. data/contrib/diff/lcs/hunk.rb +257 -0
  10. data/contrib/diff/lcs/ldiff.rb +226 -0
  11. data/contrib/diff/lcs/string.rb +19 -0
  12. data/contrib/diff_licence.txt +76 -0
  13. data/contrib/easyprompt.rb +58 -0
  14. data/contrib/easyprompt_licence.txt +504 -0
  15. data/contrib/redcloth-3.0.3.rb +1113 -0
  16. data/contrib/redcloth_license.txt +27 -0
  17. data/lib/authenticators.rb +121 -0
  18. data/lib/helpers/counter-helpers.rb +132 -0
  19. data/lib/helpers/default-helpers.rb +416 -0
  20. data/lib/helpers/mail2wiki-helper.rb +105 -0
  21. data/lib/helpers/maintenance-helpers.rb +149 -0
  22. data/lib/helpers/rss2wiki-helper.rb +47 -0
  23. data/lib/helpers/wiki2html.rb +60 -0
  24. data/lib/soks-model.rb +271 -0
  25. data/lib/soks-servlet.rb +177 -0
  26. data/lib/soks-storage.rb +187 -0
  27. data/lib/soks-upgrade-0.0.2.rb +70 -0
  28. data/lib/soks-utils.rb +327 -0
  29. data/lib/soks-view.rb +399 -0
  30. data/lib/soks.rb +27 -0
  31. data/rakefile +109 -0
  32. data/templates/default/attachment/favicon.ico +0 -0
  33. data/templates/default/attachment/logo.jpg +0 -0
  34. data/templates/default/attachment/logo.png +0 -0
  35. data/templates/default/attachment/logo.tiff +0 -0
  36. data/templates/default/attachment/newpage.js +41 -0
  37. data/templates/default/attachment/print_stylesheet.css +2 -0
  38. data/templates/default/attachment/robots.txt +6 -0
  39. data/templates/default/attachment/rss.png +0 -0
  40. data/templates/default/attachment/stylesheet.css +219 -0
  41. data/templates/default/banned_titles.txt +67 -0
  42. data/templates/default/caches/readme.txt +1 -0
  43. data/templates/default/content/Api%20for%20classes%20to%20modify%20the%20wiki.textile +30 -0
  44. data/templates/default/content/Author.textile +16 -0
  45. data/templates/default/content/Automatic%20Summaries.textile +40 -0
  46. data/templates/default/content/Automatic%20counters.textile +22 -0
  47. data/templates/default/content/Automatic%20exporters.textile +23 -0
  48. data/templates/default/content/Automatic%20importers.textile +59 -0
  49. data/templates/default/content/Automatic%20linking.textile +7 -0
  50. data/templates/default/content/Automatic%20maintenance%20helpers.textile +39 -0
  51. data/templates/default/content/Bug%3A%20Competing%20edits.textile +22 -0
  52. data/templates/default/content/Bug%3A%20Does%20not%20make%20use%20of%20if%2Dmodified%2Dsince%20r.textile +3 -0
  53. data/templates/default/content/Bug%3A%20Email%20adresses%20in%20page%20titles%20cause%20incorrec.textile +3 -0
  54. data/templates/default/content/Bug%3A%20GEM%20limits%20title%20lengths.textile +3 -0
  55. data/templates/default/content/Bug%3A%20Memory%20leak.textile +13 -0
  56. data/templates/default/content/Bug%3A%20Page%2Einserted%5Finto%20is%20never%20purged.textile +17 -0
  57. data/templates/default/content/Bug%3A%20Pages%20that%20link%20here%20may%20not%20appear%20on%20r.textile +13 -0
  58. data/templates/default/content/Bug%3A%20Textile%20mishandles%20paragraphs.textile +37 -0
  59. data/templates/default/content/Bug%3A%20Unanticipated%20Rollbacks.textile +23 -0
  60. data/templates/default/content/Bug%3A%20notextile%20does%20not%20prevent%20page%20inserts.textile +3 -0
  61. data/templates/default/content/Home%20Page.textile +22 -0
  62. data/templates/default/content/How%20to%20administrate%20this%20wiki.textile +57 -0
  63. data/templates/default/content/How%20to%20change%20the%20way%20this%20wiki%20looks.textile +32 -0
  64. data/templates/default/content/How%20to%20export%20a%20site%20from%20this%20wiki.textile +82 -0
  65. data/templates/default/content/How%20to%20get%20the%20latest%20Soks%20from%20cvs.textile +45 -0
  66. data/templates/default/content/How%20to%20hack%20soks.textile +66 -0
  67. data/templates/default/content/How%20to%20import%20a%20site%20from%20instiki.textile +15 -0
  68. data/templates/default/content/How%20to%20import%20data.textile +41 -0
  69. data/templates/default/content/How%20to%20install%20Soks.textile +33 -0
  70. data/templates/default/content/How%20to%20password%20protect%20your%20wiki.textile +53 -0
  71. data/templates/default/content/How%20to%20re%2Dbuild%20the%20page%20cache.textile +71 -0
  72. data/templates/default/content/How%20to%20report%20a%20bug.textile +9 -0
  73. data/templates/default/content/How%20to%20upgrade%20soks.textile +32 -0
  74. data/templates/default/content/How%20to%20use%20the%20Automatic%20Helper%20classes.textile +12 -0
  75. data/templates/default/content/How%20to%20use%20this%20wiki.textile +30 -0
  76. data/templates/default/content/List%20of%20changes.textile +10 -0
  77. data/templates/default/content/News%3A%20Version%201%2D0%2D0%20released.textile +19 -0
  78. data/templates/default/content/News%3A%20Version%201%2D0%2D1%20released.textile +12 -0
  79. data/templates/default/content/Pages%20to%20include%20in%20the%20distribution.textile +55 -0
  80. data/templates/default/content/Per%20Wiki%20Templates.textile +37 -0
  81. data/templates/default/content/Picture%20of%20a%20pair%20of%20soks.textile +1 -0
  82. data/templates/default/content/Planned%20Features.textile +74 -0
  83. data/templates/default/content/README.textile +64 -0
  84. data/templates/default/content/RSS%20feed.textile +9 -0
  85. data/templates/default/content/Recent%20changes%20to%20this%20site.textile +352 -0
  86. data/templates/default/content/SOKS%20features.textile +19 -0
  87. data/templates/default/content/Sidebar%20Page.textile +6 -0
  88. data/templates/default/content/Site%20Index.textile +241 -0
  89. data/templates/default/content/Soks%27s%20Licence.textile +66 -0
  90. data/templates/default/content/Tag%3A%20Include%20this%20page%20in%20the%20distribution.textile +6 -0
  91. data/templates/default/start.rb +90 -0
  92. data/templates/default/version.txt +1 -0
  93. data/templates/default/views/Page_content.rhtml +1 -0
  94. data/templates/default/views/Page_edit.rhtml +79 -0
  95. data/templates/default/views/Page_find.rhtml +35 -0
  96. data/templates/default/views/Page_linksfromrss.rhtml +24 -0
  97. data/templates/default/views/Page_listrss.rhtml +46 -0
  98. data/templates/default/views/Page_meta.rhtml +44 -0
  99. data/templates/default/views/Page_print.rhtml +6 -0
  100. data/templates/default/views/Page_revision.rhtml +39 -0
  101. data/templates/default/views/Page_revisions.rhtml +36 -0
  102. data/templates/default/views/Page_rss.rhtml +57 -0
  103. data/templates/default/views/Page_view.rhtml +8 -0
  104. data/templates/default/views/UploadPage_edit.rhtml +63 -0
  105. data/templates/default/views/frame.rhtml +63 -0
  106. data/templates/default/views/messages.yaml +7 -0
  107. data/test/html/2006Mar.html +66 -0
  108. data/test/html/poignant.html +36 -0
  109. data/test/html/poignant.textile +36 -0
  110. data/test/mock-objects.rb +69 -0
  111. data/test/test_counter-helper.rb +162 -0
  112. data/test/test_soks-helper-maintenance.rb +106 -0
  113. data/test/test_soks-helpers.rb +145 -0
  114. data/test/test_soks-model.rb +144 -0
  115. data/test/test_soks-servlet.rb +240 -0
  116. data/test/test_soks-storage.rb +108 -0
  117. data/test/test_soks-utils.rb +226 -0
  118. data/test/test_soks-view.rb +193 -0
  119. data/test/test_soks.rb +9 -0
  120. metadata +182 -0
@@ -0,0 +1,36 @@
1
+ <h3>False</h3>
2
+
3
+ <p style="float:left"><img src="i/blix-neg.gif" title="Shape of a cat." alt="Shape of a cat." /></p>
4
+
5
+ <p><em>The cat Trady Blix. Frozen in emptiness. Immaculate whiskers rigid. Placid eyes of lake. Tail of warm icicle. Sponsored by a Very Powerful Pause Button.</em></p>
6
+
7
+ <p>The darkness surrounding Blix can be called <strong>negative space</strong>. Hang on to that phrase. Let it suggest that the emptiness has a negative connotation. In a similar way, <code>nil</code> has a slightly sour note that it whistles.</p>
8
+
9
+ <p>Generally speaking, everything in Ruby has a positive charge to it. This spark flows through strings, numbers, regexps, all of it. Only two keywords wear a shady cloak: <code>nil</code> and <code>false</code> draggin us down.</p>
10
+
11
+ <p>You can test that charge with an <code>if</code> keyword. It looks very much like the <code>do</code> blocks we saw in the last chapter, in that both end with an <code>end</code>.</p>
12
+
13
+
14
+ <pre>
15
+ if plastic_cup
16
+ print "Plastic cup is on the up 'n' up!"
17
+ end
18
+ </pre>
19
+ <p>If <code>plastic_cup</code> contains either <code>nil</code> or <code>false</code>, you won&#8217;t see anything print to the screen. They&#8217;re not on the <code>if</code> guest list. So <code>if</code> isn&#8217;t going to run any of the code it&#8217;s protecting.</p>
20
+
21
+ <p>But <code>nil</code> and <code>false</code> need not walk away in shame. They may be of questionable character, but <code>unless</code> runs a smaller establishment that caters to the bedraggled. The <code>unless</code> keyword has a policy of only allowing those with a negative charge in. Who are: <code>nil</code> and <code>false</code>.</p>
22
+
23
+
24
+ <pre>
25
+ unless plastic_cup
26
+ print "Plastic cup is on the down low."
27
+ end
28
+ </pre>
29
+ <p>You can also use <code>if</code> and <code>unless</code> at the end of a single line of code, if that&#8217;s all that is being protected.</p>
30
+
31
+
32
+ <pre>
33
+ print "Yeah, plastic cup is up again!" if plastic_cup
34
+ print "Hardly. It's down." unless plastic_cup
35
+ </pre>
36
+ <p>Now that you&#8217;ve met <code>false</code>, I&#8217;m sure you can see what&#8217;s on next.</p>
@@ -0,0 +1,36 @@
1
+ h3. False
2
+
3
+ !<i/blix-neg.gif(Shape of a cat.)!
4
+
5
+ _The cat Trady Blix. Frozen in emptiness. Immaculate whiskers rigid. Placid eyes of lake. Tail of warm icicle. Sponsored by a Very Powerful Pause Button._
6
+
7
+ The darkness surrounding Blix can be called *negative space*. Hang on to that phrase. Let it suggest that the emptiness has a negative connotation. In a similar way, @nil@ has a slightly sour note that it whistles.
8
+
9
+ Generally speaking, everything in Ruby has a positive charge to it. This spark flows through strings, numbers, regexps, all of it. Only two keywords wear a shady cloak: @nil@ and @false@ draggin us down.
10
+
11
+ You can test that charge with an @if@ keyword. It looks very much like the @do@ blocks we saw in the last chapter, in that both end with an @end@.
12
+
13
+ <pre>
14
+ if plastic_cup
15
+ print "Plastic cup is on the up 'n' up!"
16
+ end
17
+ </pre>
18
+
19
+ If @plastic_cup@ contains either @nil@ or @false@, you won't see anything print to the screen. They're not on the @if@ guest list. So @if@ isn't going to run any of the code it's protecting.
20
+
21
+ But @nil@ and @false@ need not walk away in shame. They may be of questionable character, but @unless@ runs a smaller establishment that caters to the bedraggled. The @unless@ keyword has a policy of only allowing those with a negative charge in. Who are: @nil@ and @false@.
22
+
23
+ <pre>
24
+ unless plastic_cup
25
+ print "Plastic cup is on the down low."
26
+ end
27
+ </pre>
28
+
29
+ You can also use @if@ and @unless@ at the end of a single line of code, if that's all that is being protected.
30
+
31
+ <pre>
32
+ print "Yeah, plastic cup is up again!" if plastic_cup
33
+ print "Hardly. It's down." unless plastic_cup
34
+ </pre>
35
+
36
+ Now that you've met @false@, I'm sure you can see what's on next.
@@ -0,0 +1,69 @@
1
+ $:.unshift( "contrib" )
2
+
3
+ require 'yaml'
4
+ $MESSAGES = YAML.load( IO.readlines("templates/default/views/messages.yaml").join )
5
+
6
+ require 'logger'
7
+ $LOG = Logger.new(STDOUT)
8
+ $LOG.level = Logger::WARN
9
+
10
+ begin
11
+ require 'rubygems'
12
+ require_gem 'ruby-breakpoint'
13
+ rescue LoadError
14
+ $LOG.info "Breakpoint library not found. Shouldn't matter"
15
+ end
16
+
17
+ require 'fileutils'
18
+ require 'soks'
19
+
20
+ class MockWikiStore
21
+ include WikiFlatFileStore
22
+
23
+ def initialize( folder )
24
+ @folder = folder
25
+ @pages = {}
26
+ end
27
+
28
+ def mutate( pagename )
29
+ p yield( @pages[pagename.downcase] ||= Page.new( pagename ) )
30
+ end
31
+ end
32
+
33
+ module TearDownableWiki
34
+ include FileUtils
35
+
36
+ def setup
37
+ @wiki = Wiki.new( folder )
38
+ @view = View.new( @wiki, 'http://testsite.com','testcontent/views' )
39
+ end
40
+
41
+ def teardown
42
+ rmtree( folder )
43
+ end
44
+
45
+ private
46
+
47
+ def create_file( name, content )
48
+ File.open( File.join( folder, name ), 'w') { |f| f.puts content }
49
+ end
50
+
51
+ def files
52
+ Dir.entries( folder ).delete_if { |name| name =~ /^(\.+|attachment|views)$/ }.sort
53
+ end
54
+
55
+ def folder
56
+ @folder ||= make_folder
57
+ end
58
+
59
+ def make_folder
60
+ mkdir( 'testcontent' )
61
+ mkdir('testcontent/attachment')
62
+ File.symlink(File.join(Dir.getwd,'templates/default/views'),'testcontent/views')
63
+ 'testcontent'
64
+ end
65
+
66
+ def wait_for_queue_to_empty
67
+ sleep(0.1) until @wiki.event_queue.empty?
68
+ end
69
+ end
@@ -0,0 +1,162 @@
1
+ require 'test/unit'
2
+ require 'fileutils'
3
+ require 'mock-objects'
4
+ require 'generator'
5
+ require 'helpers/counter-helpers'
6
+
7
+ class TestViewCountHelper < Test::Unit::TestCase
8
+ include TearDownableWiki
9
+
10
+ def test_notification
11
+ results = []
12
+ @wiki.watch_for(:page_viewed) { |*results| }
13
+ @view.render( 'test-page','view','test-viewer')
14
+ wait_for_queue_to_empty
15
+ assert_equal( :page_viewed, results[0] )
16
+ assert_equal( 'test-page', results[1].name )
17
+ assert_equal( 'view', results[2] )
18
+ assert_equal( 'test-viewer', results[3] )
19
+ end
20
+
21
+ def test_total_count
22
+ count = ViewCountHelper.new(@wiki).counts
23
+ @view.render( 'test-page','view','test-viewer')
24
+ @view.render( 'test-page','view','test-viewer')
25
+ @view.render( 'test-page','view','test-viewer')
26
+ wait_for_queue_to_empty
27
+ assert_equal( 3, count.total )
28
+ end
29
+
30
+ def test_page_count
31
+ count = ViewCountHelper.new(@wiki, ['view'], 'Popular Pages', :test_event, 2 ).counts
32
+ @wiki.revise( 'count1','1','t1')
33
+ @wiki.revise( 'count2','2','t2')
34
+ @wiki.revise( 'count3','3','t3')
35
+ 3.times { @view.render( 'count1' ) }
36
+ 3.times { @view.render( 'count1', 'edit' ) }
37
+ 2.times { @view.render( 'count2' ) }
38
+ 1.times { @view.render( 'count3' ) }
39
+ wait_for_queue_to_empty
40
+ p1,p2,p3 = @wiki.page('count1'), @wiki.page('count2'), @wiki.page('count3')
41
+ assert_equal( 3, count[p1.name] )
42
+ assert_equal( 2, count[p2.name] )
43
+ assert_equal( 1, count[p3.name] )
44
+ assert_equal( 6, count.total )
45
+ end
46
+
47
+ def test_page_render
48
+ start_time = Time.now
49
+ test_page_count
50
+ @wiki.notify( :test_event )
51
+ wait_for_queue_to_empty
52
+ content = @wiki.page('Popular Pages').content.split "\n"
53
+ [ [ 0, "h1. Popular Pages" ],
54
+ [ 4, "| count1 | 3 |" ],
55
+ [ 5, "| count2 | 2 |" ],
56
+ [ 6, "| 1 others | 1 |" ],
57
+ [ 7, "| *Total* | *6* |" ] ].each do |i,line|
58
+ assert_equal line, content[i]
59
+ end
60
+ end
61
+
62
+ end
63
+
64
+ class TestViewerCountHelper < Test::Unit::TestCase
65
+ include TearDownableWiki
66
+
67
+ def test_notification
68
+ results = []
69
+ @wiki.watch_for(:page_viewed) { |*results| }
70
+ @view.render( 'test-page','view','test-viewer')
71
+ wait_for_queue_to_empty
72
+ assert_equal( :page_viewed, results[0] )
73
+ assert_equal( 'test-page', results[1].name )
74
+ assert_equal( 'view', results[2] )
75
+ assert_equal( 'test-viewer', results[3] )
76
+ end
77
+
78
+ def test_total_count
79
+ count = ViewerCountHelper.new(@wiki).counts
80
+ @view.render( 'test-page','view','test-viewer')
81
+ @view.render( 'test-page','view','test-viewer')
82
+ @view.render( 'test-page','view','test-viewer')
83
+ wait_for_queue_to_empty
84
+ assert_equal( 3, count.total )
85
+ end
86
+
87
+ def test_viewer_count
88
+ count = ViewerCountHelper.new(@wiki, ['view'], 'Popular Pages', :test_event, 2 ).counts
89
+ @wiki.revise( 'count1','1','t1')
90
+ @wiki.revise( 'count2','2','t2')
91
+ @wiki.revise( 'count3','3','t3')
92
+ 3.times { @view.render( 'count1', 'view', "Author1" ) }
93
+ 3.times { @view.render( 'count1', 'edit', "Author1" ) }
94
+ 2.times { @view.render( 'count2', 'view', "Author2" ) }
95
+ 1.times { @view.render( 'count3', 'view', "Author3" ) }
96
+ wait_for_queue_to_empty
97
+ assert_equal( 3, count['Author1'] )
98
+ assert_equal( 2, count['Author2'] )
99
+ assert_equal( 1, count['Author3'] )
100
+ assert_equal( 6, count.total )
101
+ end
102
+
103
+ def test_page_render
104
+ start_time = Time.now
105
+ test_viewer_count
106
+ @wiki.notify( :test_event )
107
+ wait_for_queue_to_empty
108
+ content = @wiki.page('Popular Pages').content.split "\n"
109
+ [ [ 0, "h1. Popular Pages" ],
110
+ [ 4, "| Author1 | 3 |" ],
111
+ [ 5, "| Author2 | 2 |" ],
112
+ [ 6, "| 1 others | 1 |" ],
113
+ [ 7, "| *Total* | *6* |" ] ].each do |i,line|
114
+ assert_equal line, content[i]
115
+ end
116
+ end
117
+ end
118
+
119
+
120
+ class TestAuthorCountHelper < Test::Unit::TestCase
121
+ include TearDownableWiki
122
+
123
+
124
+ def test_total_count
125
+ count = AuthorCountHelper.new(@wiki,'Principal Authors', :test_event, 2 ).counts
126
+ @wiki.revise( 'count1','1','t1')
127
+ @wiki.revise( 'count2','2','t2')
128
+ @wiki.revise( 'count3','3','t3')
129
+ wait_for_queue_to_empty
130
+ assert_equal( 3, count.total )
131
+ end
132
+
133
+ def test_author_count
134
+ count = AuthorCountHelper.new(@wiki,'Principal Authors', :test_event, 2 ).counts
135
+ @wiki.revise( 'count1','1','t1')
136
+ @wiki.revise( 'count2','1','t1')
137
+ @wiki.revise( 'count2','2','t2')
138
+ @wiki.revise( 'count3','1','t1')
139
+ @wiki.revise( 'count3','2','t2')
140
+ @wiki.revise( 'count3','3','t3')
141
+ wait_for_queue_to_empty
142
+ assert_equal( 3, count['t1'] )
143
+ assert_equal( 2, count['t2'] )
144
+ assert_equal( 1, count['t3'] )
145
+ assert_equal( 6, count.total )
146
+ end
147
+
148
+ def test_page_render
149
+ start_time = Time.now
150
+ test_author_count
151
+ @wiki.notify( :test_event )
152
+ wait_for_queue_to_empty
153
+ content = @wiki.page('Principal Authors').content.split "\n"
154
+ [ [ 0, "h1. Principal Authors" ],
155
+ [ 4, "| t1 | 3 |" ],
156
+ [ 5, "| t2 | 2 |" ],
157
+ [ 6, "| 1 others | 1 |" ],
158
+ [ 7, "| *Total* | *6* |" ] ].each do |i,line|
159
+ assert_equal line, content[i]
160
+ end
161
+ end
162
+ end
@@ -0,0 +1,106 @@
1
+ require 'test/unit'
2
+ require 'mock-objects'
3
+ require 'helpers/maintenance-helpers'
4
+
5
+ class TestDeleteOldPages < Test::Unit::TestCase
6
+ include TearDownableWiki
7
+
8
+ def setup
9
+ super
10
+ DeleteOldPagesHelper.new( @wiki, :an_event, 2 )
11
+ end
12
+
13
+ def test_delete_old_pages
14
+ assert_equal([],files)
15
+ @wiki.revise( 'home page', 'hello world', 'tamc2')
16
+ assert_equal( true, @wiki.exists?('home page') )
17
+ assert_equal( false, @wiki.page('home page').deleted? )
18
+ assert_equal(['home%20page.textile','home%20page.yaml'],files)
19
+
20
+ @wiki.delete( 'home page', 'tamc2')
21
+ @wiki.notify(:an_event )
22
+ wait_for_queue_to_empty
23
+
24
+ # Should be too soon
25
+ assert_equal( false, @wiki.exists?('home page') )
26
+ assert_equal( true, @wiki.page('home page').deleted? )
27
+ assert_equal(['home%20page.textile','home%20page.yaml'],files)
28
+
29
+ sleep( 2 )
30
+ @wiki.notify(:an_event )
31
+ wait_for_queue_to_empty
32
+
33
+ # Should now have deleted
34
+ assert_equal( false, @wiki.exists?('home page') )
35
+ assert_equal( false, @wiki.page('home page').deleted? )
36
+ assert_equal([],files)
37
+ end
38
+
39
+ end
40
+
41
+ class TestDeleteOldRevisions < Test::Unit::TestCase
42
+ include TearDownableWiki
43
+
44
+ def setup
45
+ super
46
+ DeleteOldRevisionsHelper.new( @wiki, :an_event, 2, 2)
47
+ end
48
+
49
+ def test_delete_old_revisions
50
+ 1.upto(5) do |i|
51
+ @wiki.revise('revision delete test page',"#{i}","test author")
52
+ end
53
+ page = @wiki.page('revision delete test page')
54
+ assert_equal(5,page.revisions.size)
55
+
56
+ @wiki.notify(:an_event )
57
+ wait_for_queue_to_empty
58
+
59
+ # Should be too soon
60
+ assert_equal(5,page.revisions.size)
61
+
62
+ sleep( 2 )
63
+ @wiki.notify(:an_event )
64
+ wait_for_queue_to_empty
65
+
66
+ # Should now have turned last 3 revisions into one
67
+ assert_equal(3,page.revisions.size)
68
+ assert_equal('Automatic Revision Remover',page.revisions.first.author)
69
+ assert_equal('3',page.revisions.first.content)
70
+ end
71
+ end
72
+
73
+ class TestMergeOldRevisions < Test::Unit::TestCase
74
+ include TearDownableWiki
75
+
76
+ def setup
77
+ super
78
+ MergeOldRevisionsHelper.new( @wiki, :an_event, 2, 10)
79
+ end
80
+
81
+ def test_merge_old_revisions
82
+ 1.upto(3) do |i|
83
+ @wiki.revise('revision merge test page',"#{i}","author1")
84
+ end
85
+ 3.upto(5) do |i|
86
+ @wiki.revise('revision merge test page',"#{i}","author2")
87
+ end
88
+ page = @wiki.page('revision merge test page')
89
+ assert_equal(5,page.revisions.size)
90
+
91
+ @wiki.notify(:an_event )
92
+ wait_for_queue_to_empty
93
+
94
+ # Should be too soon
95
+ assert_equal(5,page.revisions.size)
96
+
97
+ sleep( 2 )
98
+ @wiki.notify(:an_event )
99
+ wait_for_queue_to_empty
100
+
101
+ # Should now have merged each author's revisions
102
+ assert_equal(2,page.revisions.size)
103
+ assert_equal('3',page.revision(0).content)
104
+ assert_equal('5',page.revision(1).content)
105
+ end
106
+ end
@@ -0,0 +1,145 @@
1
+ require 'test/unit'
2
+ require 'fileutils'
3
+ require 'mock-objects'
4
+ require 'helpers/default-helpers'
5
+ require 'generator'
6
+
7
+ class TestAutomaticSummary < Test::Unit::TestCase
8
+ include TearDownableWiki
9
+
10
+ def test_basics
11
+ AutomaticSummary.new( @wiki, 'automatic summary' ) { |page| page.name =~ /hello/i }
12
+ @wiki.revise 'hello world', 'hello world', 'test author'
13
+ @wiki.revise 'hello john', 'hello john', 'test author'
14
+ @wiki.revise 'hello frank', 'hello frank', 'test author'
15
+ @wiki.revise 'hello frank', 'page deleted', 'test author'
16
+ @wiki.revise 'goodbye world', 'goodbye world', 'test author'
17
+ wait_for_queue_to_empty
18
+ content = @wiki.page('automatic summary').content
19
+ assert_match /hello world/, content
20
+ assert_match /hello john/, content
21
+ assert_no_match /goodbye world/, content
22
+ assert_no_match /hello frank/, content
23
+ end
24
+
25
+ def test_updates_on_revision
26
+ as = AutomaticSummary.new( @wiki, 'update on revision test' ) { |page| page.name =~ /summarise/i }
27
+ @wiki.revise('summarise 1','initial content','test author')
28
+ wait_for_queue_to_empty
29
+ assert_match(/initial content/,@wiki.page('update on revision test').content )
30
+ @wiki.revise('summarise 1','updated content','test author')
31
+ wait_for_queue_to_empty
32
+ assert_match(/updated content/,@wiki.page('update on revision test').content )
33
+ end
34
+
35
+ def test_removes_when_no_longer_true
36
+ AutomaticSummary.new( @wiki, 'remove when not true test' ) { |page| page.content =~ /hello/i }
37
+ @wiki.revise('summarise 1','hello','test author')
38
+ wait_for_queue_to_empty
39
+ assert_match(/hello/,@wiki.page('remove when not true test').content )
40
+ @wiki.revise('summarise 1','bye','test author')
41
+ wait_for_queue_to_empty
42
+ assert_no_match(/hello/,@wiki.page('remove when not true test').content )
43
+ assert_no_match(/bye/,@wiki.page('remove when not true test').content )
44
+ end
45
+
46
+ end
47
+
48
+ class TestRecentChanges < Test::Unit::TestCase
49
+ include TearDownableWiki
50
+
51
+ def test_detect_change
52
+ rc = AutomaticRecentChanges.new( @wiki)
53
+ @wiki.revise( 'testpage','B','normal person')
54
+ @wiki.revise( 'testpage2','A','normal person')
55
+ wait_for_queue_to_empty
56
+ assert_equal(2, rc.summary.to_a.size)
57
+ assert_match( /normal person/i, rctextile )
58
+ end
59
+
60
+ def test_merge_author_change
61
+ rc = AutomaticRecentChanges.new( @wiki)
62
+ @wiki.revise( 'testpage','B','normal person')
63
+ @wiki.revise( 'testpage','A','normal person')
64
+ wait_for_queue_to_empty
65
+ assert_equal(1, rc.summary.to_a.size)
66
+ assert_match( /normal person/i, rctextile )
67
+ end
68
+
69
+ def test_dont_merge_different_authors_change
70
+ @rc = AutomaticRecentChanges.new( @wiki)
71
+ @wiki.revise( 'testpage','B','p1')
72
+ @wiki.revise( 'testpage','A','p2')
73
+ wait_for_queue_to_empty
74
+ assert_equal(2, @rc.summary.to_a.size)
75
+ assert_match( /p1/i, rctextile )
76
+ assert_match( /p2/i, rctextile )
77
+ end
78
+
79
+ def test_exclude_helpers_initially
80
+ @wiki.revise( 'testpage','B','normal person')
81
+ @wiki.revise( 'testpage2','content moved from','AutomaticPageMover')
82
+ @wiki.revise( 'testpage2','A','normal person')
83
+ rc = AutomaticRecentChanges.new( @wiki)
84
+ assert_equal(['recent changes to this site','testpage','testpage2'],@wiki.map{|name,page| name }.sort)
85
+ assert_equal(2, rc.summary.to_a.size)
86
+ assert_match( /normal person/i, rctextile )
87
+ assert_no_match( /AutomaticPageMover/i, rctextile )
88
+ end
89
+
90
+ def test_exclude_helpers_later
91
+ rc = AutomaticRecentChanges.new( @wiki)
92
+ @wiki.revise( 'testpage','B','normal person')
93
+ @wiki.revise( 'testpage2','content moved from','AutomaticPageMover')
94
+ @wiki.revise( 'testpage2','A','normal person')
95
+ wait_for_queue_to_empty
96
+ assert_equal(['recent changes to this site','testpage','testpage2'],@wiki.map{|name,page| name }.sort)
97
+ assert_equal(2, rc.summary.to_a.size)
98
+ assert_match( /normal person/i, rctextile )
99
+ assert_no_match( /AutomaticPageMover/i, rctextile )
100
+ end
101
+
102
+ def test_change_in_page_capitalisation
103
+ rc = AutomaticRecentChanges.new( @wiki)
104
+ @wiki.revise( 'testpage','B','normal person')
105
+ wait_for_queue_to_empty
106
+ assert_match( /\[\[testpage\]\]/, rctextile )
107
+ assert_no_match( /\[\[TestPage\]\]/, rctextile )
108
+ @wiki.revise( 'TestPage','C','normal person')
109
+ wait_for_queue_to_empty
110
+ assert_match( /\[\[TestPage\]\]/, rctextile )
111
+ assert_equal( 1, count_matches( /\[\[TestPage\]\]/ ) )
112
+ end
113
+
114
+ private
115
+
116
+ def count_matches( regexp )
117
+ count = 0
118
+ rctextile.gsub( regexp ) { |m| count += 1 }
119
+ count
120
+ end
121
+
122
+ def rctextile
123
+ @wiki.page("Recent Changes to This Site").textile
124
+ end
125
+ end
126
+
127
+ class TestCalendar < Test::Unit::TestCase
128
+ include TearDownableWiki
129
+
130
+ def setup
131
+ super
132
+ AutomaticCalendar.new( @wiki )
133
+ AutomaticUpdateCrossLinks.new( @wiki, @view )
134
+ end
135
+
136
+ def test_2006_Mar_html
137
+ wait_for_queue_to_empty
138
+ page = @wiki.page('2006 Mar')
139
+ desired_html = IO.readlines('test/html/2006Mar.html')
140
+ actual_html = @view.redcloth( page ).split("\n").map { |l| "#{l}\n" }
141
+ SyncEnumerator.new(desired_html,actual_html).each do |desired,actual|
142
+ assert_equal( desired, actual )
143
+ end
144
+ end
145
+ end