@gohcltech/bitbucket-mcp
Version:
Bitbucket integration for Claude via Model Context Protocol
396 lines • 14.9 kB
JavaScript
/**
* @fileoverview Zod validation schemas for Bitbucket branch operations.
*
* This module provides comprehensive validation schemas for branch-related
* operations using Zod for runtime type checking and validation. These schemas
* ensure that data conforms to Bitbucket API v2.0 specifications and provide
* type-safe validation for MCP tool inputs and API responses.
*
* Key features:
* - Runtime validation of branch API responses
* - Branching model and Git Flow configuration validation
* - Branch protection and permissions schema validation
* - Default reviewer assignment rule validation
* - Input parameter validation for branch management tools
* - Type-safe schema definitions matching TypeScript interfaces
*/
import { z } from 'zod';
import { RepositoryBaseSchema } from '../common.js';
// =============================================================================
// RESPONSE SCHEMAS
// =============================================================================
/**
* Zod schema for validating Bitbucket branch API responses.
*
* This schema validates the structure of branch objects returned by
* Bitbucket's REST API v2.0. It ensures that all required fields are present
* and correctly typed, including commit metadata and navigation links.
*
* The schema uses `satisfies z.ZodType<Branch>` to guarantee that the
* validation schema matches the TypeScript interface exactly.
*
* @example
* ```typescript
* const apiResponse = await fetch('/2.0/repositories/gohcl/bitbucket-mcp/refs/branches/feature/auth');
* const rawData = await apiResponse.json();
* const branch = BranchSchema.parse(rawData);
* ```
*/
export const BranchSchema = z.object({
/**
* Branch name following git naming conventions.
* Must be a non-empty string with valid git branch name format.
*/
name: z.string().min(1, 'Branch name is required')
.max(100, 'Branch name too long')
.regex(/^[a-zA-Z0-9][a-zA-Z0-9._/-]*[a-zA-Z0-9]$|^[a-zA-Z0-9]$/, 'Invalid branch name format'),
/**
* Target commit information that this branch points to.
* Contains comprehensive metadata about the HEAD commit.
*/
target: z.object({
/**
* SHA-1 hash of the target commit.
* Must be a 40-character hexadecimal string.
*/
hash: z.string().length(40, 'Commit hash must be 40 characters')
.regex(/^[a-f0-9]{40}$/, 'Invalid commit hash format'),
/**
* ISO 8601 timestamp when the commit was created.
* Must be a valid datetime string with timezone information.
*/
date: z.string().datetime('Invalid commit date format'),
/**
* Commit author information.
* May contain user details if author is a registered Bitbucket user.
*/
author: z.object({
/**
* Optional Bitbucket user information for the commit author.
* Present only if author email matches a registered user.
*/
user: z.object({
/** Display name of the commit author */
display_name: z.string().min(1, 'Author display name is required'),
/** Unique UUID for the author's user account */
uuid: z.string().min(1, 'Author UUID is required'),
}).optional(),
}),
/**
* Commit message describing the changes.
* Contains the full commit message including title and body.
*/
message: z.string(),
}),
/**
* Collection of related URLs for the branch.
* Provides navigation links to commits and web interface.
*/
links: z.object({
/**
* API endpoint for commits on this branch.
* Links to the filtered commits API for this branch.
*/
commits: z.object({
/** Full URL to the branch's commits API endpoint */
href: z.string().url('Invalid commits link'),
}),
/**
* Web interface link to the branch page.
* Opens the branch view in Bitbucket's web interface.
*/
html: z.object({
/** Full URL to the branch page in Bitbucket */
href: z.string().url('Invalid branch HTML link'),
}),
}),
});
/**
* Zod schema for validating Bitbucket branching model API responses.
*
* This schema validates the structure of branching model configurations that
* define Git Flow, GitHub Flow, or custom branching strategies. It includes
* validation for development/production branch settings and branch type
* configurations with their naming prefixes.
*
* The schema accommodates the flexible nature of branching models where
* most fields are optional depending on the strategy type.
*
* @example
* ```typescript
* const apiResponse = await fetch('/2.0/repositories/gohcl/bitbucket-mcp/branching-model');
* const rawData = await apiResponse.json();
* const model = BranchingModelSchema.parse(rawData);
* ```
*/
export const BranchingModelSchema = z.object({
/**
* Type of branching workflow strategy.
* Defines the overall branching strategy used by the repository.
*/
type: z.enum(['git_flow', 'github_flow', 'custom'], {
errorMap: () => ({ message: 'Must be git_flow, github_flow, or custom' })
}).optional(),
/**
* Development branch configuration.
* Defines the primary development branch for ongoing work.
*/
development: z.object({
/**
* Name of the development branch.
* Must be a valid git branch name.
*/
name: z.string().min(1, 'Development branch name is required')
.regex(/^[a-zA-Z0-9][a-zA-Z0-9._/-]*[a-zA-Z0-9]$|^[a-zA-Z0-9]$/, 'Invalid branch name format'),
/**
* Whether this branch is the repository's main branch.
* Determines if development happens on the main branch.
*/
use_mainbranch: z.boolean(),
}).optional(),
/**
* Production/stable branch configuration.
* Defines the branch containing production-ready code.
*/
production: z.object({
/**
* Name of the production branch.
* Must be a valid git branch name.
*/
name: z.string().min(1, 'Production branch name is required')
.regex(/^[a-zA-Z0-9][a-zA-Z0-9._/-]*[a-zA-Z0-9]$|^[a-zA-Z0-9]$/, 'Invalid branch name format'),
/**
* Whether this branch is the repository's main branch.
* Usually true for production branches.
*/
use_mainbranch: z.boolean(),
}).optional(),
/**
* Array of branch type configurations.
* Defines naming patterns and behavior for different branch categories.
*/
branch_types: z.array(z.object({
/**
* Category of branch defining its purpose.
* Must be one of the predefined branch types.
*/
kind: z.enum(['feature', 'bugfix', 'release', 'hotfix', 'custom'], {
errorMap: () => ({ message: 'Must be feature, bugfix, release, hotfix, or custom' })
}),
/**
* Naming prefix for branches of this type.
* Should end with a separator like '/' or '-'.
*/
prefix: z.string().min(1, 'Branch prefix is required')
.max(50, 'Branch prefix too long'),
/**
* Whether branches of this type are currently enabled.
* Controls whether new branches of this type can be created.
*/
enabled: z.boolean(),
})).optional(),
/**
* Collection of related URLs for the branching model.
* Provides API endpoints for managing branching model settings.
*/
links: z.object({
/**
* Self-referential link to this branching model configuration.
*/
self: z.object({
/** API endpoint URL for this branching model */
href: z.string().url('Invalid branching model link'),
}),
}).optional(),
});
/**
* Zod schema for validating Bitbucket branch permissions API responses.
*
* This schema validates the structure of branch protection rules and restrictions
* that control access to specific branches. It includes validation for various
* restriction types, user/group exemptions, and pagination metadata.
*
* @example
* ```typescript
* const apiResponse = await fetch('/2.0/repositories/gohcl/bitbucket-mcp/branch-restrictions');
* const rawData = await apiResponse.json();
* const permissions = BranchPermissionsSchema.parse(rawData);
* ```
*/
export const BranchPermissionsSchema = z.object({
/** Array of branch restrictions */
values: z.array(z.object({
/** Unique restriction ID */
id: z.number(),
/** Restriction type */
kind: z.enum(['push', 'force', 'delete', 'restrict_merges', 'enforce_merge_checks']),
/** Branch name pattern this restriction applies to */
pattern: z.string(),
/** Users affected by this restriction */
users: z.array(z.object({
display_name: z.string(),
uuid: z.string(),
})).optional(),
/** Groups affected by this restriction */
groups: z.array(z.object({
name: z.string(),
slug: z.string(),
})).optional(),
/** Restriction value/configuration */
value: z.union([z.string(), z.number(), z.boolean()]).optional(),
/** Related links */
links: z.object({
self: z.object({
href: z.string(),
}),
}).optional(),
})),
/** Pagination information */
page: z.number().optional(),
pagelen: z.number().optional(),
size: z.number().optional(),
next: z.string().optional(),
});
/**
* Zod schema for validating Bitbucket default reviewers API responses.
*
* This schema validates the structure of automatic reviewer assignment rules
* that determine which users should be added as reviewers for pull requests
* based on branch patterns. It includes comprehensive user information and
* repository context.
*
* @example
* ```typescript
* const apiResponse = await fetch('/2.0/repositories/gohcl/bitbucket-mcp/default-reviewers');
* const rawData = await apiResponse.json();
* const reviewers = DefaultReviewersSchema.parse(rawData);
* ```
*/
export const DefaultReviewersSchema = z.object({
/** Array of default reviewer configurations */
values: z.array(z.object({
/** Default reviewer user information */
user: z.object({
display_name: z.string(),
uuid: z.string(),
account_id: z.string(),
links: z.object({
avatar: z.object({
href: z.string(),
}),
html: z.object({
href: z.string(),
}),
}),
}),
/** Branch name pattern this reviewer applies to */
pattern: z.string().optional(),
/** Repository information */
repository: z.object({
name: z.string(),
full_name: z.string(),
uuid: z.string(),
}).optional(),
})),
/** Pagination information */
page: z.number().optional(),
pagelen: z.number().optional(),
size: z.number().optional(),
next: z.string().optional(),
});
// =============================================================================
// INPUT VALIDATION SCHEMAS
// =============================================================================
/**
* Input validation schema for branch-related MCP tool parameters.
*
* This schema validates the basic parameters required by branch-related tools,
* extending the repository base schema with branch-specific validation.
* It ensures proper formatting of workspace, repository, and branch identifiers.
*
* Used by tools that operate on existing branches like get_branch, delete_branch.
*
* @example
* ```typescript
* const input = {
* workspace: 'gohcl',
* repo_slug: 'bitbucket-mcp',
* branch_name: 'feature/authentication'
* };
* const validatedInput = BranchInputSchema.parse(input);
* ```
*/
export const BranchInputSchema = RepositoryBaseSchema.extend({
/**
* Branch name following git naming conventions.
* Must be a valid git branch name without path separators.
*/
branch_name: z.string().min(1, 'Branch name is required')
.max(100, 'Branch name too long')
.regex(/^[a-zA-Z0-9][a-zA-Z0-9._/-]*[a-zA-Z0-9]$|^[a-zA-Z0-9]$/, 'Invalid branch name format'),
});
/**
* Input validation schema for the create_branch MCP tool.
*
* This schema validates parameters for creating new branches, including
* the branch name and target commit hash. It ensures that branch names
* follow git conventions and target commits are properly specified.
*
* @example
* ```typescript
* const input = {
* workspace: 'gohcl',
* repo_slug: 'bitbucket-mcp',
* name: 'feature/oauth-integration',
* target: {
* hash: 'a1b2c3d4e5f6789012345678901234567890abcd'
* }
* };
* const validatedInput = CreateBranchInputSchema.parse(input);
* ```
*/
export const CreateBranchInputSchema = RepositoryBaseSchema.extend({
/**
* Name for the new branch.
* Must follow git branch naming conventions and be unique within the repository.
*/
name: z.string().min(1, 'Branch name is required')
.max(100, 'Branch name too long')
.regex(/^[a-zA-Z0-9][a-zA-Z0-9._/-]*[a-zA-Z0-9]$|^[a-zA-Z0-9]$/, 'Invalid branch name format'),
/**
* Target commit information for the new branch.
* Specifies which commit the new branch should point to.
*/
target: z.object({
/**
* SHA-1 hash of the target commit.
* Must be a valid 40-character hexadecimal commit hash.
*/
hash: z.string().length(40, 'Target hash must be 40 characters')
.regex(/^[a-f0-9]{40}$/, 'Invalid commit hash format'),
}),
});
// =============================================================================
// TYPE GUARDS
// =============================================================================
/**
* Type guard function for branch input validation.
*
* Checks if the provided input matches the branch input schema structure,
* providing runtime type safety for branch-related operations.
*
* @param input - Unknown input to validate
* @returns True if input matches BranchInputSchema, false otherwise
*
* @example
* ```typescript
* if (isBranchInput(userInput)) {
* // userInput is now typed as { workspace: string; repo_slug: string; branch_name: string }
* console.log(`Branch: ${userInput.branch_name}`);
* }
* ```
*/
export function isBranchInput(input) {
return BranchInputSchema.safeParse(input).success;
}
//# sourceMappingURL=schemas.js.map