package online.listener;

import java.util.Objects;

import javax.servlet.ServletContext;
import javax.servlet.http.HttpSession;
import javax.servlet.http.HttpSessionAttributeListener;
import javax.servlet.http.HttpSessionBindingEvent;

/**
 * CrossContextSessionAttributeListener
 *
 * 指定されたキー（無し時はSID）のセッション情報をServletContextに設定・削除する。
 * メインのアプリのweb.xmlにこのfilterを設定する。
 * Context設定を sessionCookiePath="/" にする。
 *
 * @author Tadashi Nakayama
 */
public class CrossContextSessionAttributeListener implements HttpSessionAttributeListener {

	/**
	 * @see javax.servlet.http.HttpSessionAttributeListener
	 * #attributeAdded(javax.servlet.http.HttpSessionBindingEvent)
	 */
	@Override
	public void attributeAdded(final HttpSessionBindingEvent sbe) {
		final var sc = sbe.getSession().getServletContext();
		final var key = getKeyName(sc, sbe.getSession());
		if (key.equals(sbe.getName())) {
			sc.setAttribute(key, sbe.getValue());
		}
	}

	/**
	 * @see javax.servlet.http.HttpSessionAttributeListener
	 * #attributeRemoved(javax.servlet.http.HttpSessionBindingEvent)
	 */
	@Override
	public void attributeRemoved(final HttpSessionBindingEvent sbe) {
		final var sc = sbe.getSession().getServletContext();
		final var key = getKeyName(sc, sbe.getSession());
		if (key.equals(sbe.getName())) {
			sc.removeAttribute(key);
		}
	}

	/**
	 * @see javax.servlet.http.HttpSessionAttributeListener
	 * #attributeReplaced(javax.servlet.http.HttpSessionBindingEvent)
	 */
	@Override
	public void attributeReplaced(final HttpSessionBindingEvent sbe) {
		attributeAdded(sbe);
	}

	/**
	 * キー名取得
	 *
	 * @param sc ServletContext
	 * @param session HttpSession
	 * @return キー名
	 */
	private String getKeyName(final ServletContext sc, final HttpSession session) {
		var key = Objects.toString(sc.getInitParameter("loginInfoKey"), "");
		if (key.isEmpty()) {
			key = session.getId();
		}
		return key;
	}
}
