Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit010cf9b

Browse files
Copilottonytrg
andauthored
Add starred repository support to GitHub MCP server (#1078)
* Initial plan* Initial exploration and planning for starred repository supportCo-authored-by: tonytrg <40869903+tonytrg@users.noreply.github.com>* Implement starred repository functionality with comprehensive tests- Add ListStarredRepositories tool for listing starred repos- Add StarRepository tool for starring repositories- Add UnstarRepository tool for unstarring repositories- Update MinimalRepository struct with StarredAt field- Add comprehensive test coverage for all new functionality- Register new tools in the repos toolsetCo-authored-by: tonytrg <40869903+tonytrg@users.noreply.github.com>* Update README documentation with starred repository tools- Add list_starred_repositories tool documentation- Add star_repository tool documentation- Add unstar_repository tool documentation- Include comprehensive parameter descriptions for all new toolsCo-authored-by: tonytrg <40869903+tonytrg@users.noreply.github.com>* Add starred repository support to GitHub MCP serverCo-authored-by: tonytrg <40869903+tonytrg@users.noreply.github.com>* remove starredat from minimal view* update descriptions* remove bin* dont commit the binary---------Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>Co-authored-by: tonytrg <40869903+tonytrg@users.noreply.github.com>Co-authored-by: tonytrg <tonytrg@github.com>
1 parentb6486a3 commit010cf9b

File tree

9 files changed

+670
-1
lines changed

9 files changed

+670
-1
lines changed

‎.gitignore‎

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,4 +14,7 @@ vendor
1414
bin/
1515

1616
# macOS
17-
.DS_Store
17+
.DS_Store
18+
19+
# binary
20+
github-mcp-server

‎README.md‎

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -877,6 +877,13 @@ The following sets of tools are available (all are on by default):
877877
-`perPage`: Results per page for pagination (min 1, max 100) (number, optional)
878878
-`repo`: Repository name (string, required)
879879

880+
-**list_starred_repositories** - List starred repositories
881+
-`direction`: The direction to sort the results by. (string, optional)
882+
-`page`: Page number for pagination (min 1) (number, optional)
883+
-`perPage`: Results per page for pagination (min 1, max 100) (number, optional)
884+
-`sort`: How to sort the results. Can be either 'created' (when the repository was starred) or 'updated' (when the repository was last pushed to). (string, optional)
885+
-`username`: Username to list starred repositories for. Defaults to the authenticated user. (string, optional)
886+
880887
-**list_tags** - List tags
881888
-`owner`: Repository owner (string, required)
882889
-`page`: Page number for pagination (min 1) (number, optional)
@@ -903,6 +910,14 @@ The following sets of tools are available (all are on by default):
903910
-`perPage`: Results per page for pagination (min 1, max 100) (number, optional)
904911
-`query`: Repository search query. Examples: 'machine learning in:name stars:>1000 language:python', 'topic:react', 'user:facebook'. Supports advanced search syntax for precise filtering. (string, required)
905912

913+
-**star_repository** - Star repository
914+
-`owner`: Repository owner (string, required)
915+
-`repo`: Repository name (string, required)
916+
917+
-**unstar_repository** - Unstar repository
918+
-`owner`: Repository owner (string, required)
919+
-`repo`: Repository name (string, required)
920+
906921
</details>
907922

908923
<details>

‎github-mcp-server‎

-17.5 MB
Binary file not shown.
Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
{
2+
"annotations": {
3+
"title":"List starred repositories",
4+
"readOnlyHint":true
5+
},
6+
"description":"List starred repositories",
7+
"inputSchema": {
8+
"properties": {
9+
"direction": {
10+
"description":"The direction to sort the results by.",
11+
"enum": [
12+
"asc",
13+
"desc"
14+
],
15+
"type":"string"
16+
},
17+
"page": {
18+
"description":"Page number for pagination (min 1)",
19+
"minimum":1,
20+
"type":"number"
21+
},
22+
"perPage": {
23+
"description":"Results per page for pagination (min 1, max 100)",
24+
"maximum":100,
25+
"minimum":1,
26+
"type":"number"
27+
},
28+
"sort": {
29+
"description":"How to sort the results. Can be either 'created' (when the repository was starred) or 'updated' (when the repository was last pushed to).",
30+
"enum": [
31+
"created",
32+
"updated"
33+
],
34+
"type":"string"
35+
},
36+
"username": {
37+
"description":"Username to list starred repositories for. Defaults to the authenticated user.",
38+
"type":"string"
39+
}
40+
},
41+
"type":"object"
42+
},
43+
"name":"list_starred_repositories"
44+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
{
2+
"annotations": {
3+
"title":"Star repository",
4+
"readOnlyHint":false
5+
},
6+
"description":"Star a GitHub repository",
7+
"inputSchema": {
8+
"properties": {
9+
"owner": {
10+
"description":"Repository owner",
11+
"type":"string"
12+
},
13+
"repo": {
14+
"description":"Repository name",
15+
"type":"string"
16+
}
17+
},
18+
"required": [
19+
"owner",
20+
"repo"
21+
],
22+
"type":"object"
23+
},
24+
"name":"star_repository"
25+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
{
2+
"annotations": {
3+
"title":"Unstar repository",
4+
"readOnlyHint":false
5+
},
6+
"description":"Unstar a GitHub repository",
7+
"inputSchema": {
8+
"properties": {
9+
"owner": {
10+
"description":"Repository owner",
11+
"type":"string"
12+
},
13+
"repo": {
14+
"description":"Repository name",
15+
"type":"string"
16+
}
17+
},
18+
"required": [
19+
"owner",
20+
"repo"
21+
],
22+
"type":"object"
23+
},
24+
"name":"unstar_repository"
25+
}

‎pkg/github/repositories.go‎

Lines changed: 228 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1683,3 +1683,231 @@ func resolveGitReference(ctx context.Context, githubClient *github.Client, owner
16831683
sha=reference.GetObject().GetSHA()
16841684
return&raw.ContentOpts{Ref:ref,SHA:sha},nil
16851685
}
1686+
1687+
// ListStarredRepositories creates a tool to list starred repositories for the authenticated user or a specified user.
1688+
funcListStarredRepositories(getClientGetClientFn,t translations.TranslationHelperFunc) (tool mcp.Tool,handler server.ToolHandlerFunc) {
1689+
returnmcp.NewTool("list_starred_repositories",
1690+
mcp.WithDescription(t("TOOL_LIST_STARRED_REPOSITORIES_DESCRIPTION","List starred repositories")),
1691+
mcp.WithToolAnnotation(mcp.ToolAnnotation{
1692+
Title:t("TOOL_LIST_STARRED_REPOSITORIES_USER_TITLE","List starred repositories"),
1693+
ReadOnlyHint:ToBoolPtr(true),
1694+
}),
1695+
mcp.WithString("username",
1696+
mcp.Description("Username to list starred repositories for. Defaults to the authenticated user."),
1697+
),
1698+
mcp.WithString("sort",
1699+
mcp.Description("How to sort the results. Can be either 'created' (when the repository was starred) or 'updated' (when the repository was last pushed to)."),
1700+
mcp.Enum("created","updated"),
1701+
),
1702+
mcp.WithString("direction",
1703+
mcp.Description("The direction to sort the results by."),
1704+
mcp.Enum("asc","desc"),
1705+
),
1706+
WithPagination(),
1707+
),
1708+
func(ctx context.Context,request mcp.CallToolRequest) (*mcp.CallToolResult,error) {
1709+
username,err:=OptionalParam[string](request,"username")
1710+
iferr!=nil {
1711+
returnmcp.NewToolResultError(err.Error()),nil
1712+
}
1713+
sort,err:=OptionalParam[string](request,"sort")
1714+
iferr!=nil {
1715+
returnmcp.NewToolResultError(err.Error()),nil
1716+
}
1717+
direction,err:=OptionalParam[string](request,"direction")
1718+
iferr!=nil {
1719+
returnmcp.NewToolResultError(err.Error()),nil
1720+
}
1721+
pagination,err:=OptionalPaginationParams(request)
1722+
iferr!=nil {
1723+
returnmcp.NewToolResultError(err.Error()),nil
1724+
}
1725+
1726+
opts:=&github.ActivityListStarredOptions{
1727+
ListOptions: github.ListOptions{
1728+
Page:pagination.Page,
1729+
PerPage:pagination.PerPage,
1730+
},
1731+
}
1732+
ifsort!="" {
1733+
opts.Sort=sort
1734+
}
1735+
ifdirection!="" {
1736+
opts.Direction=direction
1737+
}
1738+
1739+
client,err:=getClient(ctx)
1740+
iferr!=nil {
1741+
returnnil,fmt.Errorf("failed to get GitHub client: %w",err)
1742+
}
1743+
1744+
varrepos []*github.StarredRepository
1745+
varresp*github.Response
1746+
ifusername=="" {
1747+
// List starred repositories for the authenticated user
1748+
repos,resp,err=client.Activity.ListStarred(ctx,"",opts)
1749+
}else {
1750+
// List starred repositories for a specific user
1751+
repos,resp,err=client.Activity.ListStarred(ctx,username,opts)
1752+
}
1753+
1754+
iferr!=nil {
1755+
returnghErrors.NewGitHubAPIErrorResponse(ctx,
1756+
fmt.Sprintf("failed to list starred repositories for user '%s'",username),
1757+
resp,
1758+
err,
1759+
),nil
1760+
}
1761+
deferfunc() {_=resp.Body.Close() }()
1762+
1763+
ifresp.StatusCode!=200 {
1764+
body,err:=io.ReadAll(resp.Body)
1765+
iferr!=nil {
1766+
returnnil,fmt.Errorf("failed to read response body: %w",err)
1767+
}
1768+
returnmcp.NewToolResultError(fmt.Sprintf("failed to list starred repositories: %s",string(body))),nil
1769+
}
1770+
1771+
// Convert to minimal format
1772+
minimalRepos:=make([]MinimalRepository,0,len(repos))
1773+
for_,starredRepo:=rangerepos {
1774+
repo:=starredRepo.Repository
1775+
minimalRepo:=MinimalRepository{
1776+
ID:repo.GetID(),
1777+
Name:repo.GetName(),
1778+
FullName:repo.GetFullName(),
1779+
Description:repo.GetDescription(),
1780+
HTMLURL:repo.GetHTMLURL(),
1781+
Language:repo.GetLanguage(),
1782+
Stars:repo.GetStargazersCount(),
1783+
Forks:repo.GetForksCount(),
1784+
OpenIssues:repo.GetOpenIssuesCount(),
1785+
Private:repo.GetPrivate(),
1786+
Fork:repo.GetFork(),
1787+
Archived:repo.GetArchived(),
1788+
DefaultBranch:repo.GetDefaultBranch(),
1789+
}
1790+
1791+
ifrepo.UpdatedAt!=nil {
1792+
minimalRepo.UpdatedAt=repo.UpdatedAt.Format("2006-01-02T15:04:05Z")
1793+
}
1794+
1795+
minimalRepos=append(minimalRepos,minimalRepo)
1796+
}
1797+
1798+
r,err:=json.Marshal(minimalRepos)
1799+
iferr!=nil {
1800+
returnnil,fmt.Errorf("failed to marshal starred repositories: %w",err)
1801+
}
1802+
1803+
returnmcp.NewToolResultText(string(r)),nil
1804+
}
1805+
}
1806+
1807+
// StarRepository creates a tool to star a repository.
1808+
funcStarRepository(getClientGetClientFn,t translations.TranslationHelperFunc) (tool mcp.Tool,handler server.ToolHandlerFunc) {
1809+
returnmcp.NewTool("star_repository",
1810+
mcp.WithDescription(t("TOOL_STAR_REPOSITORY_DESCRIPTION","Star a GitHub repository")),
1811+
mcp.WithToolAnnotation(mcp.ToolAnnotation{
1812+
Title:t("TOOL_STAR_REPOSITORY_USER_TITLE","Star repository"),
1813+
ReadOnlyHint:ToBoolPtr(false),
1814+
}),
1815+
mcp.WithString("owner",
1816+
mcp.Required(),
1817+
mcp.Description("Repository owner"),
1818+
),
1819+
mcp.WithString("repo",
1820+
mcp.Required(),
1821+
mcp.Description("Repository name"),
1822+
),
1823+
),
1824+
func(ctx context.Context,request mcp.CallToolRequest) (*mcp.CallToolResult,error) {
1825+
owner,err:=RequiredParam[string](request,"owner")
1826+
iferr!=nil {
1827+
returnmcp.NewToolResultError(err.Error()),nil
1828+
}
1829+
repo,err:=RequiredParam[string](request,"repo")
1830+
iferr!=nil {
1831+
returnmcp.NewToolResultError(err.Error()),nil
1832+
}
1833+
1834+
client,err:=getClient(ctx)
1835+
iferr!=nil {
1836+
returnnil,fmt.Errorf("failed to get GitHub client: %w",err)
1837+
}
1838+
1839+
resp,err:=client.Activity.Star(ctx,owner,repo)
1840+
iferr!=nil {
1841+
returnghErrors.NewGitHubAPIErrorResponse(ctx,
1842+
fmt.Sprintf("failed to star repository %s/%s",owner,repo),
1843+
resp,
1844+
err,
1845+
),nil
1846+
}
1847+
deferfunc() {_=resp.Body.Close() }()
1848+
1849+
ifresp.StatusCode!=204 {
1850+
body,err:=io.ReadAll(resp.Body)
1851+
iferr!=nil {
1852+
returnnil,fmt.Errorf("failed to read response body: %w",err)
1853+
}
1854+
returnmcp.NewToolResultError(fmt.Sprintf("failed to star repository: %s",string(body))),nil
1855+
}
1856+
1857+
returnmcp.NewToolResultText(fmt.Sprintf("Successfully starred repository %s/%s",owner,repo)),nil
1858+
}
1859+
}
1860+
1861+
// UnstarRepository creates a tool to unstar a repository.
1862+
funcUnstarRepository(getClientGetClientFn,t translations.TranslationHelperFunc) (tool mcp.Tool,handler server.ToolHandlerFunc) {
1863+
returnmcp.NewTool("unstar_repository",
1864+
mcp.WithDescription(t("TOOL_UNSTAR_REPOSITORY_DESCRIPTION","Unstar a GitHub repository")),
1865+
mcp.WithToolAnnotation(mcp.ToolAnnotation{
1866+
Title:t("TOOL_UNSTAR_REPOSITORY_USER_TITLE","Unstar repository"),
1867+
ReadOnlyHint:ToBoolPtr(false),
1868+
}),
1869+
mcp.WithString("owner",
1870+
mcp.Required(),
1871+
mcp.Description("Repository owner"),
1872+
),
1873+
mcp.WithString("repo",
1874+
mcp.Required(),
1875+
mcp.Description("Repository name"),
1876+
),
1877+
),
1878+
func(ctx context.Context,request mcp.CallToolRequest) (*mcp.CallToolResult,error) {
1879+
owner,err:=RequiredParam[string](request,"owner")
1880+
iferr!=nil {
1881+
returnmcp.NewToolResultError(err.Error()),nil
1882+
}
1883+
repo,err:=RequiredParam[string](request,"repo")
1884+
iferr!=nil {
1885+
returnmcp.NewToolResultError(err.Error()),nil
1886+
}
1887+
1888+
client,err:=getClient(ctx)
1889+
iferr!=nil {
1890+
returnnil,fmt.Errorf("failed to get GitHub client: %w",err)
1891+
}
1892+
1893+
resp,err:=client.Activity.Unstar(ctx,owner,repo)
1894+
iferr!=nil {
1895+
returnghErrors.NewGitHubAPIErrorResponse(ctx,
1896+
fmt.Sprintf("failed to unstar repository %s/%s",owner,repo),
1897+
resp,
1898+
err,
1899+
),nil
1900+
}
1901+
deferfunc() {_=resp.Body.Close() }()
1902+
1903+
ifresp.StatusCode!=204 {
1904+
body,err:=io.ReadAll(resp.Body)
1905+
iferr!=nil {
1906+
returnnil,fmt.Errorf("failed to read response body: %w",err)
1907+
}
1908+
returnmcp.NewToolResultError(fmt.Sprintf("failed to unstar repository: %s",string(body))),nil
1909+
}
1910+
1911+
returnmcp.NewToolResultText(fmt.Sprintf("Successfully unstarred repository %s/%s",owner,repo)),nil
1912+
}
1913+
}

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp