import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.charset.Charset;
import java.util.Base64;
import java.util.HashSet;
import java.util.Set;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.util.AntPathMatcher;
import com.eduboss.utils.StringUtil;
public class Base64AuthFilter implements Filter {
/**不需要过滤的链接*/
private Set<String> noneFilters = new HashSet<>();
private String authCode;
private static final String USERNAME = "username";
private static final String PASSWORD = "password";
@Override
public void init(FilterConfig filterConfig) throws ServletException {
//读取不用过滤的路径
try {
InputStream inputStream = getClass().getClassLoader().getResourceAsStream("none-filters.txt");
InputStreamReader inputStreamReader = new InputStreamReader(inputStream, Charset.forName("utf-8"));
BufferedReader reader = new BufferedReader(inputStreamReader);
String line = null;
while ((line = reader.readLine()) != null) {
line = line.trim();//去掉前后空格
if (!line.startsWith("#")) {
noneFilters.add(line);
}
}
reader.close();
inputStreamReader.close();
inputStream.close();
} catch (IOException e) {
throw new RuntimeException(e);
}
//读取用户名跟密码
String username = filterConfig.getInitParameter(USERNAME);
String password = filterConfig.getInitParameter(PASSWORD);
if (StringUtil.isNotBlank(username) && StringUtil.isNotBlank(password)) {
authCode = username + ":" + password;
}
}
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
String requestURI = httpServletRequest.getRequestURI();
String contextPath = httpServletRequest.getContextPath();
String uri = requestURI.replaceFirst(contextPath, "");
//如果有完全匹配的路径,通过
if (noneFilters.contains(uri)) {
chain.doFilter(request, response);
return;
}
//通配判断
AntPathMatcher matcher = new AntPathMatcher();
for (String pt : noneFilters) {
if (matcher.match(pt, uri)) {
chain.doFilter(request, response);
return;
}
}
//验证,如果没有配置的用户名密码的话直接通过
if (authCode != null) {
String auth = httpServletRequest.getHeader("Authorization");
boolean check = false;
if (auth != null && auth.length() > 6) {
auth = auth.substring(6);
auth = new String(Base64.getDecoder().decode(auth));
check = this.authCode.equals(auth);
}
if (!check) {
HttpServletResponse httpServletResponse = (HttpServletResponse) response;
httpServletResponse.setStatus(401);
httpServletResponse.setHeader("Cache-Control", "no-store");
httpServletResponse.setDateHeader("Expires", 0);
httpServletResponse.setHeader("WWW-Authenticate", "Basic Realm=\"need username and password to authenticate\"");
return;
}
}
chain.doFilter(request, response);
}
@Override
public void destroy() {
}
}