Skip to content

Commit f1d6aa5

Browse files
fetch repository content from raw urls
1 parent afcb99c commit f1d6aa5

File tree

2 files changed

+83
-21
lines changed

2 files changed

+83
-21
lines changed

pkg/github/repository_resource.go

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -117,7 +117,11 @@ func repositoryResourceContentsHandler(client *github.Client) func(ctx context.C
117117
mimeType := "text/directory"
118118
if entry.GetType() == "file" {
119119
// this is system dependent, and a best guess
120-
mimeType = mime.TypeByExtension(filepath.Ext(entry.GetName()))
120+
ext := filepath.Ext(entry.GetName())
121+
mimeType = mime.TypeByExtension(ext)
122+
if ext == ".md" {
123+
mimeType = "text/markdown"
124+
}
121125
}
122126
resources = append(resources, mcp.TextResourceContents{
123127
URI: entry.GetHTMLURL(),
@@ -152,10 +156,13 @@ func repositoryResourceContentsHandler(client *github.Client) func(ctx context.C
152156
return nil, fmt.Errorf("failed to get security analysis settings: %s", string(body))
153157
}
154158

159+
ext := filepath.Ext(fileContent.GetName())
155160
mimeType := resp.Header.Get("Content-Type")
156-
if mimeType == "" {
161+
if ext == ".md" {
162+
mimeType = "text/markdown"
163+
} else if mimeType == "" {
157164
// backstop to the file extension if the content type is not set
158-
mime.TypeByExtension(filepath.Ext(fileContent.GetName()))
165+
mimeType = mime.TypeByExtension(filepath.Ext(fileContent.GetName()))
159166
}
160167

161168
// if the content is a string, return it as text

pkg/github/repository_resource_test.go

Lines changed: 73 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@ package github
22

33
import (
44
"context"
5-
"encoding/base64"
65
"net/http"
76
"testing"
87

@@ -13,28 +12,35 @@ import (
1312
"github.com/stretchr/testify/require"
1413
)
1514

15+
var GetRawReposContentsByOwnerByRepoByPath mock.EndpointPattern = mock.EndpointPattern{
16+
Pattern: "/{owner}/{repo}/main/{path:.+}",
17+
Method: "GET",
18+
}
19+
1620
func Test_repositoryResourceContentsHandler(t *testing.T) {
1721
mockDirContent := []*github.RepositoryContent{
1822
{
19-
Type: github.Ptr("file"),
20-
Name: github.Ptr("README.md"),
21-
Path: github.Ptr("README.md"),
22-
SHA: github.Ptr("abc123"),
23-
Size: github.Ptr(42),
24-
HTMLURL: github.Ptr("https://github.com/owner/repo/blob/main/README.md"),
23+
Type: github.Ptr("file"),
24+
Name: github.Ptr("README.md"),
25+
Path: github.Ptr("README.md"),
26+
SHA: github.Ptr("abc123"),
27+
Size: github.Ptr(42),
28+
HTMLURL: github.Ptr("https://github.com/owner/repo/blob/main/README.md"),
29+
DownloadURL: github.Ptr("https://raw.githubusercontent.com/owner/repo/main/README.md"),
2530
},
2631
{
27-
Type: github.Ptr("dir"),
28-
Name: github.Ptr("src"),
29-
Path: github.Ptr("src"),
30-
SHA: github.Ptr("def456"),
31-
HTMLURL: github.Ptr("https://github.com/owner/repo/tree/main/src"),
32+
Type: github.Ptr("dir"),
33+
Name: github.Ptr("src"),
34+
Path: github.Ptr("src"),
35+
SHA: github.Ptr("def456"),
36+
HTMLURL: github.Ptr("https://github.com/owner/repo/tree/main/src"),
37+
DownloadURL: github.Ptr("https://raw.githubusercontent.com/owner/repo/main/src"),
3238
},
3339
}
3440
expectedDirContent := []mcp.TextResourceContents{
3541
{
3642
URI: "https://github.com/owner/repo/blob/main/README.md",
37-
MIMEType: "",
43+
MIMEType: "text/markdown",
3844
Text: "README.md",
3945
},
4046
{
@@ -44,20 +50,41 @@ func Test_repositoryResourceContentsHandler(t *testing.T) {
4450
},
4551
}
4652

47-
mockFileContent := &github.RepositoryContent{
53+
mockTextContent := &github.RepositoryContent{
4854
Type: github.Ptr("file"),
4955
Name: github.Ptr("README.md"),
5056
Path: github.Ptr("README.md"),
51-
Content: github.Ptr("IyBUZXN0IFJlcG9zaXRvcnkKClRoaXMgaXMgYSB0ZXN0IHJlcG9zaXRvcnku"), // Base64 encoded "# Test Repository\n\nThis is a test repository."
57+
Content: github.Ptr("# Test Repository\n\nThis is a test repository."),
5258
SHA: github.Ptr("abc123"),
5359
Size: github.Ptr(42),
5460
HTMLURL: github.Ptr("https://github.com/owner/repo/blob/main/README.md"),
5561
DownloadURL: github.Ptr("https://raw.githubusercontent.com/owner/repo/main/README.md"),
5662
}
5763

64+
mockFileContent := &github.RepositoryContent{
65+
Type: github.Ptr("file"),
66+
Name: github.Ptr("data.png"),
67+
Path: github.Ptr("data.png"),
68+
Content: github.Ptr("IyBUZXN0IFJlcG9zaXRvcnkKClRoaXMgaXMgYSB0ZXN0IHJlcG9zaXRvcnku"), // Base64 encoded "# Test Repository\n\nThis is a test repository."
69+
SHA: github.Ptr("abc123"),
70+
Size: github.Ptr(42),
71+
HTMLURL: github.Ptr("https://github.com/owner/repo/blob/main/data.png"),
72+
DownloadURL: github.Ptr("https://raw.githubusercontent.com/owner/repo/main/data.png"),
73+
}
74+
5875
expectedFileContent := []mcp.BlobResourceContents{
5976
{
60-
Blob: base64.StdEncoding.EncodeToString([]byte("IyBUZXN0IFJlcG9zaXRvcnkKClRoaXMgaXMgYSB0ZXN0IHJlcG9zaXRvcnku")),
77+
Blob: "IyBUZXN0IFJlcG9zaXRvcnkKClRoaXMgaXMgYSB0ZXN0IHJlcG9zaXRvcnku",
78+
MIMEType: "image/png",
79+
URI: "",
80+
},
81+
}
82+
83+
expectedTextContent := []mcp.TextResourceContents{
84+
{
85+
Text: "# Test Repository\n\nThis is a test repository.",
86+
MIMEType: "text/markdown",
87+
URI: "",
6188
},
6289
}
6390

@@ -94,21 +121,49 @@ func Test_repositoryResourceContentsHandler(t *testing.T) {
94121
expectError: "repo is required",
95122
},
96123
{
97-
name: "successful file content fetch",
124+
name: "successful blob content fetch",
98125
mockedClient: mock.NewMockedHTTPClient(
99126
mock.WithRequestMatch(
100127
mock.GetReposContentsByOwnerByRepoByPath,
101128
mockFileContent,
102129
),
130+
mock.WithRequestMatchHandler(
131+
GetRawReposContentsByOwnerByRepoByPath,
132+
http.HandlerFunc(func(w http.ResponseWriter, _ *http.Request) {
133+
w.Header().Set("Content-Type", "image/png")
134+
// as this is given as a png, it will return the content as a blob
135+
w.Write([]byte("# Test Repository\n\nThis is a test repository."))
136+
}),
137+
),
103138
),
104139
requestArgs: map[string]any{
105140
"owner": []string{"owner"},
106141
"repo": []string{"repo"},
107-
"path": []string{"README.md"},
142+
"path": []string{"data.png"},
108143
"branch": []string{"main"},
109144
},
110145
expectedResult: expectedFileContent,
111146
},
147+
{
148+
name: "successful text content fetch",
149+
mockedClient: mock.NewMockedHTTPClient(
150+
mock.WithRequestMatch(
151+
mock.GetReposContentsByOwnerByRepoByPath,
152+
mockTextContent,
153+
),
154+
mock.WithRequestMatch(
155+
GetRawReposContentsByOwnerByRepoByPath,
156+
[]byte("# Test Repository\n\nThis is a test repository."),
157+
),
158+
),
159+
requestArgs: map[string]any{
160+
"owner": []string{"owner"},
161+
"repo": []string{"repo"},
162+
"path": []string{"data.png"},
163+
"branch": []string{"main"},
164+
},
165+
expectedResult: expectedTextContent,
166+
},
112167
{
113168
name: "successful directory content fetch",
114169
mockedClient: mock.NewMockedHTTPClient(

0 commit comments

Comments
 (0)