The ws/wss transport carries a raw byte stream (yamux), but the
golang.org/x/net/websocket Conn defaults to text frames (PayloadType
TextFrame). Per RFC 6455 §5.6 a text frame must contain valid UTF-8, so
RFC-compliant intermediaries (API gateways / reverse proxies) validate
the payload and close the connection when the binary tunnel data is not
valid UTF-8.
This goes unnoticed peer-to-peer because x/net/websocket does not
validate UTF-8 on read, but it breaks the connection through a compliant
validating proxy. Set PayloadType to BinaryFrame on both the server
listener and the client dialer so the tunnel is framed as binary.
Move the frps dashboard Clients and Proxies views to the paginated
/api/v2/clients and /api/v2/proxies endpoints instead of fetching all
data at once, and extend server-side proxy search so the search box
keeps working under pagination.
Frontend:
- Add V2Envelope/V2Page types and getV2 HTTP helper to api/http.ts
- Add v2 paginated fetch functions to api/client.ts and api/proxy.ts
- Add ClientV2Info and ProxyV2Info types for v2 API responses
- Rewrite Clients.vue with server-side pagination, status/user search
filtering, and ElPagination component
- Rewrite Proxies.vue with server-side pagination, type tabs, client
dropdown filter, and a search box that passes q to the API
- Default page size 10, selectable sizes [10, 20, 50, 100]
Backend:
- Extend /api/v2/proxies q matching to also cover online proxy spec
fields: TCP/UDP remotePort and HTTP/HTTPS/TCPMux customDomains and
subdomain, so dashboard search no longer needs to scan every page
- Add controller_v2 tests for the new spec-field matching
SUDP payload codec follows transport wireProtocol; same-protocol v1/v1 and v2/v2 keep raw join; only mixed proxy/visitor protocols use message-aware bridge; no new capability/selection field.
* auth/oidc: cache OIDC access token and refresh before expiry
- Use Config.TokenSource(ctx) once at init to create a persistent
oauth2.TokenSource that caches the token and only refreshes on expiry
- Wrap with oauth2.ReuseTokenSourceWithExpiry for configurable early refresh
- Add tokenRefreshAdvanceDuration config option (default: 300s)
- Add unit test verifying token caching with mock HTTP server
* address review comments
* auth/oidc: fallback to per-request token fetch when expires_in is missing
When an OIDC provider omits the expires_in field, oauth2.ReuseTokenSource
treats the cached token as valid forever and never refreshes it. This causes
server-side OIDC verification to fail once the JWT's exp claim passes.
Add a nonCachingTokenSource fallback: after fetching the initial token, if
its Expiry is the zero value, swap the caching TokenSource for one that
fetches a fresh token on every request, preserving the old behavior for
providers that don't return expires_in.
* auth/oidc: fix gosec lint and add test for zero-expiry fallback
Suppress G101 false positive on test-only dummy token responses.
Add test to verify per-request token fetch when expires_in is missing.
Update caching test to account for eager initial token fetch.
* fix lint