Added support for private apis
This commit is contained in:
@@ -29,13 +29,20 @@ locals {
|
||||
upstream = v.upstream
|
||||
tls = v.tls
|
||||
fqdn = join(" ", v.fqdn)
|
||||
auth = length([for l in v.locations : true if l.private]) > 0
|
||||
locations = [for l in v.locations : {
|
||||
path = l.path
|
||||
headers = merge(l.headers, coalesce(v.default_headers, local.default_headers))
|
||||
path = l.path
|
||||
headers = merge(l.headers, coalesce(v.default_headers, local.default_headers))
|
||||
private = l.private
|
||||
upstream = l.upstream
|
||||
rewrite = l.rewrite
|
||||
}]
|
||||
custom_snippet = v.custom_snippet
|
||||
}))
|
||||
}
|
||||
services_config_checksum = sha256(jsonencode(local.services_config))
|
||||
|
||||
auth_script = file("${path.module}/resources/auth/auth_server.py")
|
||||
auth_script_checksum = sha256(local.auth_script)
|
||||
}
|
||||
|
||||
|
||||
@@ -102,10 +102,21 @@ resource "kubernetes_config_map" "nginx_default_config" {
|
||||
data = local.services_config
|
||||
}
|
||||
|
||||
resource "kubernetes_config_map" "auth_script" {
|
||||
metadata {
|
||||
name = "auth-script"
|
||||
namespace = kubernetes_namespace.reverse_proxy.metadata[0].name
|
||||
}
|
||||
|
||||
data = {
|
||||
"auth_server.py" = local.auth_script
|
||||
}
|
||||
}
|
||||
|
||||
resource "kubernetes_ingress_v1" "reverse-proxy_ingress" {
|
||||
for_each = var.services
|
||||
metadata {
|
||||
name = "reverse-proxy-ingress"
|
||||
name = format("reverse-proxy-%s", replace(each.key, ".", "-"))
|
||||
namespace = kubernetes_namespace.reverse_proxy.metadata[0].name
|
||||
|
||||
annotations = merge({
|
||||
@@ -145,6 +156,19 @@ resource "kubernetes_ingress_v1" "reverse-proxy_ingress" {
|
||||
}
|
||||
}
|
||||
|
||||
resource "kubernetes_secret" "auth_token" {
|
||||
metadata {
|
||||
name = "auth-token-secret"
|
||||
namespace = kubernetes_namespace.reverse_proxy.metadata[0].name
|
||||
}
|
||||
|
||||
data = {
|
||||
token = var.auth_token
|
||||
}
|
||||
|
||||
type = "Opaque"
|
||||
}
|
||||
|
||||
resource "kubernetes_deployment" "reverse_proxy" {
|
||||
|
||||
metadata {
|
||||
@@ -175,9 +199,10 @@ resource "kubernetes_deployment" "reverse_proxy" {
|
||||
app = "reverse-proxy"
|
||||
}
|
||||
annotations = {
|
||||
"checksum/nginx" = local.nginx_config_checksum
|
||||
"checksum/services" = local.services_config_checksum
|
||||
"checksum/wireguard" = local.wireguard_config_checksum
|
||||
"checksum/nginx" = local.nginx_config_checksum
|
||||
"checksum/services" = local.services_config_checksum
|
||||
"checksum/wireguard" = local.wireguard_config_checksum
|
||||
"checksum/auth_server" = local.auth_script_checksum
|
||||
}
|
||||
}
|
||||
spec {
|
||||
@@ -242,6 +267,34 @@ resource "kubernetes_deployment" "reverse_proxy" {
|
||||
}
|
||||
}
|
||||
|
||||
container {
|
||||
name = "auth-sidecar"
|
||||
image = "python:3.11-slim"
|
||||
|
||||
command = ["python", "/app/auth_server.py"]
|
||||
|
||||
env {
|
||||
name = "AUTH_TOKEN"
|
||||
value_from {
|
||||
secret_key_ref {
|
||||
name = "auth-token-secret"
|
||||
key = "token"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
volume_mount {
|
||||
name = "auth-script"
|
||||
mount_path = "/app"
|
||||
read_only = true
|
||||
}
|
||||
|
||||
port {
|
||||
container_port = 5000
|
||||
name = "auth"
|
||||
}
|
||||
}
|
||||
|
||||
container {
|
||||
name = "reverse-proxy"
|
||||
image = "nginx:${var.tag}"
|
||||
@@ -334,6 +387,13 @@ resource "kubernetes_deployment" "reverse_proxy" {
|
||||
}
|
||||
}
|
||||
|
||||
volume {
|
||||
name = "auth-script"
|
||||
config_map {
|
||||
name = kubernetes_config_map.auth_script.metadata[0].name
|
||||
}
|
||||
}
|
||||
|
||||
volume {
|
||||
name = "nginx"
|
||||
config_map {
|
||||
|
||||
@@ -0,0 +1,40 @@
|
||||
import os
|
||||
import logging
|
||||
from http.server import BaseHTTPRequestHandler, HTTPServer
|
||||
|
||||
# Configure logging
|
||||
logging.basicConfig(
|
||||
level=logging.INFO,
|
||||
format="%(asctime)s [%(levelname)s] %(message)s"
|
||||
)
|
||||
|
||||
EXPECTED_TOKEN = os.getenv("AUTH_TOKEN", "")
|
||||
|
||||
class AuthHandler(BaseHTTPRequestHandler):
|
||||
def do_GET(self):
|
||||
auth = self.headers.get('Authorization')
|
||||
|
||||
# Log request info
|
||||
client_ip = self.client_address[0]
|
||||
logging.info(f"Auth request from {client_ip}")
|
||||
|
||||
if auth == f"Bearer {EXPECTED_TOKEN}":
|
||||
logging.info("Authentication successful")
|
||||
self.send_response(200)
|
||||
else:
|
||||
logging.warning("Authentication failed")
|
||||
self.send_response(401)
|
||||
self.end_headers()
|
||||
|
||||
def log_message(self, format, *args):
|
||||
# Suppress default BaseHTTPRequestHandler logging
|
||||
return
|
||||
|
||||
if __name__ == '__main__':
|
||||
if not EXPECTED_TOKEN:
|
||||
logging.error("AUTH_TOKEN environment variable not set. Exiting.")
|
||||
exit(1)
|
||||
|
||||
server = HTTPServer(('', 5000), AuthHandler)
|
||||
logging.info("Auth server running on port 5000...")
|
||||
server.serve_forever()
|
||||
@@ -10,9 +10,24 @@ server {
|
||||
%{ if custom_snippet != "" ~}
|
||||
${custom_snippet}
|
||||
%{ endif ~}
|
||||
%{ if auth ~}
|
||||
location = /auth {
|
||||
internal;
|
||||
proxy_pass http://localhost:5000/;
|
||||
proxy_pass_request_body off;
|
||||
proxy_set_header Content-Length "";
|
||||
proxy_set_header Authorization $http_authorization;
|
||||
}
|
||||
%{ endif }
|
||||
%{ for l in locations ~}
|
||||
location ${l.path} {
|
||||
proxy_pass ${upstream};
|
||||
%{ if l.private ~}
|
||||
auth_request /auth;
|
||||
%{ endif ~}
|
||||
%{ if l.rewrite != "" ~}
|
||||
rewrite ${l.rewrite};
|
||||
%{ endif ~}
|
||||
proxy_pass %{ if l.upstream != "" ~}${l.upstream}%{ else ~}${upstream}%{ endif ~};
|
||||
proxy_http_version 1.1;
|
||||
%{ for k,v in l.headers ~}
|
||||
proxy_set_header ${k} ${v};
|
||||
|
||||
@@ -36,10 +36,19 @@ variable "services" {
|
||||
https_port = optional(number, 443)
|
||||
tls = optional(bool, false)
|
||||
locations = optional(list(object({
|
||||
path = string,
|
||||
headers = optional(map(string), {}),
|
||||
path = string,
|
||||
headers = optional(map(string), {}),
|
||||
private = optional(bool, false),
|
||||
upstream = optional(string, ""),
|
||||
rewrite = optional(string, "")
|
||||
})), [])
|
||||
custom_snippet = optional(string, "")
|
||||
config = optional(string, "")
|
||||
}))
|
||||
}
|
||||
|
||||
variable "auth_token" {
|
||||
description = "The authentication token to use for the reverse proxy"
|
||||
type = string
|
||||
sensitive = true
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user