Skip to content
Merged
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
6 changes: 6 additions & 0 deletions modules/tasks/doc/tasks.yml
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ paths:
get:
tags:
- Tasks
operationId: getTaskStats
summary: Get task statistics
description: Returns the estimated total number of tasks. Public endpoint — no authentication required.
responses:
Expand All @@ -29,6 +30,7 @@ paths:
get:
tags:
- Tasks
operationId: listTasks
summary: List tasks
description: Returns all tasks scoped to the current organization. Requires authentication.
security:
Expand Down Expand Up @@ -59,6 +61,7 @@ paths:
post:
tags:
- Tasks
operationId: createTask
summary: Create a task
description: Creates a new task scoped to the current organization. The requesting user is set as the task owner.
security:
Expand Down Expand Up @@ -94,6 +97,7 @@ paths:
get:
tags:
- Tasks
operationId: getTask
summary: Get a task
description: Returns a single task by ID. Ownership is enforced by CASL policy.
security:
Expand Down Expand Up @@ -123,6 +127,7 @@ paths:
put:
tags:
- Tasks
operationId: updateTask
summary: Update a task
description: Updates an existing task. All fields are optional — only provided fields are updated. Ownership is enforced by CASL policy.
security:
Expand Down Expand Up @@ -160,6 +165,7 @@ paths:
delete:
tags:
- Tasks
operationId: deleteTask
summary: Delete a task
description: Deletes a task by ID. Ownership is enforced by CASL policy.
security:
Expand Down
29 changes: 29 additions & 0 deletions modules/tasks/tests/tasks.openapi-operationid.unit.tests.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
import { describe, test, expect } from '@jest/globals';
import yaml from 'js-yaml';
import fs from 'fs';
import path from 'path';
import { fileURLToPath } from 'url';

const __dirname = path.dirname(fileURLToPath(import.meta.url));

describe('modules/tasks/doc/tasks.yml — OpenAPI operationIds:', () => {
const specPath = path.resolve(__dirname, '../doc/tasks.yml');
const spec = yaml.load(fs.readFileSync(specPath, 'utf8'));

test('every operation has a unique operationId', () => {
const operationIds = [];
for (const [, pathItem] of Object.entries(spec.paths ?? {})) {
for (const [method, operation] of Object.entries(pathItem)) {
if (['get', 'post', 'put', 'patch', 'delete'].includes(method)) {
expect(operation.operationId).toBeDefined();
expect(typeof operation.operationId).toBe('string');
operationIds.push(operation.operationId);
}
}
}
// Uniqueness check
expect(new Set(operationIds).size).toBe(operationIds.length);
// At least one operationId (tasks.yml is not empty)
expect(operationIds.length).toBeGreaterThan(0);
});
});
Loading