用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
直接命令不会经过审查 Prompt;运行前请先检查来源。
npx skills add https://github.com/bobmatnyc/claude-mpm-skills --skill phoenix-api-channels命令会保持在同一行。复制前请横向滚动并检查完整内容。
想先保存到本地?可下载 SkillsMP 当前能够提供的文件。
LinkedIn automation via the Linked API CLI - fetch profiles, search people and companies, send messages, manage connections, create posts, react, comment, and run Sales Navigator and custom workflows. Use when the user wants to interact with LinkedIn.
Xquik X data automation API - Use REST or MCP for tweet search, user lookup, follower exports, media downloads, monitors, webhooks, giveaway draws, and confirmation-gated X actions.
MCP (Model Context Protocol) - Build AI-native servers with tools, resources, and prompts. TypeScript/Python SDKs for Claude Desktop integration.
基于 SOC 职业分类
正在显示 SKILL.md
| name | phoenix-api-channels |
| description | Phoenix controllers, JSON APIs, Channels, and Presence on the BEAM |
| user-invocable | false |
| disable-model-invocation | true |
| version | 1.0.0 |
| category | toolchain |
| author | Claude MPM Team |
| license | MIT |
| progressive_disclosure | {"entry_point":{"summary":"Phoenix REST/JSON + Channels/Presence on the BEAM with contexts, plugs, auth, and PubSub.","when_to_use":["Building JSON APIs with Phoenix controllers and versioned routes","Adding WebSocket/Channels for chat, notifications, or collaborative features","Needing Presence tracking, fan-out broadcasts, and PubSub-backed updates","Integrating Ecto contexts for persistence and domain boundaries"],"quick_start":["mix phx.new my_api --no-html --no-live && cd my_api","mix deps.get && mix ecto.create","Define contexts + schemas; add routes/controllers; wire `socket` + Channel modules","Start server: mix phx.server (REST + WebSocket on http://localhost:4000)"]},"token_estimate":{"entry":170,"full":5200}} |
Phoenix excels at REST/JSON APIs and WebSocket Channels with minimal boilerplate, leveraging the BEAM for fault tolerance, lightweight processes, and supervised PubSub/Presence.
Core pillars
mix phx.new my_api --no-html --no-live
cd my_api
mix deps.get
mix ecto.create
mix phx.server
Key files:
lib/my_api_web/endpoint.ex — plugs, sockets, instrumentationlib/my_api_web/router.ex — pipelines, scopes, versioning, socketslib/my_api_web/controllers/* — REST/JSON controllerslib/my_api/* — contexts + Ecto schemas (ownership of data logic)lib/my_api_web/channels/* — Channel modulesSeparate browser vs API pipelines; version APIs with scopes.
defmodule MyApiWeb.Router do
use MyApiWeb, :router
pipeline :api do
plug :accepts, ["json"]
plug :fetch_session
plug :protect_from_forgery
plug MyApiWeb.Plugs.RequireAuth
end
scope "/api", MyApiWeb do
pipe_through :api
scope "/v1", V1, as: :v1 do
resources "/users", UserController, except: [:new, :edit]
post "/sessions", SessionController, :create
end
end
socket "/socket", MyApiWeb.UserSocket,
websocket: [connect_info: [:peer_data, :x_headers]],
longpoll: false
end
Tips
socket "/socket" for Channels; restrict transports as needed.Controllers stay thin; contexts own the logic.
defmodule MyApiWeb.V1.UserController do
use MyApiWeb, :controller
alias MyApi.Accounts
action_fallback MyApiWeb.FallbackController
def index(conn, _params) do
users = Accounts.list_users()
render(conn, :index, users: users)
end
def create(conn, params) do
with {:ok, user} <- Accounts.register_user(params) do
conn
|> put_status(:created)
|> put_resp_header("location", ~p\"/api/v1/users/#{user.id}\")
|> render(:show, user: user)
end
end
end
FallbackController centralizes error translation ({:error, :not_found} → 404 JSON).
Plugs
RequireAuth verifies bearer/session tokens, sets current_user.plug :scrub_params-style transforms in pipelines, not controllers.Contexts expose only what controllers/channels need.
defmodule MyApi.Accounts do
import Ecto.Query, warn: false
alias MyApi.{Repo, Accounts.User}
def list_users, do: Repo.all(User)
def get_user!(id), do: Repo.get!(User, id)
def register_user(attrs) do
%User{}
|> User.registration_changeset(attrs)
|> Repo.insert()
end
end
Guidelines
Ecto.Multi for multi-step operations.Scrivener, Flop) for large lists.Channel module example:
defmodule MyApiWeb.RoomChannel do
use Phoenix.Channel
alias Phoenix.Presence
def join("room:" <> room_id, _payload, socket) do
send(self(), :after_join)
{:ok, assign(socket, :room_id, room_id)}
end
def handle_info(:after_join, socket) do
Presence.track(socket, socket.assigns.user_id, %{online_at: System.system_time(:second)})
push(socket, "presence_state", Presence.list(socket))
{:noreply, socket}
end
def handle_in("message:new", %{"body" => body}, socket) do
broadcast!(socket, "message:new", %{user_id: socket.assigns.user_id, body: body})
{:noreply, socket}
end
end
PubSub from contexts
def create_order(attrs) do
with {:ok, order} <- %Order{} |> Order.changeset(attrs) |> Repo.insert() do
Phoenix.PubSub.broadcast(MyApi.PubSub, "orders", {:order_created, order})
{:ok, order}
end
end
Best practices
UserSocket.connect/3 before joining topics."tenant:" <> tenant_id <> ":room:" <> room_id).authorization: Bearer <token>; verify in plug, assign current_user.Phoenix.Token.sign/verify for short-lived join params.Endpoint with cors_plug.Use generated helpers:
defmodule MyApiWeb.UserControllerTest do
use MyApiWeb.ConnCase, async: true
test "lists users", %{conn: conn} do
conn = get(conn, ~p\"/api/v1/users\")
assert json_response(conn, 200)["data"] == []
end
end
Channel tests:
defmodule MyApiWeb.RoomChannelTest do
use MyApiWeb.ChannelCase, async: true
test "broadcasts messages" do
{:ok, _, socket} = connect(MyApiWeb.UserSocket, %{"token" => "abc"})
{:ok, _, socket} = subscribe_and_join(socket, "room:123", %{})
ref = push(socket, "message:new", %{"body" => "hi"})
assert_reply ref, :ok
assert_broadcast "message:new", %{body: "hi"}
end
end
DataCase: isolates DB per test; use fixtures/factories for setup.
:telemetry events from endpoint, controller, channel, and Ecto queries; export via OpentelemetryPhoenix and OpentelemetryEcto.Plug.Telemetry for request metrics; add logging metadata (request_id, user_id).MIX_ENV=prod mix release; configure runtime in config/runtime.exs.libcluster + distributed PubSub for multi-node Presence.UserSocket.connect/3, leading to topic exposure.action_fallback → inconsistent error shapes.Phoenix API + Channels shine when contexts own data, controllers stay thin, and Channels use PubSub/Presence with strict authorization and telemetry. The BEAM handles concurrency and fault tolerance; focus on clear boundaries and real-time experiences.