Skip to content
This repository was archived by the owner on May 14, 2024. It is now read-only.

Commit 824dd2c

Browse files
committed
Resolve issue #845
This issue resolves issue #845 by updating `@ldapjs/messages` to the latest version and adding a test that shows how the module should be used to evaluate search request scopes.
1 parent 0dfe40e commit 824dd2c

File tree

2 files changed

+117
-1
lines changed

2 files changed

+117
-1
lines changed

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
"@ldapjs/controls": "2.0.0",
1818
"@ldapjs/dn": "1.0.0",
1919
"@ldapjs/filter": "2.0.0",
20-
"@ldapjs/messages": "1.0.0",
20+
"@ldapjs/messages": "1.0.1",
2121
"@ldapjs/protocol": "^1.2.1",
2222
"abstract-logging": "^2.0.1",
2323
"assert-plus": "^1.0.0",

test/issue-845.test.js

Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
'use strict'
2+
3+
const tap = require('tap')
4+
const { SearchResultEntry, SearchRequest } = require('@ldapjs/messages')
5+
const ldapjs = require('../')
6+
7+
const server = ldapjs.createServer()
8+
9+
const SUFFIX = ''
10+
const directory = {
11+
'dc=example,dc=com': {
12+
objectclass: 'example',
13+
dc: 'example',
14+
cn: 'example'
15+
}
16+
}
17+
18+
server.bind(SUFFIX, (req, res, done) => {
19+
res.end()
20+
return done()
21+
})
22+
23+
server.search(SUFFIX, (req, res, done) => {
24+
const dn = req.dn.toString().toLowerCase()
25+
26+
if (Object.hasOwn(directory, dn) === false) {
27+
return done(Error('not in directory'))
28+
}
29+
30+
switch (req.scope) {
31+
case SearchRequest.SCOPE_BASE:
32+
case SearchRequest.SCOPE_SUBTREE: {
33+
res.send(new SearchResultEntry({ objectName: `dc=${req.scopeName}` }))
34+
break
35+
}
36+
}
37+
38+
res.end()
39+
done()
40+
})
41+
42+
tap.beforeEach(t => {
43+
return new Promise((resolve, reject) => {
44+
server.listen(0, '127.0.0.1', (err) => {
45+
if (err) return reject(err)
46+
t.context.url = server.url
47+
48+
t.context.client = ldapjs.createClient({ url: [server.url] })
49+
t.context.searchOpts = {
50+
filter: '(&(objectClass=*))',
51+
scope: 'sub',
52+
attributes: ['dn', 'cn']
53+
}
54+
55+
resolve()
56+
})
57+
})
58+
})
59+
60+
tap.afterEach(t => {
61+
return new Promise((resolve, reject) => {
62+
t.context.client.destroy()
63+
server.close((err) => {
64+
if (err) return reject(err)
65+
resolve()
66+
})
67+
})
68+
})
69+
70+
tap.test('rejects if search not in directory', t => {
71+
const { client, searchOpts } = t.context
72+
73+
client.search('dc=nope', searchOpts, (err, res) => {
74+
t.error(err)
75+
res.on('error', err => {
76+
// TODO: plain error messages should not be lost
77+
// This should be fixed in a revamp of the server code.
78+
// ~ jsumners 2023-03-08
79+
t.equal(err.lde_message, 'Operations Error')
80+
t.end()
81+
})
82+
})
83+
})
84+
85+
tap.test('base scope matches', t => {
86+
const { client, searchOpts } = t.context
87+
searchOpts.scope = 'base'
88+
89+
client.search('dc=example,dc=com', searchOpts, (err, res) => {
90+
t.error(err)
91+
res.on('error', (err) => {
92+
t.error(err)
93+
t.end()
94+
})
95+
res.on('searchEntry', entry => {
96+
t.equal(entry.objectName.toString(), 'dc=base')
97+
t.end()
98+
})
99+
})
100+
})
101+
102+
tap.test('sub scope matches', t => {
103+
const { client, searchOpts } = t.context
104+
105+
client.search('dc=example,dc=com', searchOpts, (err, res) => {
106+
t.error(err)
107+
res.on('error', (err) => {
108+
t.error(err)
109+
t.end()
110+
})
111+
res.on('searchEntry', entry => {
112+
t.equal(entry.objectName.toString(), 'dc=subtree')
113+
t.end()
114+
})
115+
})
116+
})

0 commit comments

Comments
 (0)