NutzCN Logo
问答 nutzboot如何防止SQL注入呢
发布于 1808天前 作者 Hamming 1901 次浏览 复制 上一个帖子 下一个帖子
标签:

nutzboot如何防止SQL注入呢
写个AbstractProcessor么?

package cn.wizzer.common.processor;

import cn.wizzer.common.base.Result;
import cn.wizzer.common.shiro.NutShiro;
import org.apache.commons.lang3.StringUtils;
import org.nutz.log.Log;
import org.nutz.log.Logs;
import org.nutz.mvc.ActionContext;
import org.nutz.mvc.Mvcs;
import org.nutz.mvc.impl.processor.AbstractProcessor;
import org.nutz.mvc.view.ForwardView;

import javax.servlet.http.HttpServletRequest;
import java.util.Iterator;

/**
 * SQL XSS拦截
 * Created by wizzer on 2016/7/1.
 */
public class XssSqlFilterProcessor extends AbstractProcessor {

    private static final Log log = Logs.get();
    protected String lerrorUri = "/WEB-INF/error/403.html";

    @Override
    public void process(ActionContext ac) throws Throwable {
        if (checkParams(ac)) {
            if (NutShiro.isAjax(ac.getRequest())) {
                ac.getResponse().addHeader("loginStatus", "paramsDenied");
                NutShiro.rendAjaxResp(ac.getRequest(), ac.getResponse(), Result.error(Mvcs.getMessage(ac.getRequest(), "system.paramserror")));
            } else {
                new ForwardView(lerrorUri).render(ac.getRequest(), ac.getResponse(), Mvcs.getMessage(ac.getRequest(), "system.paramserror"));
            }
            return;
        }
        doNext(ac);
    }

    protected boolean checkParams(ActionContext ac) {
        HttpServletRequest req = ac.getRequest();
        Iterator<String[]> values = req.getParameterMap().values().iterator();// 获取所有的表单参数
        Iterator<String[]> values2 = req.getParameterMap().values().iterator();// 因为是游标所以要重新获取
        boolean isError = false;
        String regEx_sql = "select|update|and|or|delete|insert|trancate|char|chr|into|substr|ascii|declare|exec|count|master|drop|execute";
        String regEx_xss = "script|iframe";
        //SQL过滤
        while (values.hasNext()) {
            String[] valueArray = (String[]) values.next();
            for (int i = 0; i < valueArray.length; i++) {
                String value = valueArray[i].toLowerCase();
                //分拆关键字
                String[] inj_stra = StringUtils.split(regEx_sql, "|");
                for (int j = 0; j < inj_stra.length; j++) {
                    // 判断如果路径参数值中含有关键字则返回true,并且结束循环
                    if ("and".equals(inj_stra[j]) || "or".equals(inj_stra[j]) || "into".equals(inj_stra[j])) {
                        if (value.contains(" " + inj_stra[j] + " ")) {
                            isError = true;
                            log.debugf("[%-4s]URI=%s %s", req.getMethod(), req.getRequestURI(), "SQL关键字过滤:" + value);
                            break;
                        }
                    } else {
                        if (value.contains(" " + inj_stra[j] + " ")
                                || value.contains(
                                inj_stra[j] + " ")) {
                            isError = true;
                            log.debugf("[%-4s]URI=%s %s", req.getMethod(), req.getRequestURI(), "SQL关键字过滤:" + value);
                            break;
                        }
                    }
                }
                if (isError) {
                    break;
                }
            }
            if (isError) {
                break;
            }
        }
        if (!isError) {
            // XSS漏洞过滤
            while (values2.hasNext()) {
                String[] valueArray = (String[]) values2.next();
                for (int i = 0; i < valueArray.length; i++) {
                    String value = valueArray[i].toLowerCase();
                    // 分拆关键字
                    String[] inj_stra = StringUtils.split(regEx_xss, "|");
                    for (int j = 0; j < inj_stra.length; j++) {
                        // 判断如果路径参数值中含有关键字则返回true,并且结束循环
                        if (value.contains("<" + inj_stra[j] + ">")
                                || value.contains("<" + inj_stra[j])
                                || value.contains(inj_stra[j] + ">")) {
                            log.debugf("[%-4s]URI=%s %s", req.getMethod(), req.getRequestURI(), "XSS关键字过滤:" + value);
                            isError = true;
                            break;
                        }
                    }
                    if (isError) {
                        break;
                    }
                }
                if (isError) {
                    break;
                }
            }
        }
        return isError;
    }
}

5 回复

页面普通查询 会涉及排序
if (Strings.isNotBlank(orderByColumn) && Strings.isNotBlank(isAsc)) {
cnd.orderBy( GenUtils.javaToTable(orderByColumn),isAsc);
}
或者 复杂SQL

    public TableDataInfo selectTableList(String tableName, String tableComment, int pageNumber, int pageSize, String orderByColumn, String isAsc) {
        String sqlstr = "select table_name, table_comment, create_time, update_time from information_schema.tables " +
                "where table_comment <> '' and table_schema = (select database()) ";
        if (Strings.isNotBlank(tableName)) {
            sqlstr += "and table_name like @tableName";
        }
        if (Strings.isNotBlank(tableComment)) {
            sqlstr += "and table_comment like @tableComment";
        }
        if (Strings.isNotBlank(orderByColumn) && Strings.isNotBlank(isAsc)) {

            sqlstr += " order by " + GenUtils.javaToTable(orderByColumn) + " " + isAsc;
        }
        Sql sql = Sqls.create(sqlstr);
        sql.params().set("tableName", "%" + tableName + "%");
        sql.params().set("tableComment", "%" + tableComment + "%");
        sql.setCallback(Sqls.callback.entities());
        Entity<TableInfo> entity = dao.getEntity(TableInfo.class);

        Pager pager = dao.createPager(pageNumber, pageSize);
        //记录数需手动设置
        pager.setRecordCount((int) Daos.queryCount(dao, sql));
        sql.setPager(pager);
        sql.setEntity(entity).setCondition(Cnd.wrap(sqlstr));
        dao.execute(sql);
//        return sql.getList(TableInfo.class);
        return new TableDataInfo(sql.getList(TableInfo.class), pager.getRecordCount());
    }

如果 注入 怎么解决呢

Sqls类有抹除特殊字符的方法

nutz果然很NB
自定义一个全局 过滤器 XssSqlFilterProcessor
自定义SQL 在过滤一遍 formatSqlFieldValue
安全

druid还有防火墙

添加回复
请先登陆
回到顶部