get_file_content
Retrieve file or directory content from Azure DevOps repositories by specifying project, repository, path, and version parameters.
Instructions
Get content of a file or directory from a repository
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| projectId | No | The ID or name of the project (Default: MyProject) | |
| organizationId | No | The ID or name of the organization (Default: mycompany) | |
| repositoryId | Yes | The ID or name of the repository | |
| path | No | Path to the file or folder | / |
| version | No | The version (branch, tag, or commit) to get content from | |
| versionType | No | Type of version specified (branch, commit, or tag) |
Implementation Reference
- Core handler function that retrieves file content or directory listing from an Azure DevOps Git repository using the Azure DevOps Node API.export async function getFileContent( connection: WebApi, projectId: string, repositoryId: string, path: string = '/', versionDescriptor?: { versionType: GitVersionType; version: string }, ): Promise<FileContentResponse> { try { const gitApi = await connection.getGitApi(); // Create version descriptor for API requests const gitVersionDescriptor: GitVersionDescriptor | undefined = versionDescriptor ? { version: versionDescriptor.version, versionType: versionDescriptor.versionType, versionOptions: undefined, } : undefined; // First, try to get items using the path to determine if it's a directory let isDirectory = false; let items: GitItem[] = []; try { items = await gitApi.getItems( repositoryId, projectId, path, VersionControlRecursionType.OneLevel, undefined, undefined, undefined, undefined, gitVersionDescriptor, ); // If multiple items are returned or the path ends with /, it's a directory isDirectory = items.length > 1 || (path !== '/' && path.endsWith('/')); } catch { // If getItems fails, try to get file content directly isDirectory = false; } if (isDirectory) { // For directories, return a formatted list of the items return { content: JSON.stringify(items, null, 2), isDirectory: true, }; } else { // For files, get the actual content try { // Get file content using the Git API const contentStream = await gitApi.getItemContent( repositoryId, path, projectId, undefined, undefined, undefined, undefined, false, gitVersionDescriptor, true, ); // Convert the stream to a string if (contentStream) { const chunks: Buffer[] = []; // Listen for data events to collect chunks contentStream.on('data', (chunk) => { chunks.push(Buffer.from(chunk)); }); // Use a promise to wait for the stream to finish const content = await new Promise<string>((resolve, reject) => { contentStream.on('end', () => { // Concatenate all chunks and convert to string const buffer = Buffer.concat(chunks); resolve(buffer.toString('utf8')); }); contentStream.on('error', (err) => { reject(err); }); }); return { content, isDirectory: false, }; } throw new Error('No content returned from API'); } catch (error) { // If it's a 404 or similar error, throw a ResourceNotFoundError if ( error instanceof Error && (error.message.includes('not found') || error.message.includes('does not exist')) ) { throw new AzureDevOpsResourceNotFoundError( `Path '${path}' not found in repository '${repositoryId}' of project '${projectId}'`, ); } throw error; } } } catch (error) { // If it's already an AzureDevOpsResourceNotFoundError, rethrow it if (error instanceof AzureDevOpsResourceNotFoundError) { throw error; } // Otherwise, wrap it in a ResourceNotFoundError throw new AzureDevOpsResourceNotFoundError( `Failed to get content for path '${path}': ${error instanceof Error ? error.message : String(error)}`, ); } }
- Zod schema defining the input parameters for the get_file_content tool, including project, repo, path, and optional version details.export const GetFileContentSchema = z.object({ projectId: z .string() .optional() .describe(`The ID or name of the project (Default: ${defaultProject})`), organizationId: z .string() .optional() .describe(`The ID or name of the organization (Default: ${defaultOrg})`), repositoryId: z.string().describe('The ID or name of the repository'), path: z .string() .optional() .default('/') .describe('Path to the file or folder'), version: z .string() .optional() .describe('The version (branch, tag, or commit) to get content from'), versionType: z .enum(['branch', 'commit', 'tag']) .optional() .describe('Type of version specified (branch, commit, or tag)'), });
- src/features/repositories/tool-definitions.ts:36-39 (registration)Registration of the get_file_content tool in the repositoriesTools array, specifying name, description, and input schema.name: 'get_file_content', description: 'Get content of a file or directory from a repository', inputSchema: zodToJsonSchema(GetFileContentSchema), },
- src/features/repositories/index.ts:113-140 (registration)Dispatcher in handleRepositoriesRequest that parses arguments with the schema and invokes the getFileContent handler for MCP tool calls.case 'get_file_content': { const args = GetFileContentSchema.parse(request.params.arguments); // Map the string version type to the GitVersionType enum let versionTypeEnum: GitVersionType | undefined; if (args.versionType && args.version) { if (args.versionType === 'branch') { versionTypeEnum = GitVersionType.Branch; } else if (args.versionType === 'commit') { versionTypeEnum = GitVersionType.Commit; } else if (args.versionType === 'tag') { versionTypeEnum = GitVersionType.Tag; } } const result = await getFileContent( connection, args.projectId ?? defaultProject, args.repositoryId, args.path, versionTypeEnum !== undefined && args.version ? { versionType: versionTypeEnum, version: args.version } : undefined, ); return { content: [{ type: 'text', text: JSON.stringify(result, null, 2) }], }; }
- Type definition for the return value of getFileContent, indicating content and whether it's a directory.export interface FileContentResponse { content: string; isDirectory: boolean; }