首页  >  文章  >  Java Spring Boot 控制器中 RequestHeader 的重复

Java Spring Boot 控制器中 RequestHeader 的重复

WBOY
WBOY转载
2024-02-06 11:36:10521浏览
问题内容

我有一组用 java 编写的 rest 控制器。最初的要求是为某些端点添加一些标头,但是我们决定在几乎所有 rest 控制器中添加这些标头字段。现在该项目包含 100 多个类似的 api:

@getmapping("/products/{comp}")
public responseentity<list<product>> getallproducts(
        @requestheader(user_hdr) string user,
        @requestheader(guid_hdr) string guid,
        @requestheader(value = caller_hdr, required = false) string caller,
        @requestheader(value = lang_hdr, required = false) string language,
        @pathvariable @notnull integer comp
) {

    return responseentity.ok(service.get(comp, productutils.processheaders(user,guid,caller,language)));

}

@getmapping("/products")
public responseentity<list<product>> getallproducts(
        @requestheader(user_hdr) string user,
        @requestheader(guid_hdr) string guid,
        @requestheader(value = caller_hdr, required = false) string caller,
        @requestheader(value = lang_hdr, required = false) string language
) {

   return responseentity.ok(service.getallrecords(productutils.processheaders(user,guid,caller,language)));

}

从代码中可以明显看出,元组用户、guid、调用者、语言在源代码中无处不在,但是,如何重构并将代码放在“一个地方”或尝试使其更丰富,这不是很明显吗?可维护。例如,如果我们需要添加第 5 个参数,则需要使用 100 个 api。

在 java spring boot 中执行此操作的规范方法是什么?

理想情况下,我想要这样的东西:

@GetMapping("/products/{comp}")
    public ResponseEntity<List<Product>> getAllProducts(
            "common handling"
            @PathVariable @NotNull Integer comp
    ) {

        return ResponseEntity.ok(service.get(comp, ProductUtils.processHeaders(user,guid,caller,language)));

    }

    @GetMapping("/products")
    public ResponseEntity<List<Product>> getAllProducts(
            "common handling"
    ) {

       return ResponseEntity.ok(service.getAllRecords(ProductUtils.processHeaders(user,guid,caller,language)));

    }

有什么想法吗?控制器建议?还有别的吗?


正确答案


为了解决代码重复问题并使代码在 spring boot 应用程序中更易于维护,您可以创建一个自定义过滤器来在公共标头到达控制器之前提取和处理它们。另外,您还可以将头参数封装成对象,以增强代码的可读性和可维护性。

总之,通过创建 requestheaders dto、实现 customheaderfilter 并将其注册到 filterregistrationbean 来集中标头处理,以在 spring boot 控制器中统一应用通用标头。

以下是建议的方法:

  1. 创建标头 dto(数据传输对象):

    定义一个表示公共标头参数的类。此类将保存从标头中提取的值。

    public class requestheaders {
        private string user;
        private string guid;
        private string caller;
        private string language;
    
        // getters and setters
    }
    
  2. 创建过滤器:

    实现过滤器来拦截传入请求并提取公共标头,然后将它们存储在请求属性中。

    import org.springframework.web.filter.onceperrequestfilter;
    import javax.servlet.filterchain;
    import javax.servlet.servletexception;
    import javax.servlet.http.httpservletrequest;
    import javax.servlet.http.httpservletresponse;
    import java.io.ioexception;
    
    public class customheaderfilter extends onceperrequestfilter {
        @override
        protected void dofilterinternal(httpservletrequest request, httpservletresponse response, filterchain filterchain)
                throws servletexception, ioexception {
    
            requestheaders headers = new requestheaders();
            headers.setuser(request.getheader("user"));
            headers.setguid(request.getheader("guid"));
            headers.setcaller(request.getheader("caller"));
            headers.setlanguage(request.getheader("language"));
    
            request.setattribute("requestheaders", headers);
    
            filterchain.dofilter(request, response);
        }
    }
    
  3. 使用 filterregistrationbean 注册过滤器:

    在主应用程序类中使用 filterregistrationbean 注册自定义过滤器。

    import org.springframework.boot.web.servlet.filterregistrationbean;
    import org.springframework.context.annotation.bean;
    import org.springframework.context.annotation.configuration;
    
    @configuration
    public class webconfig {
        @bean
        public filterregistrationbean<customheaderfilter> customheaderfilter() {
            filterregistrationbean<customheaderfilter> registrationbean = new filterregistrationbean<>();
            registrationbean.setfilter(new customheaderfilter());
            registrationbean.addurlpatterns("/api/*"); // adjust the url pattern as needed
            return registrationbean;
        }
    }
    

    自定义 addurlpatterns 方法以匹配您希望应用过滤器的 url。

  4. 修改控制器以使用 dto:

    修改您的控制器以使用 requestheaders dto 而不是单独的标头参数。

    @GetMapping("/products/{comp}")
    public ResponseEntity<List<Product>> getAllProducts(@PathVariable @NotNull Integer comp,
                                                        @ModelAttribute("requestHeaders") RequestHeaders headers) {
        return ResponseEntity.ok(service.get(comp, headers));
    }
    
    @GetMapping("/products")
    public ResponseEntity<List<Product>> getAllProducts(@ModelAttribute("requestHeaders") RequestHeaders headers) {
        return ResponseEntity.ok(service.getAllRecords(headers));
    }
    

现在,如果您需要添加新的标头参数或进行更改,您只需更新 requestheaders 类和过滤器逻辑。这种方法集中了标头处理并增强了可维护性。

以上是Java Spring Boot 控制器中 RequestHeader 的重复的详细内容。更多信息请关注PHP中文网其他相关文章!

声明:
本文转载于:stackoverflow.com。如有侵权,请联系admin@php.cn删除