1
0
Fork 0
mirror of https://github.com/zigzap/zap.git synced 2025-10-20 15:14:08 +00:00

doc update

This commit is contained in:
renerocksai 2025-03-16 16:28:23 +01:00
parent a63e47ea3d
commit f77f405320
No known key found for this signature in database
2 changed files with 77 additions and 27 deletions

View file

@ -9,11 +9,13 @@ authentication, see the [UserPassSession](../src/http_auth.zig#L319) and its
For convenience, Authenticator types exist that can authenticate requests. For convenience, Authenticator types exist that can authenticate requests.
Zap also provides an `Endpoint.Authenticating` endpoint-wrapper. Have a look at the [example](../examples/endpoint_auth) and the [tests](../src/tests/test_auth.zig). Zap also provides an `Endpoint.Authenticating` endpoint-wrapper. Have a look at
the [example](../examples/endpoint_auth) and the
[tests](../src/tests/test_auth.zig).
The following describes the Authenticator types. All of them provide the The following describes the Authenticator types. All of them provide the
`authenticateRequest()` function, which takes a `zap.Request` and returns `authenticateRequest()` function, which takes a `zap.Request` and returns a bool
a bool value whether it could be authenticated or not. value whether it could be authenticated or not.
Further down, we show how to use the Authenticators, and also the Further down, we show how to use the Authenticators, and also the
`Endpoint.Authenticating`. `Endpoint.Authenticating`.
@ -24,7 +26,7 @@ The `zap.Auth.Basic` Authenticator accepts 2 comptime values:
- `Lookup`: either a map to look up passwords for users or a set to lookup - `Lookup`: either a map to look up passwords for users or a set to lookup
base64 encoded tokens (user:pass -> base64-encode = token) base64 encoded tokens (user:pass -> base64-encode = token)
- `kind` : - `kind` :
- `UserPass` : decode the authentication header, split into user and - `UserPass` : decode the authentication header, split into user and
password, then lookup the password in the provided map and compare it. password, then lookup the password in the provided map and compare it.
- `Token68` : don't bother decoding, the 'lookup' set is filled with - `Token68` : don't bother decoding, the 'lookup' set is filled with
@ -187,7 +189,8 @@ fn on_request(r: zap.Request) void {
Here, we only show using one of the Authenticator types. See the tests for more Here, we only show using one of the Authenticator types. See the tests for more
examples. examples.
The `Endpoint.Authenticating` honors `.unauthorized` in the endpoint settings, where you can pass in a callback to deal with unauthorized requests. If you leave it to `null`, the endpoint will automatically reply with a `401 - Unauthorized` response. The `Endpoint.Authenticating` uses the `.unauthorized()` method of the endpoint
to deal with unauthorized requests. `unauthorized` must be implemented.
The example below should make clear how to wrap an endpoint into an The example below should make clear how to wrap an endpoint into an
`Endpoint.Authenticating`: `Endpoint.Authenticating`:
@ -205,18 +208,20 @@ const HTTP_RESPONSE: []const u8 =
\\ </body></html> \\ </body></html>
; ;
// authenticated requests go here pub const Endpoint = struct {
fn endpoint_http_get(e: *zap.Endpoint, r: zap.Request) void { path: []const u8,
_ = e;
r.sendBody(HTTP_RESPONSE) catch return;
}
// just for fun, we also catch the unauthorized callback // authenticated requests go here
fn endpoint_http_unauthorized(e: *zap.Endpoint, r: zap.Request) void { fn get(_: *Endpoint, r: zap.Request) void {
_ = e; r.sendBody(HTTP_RESPONSE) catch return;
r.setStatus(.unauthorized); }
r.sendBody("UNAUTHORIZED ACCESS") catch return;
} // just for fun, we also catch the unauthorized callback
fn unauthorized(_: *Endpoint, r: zap.Request) void {
r.setStatus(.unauthorized);
r.sendBody("UNAUTHORIZED ACCESS") catch return;
}
};
pub fn main() !void { pub fn main() !void {
// setup listener // setup listener
@ -233,11 +238,9 @@ pub fn main() !void {
defer listener.deinit(); defer listener.deinit();
// create mini endpoint // create mini endpoint
var ep = zap.Endpoint.init(.{ var ep : Endpoint = .{
.path = "/test", .path = "/test",
.get = endpoint_http_get, };
.unauthorized = endpoint_http_unauthorized,
});
// create authenticator // create authenticator
const Authenticator = zap.Auth.BearerSingle; const Authenticator = zap.Auth.BearerSingle;
@ -245,15 +248,15 @@ pub fn main() !void {
defer authenticator.deinit(); defer authenticator.deinit();
// create authenticating endpoint // create authenticating endpoint
const BearerAuthEndpoint = zap.Endpoint.Authenticating(Authenticator); const BearerAuthEndpoint = zap.Endpoint.Authenticating(Endpoint, Authenticator);
var auth_ep = BearerAuthEndpoint.init(&ep, &authenticator); var auth_ep = BearerAuthEndpoint.init(&ep, &authenticator);
try listener.register(auth_ep.endpoint()); try listener.register(&auth_ep);
listener.listen() catch {}; listener.listen() catch {};
std.debug.print( std.debug.print(
\\ Run the following: \\ Run the following:
\\ \\
\\ curl http://localhost:3000/test -i -H "Authorization: Bearer ABCDEFG" -v \\ curl http://localhost:3000/test -i -H "Authorization: Bearer ABCDEFG" -v
\\ curl http://localhost:3000/test -i -H "Authorization: Bearer invalid" -v \\ curl http://localhost:3000/test -i -H "Authorization: Bearer invalid" -v
\\ \\

View file

@ -1,9 +1,57 @@
//! Endpoint and supporting types.
//! Create one and define all callbacks. Then, pass it to a HttpListener's
//! `register()` function to register with the listener.
//!
//! **NOTE**: Endpoints must implement the following "interface":
//!
//! ```zig
//! /// The http request path / slug of the endpoint
//! path: []const u8,
//!
//! /// Handlers by request method:
//! pub fn get(_: *Self, _: zap.Request) void {}
//! pub fn post(_: *Self, _: zap.Request) void {}
//! pub fn put(_: *Self, _: zap.Request) void {}
//! pub fn delete(_: *Self, _: zap.Request) void {}
//! pub fn patch(_: *Self, _: zap.Request) void {}
//! pub fn options(_: *Self, _: zap.Request) void {}
//!
//! // optional, if auth stuff is used:
//! pub fn unauthorized(_: *Self, _: zap.Request) void {}
//! ```
//!
//! Example:
//! A simple endpoint listening on the /stop route that shuts down zap. The
//! main thread usually continues at the instructions after the call to
//! zap.start().
//!
//! ```zig
//! const StopEndpoint = struct {
//!
//! pub fn init( path: []const u8,) StopEndpoint {
//! return .{
//! .path = path,
//! };
//! }
//!
//! pub fn post(_: *Self, _: zap.Request) void {}
//! pub fn put(_: *Self, _: zap.Request) void {}
//! pub fn delete(_: *Self, _: zap.Request) void {}
//! pub fn patch(_: *Self, _: zap.Request) void {}
//! pub fn options(_: *Self, _: zap.Request) void {}
//!
//! pub fn get(self: *StopEndpoint, r: zap.Request) void {
//! _ = self;
//! _ = r;
//! zap.stop();
//! }
//! };
//! ```
const std = @import("std"); const std = @import("std");
const zap = @import("zap.zig"); const zap = @import("zap.zig");
const auth = @import("http_auth.zig"); const auth = @import("http_auth.zig");
const Endpoint = @This();
// zap types // zap types
const Request = zap.Request; const Request = zap.Request;
const ListenerSettings = zap.HttpListenerSettings; const ListenerSettings = zap.HttpListenerSettings;
@ -93,8 +141,7 @@ const EndpointWrapper = struct {
} }
}; };
/// Wrap an endpoint with an Authenticator -> new Endpoint of type Endpoint /// Wrap an endpoint with an Authenticator
/// is available via the `endpoint()` function.
pub fn Authenticating(EndpointType: type, Authenticator: type) type { pub fn Authenticating(EndpointType: type, Authenticator: type) type {
return struct { return struct {
authenticator: *Authenticator, authenticator: *Authenticator,