<?php
namespace Misuzu;

use RuntimeException;
use Index\MediaType;
use Index\Http\Content\MultipartFormContent;
use Index\Http\Content\Multipart\ValueMultipartFormData;
use Index\Http\Routing\Router;
use Index\Http\Routing\Processors\Before;
use Index\Http\Routing\Routes\RouteInfo;

require_once __DIR__ . '/../misuzu.php';

if(!isset($msz) || !($msz instanceof \Misuzu\MisuzuContext))
    die('Misuzu is not initialised.');

// The whole wall of shit before the router setup and dispatch should be worked away
// Lockdown things should be middleware when there's no more legacy files

ob_start();

if(is_file($msz->dbCtx->getMigrateLockPath())) {
    http_response_code(503);
    header('Content-Type: text/html; charset=utf-8');
    echo file_get_contents(sprintf('%s/error-503.html', Misuzu::PATH_PUBLIC));
    exit;
}

$request = \Index\Http\HttpRequest::fromRequest();
$msz->timings->lap('request');
$msz->registerRequestRoutes($request);

if($msz->routingCtx->domainRoles->hasRole($request->getHeaderLine('Host'), 'main')) {
    $mszRequestPath = substr($request->requestTarget, 1);
    $mszLegacyPathPrefix = Misuzu::PATH_PUBLIC_LEGACY . '/';
    $mszLegacyPath = $mszLegacyPathPrefix . $mszRequestPath;

    if(str_starts_with($mszLegacyPath, $mszLegacyPathPrefix)) {
        $mszLegacyPathReal = realpath($mszLegacyPath);
        if($mszLegacyPath === $mszLegacyPathReal || $mszLegacyPath === $mszLegacyPathReal . '/') {
            // this is here so filters can run...
            $msz->routingCtx->router->route(RouteInfo::exact(
                $request->method,
                $request->requestTarget,
                #[Before('authz:cookie')]
                function() use ($msz, $mszRequestPath) {
                    if(str_starts_with($mszRequestPath, 'manage') && !$msz->hasManageAccess())
                        return 403;
                },
            ));
            $response = $msz->routingCtx->router->handle($request);
            if($response->getBody()->getSize() > 0) {
                Router::output($response);
                exit;
            }

            if(is_dir($mszLegacyPath))
                $mszLegacyPath .= '/index.php';

            if(is_file($mszLegacyPath)) {
                // Reconstruct $_POST since PHP no longer makes it for us
                if($request->getBody()->isReadable() && empty($_POST)) {
                    $mszRequestContent = (function($contentType, $stream) {
                        if($contentType->equals('application/x-www-form-urlencoded')) {
                            parse_str((string)$stream, $postVars);
                            return $postVars;
                        }

                        if($contentType->equals('multipart/form-data'))
                            try {
                                return MultipartFormContent::parseStream($stream, $contentType->boundary);
                            } catch(RuntimeException $ex) {}

                        return null;
                    })(MediaType::parse($request->getHeaderLine('Content-Type')), $request->getBody());

                    $_POST = (function($requestContent) {
                        if(is_array($requestContent))
                            return $requestContent;

                        if($requestContent instanceof MultipartFormContent) {
                            $postVars = [];
                            foreach($requestContent->params as $name => $values) {
                                if(count($values) === 0)
                                    $postVars[$name] = '';
                                elseif(count($values) === 1)
                                    $postVars[$name] = $values[0] instanceof ValueMultipartFormData ? (string)$values[0] : '';
                                else {
                                    $postVar = [];
                                    foreach($values as $value)
                                        $postVars[] = $value instanceof ValueMultipartFormData ? (string)$value : '';

                                    $postVars[$name] = $postVar;
                                }
                            }

                            return $postVars;
                        }

                        return [];
                    })($mszRequestContent);

                    $_REQUEST = array_merge($_GET, $_POST);
                }

                require_once $mszLegacyPath;
                return;
            }
        }
    }
}

$msz->routingCtx->dispatch($request);