Skip to content

Commit cbd547e

Browse files
committed
feat: Added complete path to maintainer feature
fixes #14
1 parent 7a51698 commit cbd547e

File tree

7 files changed

+72
-33
lines changed

7 files changed

+72
-33
lines changed

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ A table of checks that will be carried out.
4848

4949
A table of maintainers for pages.
5050

51-
- PagePattern: A regular expression that is matched against the document title
51+
- PagePattern: A regular expression that is matched against the full document path. Parent pages are separated through a "/".
5252
- Maintainer: The user that should receive all notifications for pages matching this pattern
5353

5454
### Panel "Notification Template"

lib/api/Confluence.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ export class Confluence {
6868
*/
6969
public async getDocumentInfo(documentId: number): Promise<DocumentInfo> {
7070
this._log.debug(`Getting document information of document ${documentId}`)
71-
const documentUrl = `${this.confluenceUrl}/rest/api/content/${documentId}`
71+
const documentUrl = `${this.confluenceUrl}/rest/api/content/${documentId}?expand=ancestors`
7272
const document = await got(documentUrl, {
7373
username: this.confluenceUser,
7474
password: this.confluencePassword,
@@ -118,7 +118,9 @@ export class Confluence {
118118
throw new ConfluenceError(`Document ${documentId} has no URL}`)
119119
}
120120

121-
const documentInfo = new DocumentInfo(documentId, author, lastVersionDate, lastVersionMessage, title, url)
121+
const path = document.ancestors.reverse().map((ancestor) => ancestor.title)
122+
123+
const documentInfo = new DocumentInfo(documentId, author, lastVersionDate, lastVersionMessage, title, path, url)
122124

123125
return documentInfo
124126
}

lib/api/DocumentInfo.ts

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,10 @@ export interface DocumentInfo {
1616
* Document title
1717
*/
1818
title: string
19+
/**
20+
* Path to document
21+
*/
22+
path: Array<string>
1923
/**
2024
* The date of the last version
2125
*/
@@ -28,6 +32,12 @@ export interface DocumentInfo {
2832
* The document URL
2933
*/
3034
url: string
35+
36+
/**
37+
* Check whether the complete path to this document matches the given regexp
38+
* @param regexp
39+
*/
40+
matchesPath(regexp: RegExp): boolean
3141
}
3242

3343
export class DocumentInfo implements DocumentInfo {
@@ -36,14 +46,28 @@ export class DocumentInfo implements DocumentInfo {
3646
public lastVersionDate: Moment | string
3747
public lastVersionMessage: string
3848
public title: string
49+
public path: Array<string>
3950
public url: string
4051

41-
constructor(id: number, author: string, lastVersionDate: Moment, lastVersionMessage: string, title: string, url: string) {
52+
constructor(
53+
id: number,
54+
author: string,
55+
lastVersionDate: Moment,
56+
lastVersionMessage: string,
57+
title: string,
58+
path: Array<string>,
59+
url: string
60+
) {
4261
this.id = id
4362
this.author = author
4463
this.lastVersionDate = lastVersionDate
4564
this.lastVersionMessage = lastVersionMessage
4665
this.title = title
66+
this.path = path
4767
this.url = url
4868
}
69+
70+
public matchesPath(regexp: RegExp): boolean {
71+
return regexp.test(this.path.concat([this.title]).join('/'))
72+
}
4973
}

lib/api/Notification.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ export class Notification {
3535
documentInfo.lastVersionDate = (documentInfo.lastVersionDate as Moment).toISOString() as string
3636

3737
for (const maintainer of this._configuration.maintainer) {
38-
if (maintainer.pagePattern.test(documentInfo.title)) {
38+
if (documentInfo.matchesPath(maintainer.pagePattern)) {
3939
documentInfo.author = maintainer.maintainer
4040
}
4141
}

resources/configurationDocument.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@
4848
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="1d192d60-7e69-4af8-8dd6-4006a7bfc952">
4949
<ac:parameter ac:name="title">Maintainer</ac:parameter>
5050
<ac:rich-text-body>
51-
<i>This table holds a list of RegExp patterns for page titles and the associated maintainer for this pages, which will be notified instead of the last version's author.</i>
51+
<i>This table holds a list of RegExp patterns for page paths and titles and the associated maintainers (separated by ,) for this pages, which will be notified instead of the last version's author. The last author can be added as well, if desired by using _lastauthor as the username.</i>
5252
<table class="wrapped">
5353
<colgroup>
5454
<col/>

test/MockServer.ts

Lines changed: 37 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -32,10 +32,10 @@ export class MockServer {
3232
body: {
3333
storage: {
3434
value: `
35-
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="4671afbe-d914-470a-bb9e-8b7321f60f79">
36-
<ac:parameter ac:name="title">Configuration</ac:parameter>
35+
<ac:structured-macro ac:name='panel' ac:schema-version='1' ac:macro-id='4671afbe-d914-470a-bb9e-8b7321f60f79'>
36+
<ac:parameter ac:name='title'>Configuration</ac:parameter>
3737
<ac:rich-text-body>
38-
<table class="wrapped">
38+
<table class='wrapped'>
3939
<colgroup>
4040
<col/>
4141
<col/>
@@ -57,8 +57,8 @@ export class MockServer {
5757
</table>
5858
</ac:rich-text-body>
5959
</ac:structured-macro>
60-
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="ecfe796e-b701-4f30-a74a-b94dbb33daff">
61-
<ac:parameter ac:name="title">SMTP</ac:parameter>
60+
<ac:structured-macro ac:name='panel' ac:schema-version='1' ac:macro-id='ecfe796e-b701-4f30-a74a-b94dbb33daff'>
61+
<ac:parameter ac:name='title'>SMTP</ac:parameter>
6262
<ac:rich-text-body>
6363
<table>
6464
<colgroup>
@@ -68,20 +68,20 @@ export class MockServer {
6868
<tbody>
6969
<tr>
7070
<th>Host</th>
71-
<td colspan="1">localhost</td>
71+
<td colspan='1'>localhost</td>
7272
</tr>
7373
<tr>
7474
<th>Port</th>
75-
<td colspan="1">25</td>
75+
<td colspan='1'>25</td>
7676
</tr>
7777
</tbody>
7878
</table>
7979
</ac:rich-text-body>
8080
</ac:structured-macro>
81-
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="f19cd8b2-57e0-4c68-a823-8a2daee08c12">
82-
<ac:parameter ac:name="title">Checks</ac:parameter>
81+
<ac:structured-macro ac:name='panel' ac:schema-version='1' ac:macro-id='f19cd8b2-57e0-4c68-a823-8a2daee08c12'>
82+
<ac:parameter ac:name='title'>Checks</ac:parameter>
8383
<ac:rich-text-body>
84-
<table class="wrapped">
84+
<table class='wrapped'>
8585
<colgroup>
8686
<col/>
8787
<col/>
@@ -96,17 +96,17 @@ export class MockServer {
9696
<td>356</td>
9797
</tr>
9898
<tr>
99-
<td colspan="1">test2</td>
100-
<td colspan="1">1234</td>
99+
<td colspan='1'>test2</td>
100+
<td colspan='1'>1234</td>
101101
</tr>
102102
</tbody>
103103
</table>
104104
</ac:rich-text-body>
105105
</ac:structured-macro>
106-
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="1d192d60-7e69-4af8-8dd6-4006a7bfc952">
107-
<ac:parameter ac:name="title">Maintainer</ac:parameter>
106+
<ac:structured-macro ac:name='panel' ac:schema-version='1' ac:macro-id='1d192d60-7e69-4af8-8dd6-4006a7bfc952'>
107+
<ac:parameter ac:name='title'>Maintainer</ac:parameter>
108108
<ac:rich-text-body>
109-
<table class="wrapped">
109+
<table class='wrapped'>
110110
<colgroup>
111111
<col/>
112112
<col/>
@@ -117,22 +117,22 @@ export class MockServer {
117117
<th>Maintainer</th>
118118
</tr>
119119
<tr>
120-
<td>Test2</td>
120+
<td>main/Test/.*</td>
121121
<td>maintainer</td>
122122
</tr>
123123
</tbody>
124124
</table>
125125
</ac:rich-text-body>
126126
</ac:structured-macro>
127-
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="93f1d981-c841-4cb4-b6e2-5940dfe69132">
128-
<ac:parameter ac:name="title">Notification Template</ac:parameter>
127+
<ac:structured-macro ac:name='panel' ac:schema-version='1' ac:macro-id='93f1d981-c841-4cb4-b6e2-5940dfe69132'>
128+
<ac:parameter ac:name='title'>Notification Template</ac:parameter>
129129
<ac:rich-text-body>
130-
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="f8503e48-c671-4ed6-897c-def2b2c3fa29">
131-
<ac:parameter ac:name="title">Subject</ac:parameter>
130+
<ac:structured-macro ac:name='panel' ac:schema-version='1' ac:macro-id='f8503e48-c671-4ed6-897c-def2b2c3fa29'>
131+
<ac:parameter ac:name='title'>Subject</ac:parameter>
132132
<ac:rich-text-body><p>${MockServer.NOTIFICATION_SUBJECT}</p></ac:rich-text-body>
133133
</ac:structured-macro>
134-
<ac:structured-macro ac:name="panel" ac:schema-version="1" ac:macro-id="63c16112-dea3-434e-b1cb-467ff4e36d5f">
135-
<ac:parameter ac:name="title">Body</ac:parameter>
134+
<ac:structured-macro ac:name='panel' ac:schema-version='1' ac:macro-id='63c16112-dea3-434e-b1cb-467ff4e36d5f'>
135+
<ac:parameter ac:name='title'>Body</ac:parameter>
136136
<ac:rich-text-body>${MockServer.NOTIFICATION_BODY}</ac:rich-text-body>
137137
</ac:structured-macro>
138138
</ac:rich-text-body>
@@ -179,7 +179,7 @@ export class MockServer {
179179

180180
public addDocumentEndpoint(): void {
181181
this._scope
182-
.get('/rest/api/content/123')
182+
.get('/rest/api/content/123?expand=ancestors')
183183
.basicAuth({
184184
user: 'nobody',
185185
pass: 'nothing',
@@ -189,6 +189,11 @@ export class MockServer {
189189
base: 'https://example.com',
190190
webui: '/display/SAMPLE/Test',
191191
},
192+
ancestors: [
193+
{
194+
title: 'main',
195+
},
196+
],
192197
version: {
193198
by: {
194199
username: 'author',
@@ -198,7 +203,7 @@ export class MockServer {
198203
},
199204
title: 'Test',
200205
})
201-
.get('/rest/api/content/234')
206+
.get('/rest/api/content/234?expand=ancestors')
202207
.basicAuth({
203208
user: 'nobody',
204209
pass: 'nothing',
@@ -208,6 +213,14 @@ export class MockServer {
208213
base: 'https://example.com',
209214
webui: '/display/SAMPLE/Test2',
210215
},
216+
ancestors: [
217+
{
218+
title: 'main',
219+
},
220+
{
221+
title: 'Test',
222+
},
223+
],
211224
version: {
212225
by: {
213226
username: 'author2',

test/NotificationTest.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ describe('The Notification API', (): void => {
3232

3333
it('should send notifications', async (): Promise<void> => {
3434
const notification = new Notification(configuration, '', confluence, transportStub)
35-
const documentInfo = new DocumentInfo(0, 'author', moment(), 'message', 'title', 'http://example.com')
35+
const documentInfo = new DocumentInfo(0, 'author', moment(), 'message', 'title', ['main'], 'http://example.com')
3636
await notification.notify(documentInfo)
3737
chai.expect((transportStub as unknown as SinonStubbedInstance<Mail>).sendMail.calledOnce).to.be.true
3838
chai.expect(
@@ -46,7 +46,7 @@ describe('The Notification API', (): void => {
4646
})
4747
it('should use a maintainer when configured', async (): Promise<void> => {
4848
const notification = new Notification(configuration, '', confluence, transportStub)
49-
const documentInfo = new DocumentInfo(0, 'author2', moment(), 'message', 'Test2', 'http://example.com')
49+
const documentInfo = new DocumentInfo(0, 'author2', moment(), 'message', 'Test2', ['main', 'Test'], 'http://example.com')
5050
await notification.notify(documentInfo)
5151
chai.expect((transportStub as unknown as SinonStubbedInstance<Mail>).sendMail.calledOnce).to.be.true
5252
chai.expect(
@@ -60,7 +60,7 @@ describe('The Notification API', (): void => {
6060
})
6161
it('should not send notifications on a dry run', async (): Promise<void> => {
6262
const notification = new Notification(configuration, '', confluence, transportStub, true)
63-
const documentInfo = new DocumentInfo(0, 'author', moment(), 'message', 'title', 'http://example.com')
63+
const documentInfo = new DocumentInfo(0, 'author', moment(), 'message', 'title', ['main'], 'http://example.com')
6464
await notification.notify(documentInfo)
6565
chai.expect((transportStub as unknown as SinonStubbedInstance<Mail>).sendMail.notCalled).to.be.true
6666
})

0 commit comments

Comments
 (0)