Как обновить параметр заголовка и отправить его в контроллер с помощью AOP при загрузке Spring / Spring - PullRequest
0 голосов
/ 19 января 2019

Как обновить параметр заголовка и отправить его в контроллер с помощью AOP при загрузке Spring / Spring?Я могу добавить, но не могу отправить его на контроллер.Я получаю нулевое значение в контроллере.Я не хочу использовать @ Around.

  @Before("PointcutDefinition.controllerLayer()")
  public Object beforeAdvice(JoinPoint joinPoint)
  {
    HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
    request.setAttribute("traceId", ServiceUtil.getTraceId());
    return request;
  }

Обновление:

Мне удалось обновить traceId, используя следующий код.

  @Around("execution(* com.test.api.*.*(..)) && " + "args(traceId,..)")
  public Object setTraceId(ProceedingJoinPoint joinPoint, String traceId) throws Throwable
  {
    String newTraceId = ServiceUtil.getTraceId();
    Object result = joinPoint.proceed(new Object[]
    { newTraceId, "", "", "", "", "", "", "", "", "" });
    return result;
  }

В моем контроллереУ меня есть несколько методов с различным количеством аргументов.Но первым аргументом во всем методе является traceId.Я хотел бы обновить traceId в одиночку и оставить другой параметр как есть.Но в приведенном выше подходе я вынужден передать все аргументы.Есть ли способ, которым я могу обновить первый параметр в одиночку и отправить оставшиеся параметры без изменений.

Ответы [ 2 ]

0 голосов
/ 19 января 2019

Ваша проблема не в аннотации @Before, а в ошибочной установке атрибута в HttpServletRequest вместо заголовка. Атрибут! = Заголовок. Поэтому, конечно, этот параметр будет нулевым в вашем контроллере.

Заголовки в HttpServletRequest доступны только для чтения. Вам нужно будет обернуть запрос в HttpServletRequestWrapper и выполнить все виды работ для управления исходными и вашими собственными заголовками. Существует множество примеров, в том числе полный: https://wilddiary.com/adding-custom-headers-java-httpservletrequest/

Он представляет MutableHttpServletRequest, который расширяет HttpServletRequestWrapper. Вы будете сохранять состояние ваших пользовательских заголовков и просто их с оригинальными. Вам придется переопределить getHeader и getHeaderNames!

Ваш код @Before будет выглядеть примерно так:

HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
MutableHttpServletRequest wrappedRequest = new MutableHttpServletRequest(request);
request.putHeader("traceId", ServiceUtil.getTraceId());
return request;

Тем не менее, это кажется слишком длинным путем, чтобы получить немного функциональности (если вам не нужно делать это снова и снова). Для разового использования я бы просто использовал технику @Around.

Вся эта церемония добавит ценность карте!

0 голосов
/ 19 января 2019

Я смог сделать это с помощью @Around.Я считаю, что это не может быть достигнуто с помощью @ Before.

  @Around("execution(* com.test.api.*.*(..)) && " + "args(traceId,..)")
  public Object setTraceId(ProceedingJoinPoint joinPoint, String traceId) throws Throwable
  {
    String newTraceId = ServiceUtil.getTraceId();
    Object[] obj = joinPoint.getArgs();
    obj[0] = newTraceId;
    return joinPoint.proceed(obj);
  }
...