Skip to content
Merged
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
9 changes: 9 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -234,7 +234,9 @@ fn handle_stream(req: Request, chunk_size: Int) -> Response {
Static files can be sent using [`ewe.file`](https://hexdocs.pm/ewe/ewe.html#file). It accepts a path and optional `offset`/`limit` parameters. This allows serving HTML pages, assets, or binary files with minimal effort.

```gleam
import gleam/bool
import gleam/http/response
import gleam/list
import gleam/string

fn serve_file(path: String) -> Response {
Expand All @@ -243,6 +245,13 @@ fn serve_file(path: String) -> Response {
//
let dir = absname("public")
let relative = string.drop_start(path, 1)
let segments = string.split(relative, "/")

use <- bool.guard(
when: list.any(segments, fn(seg) { seg == ".." }),
return: not_found(),
)

let resolved = absname_join(dir, relative)

case string.starts_with(resolved, dir <> "/") {
Expand Down
9 changes: 9 additions & 0 deletions examples/src/serving_files.gleam
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import ewe.{type Response}
import gleam/bool
import gleam/erlang/process
import gleam/http/response
import gleam/list
import gleam/option.{None}
import gleam/string
import logging
Expand All @@ -26,6 +28,13 @@ fn serve_file(path: String) -> Response {
//
let dir = absname("public")
let relative = string.drop_start(path, 1)
let segments = string.split(relative, "/")

use <- bool.guard(
when: list.any(segments, fn(seg) { seg == ".." }),
return: not_found(),
)

let resolved = absname_join(dir, relative)

case string.starts_with(resolved, dir <> "/") {
Expand Down
Loading