import { l as parseRoute } from "../helpers-34vHGLnE.js";
import { _ as Qs, c as HttpRequest, i as HttpResponse, n as Server, r as HttpContext, s as Router, t as defineConfig } from "../define_config-Cuq6_o-f.js";
import { t as createURL } from "../helpers-BiaeWsBP.js";
import { Container } from "@adonisjs/fold";
import { Socket } from "node:net";
import proxyaddr from "proxy-addr";
import { safeStringify } from "@poppinss/utils/json";
import { AppFactory } from "@adonisjs/application/factories";
import { EncryptionFactory } from "@boringnode/encryption/factories";
import { randomUUID } from "node:crypto";
import { IncomingMessage, ServerResponse } from "node:http";
import { LoggerFactory } from "@adonisjs/logger/factories";
import { Logger } from "@adonisjs/logger";
import { Emitter } from "@adonisjs/events";
//#region factories/qs_parser_factory.ts
/**
* QS Parser factory is used to generate the query string
* parser for testing
*/
var QsParserFactory = class {
	/**
	* Default configuration options for the QS parser
	*/
	#options = {
		parse: {
			depth: 5,
			parameterLimit: 1e3,
			allowSparse: false,
			arrayLimit: 20,
			comma: true
		},
		stringify: {
			encode: true,
			encodeValuesOnly: false,
			arrayFormat: "indices",
			skipNulls: false
		}
	};
	/**
	* Merge QS parser factory options
	* @param options - Partial options to merge with existing configuration
	*/
	merge(options) {
		Object.assign(this.#options.parse, options.parse);
		Object.assign(this.#options.stringify, options.stringify);
		return this;
	}
	/**
	* Create instance of the QS parser class
	*/
	create() {
		return new Qs(this.#options);
	}
};
//#endregion
//#region factories/router.ts
/**
* Router factory is used to generate router class instances for
* testing
*/
var RouterFactory = class {
	/**
	* Factory parameters for creating router instances
	*/
	#parameters = {};
	/**
	* Returns an instance of the application class
	*/
	#getApp() {
		return this.#parameters.app || new AppFactory().create(new URL("./app/", import.meta.url));
	}
	/**
	* Returns an instance of the encryptor to encrypt
	* signed URLs
	*/
	#createEncryption() {
		return this.#parameters.encryption || new EncryptionFactory().create();
	}
	/**
	* Merge factory params
	* @param params - Partial factory parameters to merge
	*/
	merge(params) {
		Object.assign(this.#parameters, params);
		return this;
	}
	/**
	* Create router instance
	*/
	create() {
		return new Router(this.#getApp(), this.#createEncryption(), new QsParserFactory().create());
	}
};
//#endregion
//#region factories/response.ts
/**
* Response factory is used to generate response class instances for
* testing
*/
var HttpResponseFactory = class {
	/**
	* Factory parameters for creating response instances
	*/
	#parameters = {};
	/**
	* Returns the config for the request class
	*/
	#getConfig() {
		return {
			etag: false,
			serializeJSON: safeStringify,
			jsonpCallbackName: "callback",
			redirect: {
				allowedHosts: [],
				forwardQueryString: false
			},
			cookie: {
				maxAge: 90,
				path: "/",
				httpOnly: true,
				sameSite: false,
				secure: false
			},
			...this.#parameters.config
		};
	}
	/**
	* Returns the HTTP req object
	*/
	#createRequest() {
		return this.#parameters.req || new IncomingMessage(new Socket());
	}
	/**
	* Returns an instance of the router
	*/
	#createRouter() {
		return this.#parameters.router || new RouterFactory().create();
	}
	/**
	* Returns the HTTP res object
	* @param req - The incoming message request object
	*/
	#createResponse(req) {
		return this.#parameters.res || new ServerResponse(req);
	}
	/**
	* Returns an instance of the encryptor to encrypt
	* signed URLs
	*/
	#createEncryption() {
		return this.#parameters.encryption || new EncryptionFactory().create();
	}
	/**
	* Returns the logger instance
	*/
	#createLogger() {
		return this.#parameters.logger || new LoggerFactory().create();
	}
	/**
	* Merge factory params
	* @param params - Partial factory parameters to merge
	*/
	merge(params) {
		Object.assign(this.#parameters, params);
		return this;
	}
	/**
	* Create response class instance
	*/
	create() {
		const req = this.#createRequest();
		const res = this.#createResponse(req);
		const encryption = this.#createEncryption();
		const response = new HttpResponse(req, res, encryption, this.#getConfig(), this.#createRouter(), new QsParserFactory().create());
		new HttpContext(this.#parameters.request || new HttpRequestFactory().merge({
			req,
			res,
			encryption
		}).create(), response, this.#createLogger(), new Container().createResolver());
		return response;
	}
};
//#endregion
//#region factories/request.ts
/**
* Request factory is used to generate request class instances for
* testing
*/
var HttpRequestFactory = class {
	/**
	* Factory parameters for creating request instances
	*/
	#parameters = {};
	/**
	* Returns the config for the request class
	*/
	#getConfig() {
		return {
			allowMethodSpoofing: false,
			trustProxy: proxyaddr.compile("loopback"),
			subdomainOffset: 2,
			generateRequestId: false,
			createRequestId() {
				return randomUUID();
			},
			...this.#parameters.config
		};
	}
	/**
	* Returns the HTTP req object
	*/
	#createRequest() {
		const req = this.#parameters.req || new IncomingMessage(new Socket());
		if (this.#parameters.url) req.url = this.#parameters.url;
		if (this.#parameters.method) req.method = this.#parameters.method;
		return req;
	}
	/**
	* Returns the HTTP res object
	* @param req - The incoming message request object
	*/
	#createResponse(req) {
		return this.#parameters.res || new ServerResponse(req);
	}
	/**
	* Returns an instance of the encryptor to encrypt
	* signed URLs
	*/
	#createEncryption() {
		return this.#parameters.encryption || new EncryptionFactory().create();
	}
	/**
	* Merge factory params
	* @param params - Partial factory parameters to merge
	*/
	merge(params) {
		Object.assign(this.#parameters, params);
		return this;
	}
	/**
	* Create request
	*/
	create() {
		const req = this.#createRequest();
		const res = this.#createResponse(req);
		const encryption = this.#createEncryption();
		const request = new HttpRequest(req, res, encryption, this.#getConfig(), new QsParserFactory().create());
		/**
		* Wire up the HTTP context so that `request.ctx` is available, mirroring
		* the runtime where every request belongs to a context. The request is
		* handed to `HttpResponseFactory` so it reuses this instance instead of
		* creating a new one, which also prevents a recursive factory loop.
		*/
		new HttpResponseFactory().merge({
			req,
			res,
			encryption,
			request
		}).create();
		return request;
	}
};
//#endregion
//#region factories/server_factory.ts
/**
* Server factory is used to generate server class instances for
* testing
*/
var ServerFactory = class {
	/**
	* Factory parameters for creating server instances
	*/
	#parameters = {};
	/**
	* Returns the emitter instance
	*/
	#getEmitter() {
		return this.#parameters.emitter || new Emitter(this.#getApp());
	}
	/**
	* Returns the logger instance
	*/
	#getLogger() {
		return this.#parameters.logger || new Logger({ enabled: false });
	}
	/**
	* Returns the config for the server class
	*/
	#getConfig() {
		return defineConfig(this.#parameters.config || {});
	}
	/**
	* Returns an instance of the application class
	*/
	#getApp() {
		return this.#parameters.app || new AppFactory().create(new URL("./app/", import.meta.url));
	}
	/**
	* Returns an instance of the encryptor to encrypt
	* signed URLs
	*/
	#createEncryption() {
		return this.#parameters.encryption || new EncryptionFactory().create();
	}
	/**
	* Merge factory params
	* @param params - Partial factory parameters to merge
	*/
	merge(params) {
		Object.assign(this.#parameters, params);
		return this;
	}
	/**
	* Create server instance
	*/
	create() {
		return new Server(this.#getApp(), this.#createEncryption(), this.#getEmitter(), this.#getLogger(), this.#getConfig());
	}
};
//#endregion
//#region factories/http_context.ts
/**
* HttpContext factory is used to generate Http context class instances for
* testing
*/
var HttpContextFactory = class {
	/**
	* Factory parameters for creating HTTP context instances
	*/
	#parameters = {};
	/**
	* Returns the request class instance
	*/
	#createRequest() {
		if (this.#parameters.request) return this.#parameters.request;
		let { url, method, route } = this.#parameters;
		if (route) url = createURL(route.pattern, parseRoute(route.pattern), new QsParserFactory().create().stringify, route.params);
		return new HttpRequestFactory().merge({
			url,
			method
		}).create();
	}
	/**
	* Returns the response class instance
	*/
	#createResponse() {
		return this.#parameters.response || new HttpResponseFactory().create();
	}
	/**
	* Returns an instance of the logger class
	*/
	#createLogger() {
		return this.#parameters.logger || new LoggerFactory().create();
	}
	/**
	* Merge factory params
	* @param params - Partial factory parameters to merge
	*/
	merge(params) {
		Object.assign(this.#parameters, params);
		return this;
	}
	/**
	* Create HTTP context instance
	*/
	create() {
		return new HttpContext(this.#createRequest(), this.#createResponse(), this.#createLogger(), new Container().createResolver());
	}
};
//#endregion
export { HttpContextFactory, QsParserFactory, HttpRequestFactory as RequestFactory, HttpResponseFactory as ResponseFactory, RouterFactory, ServerFactory };
