diff --git a/.github/workflows/pr-checks.yml b/.github/workflows/pr-checks.yml index 95aab0af9..c2536b90a 100644 --- a/.github/workflows/pr-checks.yml +++ b/.github/workflows/pr-checks.yml @@ -55,10 +55,10 @@ jobs: working-directory: packages/${{ matrix.package }} steps: - name: Checkout - uses: actions/checkout@v4 + uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4.3.1 - name: Setup Node.js - uses: actions/setup-node@v4 + uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0 with: node-version: '20' cache: 'npm' @@ -70,3 +70,27 @@ jobs: - name: Run tests run: npm test + jsdoc-validation: + # Fails when public API methods/parameters lack JSDoc. Uses TypeDoc's + # built-in notDocumented validation (typedoc.validation.json) - no custom + # parsing. Expected to fail until existing gaps are documented or tagged + # @internal. + runs-on: ubuntu-latest + permissions: + contents: read + steps: + - name: Checkout + uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4.3.1 + + - name: Setup Node.js + uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0 + with: + node-version: '20' + cache: 'npm' + + - name: Install dependencies + run: npm ci + + - name: Validate JSDoc completeness + run: npm run docs:validate + diff --git a/package.json b/package.json index 39a0a1db7..931a11a3f 100644 --- a/package.json +++ b/package.json @@ -240,6 +240,7 @@ "docs:api": "typedoc && npm run docs:post-process && npm run docs:coded-action-app", "docs:coded-action-app": "npm run docs --prefix packages/coded-action-app", "docs:post-process": "node scripts/docs-post-process.mjs", + "docs:validate": "typedoc --options typedoc.validation.json", "lint": "oxlint", "typecheck": "tsc --noEmit", "test": "vitest", diff --git a/src/core/errors/authentication.ts b/src/core/errors/authentication.ts index e24b551c2..3a4644c54 100644 --- a/src/core/errors/authentication.ts +++ b/src/core/errors/authentication.ts @@ -10,6 +10,7 @@ import { ErrorParams } from './types'; * - Missing authentication */ export class AuthenticationError extends UiPathError { + /** @internal */ constructor(params: Partial = {}) { super(ErrorType.AUTHENTICATION, { message: params.message || ErrorMessages.AUTHENTICATION_FAILED, diff --git a/src/core/errors/authorization.ts b/src/core/errors/authorization.ts index 48c3a3bc3..00d263d28 100644 --- a/src/core/errors/authorization.ts +++ b/src/core/errors/authorization.ts @@ -10,6 +10,7 @@ import { ErrorParams } from './types'; * - Invalid scope */ export class AuthorizationError extends UiPathError { + /** @internal */ constructor(params: Partial = {}) { super(ErrorType.AUTHORIZATION, { message: params.message || ErrorMessages.ACCESS_DENIED, diff --git a/src/core/errors/guards.ts b/src/core/errors/guards.ts index 525f4de05..9e3335c63 100644 --- a/src/core/errors/guards.ts +++ b/src/core/errors/guards.ts @@ -9,6 +9,9 @@ import { NetworkError } from './network'; /** * Type guard to check if an error is a UiPathError + * + * @param error - The value to check + * @returns True if the value is a UiPathError */ export function isUiPathError(error: unknown): error is UiPathError { return error instanceof UiPathError; @@ -16,6 +19,9 @@ export function isUiPathError(error: unknown): error is UiPathError { /** * Type guard to check if an error is an AuthenticationError + * + * @param error - The value to check + * @returns True if the value is an AuthenticationError */ export function isAuthenticationError(error: unknown): error is AuthenticationError { return error instanceof AuthenticationError; @@ -23,6 +29,9 @@ export function isAuthenticationError(error: unknown): error is AuthenticationEr /** * Type guard to check if an error is an AuthorizationError + * + * @param error - The value to check + * @returns True if the value is an AuthorizationError */ export function isAuthorizationError(error: unknown): error is AuthorizationError { return error instanceof AuthorizationError; @@ -30,6 +39,9 @@ export function isAuthorizationError(error: unknown): error is AuthorizationErro /** * Type guard to check if an error is a ValidationError + * + * @param error - The value to check + * @returns True if the value is a ValidationError */ export function isValidationError(error: unknown): error is ValidationError { return error instanceof ValidationError; @@ -37,6 +49,9 @@ export function isValidationError(error: unknown): error is ValidationError { /** * Type guard to check if an error is a NotFoundError + * + * @param error - The value to check + * @returns True if the value is a NotFoundError */ export function isNotFoundError(error: unknown): error is NotFoundError { return error instanceof NotFoundError; @@ -44,6 +59,9 @@ export function isNotFoundError(error: unknown): error is NotFoundError { /** * Type guard to check if an error is a RateLimitError + * + * @param error - The value to check + * @returns True if the value is a RateLimitError */ export function isRateLimitError(error: unknown): error is RateLimitError { return error instanceof RateLimitError; @@ -51,6 +69,9 @@ export function isRateLimitError(error: unknown): error is RateLimitError { /** * Type guard to check if an error is a ServerError + * + * @param error - The value to check + * @returns True if the value is a ServerError */ export function isServerError(error: unknown): error is ServerError { return error instanceof ServerError; @@ -58,6 +79,9 @@ export function isServerError(error: unknown): error is ServerError { /** * Type guard to check if an error is a NetworkError + * + * @param error - The value to check + * @returns True if the value is a NetworkError */ export function isNetworkError(error: unknown): error is NetworkError { return error instanceof NetworkError; @@ -65,6 +89,9 @@ export function isNetworkError(error: unknown): error is NetworkError { /** * Helper to get error details in a safe way + * + * @param error - The error to extract details from + * @returns The error message and, when available, the HTTP status code */ export function getErrorDetails(error: unknown): { message: string; statusCode?: number } { if (isUiPathError(error)) { diff --git a/src/core/errors/network.ts b/src/core/errors/network.ts index 85f0bf195..0a47b577a 100644 --- a/src/core/errors/network.ts +++ b/src/core/errors/network.ts @@ -11,6 +11,7 @@ import { ErrorParams } from './types'; * - Request aborted */ export class NetworkError extends UiPathError { + /** @internal */ constructor(params: Partial = {}) { super(ErrorType.NETWORK, { message: params.message || ErrorMessages.NETWORK_ERROR, diff --git a/src/core/errors/not-found.ts b/src/core/errors/not-found.ts index 54d3aee81..3fd3272ba 100644 --- a/src/core/errors/not-found.ts +++ b/src/core/errors/not-found.ts @@ -10,6 +10,7 @@ import { ErrorParams } from './types'; * - Resource deleted */ export class NotFoundError extends UiPathError { + /** @internal */ constructor(params: Partial = {}) { super(ErrorType.NOT_FOUND, { message: params.message || ErrorMessages.RESOURCE_NOT_FOUND, diff --git a/src/core/errors/rate-limit.ts b/src/core/errors/rate-limit.ts index 02c7cec39..2ff87de19 100644 --- a/src/core/errors/rate-limit.ts +++ b/src/core/errors/rate-limit.ts @@ -9,6 +9,7 @@ import { ErrorParams } from './types'; * - API throttling */ export class RateLimitError extends UiPathError { + /** @internal */ constructor(params: Partial = {}) { super(ErrorType.RATE_LIMIT, { message: params.message || ErrorMessages.RATE_LIMIT_EXCEEDED, diff --git a/src/core/errors/server.ts b/src/core/errors/server.ts index ba024ab06..5ff1ba70a 100644 --- a/src/core/errors/server.ts +++ b/src/core/errors/server.ts @@ -10,6 +10,7 @@ import { ErrorParams } from './types'; * - Gateway timeout */ export class ServerError extends UiPathError { + /** @internal */ constructor(params: Partial = {}) { super(ErrorType.SERVER, { message: params.message || ErrorMessages.INTERNAL_SERVER_ERROR, diff --git a/src/core/errors/validation.ts b/src/core/errors/validation.ts index a668ce793..e9d6eb3fb 100644 --- a/src/core/errors/validation.ts +++ b/src/core/errors/validation.ts @@ -10,6 +10,7 @@ import { ErrorParams } from './types'; * - Invalid data format */ export class ValidationError extends UiPathError { + /** @internal */ constructor(params: Partial = {}) { super(ErrorType.VALIDATION, { message: params.message || ErrorMessages.VALIDATION_FAILED, diff --git a/src/core/telemetry/index.ts b/src/core/telemetry/index.ts index b1a4ae78b..ccbec7c66 100644 --- a/src/core/telemetry/index.ts +++ b/src/core/telemetry/index.ts @@ -28,9 +28,12 @@ import { // across every subpath bundle (`assets`, `feedback`, `tasks`, …). const sdkClient = getOrCreateClient(CLOUD_ROLE_NAME); +/** @internal */ export const track = createTrack(sdkClient); +/** @internal */ export const trackEvent = createTrackEvent(sdkClient); +/** @internal */ export const telemetryClient = { initialize(context?: TelemetryContext): void { sdkClient.initialize({ diff --git a/src/core/uipath.ts b/src/core/uipath.ts index 9fe756352..5ff9e4100 100644 --- a/src/core/uipath.ts +++ b/src/core/uipath.ts @@ -64,6 +64,11 @@ export class UiPath implements IUiPath { /** Read-only config for user convenience */ public readonly config!: Readonly; + /** + * Creates a UiPath SDK instance. + * + * @param config - Optional SDK configuration; when omitted, configuration is loaded from meta tags + */ constructor(config?: PartialUiPathConfig) { // Load configuration from meta tags const configFromMetaTags = loadFromMetaTags(); diff --git a/src/models/conversational-agent/agents/agents.models.ts b/src/models/conversational-agent/agents/agents.models.ts index e43ac570d..9bf9815de 100644 --- a/src/models/conversational-agent/agents/agents.models.ts +++ b/src/models/conversational-agent/agents/agents.models.ts @@ -91,6 +91,13 @@ function createAgentMethods( }; } +/** + * Combines raw agent data with bound methods. + * + * @param agentData - The raw agent data from API + * @param conversationService - The conversation service instance + * @returns An agent object with added methods + */ export function createAgentWithMethods( agentData: T, conversationService: ConversationServiceModel diff --git a/src/models/conversational-agent/conversations/conversations.models.ts b/src/models/conversational-agent/conversations/conversations.models.ts index fb6a83629..3f43c9daa 100644 --- a/src/models/conversational-agent/conversations/conversations.models.ts +++ b/src/models/conversational-agent/conversations/conversations.models.ts @@ -31,16 +31,23 @@ import type { SessionStream } from './types/events/session.types'; export interface ConversationSessionMethods { /** * Starts a real-time chat session for a conversation + * + * @param conversationId - The conversation ID + * @param options - Optional session options */ startSession(conversationId: string, options?: ConversationSessionOptions): SessionStream; /** * Gets an active session for a conversation + * + * @param conversationId - The conversation ID */ getSession(conversationId: string): SessionStream | undefined; /** * Ends an active session for a conversation + * + * @param conversationId - The conversation ID */ endSession(conversationId: string): void; } diff --git a/src/models/data-fabric/entities.models.ts b/src/models/data-fabric/entities.models.ts index 0b73a4558..8b243137e 100644 --- a/src/models/data-fabric/entities.models.ts +++ b/src/models/data-fabric/entities.models.ts @@ -1172,7 +1172,7 @@ function createEntityMethods(entityData: RawEntityGetResponse, service: EntitySe /** * Creates an actionable entity by combining entity metadata with data and management methods * - * @param entityMetadata - Entity metadata + * @param entityData - The raw entity data from API * @param service - The entity service instance * @returns Entity metadata with added methods */ diff --git a/src/models/orchestrator/queues.models.ts b/src/models/orchestrator/queues.models.ts index f91caed67..89db254b1 100644 --- a/src/models/orchestrator/queues.models.ts +++ b/src/models/orchestrator/queues.models.ts @@ -20,8 +20,7 @@ import { PaginatedResponse, NonPaginatedResponse, HasPaginationOptions } from '. export interface QueueServiceModel { /** * Gets all queues across folders with optional filtering and folder scoping - * - * @signature getAll(options?) → Promise<QueueGetResponse[]> + * * @param options Query options including optional folderId and pagination options * @returns Promise resolving to either an array of queues NonPaginatedResponse or a PaginatedResponse when pagination options are used. * {@link QueueGetResponse} @@ -66,6 +65,7 @@ export interface QueueServiceModel { * * @param id - Queue ID * @param folderId - Required folder ID + * @param options - Optional query options * @returns Promise resolving to a queue definition * @example * ```typescript diff --git a/src/services/orchestrator/queues/queues.ts b/src/services/orchestrator/queues/queues.ts index d5ba70aa8..c2ade1f64 100644 --- a/src/services/orchestrator/queues/queues.ts +++ b/src/services/orchestrator/queues/queues.ts @@ -104,8 +104,9 @@ export class QueueService extends FolderScopedService implements QueueServiceMod * * @param id - Queue ID * @param folderId - Required folder ID + * @param options - Optional query options * @returns Promise resolving to a queue definition - * + * * @example * ```typescript * import { Queues } from '@uipath/uipath-typescript/queues'; diff --git a/typedoc.validation.json b/typedoc.validation.json new file mode 100644 index 000000000..d6e3558be --- /dev/null +++ b/typedoc.validation.json @@ -0,0 +1,12 @@ +{ + "$schema": "https://typedoc.org/schema.json", + "extends": "./typedoc.json", + "emit": "none", + "validation": { + "notDocumented": true, + "notExported": false, + "invalidLink": false + }, + "requiredToBeDocumented": ["Method", "CallSignature", "Parameter"], + "treatValidationWarningsAsErrors": true +}