treequel 1.0.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.
- data/ChangeLog +354 -0
- data/LICENSE +27 -0
- data/README +66 -0
- data/Rakefile +345 -0
- data/Rakefile.local +43 -0
- data/bin/treeirb +14 -0
- data/bin/treequel +229 -0
- data/examples/company-directory.rb +112 -0
- data/examples/ldap-monitor.rb +143 -0
- data/examples/ldap-monitor/public/css/master.css +328 -0
- data/examples/ldap-monitor/public/images/card_small.png +0 -0
- data/examples/ldap-monitor/public/images/chain_small.png +0 -0
- data/examples/ldap-monitor/public/images/globe_small.png +0 -0
- data/examples/ldap-monitor/public/images/globe_small_green.png +0 -0
- data/examples/ldap-monitor/public/images/plug.png +0 -0
- data/examples/ldap-monitor/public/images/shadows/large-30-down.png +0 -0
- data/examples/ldap-monitor/public/images/tick.png +0 -0
- data/examples/ldap-monitor/public/images/tick_circle.png +0 -0
- data/examples/ldap-monitor/public/images/treequel-favicon.png +0 -0
- data/examples/ldap-monitor/views/backends.erb +41 -0
- data/examples/ldap-monitor/views/connections.erb +74 -0
- data/examples/ldap-monitor/views/databases.erb +39 -0
- data/examples/ldap-monitor/views/dump_subsystem.erb +14 -0
- data/examples/ldap-monitor/views/index.erb +14 -0
- data/examples/ldap-monitor/views/layout.erb +35 -0
- data/examples/ldap-monitor/views/listeners.erb +30 -0
- data/examples/ldap_state.rb +62 -0
- data/lib/treequel.rb +145 -0
- data/lib/treequel/branch.rb +589 -0
- data/lib/treequel/branchcollection.rb +204 -0
- data/lib/treequel/branchset.rb +360 -0
- data/lib/treequel/constants.rb +604 -0
- data/lib/treequel/directory.rb +541 -0
- data/lib/treequel/exceptions.rb +32 -0
- data/lib/treequel/filter.rb +704 -0
- data/lib/treequel/mixins.rb +325 -0
- data/lib/treequel/schema.rb +245 -0
- data/lib/treequel/schema/attributetype.rb +252 -0
- data/lib/treequel/schema/ldapsyntax.rb +96 -0
- data/lib/treequel/schema/matchingrule.rb +124 -0
- data/lib/treequel/schema/matchingruleuse.rb +124 -0
- data/lib/treequel/schema/objectclass.rb +289 -0
- data/lib/treequel/sequel_integration.rb +26 -0
- data/lib/treequel/utils.rb +169 -0
- data/rake/191_compat.rb +26 -0
- data/rake/dependencies.rb +76 -0
- data/rake/helpers.rb +434 -0
- data/rake/hg.rb +261 -0
- data/rake/manual.rb +782 -0
- data/rake/packaging.rb +135 -0
- data/rake/publishing.rb +318 -0
- data/rake/rdoc.rb +30 -0
- data/rake/style.rb +62 -0
- data/rake/svn.rb +668 -0
- data/rake/testing.rb +187 -0
- data/rake/verifytask.rb +64 -0
- data/rake/win32.rb +190 -0
- data/spec/lib/constants.rb +93 -0
- data/spec/lib/helpers.rb +100 -0
- data/spec/treequel/branch_spec.rb +569 -0
- data/spec/treequel/branchcollection_spec.rb +213 -0
- data/spec/treequel/branchset_spec.rb +376 -0
- data/spec/treequel/directory_spec.rb +487 -0
- data/spec/treequel/filter_spec.rb +482 -0
- data/spec/treequel/mixins_spec.rb +330 -0
- data/spec/treequel/schema/attributetype_spec.rb +237 -0
- data/spec/treequel/schema/ldapsyntax_spec.rb +83 -0
- data/spec/treequel/schema/matchingrule_spec.rb +158 -0
- data/spec/treequel/schema/matchingruleuse_spec.rb +137 -0
- data/spec/treequel/schema/objectclass_spec.rb +262 -0
- data/spec/treequel/schema_spec.rb +118 -0
- data/spec/treequel/utils_spec.rb +49 -0
- data/spec/treequel_spec.rb +179 -0
- metadata +169 -0
@@ -0,0 +1,83 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
BEGIN {
|
4
|
+
require 'pathname'
|
5
|
+
basedir = Pathname.new( __FILE__ ).dirname.parent.parent.parent
|
6
|
+
|
7
|
+
libdir = basedir + "lib"
|
8
|
+
|
9
|
+
$LOAD_PATH.unshift( libdir ) unless $LOAD_PATH.include?( libdir )
|
10
|
+
}
|
11
|
+
|
12
|
+
require 'spec'
|
13
|
+
require 'spec/lib/constants'
|
14
|
+
require 'spec/lib/helpers'
|
15
|
+
|
16
|
+
require 'yaml'
|
17
|
+
require 'ldap'
|
18
|
+
require 'ldap/schema'
|
19
|
+
require 'treequel/schema/ldapsyntax'
|
20
|
+
|
21
|
+
|
22
|
+
include Treequel::TestConstants
|
23
|
+
|
24
|
+
#####################################################################
|
25
|
+
### C O N T E X T S
|
26
|
+
#####################################################################
|
27
|
+
|
28
|
+
describe Treequel::Schema::LDAPSyntax do
|
29
|
+
include Treequel::SpecHelpers
|
30
|
+
|
31
|
+
|
32
|
+
before( :all ) do
|
33
|
+
setup_logging( :fatal )
|
34
|
+
end
|
35
|
+
|
36
|
+
before( :each ) do
|
37
|
+
@schema = mock( "treequel schema object" )
|
38
|
+
end
|
39
|
+
|
40
|
+
after( :all ) do
|
41
|
+
reset_logging()
|
42
|
+
end
|
43
|
+
|
44
|
+
|
45
|
+
describe "parsed from the 'Boolean' syntax" do
|
46
|
+
|
47
|
+
BOOLEAN_SYNTAX = %{( 1.3.6.1.4.1.1466.115.121.1.7 DESC 'Boolean' )}
|
48
|
+
|
49
|
+
before( :each ) do
|
50
|
+
@syntax = Treequel::Schema::LDAPSyntax.parse( @schema, BOOLEAN_SYNTAX )
|
51
|
+
end
|
52
|
+
|
53
|
+
it "knows what its OID is" do
|
54
|
+
@syntax.oid.should == '1.3.6.1.4.1.1466.115.121.1.7'
|
55
|
+
end
|
56
|
+
|
57
|
+
it "knows what its DESC attribute is" do
|
58
|
+
@syntax.desc.should == 'Boolean'
|
59
|
+
end
|
60
|
+
|
61
|
+
end
|
62
|
+
|
63
|
+
|
64
|
+
describe "parsed from a syntax with no DESC" do
|
65
|
+
NODESC_SYNTAX = %{( 1.3.6.1.4.1.1466.115.121.1.14 )}
|
66
|
+
|
67
|
+
before( :each ) do
|
68
|
+
@syntax = Treequel::Schema::LDAPSyntax.parse( @schema, NODESC_SYNTAX )
|
69
|
+
end
|
70
|
+
|
71
|
+
it "knows what its OID is" do
|
72
|
+
@syntax.oid.should == '1.3.6.1.4.1.1466.115.121.1.14'
|
73
|
+
end
|
74
|
+
|
75
|
+
it "knows that it doesn't have a DESC attribute" do
|
76
|
+
@syntax.desc.should be_nil()
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
end
|
81
|
+
|
82
|
+
|
83
|
+
# vim: set nosta noet ts=4 sw=4:
|
@@ -0,0 +1,158 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
BEGIN {
|
4
|
+
require 'pathname'
|
5
|
+
basedir = Pathname.new( __FILE__ ).dirname.parent.parent.parent
|
6
|
+
|
7
|
+
libdir = basedir + "lib"
|
8
|
+
|
9
|
+
$LOAD_PATH.unshift( libdir ) unless $LOAD_PATH.include?( libdir )
|
10
|
+
}
|
11
|
+
|
12
|
+
require 'spec'
|
13
|
+
require 'spec/lib/constants'
|
14
|
+
require 'spec/lib/helpers'
|
15
|
+
|
16
|
+
require 'yaml'
|
17
|
+
require 'ldap'
|
18
|
+
require 'ldap/schema'
|
19
|
+
require 'treequel/schema/matchingrule'
|
20
|
+
|
21
|
+
|
22
|
+
include Treequel::TestConstants
|
23
|
+
include Treequel::Constants
|
24
|
+
|
25
|
+
#####################################################################
|
26
|
+
### C O N T E X T S
|
27
|
+
#####################################################################
|
28
|
+
|
29
|
+
describe Treequel::Schema::MatchingRule do
|
30
|
+
include Treequel::SpecHelpers
|
31
|
+
|
32
|
+
|
33
|
+
before( :all ) do
|
34
|
+
setup_logging( :fatal )
|
35
|
+
@datadir = Pathname( __FILE__ ).dirname.parent.parent + 'data'
|
36
|
+
end
|
37
|
+
|
38
|
+
before( :each ) do
|
39
|
+
@schema = mock( "treequel schema object" )
|
40
|
+
end
|
41
|
+
|
42
|
+
after( :all ) do
|
43
|
+
reset_logging()
|
44
|
+
end
|
45
|
+
|
46
|
+
|
47
|
+
describe "parsed from the 'octetStringMatch' matchingRule" do
|
48
|
+
|
49
|
+
OCTETSTRINGMATCH_RULE = %{( 2.5.13.17 NAME 'octetStringMatch' SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 )}
|
50
|
+
|
51
|
+
before( :each ) do
|
52
|
+
@rule = Treequel::Schema::MatchingRule.parse( @schema, OCTETSTRINGMATCH_RULE )
|
53
|
+
end
|
54
|
+
|
55
|
+
it "knows what OID corresponds to the type" do
|
56
|
+
@rule.oid.should == '2.5.13.17'
|
57
|
+
end
|
58
|
+
|
59
|
+
it "knows what its NAME attribute is" do
|
60
|
+
@rule.name.should == :octetStringMatch
|
61
|
+
end
|
62
|
+
|
63
|
+
it "knows what its SYNTAX OID is" do
|
64
|
+
@rule.syntax_oid.should == '1.3.6.1.4.1.1466.115.121.1.40'
|
65
|
+
end
|
66
|
+
|
67
|
+
it "knows what its syntax is" do
|
68
|
+
@schema.should_receive( :ldap_syntaxes ).
|
69
|
+
and_return({ '1.3.6.1.4.1.1466.115.121.1.40' => :the_syntax })
|
70
|
+
@rule.syntax.should == :the_syntax
|
71
|
+
end
|
72
|
+
|
73
|
+
it "knows that it is not obsolete" do
|
74
|
+
@rule.should_not be_obsolete()
|
75
|
+
end
|
76
|
+
|
77
|
+
end
|
78
|
+
|
79
|
+
describe "parsed from an matchingRule that has a DESC attribute" do
|
80
|
+
|
81
|
+
DESCRIBED_RULE = %{( 9.9.9.9.9 DESC 'Hot dog propulsion device' SYNTAX 9.9.9.9.9.9 )}
|
82
|
+
|
83
|
+
before( :each ) do
|
84
|
+
@rule = Treequel::Schema::MatchingRule.parse( @schema, DESCRIBED_RULE )
|
85
|
+
end
|
86
|
+
|
87
|
+
it "knows what its DESC attribute" do
|
88
|
+
@rule.desc.should == 'Hot dog propulsion device'
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
|
93
|
+
describe "parsed from an matchingRule that doesn't have a NAME attribute" do
|
94
|
+
|
95
|
+
ANONYMOUS_RULE = %{( 9.9.9.9.9 SYNTAX 9.9.9.9.9.9 )}
|
96
|
+
|
97
|
+
before( :each ) do
|
98
|
+
@rule = Treequel::Schema::MatchingRule.parse( @schema, ANONYMOUS_RULE )
|
99
|
+
end
|
100
|
+
|
101
|
+
it "knows that its NAME is nil" do
|
102
|
+
@rule.name.should be_nil()
|
103
|
+
end
|
104
|
+
|
105
|
+
end
|
106
|
+
|
107
|
+
describe "parsed from an matchingRule that has a list as the value of its NAME attribute" do
|
108
|
+
|
109
|
+
MULTINAME_MATCHINGRULE = %{( 1.1.1.1 NAME ('firstname' 'secondname') SYNTAX 9.9.9.9.9.9 )}
|
110
|
+
|
111
|
+
before( :each ) do
|
112
|
+
@rule = Treequel::Schema::MatchingRule.parse( @schema, MULTINAME_MATCHINGRULE )
|
113
|
+
end
|
114
|
+
|
115
|
+
it "knows what both names are" do
|
116
|
+
@rule.names.should have(2).members
|
117
|
+
@rule.names.should include( :firstname, :secondname )
|
118
|
+
end
|
119
|
+
|
120
|
+
it "returns the first of its names for the #name method" do
|
121
|
+
@rule.name.should == :firstname
|
122
|
+
end
|
123
|
+
|
124
|
+
end
|
125
|
+
|
126
|
+
describe "parsed from an matchingRule that has escaped characters in its DESC attribute" do
|
127
|
+
|
128
|
+
ESCAPED_DESC_MATCHINGRULE = %{( 1.1.1.1 DESC } +
|
129
|
+
%{'This spec\\27s example, which includes a \\5c character.' SYNTAX 9.9.9.9.9.9 )}
|
130
|
+
|
131
|
+
before( :each ) do
|
132
|
+
@rule = Treequel::Schema::MatchingRule.parse( @schema, ESCAPED_DESC_MATCHINGRULE )
|
133
|
+
end
|
134
|
+
|
135
|
+
it "unscapes the escaped characters" do
|
136
|
+
@rule.desc.should == %{This spec's example, which includes a \\ character.}
|
137
|
+
end
|
138
|
+
|
139
|
+
end
|
140
|
+
|
141
|
+
describe "parsed from an matchingRule that has the OBSOLETE attribute" do
|
142
|
+
|
143
|
+
OBSOLETE_MATCHINGRULE = %{( 1.1.1.1 OBSOLETE SYNTAX 9.9.9.9.9.9 )}
|
144
|
+
|
145
|
+
before( :each ) do
|
146
|
+
@rule = Treequel::Schema::MatchingRule.parse( @schema, OBSOLETE_MATCHINGRULE )
|
147
|
+
end
|
148
|
+
|
149
|
+
it "knows that it's obsolete" do
|
150
|
+
@rule.should be_obsolete()
|
151
|
+
end
|
152
|
+
|
153
|
+
end
|
154
|
+
|
155
|
+
end
|
156
|
+
|
157
|
+
|
158
|
+
# vim: set nosta noet ts=4 sw=4:
|
@@ -0,0 +1,137 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
BEGIN {
|
4
|
+
require 'pathname'
|
5
|
+
basedir = Pathname.new( __FILE__ ).dirname.parent.parent.parent
|
6
|
+
|
7
|
+
libdir = basedir + "lib"
|
8
|
+
|
9
|
+
$LOAD_PATH.unshift( libdir ) unless $LOAD_PATH.include?( libdir )
|
10
|
+
}
|
11
|
+
|
12
|
+
require 'spec'
|
13
|
+
require 'spec/lib/constants'
|
14
|
+
require 'spec/lib/helpers'
|
15
|
+
|
16
|
+
require 'yaml'
|
17
|
+
require 'ldap'
|
18
|
+
require 'ldap/schema'
|
19
|
+
require 'treequel/schema/matchingruleuse'
|
20
|
+
|
21
|
+
|
22
|
+
include Treequel::TestConstants
|
23
|
+
include Treequel::Constants
|
24
|
+
|
25
|
+
#####################################################################
|
26
|
+
### C O N T E X T S
|
27
|
+
#####################################################################
|
28
|
+
|
29
|
+
describe Treequel::Schema::MatchingRuleUse do
|
30
|
+
include Treequel::SpecHelpers
|
31
|
+
|
32
|
+
|
33
|
+
before( :all ) do
|
34
|
+
setup_logging( :fatal )
|
35
|
+
@datadir = Pathname( __FILE__ ).dirname.parent.parent + 'data'
|
36
|
+
end
|
37
|
+
|
38
|
+
before( :each ) do
|
39
|
+
@schema = mock( "treequel schema object" )
|
40
|
+
end
|
41
|
+
|
42
|
+
after( :all ) do
|
43
|
+
reset_logging()
|
44
|
+
end
|
45
|
+
|
46
|
+
|
47
|
+
describe "parsed from the 'uniqueMemberMatch' matchingRuleUse" do
|
48
|
+
|
49
|
+
UNIQUE_MEMBER_MATCH_DESC = %{( 2.5.13.23 NAME 'uniqueMemberMatch' APPLIES uniqueMember )}
|
50
|
+
|
51
|
+
before( :each ) do
|
52
|
+
@ruleuse = Treequel::Schema::MatchingRuleUse.parse( @schema, UNIQUE_MEMBER_MATCH_DESC )
|
53
|
+
end
|
54
|
+
|
55
|
+
it "knows what its OID is" do
|
56
|
+
@ruleuse.oid.should == '2.5.13.23'
|
57
|
+
end
|
58
|
+
|
59
|
+
it "knows what its NAME attribute is" do
|
60
|
+
@ruleuse.name.should == :uniqueMemberMatch
|
61
|
+
end
|
62
|
+
|
63
|
+
it "knows that it is not obsolete" do
|
64
|
+
@ruleuse.should_not be_obsolete()
|
65
|
+
end
|
66
|
+
|
67
|
+
it "knows what the OIDs of the attribute types it applies to are" do
|
68
|
+
@ruleuse.attr_oids.should == [:uniqueMember]
|
69
|
+
end
|
70
|
+
|
71
|
+
it "knows what Treequel::Schema::AttributeType objects it applies to are" do
|
72
|
+
@schema.should_receive( :attribute_types ).
|
73
|
+
and_return({ :uniqueMember => :a_attrtype_object })
|
74
|
+
@ruleuse.attribute_types.should == [ :a_attrtype_object ]
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
|
79
|
+
describe "parsed from a matchingRuleUse with a DESC attribute" do
|
80
|
+
DESCRIPTIVE_MATCHRULEUSE_DESC = %{( 9.9.9.9.9 DESC 'Woop' APPLIES uniqueMember )}
|
81
|
+
|
82
|
+
before( :each ) do
|
83
|
+
@ruleuse = Treequel::Schema::MatchingRuleUse.parse( @schema, DESCRIPTIVE_MATCHRULEUSE_DESC )
|
84
|
+
end
|
85
|
+
|
86
|
+
it "knows what its description is" do
|
87
|
+
@ruleuse.desc.should == "Woop"
|
88
|
+
end
|
89
|
+
|
90
|
+
end
|
91
|
+
|
92
|
+
|
93
|
+
describe "parsed from a matchingRuleUse with more than one applicable attribute type" do
|
94
|
+
PHONENUMBER_MATCHRULEUSE_DESC = %{( 2.5.13.20 NAME 'telephoneNumberMatch' APPLIES } +
|
95
|
+
%{( telephoneNumber $ homePhone $ mobile $ pager ) )}
|
96
|
+
|
97
|
+
before( :each ) do
|
98
|
+
@ruleuse = Treequel::Schema::MatchingRuleUse.parse( @schema, PHONENUMBER_MATCHRULEUSE_DESC )
|
99
|
+
end
|
100
|
+
|
101
|
+
it "knows what the OIDs of the attribute types it applies to are" do
|
102
|
+
@ruleuse.attr_oids.should have(4).members
|
103
|
+
@ruleuse.attr_oids.should include( :telephoneNumber, :homePhone, :mobile, :pager )
|
104
|
+
end
|
105
|
+
|
106
|
+
it "knows what Treequel::Schema::AttributeType objects it applies to are" do
|
107
|
+
oidmap = {
|
108
|
+
:telephoneNumber => :phone_number_attr,
|
109
|
+
:homePhone => :home_phone_attr,
|
110
|
+
:mobile => :mobile_attr,
|
111
|
+
:pager => :pager_attr,
|
112
|
+
}
|
113
|
+
@schema.should_receive( :attribute_types ).at_least( 4 ).times.
|
114
|
+
and_return( oidmap )
|
115
|
+
@ruleuse.attribute_types.should have(4).members
|
116
|
+
@ruleuse.attribute_types.should include( *oidmap.values )
|
117
|
+
end
|
118
|
+
end
|
119
|
+
|
120
|
+
|
121
|
+
describe "parsed from a matchingRuleUse that is marked as OBSOLETE" do
|
122
|
+
OBSOLETE_MATCHRULEUSE_DESC = %{( 9.9.9.9.9 OBSOLETE APPLIES uniqueMember )}
|
123
|
+
|
124
|
+
before( :each ) do
|
125
|
+
@ruleuse = Treequel::Schema::MatchingRuleUse.parse( @schema, OBSOLETE_MATCHRULEUSE_DESC )
|
126
|
+
end
|
127
|
+
|
128
|
+
it "knows that it's obsolete" do
|
129
|
+
@ruleuse.should be_obsolete()
|
130
|
+
end
|
131
|
+
|
132
|
+
end
|
133
|
+
|
134
|
+
end
|
135
|
+
|
136
|
+
|
137
|
+
# vim: set nosta noet ts=4 sw=4:
|
@@ -0,0 +1,262 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
BEGIN {
|
4
|
+
require 'pathname'
|
5
|
+
basedir = Pathname.new( __FILE__ ).dirname.parent.parent.parent
|
6
|
+
|
7
|
+
libdir = basedir + "lib"
|
8
|
+
|
9
|
+
$LOAD_PATH.unshift( libdir ) unless $LOAD_PATH.include?( libdir )
|
10
|
+
}
|
11
|
+
|
12
|
+
begin
|
13
|
+
require 'spec'
|
14
|
+
require 'spec/lib/constants'
|
15
|
+
require 'spec/lib/helpers'
|
16
|
+
|
17
|
+
require 'yaml'
|
18
|
+
require 'ldap'
|
19
|
+
require 'ldap/schema'
|
20
|
+
require 'treequel/schema/objectclass'
|
21
|
+
require 'treequel/schema/attributetype'
|
22
|
+
rescue LoadError
|
23
|
+
unless Object.const_defined?( :Gem )
|
24
|
+
require 'rubygems'
|
25
|
+
retry
|
26
|
+
end
|
27
|
+
raise
|
28
|
+
end
|
29
|
+
|
30
|
+
|
31
|
+
include Treequel::TestConstants
|
32
|
+
include Treequel::Constants
|
33
|
+
|
34
|
+
#####################################################################
|
35
|
+
### C O N T E X T S
|
36
|
+
#####################################################################
|
37
|
+
|
38
|
+
describe Treequel::Schema::ObjectClass do
|
39
|
+
include Treequel::SpecHelpers
|
40
|
+
|
41
|
+
|
42
|
+
before( :all ) do
|
43
|
+
setup_logging( :fatal )
|
44
|
+
@datadir = Pathname( __FILE__ ).dirname.parent.parent + 'data'
|
45
|
+
end
|
46
|
+
|
47
|
+
before( :each ) do
|
48
|
+
@schema = mock( "Treequel schema" )
|
49
|
+
end
|
50
|
+
|
51
|
+
after( :all ) do
|
52
|
+
reset_logging()
|
53
|
+
end
|
54
|
+
|
55
|
+
|
56
|
+
describe "parsed from the 'top' objectClass" do
|
57
|
+
|
58
|
+
TOP_OBJECTCLASS = %{( 2.5.6.0 NAME 'top' DESC 'top of the superclass chain' ABSTRACT } +
|
59
|
+
%{MUST objectClass )}
|
60
|
+
|
61
|
+
before( :each ) do
|
62
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, TOP_OBJECTCLASS )
|
63
|
+
end
|
64
|
+
|
65
|
+
it "is an AbstractObjectClass because its 'kind' is 'ABSTRACT'" do
|
66
|
+
@oc.should be_an_instance_of( Treequel::Schema::AbstractObjectClass )
|
67
|
+
end
|
68
|
+
|
69
|
+
it "knows what OID corresponds to the class" do
|
70
|
+
@oc.oid.should == '2.5.6.0'
|
71
|
+
end
|
72
|
+
|
73
|
+
it "knows what its NAME attribute is" do
|
74
|
+
@oc.name.should == :top
|
75
|
+
end
|
76
|
+
|
77
|
+
it "knows what its DESC attribute is" do
|
78
|
+
@oc.desc.should == 'top of the superclass chain'
|
79
|
+
end
|
80
|
+
|
81
|
+
it "knows that it has one MUST attribute" do
|
82
|
+
@oc.must_oids.should have( 1 ).member
|
83
|
+
@oc.must_oids.should == [ :objectClass ]
|
84
|
+
end
|
85
|
+
|
86
|
+
it "returns attribute objects for its MUST OIDs" do
|
87
|
+
@schema.should_receive( :attribute_types ).at_least( :once ).
|
88
|
+
and_return({ :objectClass => :attribute_type })
|
89
|
+
|
90
|
+
@oc.must.should have( 1 ).member
|
91
|
+
@oc.must.should == [ :attribute_type ]
|
92
|
+
end
|
93
|
+
|
94
|
+
it "returns attribute objects for its MAY OIDs" do
|
95
|
+
@schema.should_receive( :attribute_types ).at_least( :once ).
|
96
|
+
and_return({ :objectClass => :attribute_type })
|
97
|
+
|
98
|
+
@oc.must.should have( 1 ).member
|
99
|
+
@oc.must.should == [ :attribute_type ]
|
100
|
+
end
|
101
|
+
|
102
|
+
it "knows that it doesn't have any MAY attributes" do
|
103
|
+
@oc.may_oids.should be_empty()
|
104
|
+
end
|
105
|
+
|
106
|
+
it "knows that it is not obsolete" do
|
107
|
+
@oc.should_not be_obsolete()
|
108
|
+
end
|
109
|
+
|
110
|
+
it "knows that it doesn't have a superclass" do
|
111
|
+
@oc.sup.should be_nil()
|
112
|
+
end
|
113
|
+
|
114
|
+
end
|
115
|
+
|
116
|
+
|
117
|
+
describe "parsed from the 'organizationalUnit' objectClass" do
|
118
|
+
|
119
|
+
OU_OBJECTCLASS = %{( 2.5.6.5 NAME 'organizationalUnit' } +
|
120
|
+
%{DESC 'RFC2256: an organizational unit' SUP top STRUCTURAL } +
|
121
|
+
%{MUST ou MAY ( userPassword $ searchGuide $ seeAlso $ } +
|
122
|
+
%{businessCategory $ x121Address $ registeredAddress $ } +
|
123
|
+
%{destinationIndicator $ preferredDeliveryMethod $ telexNumber $ } +
|
124
|
+
%{teletexTerminalIdentifier $ telephoneNumber $ internationaliSDNNumber $ } +
|
125
|
+
%{facsimileTelephoneNumber $ street $ postOfficeBox $ postalCode $ postalAddress $ } +
|
126
|
+
%{physicalDeliveryOfficeName $ st $ l $ description ) )}
|
127
|
+
|
128
|
+
before( :each ) do
|
129
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, OU_OBJECTCLASS )
|
130
|
+
end
|
131
|
+
|
132
|
+
it "is a StructuralObjectClass because its kind is 'STRUCTURAL'" do
|
133
|
+
@oc.should be_an_instance_of( Treequel::Schema::StructuralObjectClass )
|
134
|
+
end
|
135
|
+
|
136
|
+
it "knows what OID corresponds to the class" do
|
137
|
+
@oc.oid.should == '2.5.6.5'
|
138
|
+
end
|
139
|
+
|
140
|
+
it "knows what its NAME attribute is" do
|
141
|
+
@oc.name.should == :organizationalUnit
|
142
|
+
end
|
143
|
+
|
144
|
+
it "knows what its DESC attribute is" do
|
145
|
+
@oc.desc.should == 'RFC2256: an organizational unit'
|
146
|
+
end
|
147
|
+
|
148
|
+
it "knows that it has one MUST attribute" do
|
149
|
+
@oc.must_oids.should have( 1 ).member
|
150
|
+
@oc.must_oids.should == [ :ou ]
|
151
|
+
end
|
152
|
+
|
153
|
+
it "knows what its MAY attributes are" do
|
154
|
+
@oc.may_oids.should have( 21 ).members
|
155
|
+
@oc.may_oids.should include( :userPassword, :searchGuide, :seeAlso, :businessCategory,
|
156
|
+
:x121Address, :registeredAddress, :destinationIndicator, :preferredDeliveryMethod,
|
157
|
+
:telexNumber, :teletexTerminalIdentifier, :telephoneNumber, :internationaliSDNNumber,
|
158
|
+
:facsimileTelephoneNumber, :street, :postOfficeBox, :postalCode, :postalAddress,
|
159
|
+
:physicalDeliveryOfficeName, :st, :l, :description )
|
160
|
+
end
|
161
|
+
|
162
|
+
end
|
163
|
+
|
164
|
+
|
165
|
+
describe "parsed from an objectClass that doesn't specify an explicit KIND attribute" do
|
166
|
+
|
167
|
+
KINDLESS_OBJECTCLASS = %{( 1.1.1.1 )}
|
168
|
+
|
169
|
+
before( :each ) do
|
170
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, KINDLESS_OBJECTCLASS )
|
171
|
+
end
|
172
|
+
|
173
|
+
it "is the default kind (STRUCTURAL)" do
|
174
|
+
@oc.should be_an_instance_of( Treequel::Schema::StructuralObjectClass )
|
175
|
+
end
|
176
|
+
|
177
|
+
end
|
178
|
+
|
179
|
+
describe "parsed from an objectClass that has a list as the value of its NAME attribute" do
|
180
|
+
|
181
|
+
MULTINAME_OBJECTCLASS = %{( 1.1.1.1 NAME ('firstname' 'secondname') )}
|
182
|
+
|
183
|
+
before( :each ) do
|
184
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, MULTINAME_OBJECTCLASS )
|
185
|
+
end
|
186
|
+
|
187
|
+
it "knows what both names are" do
|
188
|
+
@oc.names.should have(2).members
|
189
|
+
@oc.names.should include( :firstname, :secondname )
|
190
|
+
end
|
191
|
+
|
192
|
+
it "returns the first of its names for the #name method" do
|
193
|
+
@oc.name.should == :firstname
|
194
|
+
end
|
195
|
+
|
196
|
+
end
|
197
|
+
|
198
|
+
describe "parsed from an objectClass that has escaped characters in its DESC attribute" do
|
199
|
+
|
200
|
+
ESCAPED_DESC_OBJECTCLASS = %{( 1.1.1.1 DESC } +
|
201
|
+
%{'This spec\\27s example, which includes a \\5c character.' )}
|
202
|
+
|
203
|
+
before( :each ) do
|
204
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, ESCAPED_DESC_OBJECTCLASS )
|
205
|
+
end
|
206
|
+
|
207
|
+
it "unscapes the escaped characters" do
|
208
|
+
@oc.desc.should == %{This spec's example, which includes a \\ character.}
|
209
|
+
end
|
210
|
+
|
211
|
+
end
|
212
|
+
|
213
|
+
describe "parsed from an objectClass that has the OBSOLETE attribute" do
|
214
|
+
|
215
|
+
OBSOLETE_OBJECTCLASS = %{( 1.1.1.1 OBSOLETE )}
|
216
|
+
|
217
|
+
before( :each ) do
|
218
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, OBSOLETE_OBJECTCLASS )
|
219
|
+
end
|
220
|
+
|
221
|
+
it "knows that it's obsolete" do
|
222
|
+
@oc.should be_obsolete()
|
223
|
+
end
|
224
|
+
|
225
|
+
end
|
226
|
+
|
227
|
+
describe "parsed from an objectClass that has organizationalPerson as its SUP" do
|
228
|
+
|
229
|
+
SUB_OBJECTCLASS = %{( 1.1.1.1 SUP organizationalPerson )}
|
230
|
+
|
231
|
+
before( :each ) do
|
232
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, SUB_OBJECTCLASS )
|
233
|
+
end
|
234
|
+
|
235
|
+
it "returns the corresponding objectClass from its schema" do
|
236
|
+
@schema.should_receive( :object_classes ).
|
237
|
+
and_return({ :organizationalPerson => :organizationalPerson_objectclass })
|
238
|
+
@oc.sup.should == :organizationalPerson_objectclass
|
239
|
+
end
|
240
|
+
|
241
|
+
end
|
242
|
+
|
243
|
+
describe "parsed from an objectClass that has no explicit SUP" do
|
244
|
+
|
245
|
+
ORPHAN_OBJECTCLASS = %{( 1.1.1.1 )}
|
246
|
+
|
247
|
+
before( :each ) do
|
248
|
+
@oc = Treequel::Schema::ObjectClass.parse( @schema, ORPHAN_OBJECTCLASS )
|
249
|
+
end
|
250
|
+
|
251
|
+
it "returns the objectClass for 'top' from its schema" do
|
252
|
+
@schema.should_receive( :object_classes ).
|
253
|
+
and_return({ :top => :top_objectclass })
|
254
|
+
@oc.sup.should == :top_objectclass
|
255
|
+
end
|
256
|
+
|
257
|
+
end
|
258
|
+
|
259
|
+
end
|
260
|
+
|
261
|
+
|
262
|
+
# vim: set nosta noet ts=4 sw=4:
|