Skip to content

Commit 6177244

Browse files
committed
fix: accept operations that reference an inline channel message
The V3 OperationMessages rule compared from the channel message's side, so an inline channel message used object equality and never matched the operation's reference, failing valid documents. It now compares from both sides.
1 parent c689639 commit 6177244

2 files changed

Lines changed: 104 additions & 1 deletion

File tree

‎src/ByteBard.AsyncAPI/Validation/Rules/AsyncApiOperationRules.cs‎

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,8 @@ private static bool AllOperationsMessagesReferencesChannelMessages(
9292

9393
private static bool OperationMessageReferencesAnyChannelMessage(
9494
AsyncApiMessageReference operationMessage, ICollection<AsyncApiMessage> channelMessages) =>
95-
channelMessages.Any(channelMessage => channelMessage.Equals(operationMessage));
95+
// Only references know how to compare themselves to their target, so an inline channel message
96+
// has to be compared from the operation's side, and a referenced one from the channel's side.
97+
channelMessages.Any(channelMessage => operationMessage.Equals(channelMessage) || channelMessage.Equals(operationMessage));
9698
}
9799
}

‎test/ByteBard.AsyncAPI.Tests/Validation/ValidationRuleTests.cs‎

Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -218,6 +218,107 @@ public void V3_OperationMessage_NotReferencingARootChannel_DiagnosticsError()
218218
diagnostic.Errors.First().Pointer.Should().Be("#/operations/onMessageReceived");
219219
}
220220

221+
[Test]
222+
public void V3_OperationMessage_ReferencingAnInlineChannelMessage_Passes()
223+
{
224+
var input =
225+
"""
226+
asyncapi: 3.0.0
227+
info:
228+
title: Chat Application
229+
version: 1.0.0
230+
channels:
231+
chatPersonId:
232+
address: chat.{personId}
233+
messages:
234+
messageReceived:
235+
name: text
236+
payload:
237+
type: string
238+
operations:
239+
onMessageReceived:
240+
title: Message received
241+
action: receive
242+
channel:
243+
$ref: '#/channels/chatPersonId'
244+
messages:
245+
- $ref: '#/channels/chatPersonId/messages/messageReceived'
246+
""";
247+
248+
new AsyncApiStringReader().Read(input, out var diagnostic);
249+
diagnostic.Errors.Should().BeEmpty();
250+
}
251+
252+
[Test]
253+
public void V3_OperationMessage_ReferencingAChannelMessageThatReferencesAComponent_Passes()
254+
{
255+
var input =
256+
"""
257+
asyncapi: 3.0.0
258+
info:
259+
title: Chat Application
260+
version: 1.0.0
261+
channels:
262+
chatPersonId:
263+
address: chat.{personId}
264+
messages:
265+
messageReceived:
266+
$ref: '#/components/messages/messageReceived'
267+
operations:
268+
onMessageReceived:
269+
title: Message received
270+
action: receive
271+
channel:
272+
$ref: '#/channels/chatPersonId'
273+
messages:
274+
- $ref: '#/channels/chatPersonId/messages/messageReceived'
275+
components:
276+
messages:
277+
messageReceived:
278+
name: text
279+
payload:
280+
type: string
281+
""";
282+
283+
new AsyncApiStringReader().Read(input, out var diagnostic);
284+
diagnostic.Errors.Should().BeEmpty();
285+
}
286+
287+
[Test]
288+
public void V3_OperationMessage_ReferencingTheComponentAChannelMessageReferences_Passes()
289+
{
290+
var input =
291+
"""
292+
asyncapi: 3.0.0
293+
info:
294+
title: Chat Application
295+
version: 1.0.0
296+
channels:
297+
chatPersonId:
298+
address: chat.{personId}
299+
messages:
300+
messageReceived:
301+
$ref: '#/components/messages/messageReceived'
302+
operations:
303+
onMessageReceived:
304+
title: Message received
305+
action: receive
306+
channel:
307+
$ref: '#/channels/chatPersonId'
308+
messages:
309+
- $ref: '#/components/messages/messageReceived'
310+
components:
311+
messages:
312+
messageReceived:
313+
name: text
314+
payload:
315+
type: string
316+
""";
317+
318+
new AsyncApiStringReader().Read(input, out var diagnostic);
319+
diagnostic.Errors.Should().BeEmpty();
320+
}
321+
221322
[Test]
222323
[TestCase("chat")]
223324
[TestCase("/some/chat/{personId}")]

0 commit comments

Comments
 (0)