diff --git a/graal/reflect-config.json b/graal/reflect-config.json index 37f82ed..57ab264 100644 --- a/graal/reflect-config.json +++ b/graal/reflect-config.json @@ -8,12 +8,22 @@ "allPublicConstructors" : true, "allRecordComponents": true },{ - "name" : "io.github.danthe1st.httpsintercept.rules.SetHeaderRule", + "name" : "io.github.danthe1st.httpsintercept.rules.pre.SetRequestHeaderRule", + "allPublicConstructors" : true, + "allRecordComponents": true + },{ + "name" : "io.github.danthe1st.httpsintercept.rules.post.HtmlBasedBlocker", "allPublicConstructors" : true, "allRecordComponents": true },{ "name" : "java.util.HashSet", "allPublicConstructors" : true + },{ + "name" : "java.nio.file.Path", + "allPublicMethods" : true + },{ + "name" : "java.util.regex.Pattern", + "allPublicMethods" : true },{ "name" : "java.util.ArrayList", "allPublicConstructors" : true diff --git a/pom.xml b/pom.xml index d96e785..58e516f 100644 --- a/pom.xml +++ b/pom.xml @@ -42,6 +42,11 @@ jackson-dataformat-yaml 2.13.0 + + org.jsoup + jsoup + 1.17.2 + org.junit.jupiter junit-jupiter-api diff --git a/src/main/java/io/github/danthe1st/httpsintercept/HttpsIntercept.java b/src/main/java/io/github/danthe1st/httpsintercept/HttpsIntercept.java index 4546a21..f2d5f24 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/HttpsIntercept.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/HttpsIntercept.java @@ -11,14 +11,18 @@ import io.github.danthe1st.httpsintercept.handler.ServerHandlersInit; import io.netty.bootstrap.Bootstrap; import io.netty.bootstrap.ServerBootstrap; +import io.netty.channel.ChannelFuture; import io.netty.channel.ChannelOption; import io.netty.channel.EventLoopGroup; import io.netty.channel.nio.NioEventLoopGroup; import io.netty.channel.socket.nio.NioServerSocketChannel; import io.netty.channel.socket.nio.NioSocketChannel; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; public class HttpsIntercept { private static final int LOCAL_PORT = Integer.getInteger("localPort", 1337); + private static final Logger LOG = LoggerFactory.getLogger(HttpsIntercept.class); public static void main(String[] args) throws InterruptedException, IOException, KeyStoreException, NoSuchAlgorithmException, CertificateException, UnrecoverableKeyException { @@ -33,11 +37,15 @@ public static void main(String[] args) throws InterruptedException, IOException, .channel(NioSocketChannel.class); ServerBootstrap serverBootstrap = new ServerBootstrap(); - serverBootstrap.group(bossGroup, workerGroup) + ChannelFuture serverFuture = serverBootstrap.group(bossGroup, workerGroup) .channel(NioServerSocketChannel.class) .childHandler(new ServerHandlersInit(clientBootstrap, config)) .childOption(ChannelOption.AUTO_READ, true) - .bind(LOCAL_PORT).sync().channel().closeFuture().sync(); + .bind(LOCAL_PORT).sync(); + + LOG.info("Https intercept is ready"); + + serverFuture.channel().closeFuture().sync(); }finally{ bossGroup.shutdownGracefully(); workerGroup.shutdownGracefully(); diff --git a/src/main/java/io/github/danthe1st/httpsintercept/config/Config.java b/src/main/java/io/github/danthe1st/httpsintercept/config/Config.java index 63b9852..e422c4d 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/config/Config.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/config/Config.java @@ -4,22 +4,34 @@ import java.io.Reader; import java.nio.file.Files; import java.nio.file.Path; +import java.util.Collections; import java.util.List; -import java.util.Objects; import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.dataformat.yaml.YAMLFactory; +import io.github.danthe1st.httpsintercept.rules.PostForwardRule; import io.github.danthe1st.httpsintercept.rules.PreForwardRule; public record Config( HostMatcherConfig ignoredHosts, - List preForwardRules + List preForwardRules, + List postForwardRules ) { - public Config(HostMatcherConfig ignoredHosts, List preForwardRules) { - Objects.requireNonNull(ignoredHosts); + public Config(HostMatcherConfig ignoredHosts, List preForwardRules, List postForwardRules) { + if(ignoredHosts == null){ + ignoredHosts = new HostMatcherConfig(null, null, null); + } this.ignoredHosts = ignoredHosts; - this.preForwardRules = List.copyOf(preForwardRules); + this.preForwardRules = emptyIfNull(preForwardRules); + this.postForwardRules = emptyIfNull(postForwardRules); + } + + private List emptyIfNull(List preForwardRules) { + if(preForwardRules == null){ + return Collections.emptyList(); + } + return List.copyOf(preForwardRules); } public static Config load(Path path) throws IOException { diff --git a/src/main/java/io/github/danthe1st/httpsintercept/handler/ServerHandlersInit.java b/src/main/java/io/github/danthe1st/httpsintercept/handler/ServerHandlersInit.java index 5c84c3c..4b8f1d8 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/handler/ServerHandlersInit.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/handler/ServerHandlersInit.java @@ -15,7 +15,9 @@ import io.github.danthe1st.httpsintercept.handler.sni.CustomSniHandler; import io.github.danthe1st.httpsintercept.handler.sni.SNIHandlerMapping; import io.github.danthe1st.httpsintercept.matcher.IterativeHostMatcher; +import io.github.danthe1st.httpsintercept.rules.PostForwardRule; import io.github.danthe1st.httpsintercept.rules.PreForwardRule; +import io.github.danthe1st.httpsintercept.rules.ProcessingRule; import io.netty.bootstrap.Bootstrap; import io.netty.channel.ChannelInitializer; import io.netty.channel.socket.SocketChannel; @@ -31,27 +33,30 @@ public class ServerHandlersInit extends ChannelInitializer { private final Bootstrap clientBootstrapTemplate; private final SNIHandlerMapping sniMapping; - private final Config config; - private final IterativeHostMatcher preForwardMatcher; private final IterativeHostMatcher ignoredHostMatcher; + private final IterativeHostMatcher preForwardMatcher; + private final IterativeHostMatcher postForwardMatcher; public ServerHandlersInit(Bootstrap clientBootstrap, Config config) throws KeyStoreException, NoSuchAlgorithmException, CertificateException, IOException, UnrecoverableKeyException { this.clientBootstrapTemplate = clientBootstrap; sniMapping = SNIHandlerMapping.createMapping(); - this.config = config; - List preForwardRules = config.preForwardRules(); - List> rules = new ArrayList<>(); - for(PreForwardRule preForwardRule : preForwardRules){ - HostMatcherConfig hostMatcher = preForwardRule.hostMatcher(); + preForwardMatcher = createMatcherFromRules(config.preForwardRules()); + postForwardMatcher = createMatcherFromRules(config.postForwardRules()); + ignoredHostMatcher = new IterativeHostMatcher<>(List.of(Map.entry(config.ignoredHosts(), new Object()))); + } + + private IterativeHostMatcher createMatcherFromRules(List ruleList) { + List> rules = new ArrayList<>(); + for(T rule : ruleList){ + HostMatcherConfig hostMatcher = rule.hostMatcher(); if(hostMatcher == null){ hostMatcher = new HostMatcherConfig(null, null, null); } - rules.add(Map.entry(hostMatcher, preForwardRule)); + rules.add(Map.entry(hostMatcher, rule)); } - preForwardMatcher = new IterativeHostMatcher<>(rules); - ignoredHostMatcher = new IterativeHostMatcher<>(List.of(Map.entry(config.ignoredHosts(), new Object()))); + return new IterativeHostMatcher<>(rules); } @Override @@ -60,8 +65,8 @@ protected void initChannel(SocketChannel socketChannel) throws Exception { socketChannel.pipeline().addLast( sniHandler, new HttpServerCodec(), - new HttpObjectAggregator(1048576), - new IncomingHttpRequestHandler(sniHandler, clientBootstrapTemplate, preForwardMatcher) + new HttpObjectAggregator(Integer.MAX_VALUE), + new IncomingHttpRequestHandler(sniHandler, clientBootstrapTemplate, preForwardMatcher, postForwardMatcher) ); } } diff --git a/src/main/java/io/github/danthe1st/httpsintercept/handler/http/HttpResponseContentAccessor.java b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/HttpResponseContentAccessor.java new file mode 100644 index 0000000..93f7a64 --- /dev/null +++ b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/HttpResponseContentAccessor.java @@ -0,0 +1,34 @@ +package io.github.danthe1st.httpsintercept.handler.http; + +import java.nio.charset.StandardCharsets; + +import io.netty.buffer.ByteBuf; +import io.netty.handler.codec.http.FullHttpResponse; +import org.bouncycastle.util.Arrays; + +public class HttpResponseContentAccessor { + private ByteBuf contentBuf; + private byte[] bytes; + + public HttpResponseContentAccessor(FullHttpResponse res) { + contentBuf = res.content(); + } + + public byte[] getBytes() { + ensureBytesPresent(); + return Arrays.copyOf(bytes, bytes.length); + } + + public String getAsString() { + ensureBytesPresent(); + return new String(bytes, StandardCharsets.UTF_8); + } + + private void ensureBytesPresent() { + if(bytes == null){ + ByteBuf buf = contentBuf.copy(); + bytes = new byte[buf.readableBytes()]; + buf.readBytes(bytes); + } + } +} \ No newline at end of file diff --git a/src/main/java/io/github/danthe1st/httpsintercept/handler/http/IncomingHttpRequestHandler.java b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/IncomingHttpRequestHandler.java index 1d8157c..e047d68 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/handler/http/IncomingHttpRequestHandler.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/IncomingHttpRequestHandler.java @@ -5,6 +5,7 @@ import java.io.PrintStream; import io.github.danthe1st.httpsintercept.matcher.IterativeHostMatcher; +import io.github.danthe1st.httpsintercept.rules.PostForwardRule; import io.github.danthe1st.httpsintercept.rules.PreForwardRule; import io.netty.bootstrap.Bootstrap; import io.netty.buffer.Unpooled; @@ -31,16 +32,18 @@ public final class IncomingHttpRequestHandler extends SimpleChannelInboundHandle private final SniHandler sniHandler; private final Bootstrap clientBootstrap; private final IterativeHostMatcher hostMatcher; + private final IterativeHostMatcher postForwardMatcher; /** * @param sniHandler Netty handler for Server Name Identification (contains the actual target host name) * @param clientSslContext {@link SslContext} used for the outgoing request * @param clientBootstrap template for sending the outgoing request */ - public IncomingHttpRequestHandler(SniHandler sniHandler, Bootstrap clientBootstrap, IterativeHostMatcher hostMatcher) { + public IncomingHttpRequestHandler(SniHandler sniHandler, Bootstrap clientBootstrap, IterativeHostMatcher hostMatcher, IterativeHostMatcher postForwardMatcher) { this.sniHandler = sniHandler; this.clientBootstrap = clientBootstrap; this.hostMatcher = hostMatcher; + this.postForwardMatcher = postForwardMatcher; } @Override @@ -68,7 +71,7 @@ private void forwardRequest(ChannelHandlerContext channelHandlerContext, FullHtt } Bootstrap actualClientBootstrap = clientBootstrap.clone() - .handler(new OutgoingHttpRequestHandler(channelHandlerContext, hostname)); + .handler(new OutgoingHttpRequestHandler(channelHandlerContext, fullHttpRequest, hostname, postForwardMatcher)); try{ Channel outChannel = actualClientBootstrap.connect(hostname, 443) .sync() diff --git a/src/main/java/io/github/danthe1st/httpsintercept/handler/http/OutgoingHttpRequestHandler.java b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/OutgoingHttpRequestHandler.java index 28cc236..b68e534 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/handler/http/OutgoingHttpRequestHandler.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/OutgoingHttpRequestHandler.java @@ -3,11 +3,15 @@ import javax.net.ssl.SSLContext; import javax.net.ssl.SSLEngine; +import io.github.danthe1st.httpsintercept.matcher.IterativeHostMatcher; +import io.github.danthe1st.httpsintercept.rules.PostForwardRule; import io.netty.channel.ChannelHandlerContext; import io.netty.channel.ChannelInitializer; import io.netty.channel.ChannelPipeline; import io.netty.channel.socket.SocketChannel; +import io.netty.handler.codec.http.FullHttpRequest; import io.netty.handler.codec.http.HttpClientCodec; +import io.netty.handler.codec.http.HttpObjectAggregator; import io.netty.handler.ssl.SslHandler; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -21,10 +25,15 @@ final class OutgoingHttpRequestHandler extends ChannelInitializer private final ChannelHandlerContext originalClientContext; private final String hostname; + private final FullHttpRequest fullHttpRequest; - OutgoingHttpRequestHandler(ChannelHandlerContext originalClientContext, String hostname) { + private final IterativeHostMatcher postForwardMatcher; + + OutgoingHttpRequestHandler(ChannelHandlerContext originalClientContext, FullHttpRequest fullHttpRequest, String hostname, IterativeHostMatcher postForwardMatcher) { this.originalClientContext = originalClientContext; this.hostname = hostname; + this.fullHttpRequest = fullHttpRequest; + this.postForwardMatcher = postForwardMatcher; } @Override @@ -38,7 +47,8 @@ protected void initChannel(SocketChannel ch) throws Exception { p.addLast( new SslHandler(engine), new HttpClientCodec(), // encode/decode HTTP - new ResponseHandler(originalClientContext) + new HttpObjectAggregator(Integer.MAX_VALUE), + new ResponseHandler(originalClientContext, fullHttpRequest, postForwardMatcher.matchesAsIterable(hostname)) ); } diff --git a/src/main/java/io/github/danthe1st/httpsintercept/handler/http/ResponseHandler.java b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/ResponseHandler.java index 292968f..1f6a83f 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/handler/http/ResponseHandler.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/handler/http/ResponseHandler.java @@ -1,8 +1,10 @@ package io.github.danthe1st.httpsintercept.handler.http; +import io.github.danthe1st.httpsintercept.rules.PostForwardRule; import io.netty.channel.ChannelHandlerContext; import io.netty.channel.ChannelInboundHandlerAdapter; -import io.netty.handler.codec.http.LastHttpContent; +import io.netty.handler.codec.http.FullHttpRequest; +import io.netty.handler.codec.http.FullHttpResponse; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -14,21 +16,39 @@ final class ResponseHandler extends ChannelInboundHandlerAdapter { private static final Logger LOG = LoggerFactory.getLogger(ResponseHandler.class); private final ChannelHandlerContext originalClientContext; + private final Iterable postForwardRules; - public ResponseHandler(ChannelHandlerContext originalClientContext) { + private final FullHttpRequest fullHttpRequest; + + public ResponseHandler(ChannelHandlerContext originalClientContext, FullHttpRequest fullHttpRequest, Iterable postForwardRules) { this.originalClientContext = originalClientContext; + this.fullHttpRequest = fullHttpRequest; + this.postForwardRules = postForwardRules; } @Override public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception { LOG.debug("read: {}", msg); - originalClientContext.writeAndFlush(msg); - if(msg instanceof LastHttpContent){ - LOG.debug("last HTTP content"); - originalClientContext.channel().close(); - ctx.channel().close(); + if(msg instanceof FullHttpResponse res){ + processRules(res); + }else{ + LOG.error("respose message not assignable to FullHttpResponse: {}", msg); + originalClientContext.writeAndFlush(msg); + } + + originalClientContext.channel().close(); + ctx.channel().close(); + } + + private void processRules(FullHttpResponse res) { + HttpResponseContentAccessor contentAccessor = new HttpResponseContentAccessor(res); + for(PostForwardRule rule : postForwardRules){ + if(!rule.processRequest(fullHttpRequest, res, contentAccessor, originalClientContext.channel())){ + return; + } } + originalClientContext.writeAndFlush(res); } @Override diff --git a/src/main/java/io/github/danthe1st/httpsintercept/handler/sni/SNIHandlerMapping.java b/src/main/java/io/github/danthe1st/httpsintercept/handler/sni/SNIHandlerMapping.java index 1c7bb39..711ff3c 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/handler/sni/SNIHandlerMapping.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/handler/sni/SNIHandlerMapping.java @@ -56,7 +56,7 @@ private SNIHandlerMapping() throws KeyStoreException, IOException, NoSuchAlgorit char[] passphrase = secretLines.get(0).toCharArray(); char[] privateKeyPassword = secretLines.get(1).toCharArray(); - LOG.info("Initiating SSL context"); + LOG.debug("Initiating SSL context"); ks = KeyStore.getInstance("JKS"); diff --git a/src/main/java/io/github/danthe1st/httpsintercept/matcher/HostPartIterator.java b/src/main/java/io/github/danthe1st/httpsintercept/matcher/HostPartIterator.java index c0179e5..8aba04f 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/matcher/HostPartIterator.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/matcher/HostPartIterator.java @@ -26,10 +26,15 @@ protected Iterator findNextIterator() { if(hostParts.containsKey(hostPart)){ current = hostParts.get(hostPart).iterator(); if(current.hasNext()){ + nextIndex(); return current; } } - }while((index = hostname.indexOf('.', index) + 1) != 0 && index < hostname.length()); + }while(nextIndex() != 0 && index < hostname.length()); return Collections.emptyIterator(); } + + private int nextIndex() { + return index = hostname.indexOf('.', index) + 1; + } } \ No newline at end of file diff --git a/src/main/java/io/github/danthe1st/httpsintercept/rules/PostForwardRule.java b/src/main/java/io/github/danthe1st/httpsintercept/rules/PostForwardRule.java new file mode 100644 index 0000000..4b1f383 --- /dev/null +++ b/src/main/java/io/github/danthe1st/httpsintercept/rules/PostForwardRule.java @@ -0,0 +1,16 @@ +package io.github.danthe1st.httpsintercept.rules; + +import com.fasterxml.jackson.annotation.JsonSubTypes; +import com.fasterxml.jackson.annotation.JsonSubTypes.Type; +import com.fasterxml.jackson.annotation.JsonTypeInfo; +import io.github.danthe1st.httpsintercept.handler.http.HttpResponseContentAccessor; +import io.github.danthe1st.httpsintercept.rules.post.HtmlBasedBlocker; +import io.netty.channel.Channel; +import io.netty.handler.codec.http.FullHttpRequest; +import io.netty.handler.codec.http.FullHttpResponse; + +@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "type") +@JsonSubTypes({ @Type(name = "htmlBasedBlock", value = HtmlBasedBlocker.class) }) +public interface PostForwardRule extends ProcessingRule { + boolean processRequest(FullHttpRequest fullHttpRequest, FullHttpResponse response, HttpResponseContentAccessor responseContentAccessor, Channel channel); +} diff --git a/src/main/java/io/github/danthe1st/httpsintercept/rules/PreForwardRule.java b/src/main/java/io/github/danthe1st/httpsintercept/rules/PreForwardRule.java index 04a6077..4a72166 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/rules/PreForwardRule.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/rules/PreForwardRule.java @@ -3,11 +3,12 @@ import com.fasterxml.jackson.annotation.JsonSubTypes; import com.fasterxml.jackson.annotation.JsonSubTypes.Type; import com.fasterxml.jackson.annotation.JsonTypeInfo; +import io.github.danthe1st.httpsintercept.rules.pre.SetRequestHeaderRule; import io.netty.channel.Channel; import io.netty.handler.codec.http.FullHttpRequest; @JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "type") -@JsonSubTypes({ @Type(name = "addHeader", value = SetHeaderRule.class) }) +@JsonSubTypes({ @Type(name = "addHeader", value = SetRequestHeaderRule.class) }) public interface PreForwardRule extends ProcessingRule { boolean processRequest(FullHttpRequest fullHttpRequest, Channel channel); } diff --git a/src/main/java/io/github/danthe1st/httpsintercept/rules/post/HtmlBasedBlocker.java b/src/main/java/io/github/danthe1st/httpsintercept/rules/post/HtmlBasedBlocker.java new file mode 100644 index 0000000..fcf0005 --- /dev/null +++ b/src/main/java/io/github/danthe1st/httpsintercept/rules/post/HtmlBasedBlocker.java @@ -0,0 +1,96 @@ +package io.github.danthe1st.httpsintercept.rules.post; + +import java.io.IOException; +import java.io.UncheckedIOException; +import java.nio.file.Files; +import java.nio.file.Path; +import java.util.regex.Pattern; + +import io.github.danthe1st.httpsintercept.config.HostMatcherConfig; +import io.github.danthe1st.httpsintercept.handler.http.HttpResponseContentAccessor; +import io.github.danthe1st.httpsintercept.rules.PostForwardRule; +import io.netty.buffer.Unpooled; +import io.netty.channel.Channel; +import io.netty.handler.codec.http.DefaultFullHttpResponse; +import io.netty.handler.codec.http.FullHttpRequest; +import io.netty.handler.codec.http.FullHttpResponse; +import io.netty.handler.codec.http.HttpResponseStatus; +import io.netty.handler.codec.http.HttpVersion; +import org.jsoup.Jsoup; +import org.jsoup.nodes.Document; +import org.jsoup.nodes.Element; + +public record HtmlBasedBlocker( + HostMatcherConfig hostMatcher, + String selector, Pattern matcher, + int status, String responseContentType, String responsePath) + implements PostForwardRule { + + public HtmlBasedBlocker(HostMatcherConfig hostMatcher, + String selector, Pattern matcher, + int status, String responseContentType, + String responsePath) { + if(status <= 0){ + status = 500; + } + if(responseContentType==null) { + responseContentType = "text/html"; + } + + this.hostMatcher = hostMatcher; + this.selector = selector; + this.matcher = matcher; + this.status = status; + this.responseContentType = responseContentType; + this.responsePath = responsePath; + } + + @Override + public boolean processRequest(FullHttpRequest fullHttpRequest, FullHttpResponse response, HttpResponseContentAccessor responseContentAccessor, Channel channel) { + String contentType = response.headers().get("Content-Type"); + if(contentType.startsWith("text/html")){ + String html = responseContentAccessor.getAsString(); + Document doc = Jsoup.parse(html); + for(Element element : doc.select(selector)){ + if(matcher.matcher(element.html()).matches()){ + FullHttpResponse newResponse; + try{ + newResponse = new DefaultFullHttpResponse( + HttpVersion.HTTP_1_1, + HttpResponseStatus.valueOf(status), + Unpooled.copiedBuffer(getResponseBytes()) + ); + newResponse.headers().add("Content-Type", contentType); + }catch(IOException e){ + throw new UncheckedIOException(e); + } + channel.writeAndFlush(newResponse); + return false; + } + } + } + + return true; + } + + private byte[] getResponseBytes() throws IOException { + if(responsePath == null){ + return """ + + + + Blocked + + +

Content has been blocked!

+

+ HTTPs-intercept blocked this response. +

+ + + """.getBytes(); + } + return Files.readAllBytes(Path.of(responsePath)); + } + +} diff --git a/src/main/java/io/github/danthe1st/httpsintercept/rules/SetHeaderRule.java b/src/main/java/io/github/danthe1st/httpsintercept/rules/pre/SetRequestHeaderRule.java similarity index 66% rename from src/main/java/io/github/danthe1st/httpsintercept/rules/SetHeaderRule.java rename to src/main/java/io/github/danthe1st/httpsintercept/rules/pre/SetRequestHeaderRule.java index abbcf2f..e41f867 100644 --- a/src/main/java/io/github/danthe1st/httpsintercept/rules/SetHeaderRule.java +++ b/src/main/java/io/github/danthe1st/httpsintercept/rules/pre/SetRequestHeaderRule.java @@ -1,18 +1,19 @@ -package io.github.danthe1st.httpsintercept.rules; +package io.github.danthe1st.httpsintercept.rules.pre; import java.util.Map; import io.github.danthe1st.httpsintercept.config.HostMatcherConfig; +import io.github.danthe1st.httpsintercept.rules.PreForwardRule; import io.netty.channel.Channel; import io.netty.handler.codec.http.FullHttpRequest; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -public record SetHeaderRule(HostMatcherConfig hostMatcher, +public record SetRequestHeaderRule(HostMatcherConfig hostMatcher, Map headers) implements PreForwardRule { - private static final Logger LOG = LoggerFactory.getLogger(SetHeaderRule.class); + private static final Logger LOG = LoggerFactory.getLogger(SetRequestHeaderRule.class); @Override public boolean processRequest(FullHttpRequest fullHttpRequest, Channel channel) {