Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/Exceptionless.Web/Controllers/EventController.cs
Original file line number Diff line number Diff line change
Expand Up @@ -580,7 +580,7 @@ public async Task<ActionResult<ICollection<PersistentEvent>>> GetByReferenceIdAs

var ti = GetTimeInfo(null, offset, organizations.GetRetentionUtcCutoff(_appOptions.MaximumRetentionDays, _timeProvider));
var sf = new AppFilter(organizations) { IsUserOrganizationsFilter = true };
return await GetInternalAsync(sf, ti, String.Concat("reference:", referenceId), null, mode, page, limit, before, after, includeTotal: ShouldIncludeTotal(include));
return await GetInternalAsync(sf, ti, $"(reference:{referenceId} OR ref.parent:{referenceId})", null, mode, page, limit, before, after, includeTotal: ShouldIncludeTotal(include));
}

/// <summary>
Expand Down Expand Up @@ -618,7 +618,7 @@ public async Task<ActionResult<ICollection<PersistentEvent>>> GetByReferenceIdAs

var ti = GetTimeInfo(null, offset, organization.GetRetentionUtcCutoff(project, _appOptions.MaximumRetentionDays, _timeProvider));
var sf = new AppFilter(project, organization);
return await GetInternalAsync(sf, ti, String.Concat("reference:", referenceId), null, mode, page, limit, before, after, includeTotal: ShouldIncludeTotal(include));
return await GetInternalAsync(sf, ti, $"(reference:{referenceId} OR ref.parent:{referenceId})", null, mode, page, limit, before, after, includeTotal: ShouldIncludeTotal(include));
}

/// <summary>
Expand Down
27 changes: 27 additions & 0 deletions tests/Exceptionless.Tests/Controllers/EventControllerTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,33 @@ public async Task GetByReferenceIdAsync_WithExistingReference_ReturnsMatchingEve
Assert.Equal(referenceId, ev.ReferenceId);
}

[Theory]
[InlineData(false)]
[InlineData(true)]
public async Task GetByReferenceIdAsync_WithOnlyParentReference_ReturnsMatchingEvents(bool projectScoped)
{
// Arrange
string referenceId = Guid.NewGuid().ToString("N");
await CreateDataAsync(d => d.Event().TestProject().Reference("parent", referenceId).Message("parent reference route"));
await RefreshDataAsync();

string[] paths = projectScoped
? ["projects", SampleDataService.TEST_PROJECT_ID, "events", "by-ref", referenceId]
: ["events", "by-ref", referenceId];

// Act
var events = await SendRequestAsAsync<IReadOnlyCollection<PersistentEvent>>(r => r
.AsTestOrganizationUser()
.AppendPaths(paths)
.StatusCodeShouldBeOk()
);

// Assert
Assert.NotNull(events);
var ev = Assert.Single(events);
Assert.Equal(referenceId, ev.GetEventReference("parent"));
}

[Fact]
public async Task GetCountByOrganizationAsync_WithExistingEvents_ReturnsOrganizationCount()
{
Expand Down
8 changes: 8 additions & 0 deletions tests/http/events.http
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,14 @@ Content-Type: application/json
"reference_id": "{{referenceId}}"
}

### By ReferenceId
GET {{apiUrl}}/events/by-ref/{{referenceId}}
Authorization: Bearer {{token}}

### By ReferenceId And Project
GET {{apiUrl}}/projects/{{projectId}}/events/by-ref/{{referenceId}}
Authorization: Bearer {{token}}

### Post User Description
POST {{apiUrl}}/events/by-ref/{{referenceId}}/user-description?access_token={{clientToken}}
Content-Type: application/json
Expand Down