mcpField
R
revamp

revamp

远程服务
revampvacations.com地图与出行0今天更新

关于 revamp

revamp 是面向旅行者和旅游经营者的亚美尼亚旅游市场平台,可浏览住宿、餐厅、旅游和地区体验,并根据实时已发布目录生成行程。平台还提供经营者刊登管理与审核流程;目前尚未接入实际付款。

主要功能

  1. 01搜索并筛选旅游目录
  2. 02地图与亚美尼亚图集浏览
  3. 03按实时目录生成逐日行程
  4. 04经营者管理住宿和旅游项目
  5. 05审核后发布新项目

适用场景

  1. 01查找特定地区的住宿、餐厅或旅游
  2. 02根据已发布项目规划逐日行程
  3. 03经营者提交和维护住宿或旅游项目

配置

远程服务无需本地安装。选择你使用的客户端,复制配置或使用一键安装。

服务地址https://mcp.revampvacations.com/mcp
一键复制安装命令
Claude CodeTerminal
Cursor.cursor/mcp.json
VS Code.vscode/mcp.json
Claude Desktopclaude_desktop_config.json
Windsurf~/.codeium/windsurf/mcp_config.json

命令在终端中运行;JSON 粘贴到对应客户端的 MCP 配置后重启。需要授权的服务会在首次连接时提示登录。

工具

4
参数类型必填说明
typeenum否限定为一种列表类型。stay | tour | experience | eat | place
limitinteger否最大结果数(默认值为 10)。
querystring否按标题、描述、标签、菜系和城市进行全文匹配。
regionstring否亚美尼亚的地区或城市,例如 'Yerevan'、'Tavush'、'Dilijan'。
cuisinestring否适用于餐厅:菜系或场所类型,例如 'Armenian'、'Fast food'。

详细介绍

重塑 Revamp 旅行市场

Revamp Travel 是一个双边 Armenian 旅行市场。旅行者可以通过编辑内容、搜索和交互式 Armenia 地图册,浏览住宿地点、餐厅、旅行团和地区体验。运营商可以注册自己的账户并创建住宿/旅行团列表——也可以从其他网站上的现有列表链接开始,快速预填信息——之后这些列表会经过简短审核,才会在其他地方显示。AI 行程规划器会根据实时发布的目录生成行程。

当前状态

该代码库是一个全栈应用:React SPA 直接连接 Supabase(Postgres + Auth + Row-Level Security),用于管理账户和列表;前端还有一个小型 Express API,负责两项工作——由 Anthropic 提供支持的行程规划器,以及供运营商控制面板使用的链接导入预填辅助功能。这是里程碑 A:真实账户、真实的运营商自有列表、由 RLS 强制执行的所有权,以及审核/发布关卡——但尚未接入真实支付。预订 CTA 会如实显示相应状态:未登录时显示“登录以预订”;已登录时显示禁用的“支付功能即将推出”状态。显示的价格是真实价格(每个列表中的 price_cents),但目前不会收取任何费用——这属于里程碑 B(Stripe),已在 CLAUDE.md 中规划,但尚未构建。

区域包含内容
首页探索主视觉、统一搜索、类别入口、精选列表、地区、地图册预览和结尾 CTA。
市场目录文本搜索、类别筛选、地区筛选、空状态、响应式卡片,以及桌面/移动端地图视图。
列表住宿/餐厅共用详情模板,以及专用的 GetYourGuide 风格旅行团详情布局;两者均包含图库、详情、设施、根据身份验证状态显示的预订 CTA、位置地图册和相关记录。
账户(/login、/signup)通过 Supabase Auth 自助注册为旅行者或运营商。
运营商控制面板(/dashboard)添加、编辑和删除自己的住宿和旅行团列表,也可以从粘贴的链接开始(尽力从该页面自身的公开元数据中预填标题/描述/照片引用——绝不抓取网页,也绝不自动保存第三方照片)。新列表和重新提交的列表会进入审核,审核通过前对其他人不可见;已上线列表的编辑会立即保存。写入操作直接发送到 Supabase,并由 Row-Level Security 限定为已登录的运营商所有——而非依赖客户端强制执行。餐厅列表仅由编辑团队维护/作为种子数据提供。
审核队列(/admin)批准待审核列表或退回列表;仅有一个管理员账户(通过 SQL 提升权限,不提供注册切换项)。批准后立即发布;附上备注退回列表后,运营商可以修正并重新提交。
AI 行程规划器(/plan)按天生成行程,由服务端调用 Anthropic API,并以网站的实时已发布住宿/旅行团/餐厅目录为依据。需要 ANTHROPIC_API_KEY(见下文“环境”)。
地图基于确定性 SVG 的 Armenia 地图册,包含价格标记和同步选择。无需外部地图密钥。
品牌实现 Revamp 品牌手册:小写的 revamp. 字标、紧凑标志 re.、#F15822 橙色、#212121 炭灰色、白色、圆角造型和无衬线字体。

技术

客户端使用 React 19、TypeScript、Vite 7、Tailwind CSS 4、Wouter、Radix UI/shadcn 组件、Lucide 图标和 Sonner,并直接连接 Supabase(@supabase/supabase-js)来处理身份验证和列表。Express、Zod 和官方 @anthropic-ai/sdk 保留在服务端,用于处理唯一需要浏览器无法持有的密钥的路由——AI 行程规划器。列表不再使用 JSON 文件或进程内存储。

要求

使用 Node.js 22 或更高版本、pnpm 10 或更高版本,以及一个 Supabase 项目(免费套餐即可)。

node --version
pnpm --version

本地设置

pnpm install
cp .env.example .env
# fill in VITE_SUPABASE_URL / VITE_SUPABASE_ANON_KEY to run against real accounts + listings
# fill in ANTHROPIC_API_KEY to enable /plan
pnpm dev

如果未设置 Supabase 变量,应用仍可运行,并使用静态的 shared/listings.ts 种子数据作为只读备用数据进行浏览(ListingsContext 会报告 offline: true)——足以查看界面,但注册、登录和任何写入操作都会失败。请参阅下方的“Supabase 设置”,以启用真实数据。

pnpm dev 会通过 concurrently 同时运行两个进程:Vite(客户端,支持 HMR)和 Express API(通过 tsx watch 运行 server/index.ts,监听 API_PORT,默认值为 3001)——API 进程现在只提供 /api/plan-trip。Vite 会将 /api/* 请求代理到该进程,因此打开 Vite 输出的 URL 即可——无需直接访问 API 自己的端口。

Supabase 设置

  1. 在 supabase.com 创建项目。从其 API 设置中复制 Project URL 和 anon/public key,填入 .env 中的 VITE_SUPABASE_URL / VITE_SUPABASE_ANON_KEY。

  2. 按顺序各运行一次 supabase/migrations/0001_init.sql 和 supabase/migrations/0002_review_gate_and_admin.sql——将它们粘贴到 SQL Editor 中,或使用 CLI 通过 supabase db push/psql 运行。两者会创建 profiles、listings、审核门控触发器,以及应用所依赖的所有行级安全策略。

  3. 启动应用(pnpm dev,或部署应用),并在 /signup 注册一个真实账户,选择 Operator。该账户将成为用于管理种子目录的“Revamp”主账户。

  4. 仅在本地,将 SUPABASE_SERVICE_ROLE_KEY(从同一 API 设置页面获取——请妥善保密)、SEED_OPERATOR_EMAIL 和 SEED_OPERATOR_PASSWORD(第 3 步创建的账户)添加到 .env,然后运行:

    pnpm seed:catalog
    

    这会将 shared/listings.ts 中的种子住宿、旅行团和餐厅导入真实的 listings 表,并归属到该运营者账户;这些条目会自动通过审核并立即上线(已审核内容的批量导入不应进入审核队列)。可安全重复运行——系统会按 slug 匹配已有记录并跳过。具体说明为何餐厅导入需要服务角色密钥,请参阅 scripts/seed-catalog.ts 文件头部的注释。

  5. 若要审核真实提交,请为自己注册一个单独账户(不要使用主账户),并将其提升为管理员——在 /signup 正常注册,在 Supabase 控制面板中找到你的用户 ID(Authentication → Users),然后在 SQL Editor 中运行:

    update public.profiles set role = 'admin' where id = '<your-user-id>';
    

    按设计,用户无法自行注册管理员账户。使用该账户登录并打开 /admin,即可批准待审核条目,或附上说明将其退回。

验证和生产构建

pnpm check
pnpm build
pnpm preview

pnpm build 会将客户端构建到 dist/public,并将 Express 服务打包到 dist/index.js。pnpm preview(Vite 的静态预览)只会提供客户端——构建后如需运行完整应用:

pnpm start

此单一进程会在同一个 PORT(默认值为 3000)上提供已构建的 SPA 和 /api/plan-trip 路由。

项目结构

client/
  index.html
  public/
    brand/revamp-mark.svg
    images/                 # self-hosted brand illustrations (see Assets below)
  src/
    components/
      ui/
      ArmeniaMap.tsx
      BookingCta.tsx         # auth-aware booking CTA, shared by every listing detail layout
      BrandMark.tsx
      ListingCard.tsx
      RequireRole.tsx        # route guard for /dashboard
      SearchBar.tsx
      SiteFooter.tsx
      SiteHeader.tsx          # includes the auth-aware account menu
      TourCard.tsx
      TourDetail.tsx
    contexts/
      ThemeContext.tsx
      AuthContext.tsx         # Supabase Auth session/profile state (traveler | operator | admin)
      ListingsContext.tsx     # live catalog: reads/writes the Supabase `listings` table directly
    data/
      listings.ts             # thin compatibility barrel over shared/listings.ts
    lib/
      api.ts                   # fetch wrapper for /api/plan-trip and /api/import-listing
      supabase.ts               # browser Supabase client
      slug.ts                   # slugify() for new listing titles
      tourFacts.ts
    pages/
      Explore.tsx
      Home.tsx
      ListingPage.tsx
      Dashboard.tsx            # operator-only: add/edit/delete own stay & tour listings, link-prefill
      AdminReview.tsx           # admin-only: approve/reject pending listings
      Login.tsx
      Signup.tsx
      MapPage.tsx
      Plan.tsx                 # AI trip planner
      Tours.tsx
      NotFound.tsx
    App.tsx
    index.css
    main.tsx
server/
  index.ts                   # Express app: JSON body parsing, API routes, static SPA serving
  routes.ts                  # POST /api/plan-trip and POST /api/import-listing — listings CRUD is gone (Supabase + RLS replaced it)
  supabase.ts                 # anon-key server client: planner catalog digest + verifyUser() for import-listing auth
  urlPrefill.ts                # best-effort OpenGraph/meta-tag fetch for the link-prefill assist, with an SSRF guard
  planner.ts                  # Anthropic API call + prompt/response handling for the trip planner
supabase/
  migrations/
    0001_init.sql              # profiles + listings schema, triggers, and every RLS policy
    0002_review_gate_and_admin.sql  # pending/review-note columns, admin role, review-gate trigger
scripts/
  seed-catalog.ts              # one-time import of shared/listings.ts into the live `listings` table
shared/
  listings.ts                # canonical Listing type, seed data, and constants (client + server + scripts)
  const.ts
CLAUDE.md
brandbook-implementation.md
marketplace-spec.md
ENVIRONMENT.md

产品路由

URL用途
/编辑精选首页和统一搜索。
/explore展示所有条目,支持搜索和筛选。
/explore/stay住宿分类。
/explore/eat餐厅分类。
/explore/tour旅行团分类(专用的 GetYourGuide 风格浏览器)。
/map以地图为核心的探索页面。
/listing/:slug单个条目的详情页。
/planAI 行程规划器。
/dashboard仅限运营者:添加、编辑和删除自己的住宿和旅行团条目。
/admin仅限管理员:审核待处理条目、批准条目或附上说明将其退回。
/login登录。
/signup注册成为旅行者或运营者。

编辑清单

根据操作内容,有两种方式:

  • **日常操作/供实际运营人员使用:**以运营人员身份在 /signup 注册,然后打开 /dashboard 并使用表单界面;也可以先使用“从链接预填”,从粘贴的 URL 自身的公开元数据中填入标题/描述。写入内容会直接进入 Supabase listings 表,并通过行级安全(Row-Level Security,supabase/migrations/0001_init.sql、0002_review_gate_and_admin.sql)限定为仅限你自己的账户——客户端无法自行强制执行这一限制。新建或重新提交的清单会设为 pending,在管理员于 /admin 批准之前不会显示在任何其他位置;编辑已发布的清单后会立即保存并显示(包括卡片、筛选条件、地图标记、相关内容以及基于 slug 的详情页,这些内容都通过 client/src/contexts/ListingsContext.tsx 中的 ListingsContext 实时读取),无需再次审核。
  • 为全新安装植入数据:shared/listings.ts 是一次性数据源,pnpm seed:catalog(scripts/seed-catalog.ts)会将其中内容导入 Supabase listings 表,并归属一个名为 “Revamp” 的内部运营账户——请参阅上文的 Supabase 设置。之后编辑 shared/listings.ts 只会影响未来运行 pnpm seed:catalog 时的数据(可以安全地重复运行;现有行会按 slug 匹配并跳过),不会影响已上线的行。餐厅(type: "eat")仅用于种子数据/编辑内容;RLS 完全没有针对 type = 'eat' 的插入策略,因此任何运营人员——包括内部账户——都无法通过常规应用创建、编辑或删除此类条目(shared/listings.ts 中的 EDITABLE_LISTING_TYPES 仅包含 stay 和 tour)。

无论采用哪种方式:坐标都必须在亚美尼亚境内(纬度 38–42,经度 43–47——由数据库检查约束强制执行),不得编造客户评分、评论、推荐语、预订次数或认证声明。

品牌指南

进行视觉更改前,请先阅读 brandbook-implementation.md。正式品牌系统简约且严格受控。请使用完整的小写 revamp. 字标(末尾带句点)、紧凑的 re. 标识、橙色 #F15822、炭灰色 #212121 和白色 #FFFFFF。指定的品牌字体系列为 Circular Std;除非环境中提供了 Circular Std,否则代码会使用获得许可、可安全用于 Web 的视觉替代字体 Manrope。

资源与可移植性

图片 URL 定义在 shared/listings.ts 中。所有随项目提供的图片都是自托管的品牌插图,位于 client/public/images/ 下(纯 SVG,不会发起外部请求)——该市场没有任何外部图片依赖,图片功能可完全离线/在隔离网络环境中运行。只要有真实摄影图片,就请替换为真实照片:更新 shared/listings.ts 顶部的 assets 映射并重新植入数据,或者通过 /dashboard 为每条清单设置 image URL(仅限 stay/tour)。

环境

目录和浏览体验无需任何密钥即可只读运行(使用静态种子数据作为回退),但账户和实际写入需要 VITE_SUPABASE_URL/VITE_SUPABASE_ANON_KEY。AI 行程规划器需要 ANTHROPIC_API_KEY(仅在服务端使用,不会发送到浏览器)。链接预填助手(POST /api/import-listing)无需新增密钥——它会复用同一个 anon-key Supabase 客户端来验证调用者是否已登录,然后直接获取粘贴的 URL。完整变量列表请参阅 ENVIRONMENT.md,其中还包括仅供种子脚本使用的 Supabase service-role 密钥,以及可选的 ANTHROPIC_MODEL/API_PORT 覆盖项。

Claude Code

Claude Code 应先阅读 CLAUDE.md。该文件介绍了架构、不可妥协的内容/品牌/支付诚信约束、Supabase 数据模型和 RLS 设计、路由行为、组件规范、资源模型、质量门槛以及常见更改方案。

部署说明

服务仍有两个有意保留的职责(参见 CLAUDE.md):调用 Anthropic API 规划行程,以及获取用户粘贴的 URL 的公开元数据,以辅助预填链接(需通过登录检查和 SSRF 防护)。其余所有功能——账户、房源、所有权以及审核/发布关卡——都由 Supabase 负责,并通过行级安全策略和数据库触发器保护,而非依赖应用代码。目前仍没有真正的支付处理或预订确认;那是里程碑 B,是像这次升级一样有意规划的升级,而不是临时加到 BookingCta.tsx 上。要部署为单个 Node 进程:按顺序运行两个 Supabase 迁移(0001_init.sql,然后是 0002_review_gate_and_admin.sql)并运行一次种子脚本,将你自己的账户提升为 admin(参见上文 Supabase 设置),使用 pnpm build 构建,并设置 PORT、VITE_SUPABASE_URL、VITE_SUPABASE_ANON_KEY 和 ANTHROPIC_API_KEY 后运行 pnpm start。

Netlify(无服务器)

此仓库已配置为部署到 Netlify,API 将作为无服务器函数运行,而非持久进程:

  • netlify.toml — 执行 pnpm build 构建 → 发布 dist/public;函数目录为 netlify/functions;在 /* 上配置 prerender 边缘函数;将 /api/* → /.netlify/functions/api/:splat 重写;将 /robots.txt + /sitemap.xml 重写到函数;为 wouter 配置 SPA 回退(/* → /index.html);并在 /dashboard//admin 上设置 X-Robots-Tag: noindex 标头。
  • netlify/functions/api.ts — 使用 serverless-http 封装共享的 Express app(server/app.ts)。API 包括 POST /api/plan-trip、POST /api/import-listing、POST /api/sync-ical、动态生成的 robots.txt/sitemap.xml,以及 GET /api/prerender;账户、房源和审核关卡则由浏览器在 RLS 保护下直接连接 Supabase。
  • netlify/edge-functions/prerender.ts — 用于 SEO/爬虫发现。Deno 边缘函数会为非 JS 爬虫(Googlebot、GPTBot、ClaudeBot、PerplexityBot、Twitterbot,……)提供由 server/prerender.ts 生成的真实服务器渲染 HTML(通过 /api/prerender),而真实访客则收到未经修改的 SPA。浏览器和 JS 爬虫所需的真实页面级 <title>/meta/OG/JSON-LD 由 client/src/hooks/useDocumentMeta.ts 提供。无需新增依赖或环境变量——渲染器使用手写 HTML,robots/sitemap 的来源则根据每个请求推导。
  • 环境变量(Site configuration → Environment variables):
    • VITE_SUPABASE_URL、VITE_SUPABASE_ANON_KEY — 构建时(Vite 会将其内联到客户端)和函数运行时(规划器会读取已发布的目录,且 /api/import-listing 会使用 anon key 验证调用方的 bearer token)都需要这些变量。首次构建前就应设置;值必须是完整的 https://<project-ref>.supabase.co,否则客户端会回退到只读的 shared/listings.ts 种子数据。更改这些值需要重新构建(重新部署),仅保存变量并不足够。
    • ANTHROPIC_API_KEY(以及可选的 ANTHROPIC_MODEL)— 仅在运行时使用,供 /api/plan-trip 使用。
    • 切勿在 Netlify 上设置 SUPABASE_SERVICE_ROLE_KEY — 它仅用于在本地一次性运行 pnpm seed:catalog。
  • 将 GitHub 仓库连接到 Netlify 后,每次推送到 main 都会持续部署。Supabase 迁移(0001–0005,包括 0005 为运营人员上传照片创建的 listing-photos Storage 存储桶)、pnpm seed:catalog 以及管理员权限提升都是单独的一次性步骤(参见 Supabase 设置)。

评论

支持 Markdown

第一次接触 MCP?

从协议是什么,到在客户端里装上第一个服务,这几条回答覆盖了大多数入门问题。

一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。