Skip to content

Commit 52aedf2

Browse files
committed
Merge branch 'main' into make-tools
2 parents 948425f + 15d4901 commit 52aedf2

18 files changed

Lines changed: 620 additions & 151 deletions

File tree

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,3 +6,4 @@ wiki/
66
.r*
77
deps/
88
/result
9+
tags

CHANGELOG.md

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,47 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8+
9+
## [5.11.0] - 2025-06-26
10+
11+
### Added
12+
13+
- **XDG Base Directory Specification Support**: Migrated from hardcoded ~/.mcp-hub paths to XDG-compliant directories
14+
- Marketplace cache now uses XDG data directory (`~/.local/share/mcp-hub/cache`)
15+
- Logs now use XDG state directory (`~/.local/state/mcp-hub/logs`)
16+
- OAuth storage now uses XDG data directory (`~/.local/share/mcp-hub/oauth`)
17+
- Backward compatibility maintained for existing ~/.mcp-hub installations
18+
- New XDG paths utility module with automatic fallback logic
19+
20+
### Enhanced
21+
22+
- Updated documentation to reflect new XDG-compliant path structure
23+
- Improved file organization following Linux filesystem standards
24+
25+
26+
## [5.10.0] - 2025-06-24
27+
28+
### Added
29+
30+
- Integrated support for MCP Hub's unified endpoint feature
31+
- Added documentation for the dual-interface approach (management + MCP endpoint)
32+
- Added configuration examples for unified endpoint usage
33+
34+
## [5.9.0] - 2025-06-24
35+
36+
### Added
37+
38+
- Improved OAuth flow for remote/headless servers
39+
- New auth popup UI with clear instructions
40+
- Manual callback URL support for headless environments
41+
- Auto-closing popup on successful authorization
42+
- Better error handling and validation
43+
- Tab navigation between info and input windows
44+
45+
### Changed
46+
47+
- Updated mcp-hub dependency to v3.5.0 for improved OAuth support
48+
849
## [5.8.0] - 2025-06-23
950

1051
### Added
@@ -872,3 +913,4 @@ extensions = {
872913
- Detailed documentation and examples
873914
- Integration with lazy.nvim package manager
874915

916+

README.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -28,13 +28,14 @@ MCP Hub is a MCP client for neovim that seamlessly integrates [MCP (Model Contex
2828

2929
## 💜 Sponsors
3030

31-
<!-- sponsors --> <p align="center"> <a href="https://github.com/CryogenicPlanet"><img src="https://github.com/CryogenicPlanet.png" width="60px" alt="CryogenicPlanet" /></a> <a href="https://github.com/yingmanwumen"><img src="https://github.com/yingmanwumen.png" width="60px" alt="yingmanwumen" /></a> <a href="https://github.com/yetone"><img src="https://github.com/yetone.png" width="60px" alt="Yetone" /></a> <a href="https://github.com/omarcresp"><img src="https://github.com/omarcresp.png" width="60px" alt="omarcresp" /></a> <a href="https://github.com/petermoser"><img src="https://github.com/petermoser.png" width="60px" alt="petermoser" /></a> <a href="https://github.com/watsy0007"><img src="https://github.com/watsy0007.png" width="60px" alt="watsy0007" /></a> <a href="https://github.com/kohane27"><img src="https://github.com/kohane27.png" width="60px" alt="kohane27" /></a> <a href="https://github.com/copleykj"><img src="https://github.com/copleykj.png" width="60px" alt="Kelly Copley" /></a></p><!-- sponsors -->
31+
<!-- sponsors --> <p align="center"> <a href="https://github.com/CryogenicPlanet"><img src="https://github.com/CryogenicPlanet.png" width="50px" alt="CryogenicPlanet" /></a> <a href="https://github.com/olimorris"><img src="https://github.com/olimorris.png" width="50px" alt="Oli Morris" /></a> <a href="https://github.com/supermemoryai"><img src="https://github.com/supermemoryai.png" width="50px" alt="Super Memory" /></a> <a href="https://github.com/yingmanwumen"><img src="https://github.com/yingmanwumen.png" width="50px" alt="yingmanwumen" /></a> <a href="https://github.com/yetone"><img src="https://github.com/yetone.png" width="50px" alt="Yetone" /></a> <a href="https://github.com/omarcresp"><img src="https://github.com/omarcresp.png" width="50px" alt="omarcresp" /></a> <a href="https://github.com/petermoser"><img src="https://github.com/petermoser.png" width="50px" alt="petermoser" /></a> <a href="https://github.com/watsy0007"><img src="https://github.com/watsy0007.png" width="50px" alt="watsy0007" /></a> <a href="https://github.com/kohane27"><img src="https://github.com/kohane27.png" width="50px" alt="kohane27" /></a> <a href="https://github.com/copleykj"><img src="https://github.com/copleykj.png" width="50px" alt="Kelly Copley" /></a><a href="https://github.com/nom-social"><img src="https://github.com/nom-social.png" width="50px" alt="Nom Social" /></a></p><!-- sponsors -->
3232

3333
<p align="center">
3434
<b>Special thanks to:</b>
3535
</p>
3636
<p align="center">
37-
<a href="https://dub.sh/composio-mcp" target="_blank"> <img src="https://composio.dev/wp-content/uploads/2025/01/Composio-logo-25.png" height="30px" alt="Composio.dev logo" /> </a>
37+
<a href="https://dub.sh/composio-mcp" target="_blank"> <img src="https://ravitemer.github.io/mcphub.nvim/sponsors/composio-logo.png" height="60px" alt="Composio.dev logo" /> </a>
38+
<a href="https://vapi.ai" target="_blank"> <img src="https://github.com/user-attachments/assets/32b4d458-b2d1-484d-b096-dfb083b44c2c" height="60px" alt="Vapi logo" /></a>
3839
</p>
3940

4041
## ✨ Features

doc/.vitepress/config.mjs

Lines changed: 6 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,12 @@ export default withMermaid(
4545
sponsors: {
4646
enabled: true,
4747
cards: [
48+
{
49+
href: "https://vapi.ai",
50+
image: "/mcphub.nvim/sponsors/vapi.png",
51+
text: "Build Voice AI Agents with VAPI MCP Server",
52+
alt: "Vapi"
53+
},
4854
{
4955
href: "https://www.warp.dev/mcp-hub-nvim",
5056
image: "/mcphub.nvim/sponsors/warp.png",
@@ -125,31 +131,6 @@ export default withMermaid(
125131
{ text: "Troubleshooting", link: "/other/troubleshooting" },
126132
],
127133
},
128-
// {
129-
// text: "Usage",
130-
// collapsed: false,
131-
// items: [
132-
// { text: "Introduction", link: "/usage/introduction" },
133-
// { text: "Action Palette", link: "/usage/action-palette" },
134-
// {
135-
// text: "Chat Buffer",
136-
// link: "/usage/chat-buffer/",
137-
// collapsed: true,
138-
// items: [
139-
// { text: "Agents/Tools", link: "/usage/chat-buffer/agents" },
140-
// {
141-
// text: "Slash Commands",
142-
// link: "/usage/chat-buffer/slash-commands",
143-
// },
144-
// { text: "Variables", link: "/usage/chat-buffer/variables" },
145-
// ],
146-
// },
147-
// { text: "Events", link: "/usage/events" },
148-
// { text: "Inline Assistant", link: "/usage/inline-assistant" },
149-
// { text: "User Interface", link: "/usage/ui" },
150-
// { text: "Workflows", link: "/usage/workflows" },
151-
// ],
152-
// },
153134
],
154135
outline: {
155136
level: [2, 3],

doc/.vitepress/theme/Sponsors.vue

Lines changed: 76 additions & 77 deletions
Original file line numberDiff line numberDiff line change
@@ -1,99 +1,91 @@
11
<script setup lang="ts">
22
import type { DefaultTheme } from 'vitepress/theme'
3-
import { ref, watch, onMounted } from 'vue'
3+
import { ref, watch, onMounted, onUnmounted, computed } from 'vue'
44
import { useData } from 'vitepress'
55
6-
const { page } = useData()
6+
const currentSponsorIndex = ref(0)
7+
let intervalId: ReturnType<typeof setInterval> | null = null
8+
const INTERVAL_DURATION = 10000 // Cycle every 10 seconds
9+
710
const props = defineProps<{
811
sponsors: DefaultTheme.sponsors
912
}>()
1013
11-
const sponsors = props.sponsors
12-
13-
const container = ref()
14-
15-
let currentCard = ref(0)
16-
//Cycle through the ads on every new page
17-
function refresh() {
18-
if (sponsors && sponsors.cards) {
19-
const cards = sponsors.cards
20-
const index = (currentCard.value) % cards.length
21-
const card = cards[index]
22-
currentCard.value = index + 1
23-
// Clear existing content
24-
container.value.innerHTML = ''
25-
26-
const link = document.createElement('a')
27-
link.href = card.href
28-
link.target = '_blank'
29-
link.rel = 'noopener'
30-
31-
const img = document.createElement('img')
32-
img.src = card.image
33-
img.alt = card.alt
34-
35-
const cardContent = document.createElement('div')
36-
cardContent.className = 'card-content'
37-
38-
link.appendChild(img)
39-
cardContent.appendChild(link)
40-
41-
const title = document.createElement('a')
42-
title.href = card.href
43-
title.target = '_blank'
44-
title.rel = 'noopener'
45-
title.className = 'carbon-text'
46-
title.textContent = card.text
47-
cardContent.appendChild(title)
48-
49-
const poweredBy = document.createElement("a")
50-
poweredBy.className = "carbon-poweredby"
51-
poweredBy.textContent = "Featured Sponsor"
52-
poweredBy.href = "https://github.com/sponsors/ravitemer"
53-
poweredBy.target = '_blank'
54-
poweredBy.rel = 'noopener'
55-
cardContent.appendChild(poweredBy)
56-
57-
container.value.appendChild(cardContent)
14+
const { page } = useData()
15+
16+
const sponsorCards = computed(() => props.sponsors?.cards || [])
17+
18+
const displaySponsor = computed(() => {
19+
if (sponsorCards.value.length === 0) {
20+
return null
21+
}
22+
return sponsorCards.value[currentSponsorIndex.value]
23+
})
24+
25+
function startCycling() {
26+
stopCycling() // Clear any existing interval before starting a new one
27+
28+
if (sponsorCards.value.length > 1) { // Only cycle if there's more than one sponsor
29+
intervalId = setInterval(() => {
30+
currentSponsorIndex.value = (currentSponsorIndex.value + 1) % sponsorCards.value.length
31+
}, INTERVAL_DURATION)
5832
}
5933
}
6034
61-
let isInitialized = false
62-
function init() {
63-
if (!isInitialized) {
64-
isInitialized = true
65-
refresh()
35+
// Function to stop the ad cycling interval
36+
function stopCycling() {
37+
if (intervalId) {
38+
clearInterval(intervalId)
39+
intervalId = null
6640
}
6741
}
68-
watch(() => page.value.relativePath, () => {
69-
if (isInitialized) {
70-
refresh()
42+
43+
// Lifecycle hook: When the component is mounted, start cycling
44+
onMounted(() => {
45+
if (props.sponsors?.enabled) {
46+
startCycling()
7147
}
7248
})
7349
74-
// no need to account for option changes during dev, we can just
75-
// refresh the page
76-
if (sponsors && sponsors.enabled) {
77-
onMounted(() => {
78-
init()
79-
})
80-
}
50+
// Lifecycle hook: When the component is unmounted, stop cycling
51+
onUnmounted(() => {
52+
stopCycling()
53+
})
54+
8155
</script>
8256

8357
<template>
84-
<div class="VpSponsorCard" ref="container" />
58+
<div class="VpSponsorCard">
59+
<!-- Use Vue's Transition component for smooth fade effects -->
60+
<Transition name="sponsor-fade" mode="out-in">
61+
<div v-if="sponsors?.enabled && displaySponsor" :key="currentSponsorIndex" class="card-content">
62+
<a :href="displaySponsor.href" target="_blank" rel="noopener">
63+
<img :src="displaySponsor.image" :alt="displaySponsor.alt">
64+
</a>
65+
<a :href="displaySponsor.href" target="_blank" rel="noopener" class="carbon-text">
66+
{{ displaySponsor.text }}
67+
</a>
68+
<a href="https://github.com/sponsors/ravitemer" target="_blank" rel="noopener" class="carbon-poweredby">
69+
Featured Sponsor
70+
</a>
71+
</div>
72+
<!-- Optional: Placeholder or empty state when no sponsor is displayed -->
73+
<div v-else>
74+
<!-- Content to display when no sponsor is active or enabled -->
75+
</div>
76+
</Transition>
77+
</div>
8578
</template>
8679

8780
<style scoped>
8881
.VpSponsorCard {
8982
display: flex;
9083
margin-top: 10px;
91-
/* margin-left: 10px; */
9284
justify-content: center;
9385
align-items: center;
9486
padding: 24px;
9587
border-radius: 12px;
96-
min-height: 256px;
88+
min-height: 256px; /* Maintain height during transitions to prevent layout shifts */
9789
text-align: center;
9890
line-height: 18px;
9991
font-size: 12px;
@@ -111,7 +103,7 @@ if (sponsors && sponsors.enabled) {
111103
margin: 0 auto;
112104
padding-top: 12px;
113105
color: var(--vp-carbon-ads-text-color);
114-
transition: color 0.25s;
106+
transition: color 0.2s;
115107
}
116108
117109
.VpSponsorCard :deep(.carbon-text:hover) {
@@ -125,24 +117,31 @@ if (sponsors && sponsors.enabled) {
125117
font-weight: 500;
126118
color: var(--vp-carbon-ads-poweredby-color);
127119
text-transform: uppercase;
128-
transition: color 0.25s;
120+
transition: color 0.2s;
129121
}
130122
131123
.VpSponsorCard :deep(.carbon-poweredby:hover) {
132124
color: var(--vp-carbon-ads-hover-poweredby-color);
133125
}
134126
135-
.VpSponsorCard :deep(> div) {
136-
display: none;
137-
}
138-
139-
.VpSponsorCard :deep(> div:first-of-type) {
140-
display: block;
141-
}
142-
127+
/* Base styles for the content container */
143128
.card-content {
144129
display: flex;
145130
flex-direction: column;
146131
align-items: center;
132+
width: 100%; /* Ensure content fills available space within VpSponsorCard */
133+
/* Opacity and transition handled by Vue's Transition classes */
147134
}
135+
136+
/* Vue Transition classes for fade effect */
137+
.sponsor-fade-enter-active,
138+
.sponsor-fade-leave-active {
139+
transition: opacity 0.2s ease; /* Adjust transition duration as desired */
140+
}
141+
142+
.sponsor-fade-enter-from,
143+
.sponsor-fade-leave-to {
144+
opacity: 0;
145+
}
146+
148147
</style>

0 commit comments

Comments
 (0)