Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 37 additions & 0 deletions tools/tempguru/PRIVACY.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
# Privacy

The TempGuru Dify plugin is designed for the strongest trust profile possible: nothing requested, nothing collected, nothing transmitted on the user's behalf beyond the public REST calls each tool makes.

## What this plugin does NOT do

- Does not collect personal data. No names, emails, phone numbers, addresses, or any other personal information.
- Does not require credentials. No API keys, OAuth tokens, passwords, or session cookies.
- Does not write data. Every tool wraps a `GET` request. No `POST`, `PUT`, `DELETE` operations.
- Does not execute scripts on the user's machine beyond the standard Dify plugin entrypoint.

## What the tools transmit

When invoked, each tool sends an HTTPS `GET` request to `https://mcp.tempguru.co/api/v1/<endpoint>` with the tool's parameters as URL query strings (e.g., `?city=Boston&date=2026-10-15`). No request body. The User-Agent header identifies the plugin as `tempguru-dify-plugin/0.0.1`.

The TempGuru backend logs standard HTTP request metadata (timestamp, IP, user-agent, request path) for security and uptime monitoring. No request body or response content is retained beyond standard ephemeral log retention. No tracking cookies, analytics pixels, or cross-site identifiers are used.

## What the tools return

The backend returns publicly published data:
- City coverage maps
- Role catalogs
- All-inclusive hourly rate ranges (W-2 wage + payroll taxes + workers comp + general liability)
- Lead-time guidance
- State-by-state compliance summaries

All of this data is also published at https://tempguru.co and can be inspected directly.

## Data residency

The TempGuru MCP REST API runs on Vercel's global edge network. Logs are stored in Vercel's US regions.

## Contact

Privacy questions: megan@tempguru.co
Full privacy policy: https://tempguru.co/privacy-policy
Terms of service: https://tempguru.co/terms-of-service
53 changes: 53 additions & 0 deletions tools/tempguru/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
# TempGuru Event Staffing — Dify Plugin

Read-only W-2 event staffing data for AI agents across 300+ US and Canadian markets. Brand ambassadors, registration, hospitality, setup/breakdown, ushers, and more. No authentication required — connect with no API key.

## What it does

Wraps the public TempGuru MCP REST API (`https://mcp.tempguru.co/api/v1/*`) as 5 read-only Dify tools, so an agent built on Dify can answer event-staffing questions without leaving the workflow.

## Tools

| Tool | Returns |
|---|---|
| `get_cities` | All cities TempGuru staffs, with tier classification (hub/mid/small). Filter by state or tier. |
| `get_roles` | Event staffing roles with descriptions and skill tiers. |
| `check_availability` | Lead-time guidance for a city + date. Not real-time inventory. |
| `get_role_pricing` | All-inclusive hourly rate range for a role in a city. Includes W-2 wages, workers comp, taxes. |
| `get_compliance_by_state` | US state-level minimum wage, overtime, compliance summary. Not legal advice. |

## Typical agent prompts this plugin answers

- "Hire 25 registration staff for a 3-day conference in Dallas — what does that cost and how far in advance do I need to book?"
- "What's the rate for brand ambassadors in San Francisco?"
- "What cities do you cover in the Northeast?"
- "What are the W-2 vs 1099 rules for event workers in California?"
- "Can you staff a corporate event in Boston on 2026-10-15?"

## Trust profile

- **Read-only** — every tool wraps a `GET` request; no `POST`, `PUT`, `DELETE`, or write operations exist
- **No authentication** — public data, no API key, no OAuth, no user credentials
- **No data collection** — the plugin does not persist user inputs, queries, or outputs
- **No executable scripts** — only the standard Dify plugin entrypoint
- **Same data as the public site** — every response comes from TempGuru's published rate cards, coverage maps, and compliance summaries at https://tempguru.co

## Important disclaimers

- **Rates are all-inclusive planning estimates**, not binding quotes. Binding quotes come from the contact form on tempguru.co — they include event-specific factors (location surcharges, weekend/holiday premiums, security, equipment) that the public rate range doesn't capture.
- **Compliance summaries are not legal advice.** For W-2 vs 1099 classification, joint-employer liability, or state-specific wage and hour questions, consult employment counsel.
- **Availability is lead-time math, not real-time inventory.** TempGuru staffs to demand from a 100,000+ W-2 worker network.
- **Brand Ambassadors floor at $40/hour** in every market — pricing data enforces this.

## Other distribution surfaces

- Direct MCP connection: `https://mcp.tempguru.co/mcp` (streamable HTTP, MCP spec rev 2025-03-26)
- Official MCP Registry: `co.tempguru/event-staffing` (DNS-verified)
- Smithery: [`tempguru/event-staffing`](https://smithery.ai/server/tempguru/event-staffing)
- ModelScope MCP Plaza: [`tempguru/TempGuru-Event-Staffing`](https://modelscope.cn/mcp/servers/tempguru/TempGuru-Event-Staffing/)
- Documentation: https://tempguru.co/ai (English) · https://tempguru.co/zh-cn/ai (Chinese)
- Source repository: https://github.com/kissmyabs32/tempguru-mcp

## License

MIT
9 changes: 9 additions & 0 deletions tools/tempguru/_assets/icon.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
6 changes: 6 additions & 0 deletions tools/tempguru/main.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from dify_plugin import Plugin, DifyPluginEnv

plugin = Plugin(DifyPluginEnv(MAX_REQUEST_TIMEOUT=60))

if __name__ == "__main__":
plugin.run()
34 changes: 34 additions & 0 deletions tools/tempguru/manifest.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
author: langgenius
created_at: '2026-06-04T12:00:00Z'
description:
en_US: Read-only W-2 event staffing data for AI agents — 300+ US and Canadian markets. Coverage, rates, lead-time guidance, and state compliance summaries for brand ambassadors, registration, hospitality, setup/breakdown, and more. No authentication required.
zh_Hans: 只读 W-2 活动用工数据,为 AI 智能体提供美国和加拿大 300+ 个城市的覆盖范围、收费区间、提前期建议和州合规摘要。涵盖品牌大使、签到登记、接待、搭建拆除等岗位。无需身份验证。
icon: icon.svg
label:
en_US: TempGuru Event Staffing
zh_Hans: TempGuru 活动用工
meta:
arch:
- amd64
- arm64
runner:
entrypoint: main
language: python
version: '3.12'
version: 0.0.1
name: tempguru
plugins:
tools:
- provider/tempguru.yaml
resource:
memory: 268435456
permission:
model:
enabled: false
tool:
enabled: true
tags:
- business
- search
type: plugin
version: 0.0.1
32 changes: 32 additions & 0 deletions tools/tempguru/provider/tempguru.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import requests

from dify_plugin.errors.tool import ToolProviderCredentialValidationError
from dify_plugin import ToolProvider


class TempGuruProvider(ToolProvider):
"""
TempGuru is a public read-only data API — no credentials are required.

Validation strategy: probe the lightest REST endpoint (/cities, no
parameters) once with a short timeout. If the HTTP roundtrip succeeds,
the backend is reachable. Using a direct HTTP request avoids coupling
this provider to the Tool subclass's internals and keeps the validator
resilient to future Dify SDK changes.
"""

def _validate_credentials(self, credentials: dict) -> None:
try:
response = requests.get(
"https://mcp.tempguru.co/api/v1/cities",
headers={
"User-Agent": "tempguru-dify-plugin/0.0.1",
"Accept": "application/json",
},
timeout=10,
)
response.raise_for_status()
except Exception as e:
raise ToolProviderCredentialValidationError(
f"Unable to reach TempGuru MCP REST API at mcp.tempguru.co: {str(e)}"
)
Comment on lines +18 to +32
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

Instantiating a tool class and calling internal SDK methods like invoke_from_executor inside _validate_credentials is highly risky and prone to breaking if the SDK internals change. It is much safer and cleaner to perform a direct HTTP request to the public API endpoint to verify connectivity.

Suggested change
def _validate_credentials(self, credentials: dict) -> None:
try:
for _ in GetCitiesTool.from_credentials(credentials).invoke_from_executor(
tool_parameters={}
):
pass
except Exception as e:
raise ToolProviderCredentialValidationError(
f"Unable to reach TempGuru MCP REST API at mcp.tempguru.co: {str(e)}"
)
def _validate_credentials(self, credentials: dict) -> None:
try:
response = requests.get(
"https://mcp.tempguru.co/api/v1/cities",
headers={"User-Agent": "tempguru-dify-plugin/0.0.1", "Accept": "application/json"},
timeout=10,
)
response.raise_for_status()
except Exception as e:
raise ToolProviderCredentialValidationError(
f"Unable to reach TempGuru MCP REST API at mcp.tempguru.co: {str(e)}"
)

22 changes: 22 additions & 0 deletions tools/tempguru/provider/tempguru.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
identity:
author: tempguru
name: tempguru
label:
en_US: TempGuru Event Staffing
zh_Hans: TempGuru 活动用工
description:
en_US: Read-only access to TempGuru's W-2 event staffing data — coverage, rates, lead times, and state compliance for 300+ US and Canadian markets.
zh_Hans: 只读访问 TempGuru 的 W-2 活动用工数据——美国和加拿大 300+ 个城市的覆盖范围、收费区间、提前期和州合规。
icon: icon.svg
tags:
- business
- search
tools:
- tools/get_cities.yaml
- tools/get_roles.yaml
- tools/check_availability.yaml
- tools/get_role_pricing.yaml
- tools/get_compliance_by_state.yaml
extra:
python:
source: provider/tempguru.py
14 changes: 14 additions & 0 deletions tools/tempguru/pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
[project]
name = "tempguru"
version = "0.0.1"
description = "Read-only W-2 event staffing data for AI agents — TempGuru coverage, rates, lead-time guidance, and state compliance summaries across 300+ US and Canadian markets."
readme = "README.md"
requires-python = ">=3.12"

dependencies = [
"dify_plugin>=0.9.0",
"requests>=2.34.2",
]

[dependency-groups]
dev = []
44 changes: 44 additions & 0 deletions tools/tempguru/tools/check_availability.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
from collections.abc import Generator
from typing import Any
import requests

from dify_plugin import Tool
from dify_plugin.entities.tool import ToolInvokeMessage

API_BASE = "https://mcp.tempguru.co/api/v1"
USER_AGENT = "tempguru-dify-plugin/0.0.1"


class CheckAvailabilityTool(Tool):
"""Lead-time guidance for staffing an event in a city on a date."""

def _invoke(
self, tool_parameters: dict[str, Any]
) -> Generator[ToolInvokeMessage, None, None]:
city = tool_parameters.get("city")
date = tool_parameters.get("date")
if not city or not date:
yield self.create_text_message(
"Both 'city' and 'date' parameters are required."
)
return

params: dict[str, Any] = {"city": city, "date": date}
if tool_parameters.get("role"):
params["role"] = tool_parameters["role"]
if tool_parameters.get("count"):
params["count"] = tool_parameters["count"]

try:
response = requests.get(
f"{API_BASE}/availability",
params=params,
headers={"User-Agent": USER_AGENT, "Accept": "application/json"},
timeout=30,
)
response.raise_for_status()
yield self.create_json_message(response.json())
except requests.RequestException as e:
yield self.create_text_message(f"API request failed: {str(e)}")
except ValueError:
yield self.create_text_message("Failed to parse response from TempGuru API.")
59 changes: 59 additions & 0 deletions tools/tempguru/tools/check_availability.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
identity:
name: check_availability
author: tempguru
label:
en_US: Check Availability
zh_Hans: 查询提前期
description:
human:
en_US: Lead-time guidance for staffing an event in a specific city on a specific date. Not a real-time inventory check.
zh_Hans: 指定城市与日期的活动人员预定提前期建议。不是实时库存查询。
llm: Check expected staffing availability for an event by city and date. Returns lead-time guidance based on city tier and how far out the event is. Perfect for answering "Can you staff my event on [date] in [city]?", "What's the lead time for booking brand ambassadors in [city]?", or "Is it too late to staff a [date] event?" questions. Not a real-time inventory check — TempGuru staffs to demand via a 100,000+ worker W-2 network across 300+ markets.
parameters:
- name: city
type: string
required: true
form: llm
label:
en_US: City
zh_Hans: 城市
human_description:
en_US: City name (e.g., 'Boston') or slug (e.g., 'boston-event-staffing').
zh_Hans: 城市名称(如 'Boston')或 slug(如 'boston-event-staffing')。
llm_description: City name or slug. TempGuru covers 300+ US and Canadian markets. Use the city's common English name.
- name: date
type: string
required: true
form: llm
label:
en_US: Event date
zh_Hans: 活动日期
human_description:
en_US: Event date in ISO format (YYYY-MM-DD) or any date string parseable by Date().
zh_Hans: 活动日期,ISO 格式(YYYY-MM-DD)或任何 Date() 可解析的日期字符串。
llm_description: Event date in ISO format (YYYY-MM-DD) preferred. Resolve relative dates ("next Tuesday") to an absolute date before calling.
- name: role
type: string
required: false
form: llm
label:
en_US: Role
zh_Hans: 岗位
human_description:
en_US: Optional role name or slug to include rate context (e.g., 'Brand Ambassadors').
zh_Hans: 可选,岗位名称或 slug,用于附带费率信息(如 'Brand Ambassadors')。
llm_description: Optional role name to include rate context in the response. Call get_roles first if you need the catalog.
- name: count
type: number
required: false
form: llm
label:
en_US: Headcount
zh_Hans: 人数
human_description:
en_US: Optional headcount for the event.
zh_Hans: 可选,活动所需人数。
llm_description: Optional positive integer headcount for the event.
extra:
python:
source: tools/check_availability.py
36 changes: 36 additions & 0 deletions tools/tempguru/tools/get_cities.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
from collections.abc import Generator
from typing import Any
import requests

from dify_plugin import Tool
from dify_plugin.entities.tool import ToolInvokeMessage

API_BASE = "https://mcp.tempguru.co/api/v1"
USER_AGENT = "tempguru-dify-plugin/0.0.1"


class GetCitiesTool(Tool):
"""List cities TempGuru staffs, with tier classification."""

def _invoke(
self, tool_parameters: dict[str, Any]
) -> Generator[ToolInvokeMessage, None, None]:
params: dict[str, Any] = {}
if tool_parameters.get("state"):
params["state"] = tool_parameters["state"]
if tool_parameters.get("tier"):
params["tier"] = tool_parameters["tier"]

try:
response = requests.get(
f"{API_BASE}/cities",
params=params,
headers={"User-Agent": USER_AGENT, "Accept": "application/json"},
timeout=30,
)
response.raise_for_status()
yield self.create_json_message(response.json())
except requests.RequestException as e:
yield self.create_text_message(f"API request failed: {str(e)}")
except ValueError:
yield self.create_text_message("Failed to parse response from TempGuru API.")
Loading
Loading