olag 0.1.16 → 0.1.17

Sign up to get free protection for your applications and to get access to all the features.
data/ChangeLog CHANGED
@@ -1,3 +1,7 @@
1
+ 2012-01-15 Oren Ben-Kiki <github-oren@ben-kiki.org>
2
+
3
+ * Add WithTempdir mix-in module.
4
+
1
5
  2012-01-07 Oren Ben-Kiki <github-oren@ben-kiki.org>
2
6
 
3
7
  * Improve HAskell configuration comment.
@@ -2025,7 +2025,7 @@ number of Git commits by running <tt>rake version</tt>.
2025
2025
  </tr>
2026
2026
  </table>
2027
2027
  <pre class='ruby code syntax'>
2028
- <span class="Type">VERSION</span> = <span class="Special">&quot;</span><span class="Constant">0.1.16</span><span class="Special">&quot;</span>
2028
+ <span class="Type">VERSION</span> = <span class="Special">&quot;</span><span class="Constant">0.1.17</span><span class="Special">&quot;</span>
2029
2029
 
2030
2030
  end
2031
2031
  </pre>
@@ -2725,6 +2725,274 @@ end
2725
2725
  </div>
2726
2726
  </div>
2727
2727
  </p>
2728
+ <h3>Sorting Hash tables YAML keys</h3>
2729
+ <p>
2730
+ In order to get deterministic test results, and for general
2731
+ hukman-friendlyness, it is often desirable to sort hash table keys when dumping
2732
+ it to YAML. In Ruby 1.8.x, this isn't the default. It is possible to introduce
2733
+ this behavior using the following hack:
2734
+ </p>
2735
+ <p>
2736
+ <div class="named_with_containers chunk">
2737
+ <div class="chunk name">
2738
+ <a name="lib-olag-hash-sorted-yaml-rb">
2739
+ <span>lib/olag/hash_sorted_yaml.rb</span>
2740
+ </a>
2741
+ </div>
2742
+ <div class="chunk html">
2743
+ <pre class='ruby code syntax'>
2744
+ <span class="PreProc">require</span> <span class="Special">&quot;</span><span class="Constant">yaml</span><span class="Special">&quot;</span>
2745
+
2746
+ <span class="Statement">if</span> <span class="Identifier">RUBY_VERSION</span>.include?(<span class="Special">&quot;</span><span class="Constant">1.8</span><span class="Special">&quot;</span>)
2747
+
2748
+ </pre>
2749
+ <table class='layout'>
2750
+ <tr>
2751
+ <td class='indentation'>
2752
+ <pre> </pre>
2753
+ </td>
2754
+ <td class='html'>
2755
+ <div class='rdoc comment markup'>
2756
+ <p>
2757
+ Modify the hash class to emit YAML sorted keys. This is an ugly hack,
2758
+ specifically for Ruby 1.8.*.
2759
+ </p>
2760
+ </div>
2761
+ </td>
2762
+ </tr>
2763
+ </table>
2764
+ <pre class='ruby code syntax'>
2765
+ <span class="PreProc">class</span> <span class="Type">Hash</span>
2766
+
2767
+ </pre>
2768
+ <table class='layout'>
2769
+ <tr>
2770
+ <td class='indentation'>
2771
+ <pre> </pre>
2772
+ </td>
2773
+ <td class='html'>
2774
+ <div class='rdoc comment markup'>
2775
+ <p>
2776
+ Provide access to the old, unsorted implementation.
2777
+ </p>
2778
+ </div>
2779
+ </td>
2780
+ </tr>
2781
+ </table>
2782
+ <pre class='ruby code syntax'>
2783
+ <span class="PreProc">alias</span> <span class="Constant">:unsorted_to_yaml</span> <span class="Constant">:to_yaml</span>
2784
+
2785
+ </pre>
2786
+ <table class='layout'>
2787
+ <tr>
2788
+ <td class='indentation'>
2789
+ <pre> </pre>
2790
+ </td>
2791
+ <td class='html'>
2792
+ <div class='rdoc comment markup'>
2793
+ <p>
2794
+ Return the hash in YAML format with sorted keys.
2795
+ </p>
2796
+ </div>
2797
+ </td>
2798
+ </tr>
2799
+ </table>
2800
+ <pre class='ruby code syntax'>
2801
+ <span class="PreProc">def</span> <span class="Identifier">to_yaml</span>(opts = {})
2802
+ <span class="Type">YAML</span>::quick_emit(<span class="Constant">self</span>, opts) <span class="Statement">do</span> |<span class="Identifier">out</span>|
2803
+ out.map(taguri, to_yaml_style) <span class="Statement">do</span> |<span class="Identifier">map</span>|
2804
+ to_yaml_sorted_keys.each <span class="Statement">do</span> |<span class="Identifier">key</span>|
2805
+ map.add(key, fetch(key))
2806
+ <span class="Statement">end</span>
2807
+ <span class="Statement">end</span>
2808
+ <span class="Statement">end</span>
2809
+ <span class="PreProc">end</span>
2810
+
2811
+ </pre>
2812
+ <table class='layout'>
2813
+ <tr>
2814
+ <td class='indentation'>
2815
+ <pre> </pre>
2816
+ </td>
2817
+ <td class='html'>
2818
+ <div class='rdoc comment markup'>
2819
+ <p>
2820
+ Return the hash keys, sorted for emitting into YAML.
2821
+ </p>
2822
+ </div>
2823
+ </td>
2824
+ </tr>
2825
+ </table>
2826
+ <pre class='ruby code syntax'>
2827
+ <span class="PreProc">def</span> <span class="Identifier">to_yaml_sorted_keys</span>
2828
+ <span class="Statement">begin</span>
2829
+ <span class="Statement">return</span> keys.sort
2830
+ <span class="Statement">rescue</span>
2831
+ <span class="Statement">return</span> to_yaml_lexicographically_sorted_keys
2832
+ <span class="Statement">end</span>
2833
+ <span class="PreProc">end</span>
2834
+
2835
+ </pre>
2836
+ <table class='layout'>
2837
+ <tr>
2838
+ <td class='indentation'>
2839
+ <pre> </pre>
2840
+ </td>
2841
+ <td class='html'>
2842
+ <div class='rdoc comment markup'>
2843
+ <p>
2844
+ Return the hash keys, sorted lexicographically for emitting into YAML.
2845
+ </p>
2846
+ </div>
2847
+ </td>
2848
+ </tr>
2849
+ </table>
2850
+ <pre class='ruby code syntax'>
2851
+ <span class="PreProc">def</span> <span class="Identifier">to_yaml_lexicographically_sorted_keys</span>
2852
+ <span class="Statement">begin</span>
2853
+ <span class="Statement">return</span> keys.sort_by {|<span class="Identifier">key</span>| key.to_s}
2854
+ <span class="Statement">rescue</span>
2855
+ <span class="Statement">return</span> keys
2856
+ <span class="Statement">end</span>
2857
+ <span class="PreProc">end</span>
2858
+
2859
+ end
2860
+
2861
+ end
2862
+ </pre>
2863
+ </div>
2864
+ </div>
2865
+ </p>
2866
+ <p>
2867
+ Here is a simple test demonstrating using it:
2868
+ </p>
2869
+ <p>
2870
+ <div class="named_with_containers chunk">
2871
+ <div class="chunk name">
2872
+ <a name="test-sorted-keys-rb">
2873
+ <span>test/sorted_keys.rb</span>
2874
+ </a>
2875
+ </div>
2876
+ <div class="chunk html">
2877
+ <pre class='ruby code syntax'>
2878
+ <span class="PreProc">require</span> <span class="Special">&quot;</span><span class="Constant">olag/hash_sorted_yaml</span><span class="Special">&quot;</span>
2879
+ <span class="PreProc">require</span> <span class="Special">&quot;</span><span class="Constant">test/spec</span><span class="Special">&quot;</span>
2880
+
2881
+ </pre>
2882
+ <table class='layout'>
2883
+ <tr>
2884
+ <td class='indentation'>
2885
+ <pre></pre>
2886
+ </td>
2887
+ <td class='html'>
2888
+ <div class='rdoc comment markup'>
2889
+ <p>
2890
+ An uncomparable class. Keys of this class will cause the Hash to be emitted
2891
+ in string sort order.
2892
+ </p>
2893
+ </div>
2894
+ </td>
2895
+ </tr>
2896
+ </table>
2897
+ <pre class='ruby code syntax'>
2898
+ <span class="PreProc">class</span> <span class="Type">Uncomparable</span>
2899
+
2900
+ <span class="PreProc">def</span> <span class="Identifier">initialize</span>(value)
2901
+ <span class="Identifier">@value</span> = value
2902
+ <span class="PreProc">end</span>
2903
+
2904
+ <span class="PreProc">def</span> <span class="Identifier">to_yaml</span>(opts = {})
2905
+ <span class="Statement">return</span> <span class="Identifier">@value</span>.to_yaml(opts)
2906
+ <span class="PreProc">end</span>
2907
+
2908
+ <span class="PreProc">def</span> <span class="Identifier">to_s</span>
2909
+ <span class="Statement">return</span> <span class="Identifier">@value</span>.to_s
2910
+ <span class="PreProc">end</span>
2911
+
2912
+ <span class="Special">%w(</span><span class="Constant">&lt;=&gt; &lt; &lt;= &gt;= &gt;</span><span class="Special">)</span>.each <span class="Statement">do</span> |<span class="Identifier">operator</span>|
2913
+ define_method(operator) { <span class="Statement">raise</span> <span class="Special">&quot;</span><span class="Constant">Prevent operator: </span><span class="Special">#{</span>operator<span class="Special">}</span><span class="Special">&quot;</span> }
2914
+ <span class="Statement">end</span>
2915
+
2916
+ <span class="PreProc">end</span>
2917
+
2918
+ </pre>
2919
+ <table class='layout'>
2920
+ <tr>
2921
+ <td class='indentation'>
2922
+ <pre></pre>
2923
+ </td>
2924
+ <td class='html'>
2925
+ <div class='rdoc comment markup'>
2926
+ <p>
2927
+ An uncomparable class that can’t be converted to a string. Keys of this
2928
+ class will cause the Hash to be emitted in unsorted order.
2929
+ </p>
2930
+ </div>
2931
+ </td>
2932
+ </tr>
2933
+ </table>
2934
+ <pre class='ruby code syntax'>
2935
+ <span class="PreProc">class</span> <span class="Type">Unsortable</span> &lt; <span class="Type">Uncomparable</span>
2936
+
2937
+ <span class="PreProc">def</span> <span class="Identifier">to_s</span>
2938
+ <span class="Statement">raise</span> <span class="Special">&quot;</span><span class="Constant">Prevent conversion to string as well.</span><span class="Special">&quot;</span>
2939
+ <span class="PreProc">end</span>
2940
+
2941
+ <span class="PreProc">end</span>
2942
+
2943
+ </pre>
2944
+ <table class='layout'>
2945
+ <tr>
2946
+ <td class='indentation'>
2947
+ <pre></pre>
2948
+ </td>
2949
+ <td class='html'>
2950
+ <div class='rdoc comment markup'>
2951
+ <p>
2952
+ Test sorting keys of YAML generated from Hash tables.
2953
+ </p>
2954
+ </div>
2955
+ </td>
2956
+ </tr>
2957
+ </table>
2958
+ <pre class='ruby code syntax'>
2959
+ <span class="PreProc">class</span> <span class="Type">TestSortedKeys</span> &lt; ::<span class="Type">Test</span>::<span class="Type">Unit</span>::<span class="Type">TestCase</span>
2960
+
2961
+ <span class="Type">SORTED_NUMERICALLY</span> = &lt;&lt;-<span class="Special">EOF</span>.unindent
2962
+ <span class="Constant"> ---</span>
2963
+ <span class="Constant"> 2: 2</span>
2964
+ <span class="Constant"> 4: 4</span>
2965
+ <span class="Constant"> 11: 1</span>
2966
+ <span class="Constant"> 33: 3</span>
2967
+ <span class="Constant"> </span><span class="Special">EOF</span>
2968
+
2969
+ <span class="Type">SORTED_LEXICOGRAPHICALLY</span> = &lt;&lt;-<span class="Special">EOF</span>.unindent
2970
+ <span class="Constant"> ---</span>
2971
+ <span class="Constant"> 11: 1</span>
2972
+ <span class="Constant"> 2: 2</span>
2973
+ <span class="Constant"> 33: 3</span>
2974
+ <span class="Constant"> 4: 4</span>
2975
+ <span class="Constant"> </span><span class="Special">EOF</span>
2976
+
2977
+ <span class="PreProc">def</span> <span class="Identifier">test_sortable_keys</span>
2978
+ { <span class="Constant">2</span> =&gt; <span class="Constant">2</span>, <span class="Constant">4</span> =&gt; <span class="Constant">4</span>, <span class="Constant">11</span> =&gt; <span class="Constant">1</span>, <span class="Constant">33</span> =&gt; <span class="Constant">3</span> }.to_yaml.gsub(<span class="Special">/</span><span class="Constant"> </span><span class="Special">+</span><span class="Special">$</span><span class="Special">/</span>, <span class="Special">&quot;&quot;</span>).should == <span class="Type">SORTED_NUMERICALLY</span>
2979
+ <span class="PreProc">end</span>
2980
+
2981
+ <span class="PreProc">def</span> <span class="Identifier">test_uncomparable_keys</span>
2982
+ { <span class="Type">Uncomparable</span>.new(<span class="Constant">11</span>) =&gt; <span class="Constant">1</span>, <span class="Constant">2</span> =&gt; <span class="Constant">2</span>, <span class="Constant">33</span> =&gt; <span class="Constant">3</span>, <span class="Constant">4</span> =&gt; <span class="Constant">4</span> }.to_yaml.gsub(<span class="Special">/</span><span class="Constant"> </span><span class="Special">+</span><span class="Special">$</span><span class="Special">/</span>, <span class="Special">&quot;&quot;</span>).should == <span class="Type">SORTED_LEXICOGRAPHICALLY</span>
2983
+ <span class="PreProc">end</span>
2984
+
2985
+ <span class="PreProc">def</span> <span class="Identifier">test_unsortable_keys</span>
2986
+ yaml_should_not = { <span class="Type">Unsortable</span>.new(<span class="Constant">11</span>) =&gt; <span class="Constant">1</span>, <span class="Constant">2</span> =&gt; <span class="Constant">2</span>, <span class="Constant">33</span> =&gt; <span class="Constant">3</span>, <span class="Constant">4</span> =&gt; <span class="Constant">4</span> }.to_yaml.gsub(<span class="Special">/</span><span class="Constant"> </span><span class="Special">+</span><span class="Special">$</span><span class="Special">/</span>, <span class="Special">&quot;&quot;</span>).should.not
2987
+ yaml_should_not == <span class="Type">SORTED_NUMERICALLY</span>
2988
+ yaml_should_not == <span class="Type">SORTED_LEXICOGRAPHICALLY</span>
2989
+ <span class="PreProc">end</span>
2990
+
2991
+ <span class="PreProc">end</span>
2992
+ </pre>
2993
+ </div>
2994
+ </div>
2995
+ </p>
2728
2996
  <h3>Collecting errors</h3>
2729
2997
  <p>
2730
2998
  In library code, it is bad practice to terminate the program on an error.
@@ -197,6 +197,19 @@ And here is the implementation:
197
197
 
198
198
  [[lib/olag/hash_struct.rb|named_chunk_with_containers]]
199
199
 
200
+ ### Sorting Hash tables YAML keys ###
201
+
202
+ In order to get deterministic test results, and for general
203
+ hukman-friendlyness, it is often desirable to sort hash table keys when dumping
204
+ it to YAML. In Ruby 1.8.x, this isn't the default. It is possible to introduce
205
+ this behavior using the following hack:
206
+
207
+ [[lib/olag/hash_sorted_yaml.rb|named_chunk_with_containers]]
208
+
209
+ Here is a simple test demonstrating using it:
210
+
211
+ [[test/sorted_keys.rb|named_chunk_with_containers]]
212
+
200
213
  ### Collecting errors ###
201
214
 
202
215
  In library code, it is bad practice to terminate the program on an error.
@@ -0,0 +1,43 @@
1
+ require "yaml"
2
+
3
+ if RUBY_VERSION.include?("1.8")
4
+
5
+ # Modify the hash class to emit YAML sorted keys. This is an ugly hack,
6
+ # specifically for Ruby 1.8.*.
7
+ class Hash
8
+
9
+ # Provide access to the old, unsorted implementation.
10
+ alias :unsorted_to_yaml :to_yaml
11
+
12
+ # Return the hash in YAML format with sorted keys.
13
+ def to_yaml(opts = {})
14
+ YAML::quick_emit(self, opts) do |out|
15
+ out.map(taguri, to_yaml_style) do |map|
16
+ to_yaml_sorted_keys.each do |key|
17
+ map.add(key, fetch(key))
18
+ end
19
+ end
20
+ end
21
+ end
22
+
23
+ # Return the hash keys, sorted for emitting into YAML.
24
+ def to_yaml_sorted_keys
25
+ begin
26
+ return keys.sort
27
+ rescue
28
+ return to_yaml_lexicographically_sorted_keys
29
+ end
30
+ end
31
+
32
+ # Return the hash keys, sorted lexicographically for emitting into YAML.
33
+ def to_yaml_lexicographically_sorted_keys
34
+ begin
35
+ return keys.sort_by {|key| key.to_s}
36
+ rescue
37
+ return keys
38
+ end
39
+ end
40
+
41
+ end
42
+
43
+ end
@@ -3,6 +3,6 @@ module Olag
3
3
 
4
4
  # This version number. The third number is automatically updated to track the
5
5
  # number of Git commits by running <tt>rake version</tt>.
6
- VERSION = "0.1.16"
6
+ VERSION = "0.1.17"
7
7
 
8
8
  end
@@ -0,0 +1,69 @@
1
+ require "olag/hash_sorted_yaml"
2
+ require "test/spec"
3
+
4
+ # An uncomparable class. Keys of this class will cause the Hash to be emitted
5
+ # in string sort order.
6
+ class Uncomparable
7
+
8
+ def initialize(value)
9
+ @value = value
10
+ end
11
+
12
+ def to_yaml(opts = {})
13
+ return @value.to_yaml(opts)
14
+ end
15
+
16
+ def to_s
17
+ return @value.to_s
18
+ end
19
+
20
+ %w(<=> < <= >= >).each do |operator|
21
+ define_method(operator) { raise "Prevent operator: #{operator}" }
22
+ end
23
+
24
+ end
25
+
26
+ # An uncomparable class that can't be converted to a string. Keys of this class
27
+ # will cause the Hash to be emitted in unsorted order.
28
+ class Unsortable < Uncomparable
29
+
30
+ def to_s
31
+ raise "Prevent conversion to string as well."
32
+ end
33
+
34
+ end
35
+
36
+ # Test sorting keys of YAML generated from Hash tables.
37
+ class TestSortedKeys < ::Test::Unit::TestCase
38
+
39
+ SORTED_NUMERICALLY = <<-EOF.unindent
40
+ ---
41
+ 2: 2
42
+ 4: 4
43
+ 11: 1
44
+ 33: 3
45
+ EOF
46
+
47
+ SORTED_LEXICOGRAPHICALLY = <<-EOF.unindent
48
+ ---
49
+ 11: 1
50
+ 2: 2
51
+ 33: 3
52
+ 4: 4
53
+ EOF
54
+
55
+ def test_sortable_keys
56
+ { 2 => 2, 4 => 4, 11 => 1, 33 => 3 }.to_yaml.gsub(/ +$/, "").should == SORTED_NUMERICALLY
57
+ end
58
+
59
+ def test_uncomparable_keys
60
+ { Uncomparable.new(11) => 1, 2 => 2, 33 => 3, 4 => 4 }.to_yaml.gsub(/ +$/, "").should == SORTED_LEXICOGRAPHICALLY
61
+ end
62
+
63
+ def test_unsortable_keys
64
+ yaml_should_not = { Unsortable.new(11) => 1, 2 => 2, 33 => 3, 4 => 4 }.to_yaml.gsub(/ +$/, "").should.not
65
+ yaml_should_not == SORTED_NUMERICALLY
66
+ yaml_should_not == SORTED_LEXICOGRAPHICALLY
67
+ end
68
+
69
+ end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: olag
3
3
  version: !ruby/object:Gem::Version
4
- hash: 59
4
+ hash: 57
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
8
  - 1
9
- - 16
10
- version: 0.1.16
9
+ - 17
10
+ version: 0.1.17
11
11
  platform: ruby
12
12
  authors:
13
13
  - Oren Ben-Kiki
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2012-01-15 00:00:00 Z
18
+ date: 2012-01-17 00:00:00 Z
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
21
21
  name: Saikuro
@@ -174,6 +174,7 @@ files:
174
174
  - lib/olag/errors.rb
175
175
  - lib/olag/gem_specification.rb
176
176
  - lib/olag/globals.rb
177
+ - lib/olag/hash_sorted_yaml.rb
177
178
  - lib/olag/hash_struct.rb
178
179
  - lib/olag/rake.rb
179
180
  - lib/olag/string_unindent.rb
@@ -193,6 +194,7 @@ files:
193
194
  - test/collect_errors.rb
194
195
  - test/missing_keys.rb
195
196
  - test/run_application.rb
197
+ - test/sorted_keys.rb
196
198
  - test/unindent_text.rb
197
199
  - README.rdoc
198
200
  - LICENSE
@@ -203,7 +205,7 @@ licenses: []
203
205
  post_install_message:
204
206
  rdoc_options:
205
207
  - --title
206
- - Olag 0.1.16
208
+ - Olag 0.1.17
207
209
  - --main
208
210
  - README.rdoc
209
211
  - --line-numbers
@@ -241,4 +243,5 @@ test_files:
241
243
  - test/collect_errors.rb
242
244
  - test/missing_keys.rb
243
245
  - test/run_application.rb
246
+ - test/sorted_keys.rb
244
247
  - test/unindent_text.rb