Я использую MyFaces 2.2.3 с сохранением состояния на стороне клиента + PrimeFaces
После запроса того, как предотвратить повторное использование ViewState в разных сеансах, я был рассказанный BalusC, что я могу вставлять свой собственный токен CSRF, переопределяя средство рендеринга, чтобы значение было токеном CSRF,
Я ищу решение, которое не заставит меня изменять мои страницы xhtml вообще:)
BalusC предложил лучший способ предотвратить атаку CSRF, расширив ViewHandlerWrapper
, и он отлично работает, мне только пришлось немного изменить restoreView
public UIViewRoot restoreView(FacesContext context, String viewId) {
UIViewRoot view = super.restoreView(context, viewId);
if (getCsrfToken(context).equals(view.getAttributes().get(CSRF_TOKEN_KEY))) {
return view;
} else {
HttpSession session = (HttpSession) context.getExternalContext().getSession(false);
if (session != null) {
session.invalidate(); //invalidate session so (my custom and unrelated) PhaseListener will notice that its a bad session now
}
try {
FacesContext.getCurrentInstance().getExternalContext().redirect("CSRF detected and blocked"); //better looking user feedback
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
}
Старое решение
<ы > Я пробовал без успеха до сих пор,
Добавлен в faces-config.xml
<render-kit>
<renderer>
<component-family>javax.faces.Form</component-family>
<renderer-type>javax.faces.Form</renderer-type>
<renderer-class>com.communitake.mdportal.renderers.CTFormRenderer</renderer-class>
</renderer>
</render-kit>
Тогда в CTFormRenderer.java
@Override
public void encodeEnd(FacesContext context, UIComponent arg1) throws IOException {
//how to set form value be a CSRF token?
}
@Override
public void decode(FacesContext context, UIComponent component) {
HttpSession session = (HttpSession) context.getExternalContext().getSession(false);
String token = (String) session.getAttribute(CSRFTOKEN_NAME);
String tokenFromForm = //how to get the value stored in form value attribute because (String) component.getAttributes().get("value"); return null
//check token against tokenFromForm...
}
Я не хочу добавлять пользовательский компонент к каждому h:form
, вместо этого хочу расширить средство отображения form
, поэтому вся моя форма будет иметь csrf token
.