# Behavior traces — labstack/echo

> Canonical page: https://codevetter.com/unpack/echo/behavior-traces

# Behavior traces — labstack/echo

Scanned commit 99c395d846e079d4cffd29de9298d1dd829e8b04 (2026-10-01). Generated by codevetter codevetter 1.15.0 on 2026-10-02.

Source inspection; upstream code and tests were not executed.

The following traces follow source execution order through concrete framework flows. Startup proceeds from construction and registration into listener creation and shutdown coordination. A bound API request proceeds through dispatch, input conversion, and output serialization. Static-file delivery, proxy requests, and rate-limit decisions expose additional filesystem, network, and state boundaries.
- Startup configuration: New → NewRouter → contextPool.New installation → buildRouterChains; GET → Add → Echo.add → optional OnAddRoute → Router.Add. Registration also raises contextPathParamAllocSize when a route needs more parameters. — [echo.go#L400-L443](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L400-L443) [echo.go#L541-L545](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L541-L545) [echo.go#L739-L773](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L739-L773)
- Server startup and stop: Echo.Start → signal.NotifyContext → StartConfig.Start → start → Listen → optional tls.NewListener → BeforeServeFunc → server.Serve. Context cancellation triggers gracefulShutdown → server.Shutdown with a default ten-second timeout; http.ErrServerClosed is suppressed. — [echo.go#L870-L874](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L870-L874) [server.go#L63-L65](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/server.go#L63-L65) [server.go#L119-L167](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/server.go#L119-L167) [server.go#L181-L200](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/server.go#L181-L200)
- Request dispatch: ServeHTTP → serveHTTP → Context.Reset → preChain when registered → Router.Route → global chain → dispatch → route handler. applyMiddleware wraps in reverse registration order so the first registered middleware enters first; returned errors reach HTTPErrorHandler. — [echo.go#L430-L443](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L430-L443) [echo.go#L828-L846](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L828-L846) [echo.go#L911-L915](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L911-L915)
- Bound API input: handler calls Context.Bind → DefaultBinder.Bind → BindPathValues → method-conditional BindQueryParams → BindBody. JSON bodies call JSONSerializer.Deserialize; unsupported nonempty body media types return 415. Validation occurs only if the handler separately calls Context.Validate. — [context.go#L459-L469](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/context.go#L459-L469) [bind.go#L68-L105](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/bind.go#L68-L105) [bind.go#L127-L140](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/bind.go#L127-L140) [json.go#L47-L65](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/json.go#L47-L65)
- API output/error: Context.JSON → json → DefaultJSONSerializer.Serialize → delayedStatusWriter.Write → Response.WriteHeader/Write. On a returned error, DefaultHTTPErrorHandler checks commitment, extracts HTTPStatusCoder, chooses JSON payload shape, and sends NoContent instead of JSON for HEAD. — [context.go#L568-L592](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/context.go#L568-L592) [json.go#L28-L33](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/json.go#L28-L33) [response.go#L149-L157](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/response.go#L149-L157) [echo.go#L465-L517](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L465-L517)
- Static file delivery: Echo.Static → MustSubFS → GET wildcard registration → StaticDirectoryHandler. At request time the handler rejects unclean paths, optionally unescapes and rechecks them, runs fs.Stat, redirects directories when needed, then fsFile opens the file/index and calls http.ServeContent. — [echo.go#L629-L637](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L629-L637) [echo.go#L665-L702](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L665-L702) [echo.go#L976-L981](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/echo.go#L976-L981) [context.go#L704-L729](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/context.go#L704-L729)
- Proxy action: ProxyConfig.ToMiddleware → rewriteURL → overwrite IP/scheme headers → Balancer.Next → store selected target → proxyHTTP or proxyRaw. HTTP errors are stored under _error; retries require remaining RetryCount and RetryFilter approval, while missing targets immediately return 502. — [middleware/proxy.go#L337-L411](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/middleware/proxy.go#L337-L411) [middleware/proxy.go#L424-L450](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/middleware/proxy.go#L424-L450)
- Rate-limit state: RateLimiter middleware → IdentifierExtractor → RateLimiterMemoryStore.AllowContext → allow → lookup/create Visitor → update lastSeen → optional cleanupStaleVisitors → AllowN → setRateLimitHeaders. Denial invokes DenyHandler, which defaults to a wrapped 429; the visitor map is process-local memory. — [middleware/rate_limiter.go#L60-L72](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/middleware/rate_limiter.go#L60-L72) [middleware/rate_limiter.go#L149-L164](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/middleware/rate_limiter.go#L149-L164) [middleware/rate_limiter.go#L263-L314](https://github.com/labstack/echo/blob/99c395d846e079d4cffd29de9298d1dd829e8b04/middleware/rate_limiter.go#L263-L314)

Every claim links to its cited files at the pinned commit. Citations identify source evidence; they do not establish runtime correctness. Independent CodeVetter scan — not reviewed by upstream maintainers.

## Public product links

- [CodeVetter](https://codevetter.com/)
- [Download](https://codevetter.com/download)
- [Documentation](https://codevetter.com/docs/)
- [Source](https://github.com/Codevetter/codevetter)
