Готовая выписка с SQL вопросом запроса - PullRequest
0 голосов
/ 17 марта 2020

Код, показанный ниже, используется для поиска в списках вакансий, подготовленный оператор был добавлен для предотвращения SQL инъекций, которые также уязвимы. Поиск оператора запроса работал до добавления подготовленного оператора, однако теперь ничего не возвращает. Кто-нибудь может увидеть, что я делаю не так? Спасибо. Предыдущий код выглядел так:

try (Connection con = DriverManager.getConnection("jdbc:mysql://localhost:3306/SQL_DB", "root", "root"); Statement stmt = con.createStatement()) { rs = stmt.executeQuery(queryStatement);

Код теперь выглядит так:

public List<jobs> searchjobs(@RequestParam String query) {
    log.debug("REST request to search jobs for query {}", query);


    String queryStatement = "SELECT * FROM jobs WHERE description like '%" + query + "%'";
    log.info("Final SQL query {}", queryStatement);

    ResultSet rs = null;

    try (Connection con = DriverManager.getConnection("jdbc:mysql://localhost:3306/SQL_DB", "root", "root");
        PreparedStatement stmt = con.prepareStatement(queryStatement)) {
        stmt.setString(1, query);
        rs = stmt.executeQuery(queryStatement);
        return extractjobs(rs);
    } catch (SQLException ex) {
        log.error(ex.getMessage(), ex);
        return new ArrayList();
    } finally {
        try {
            if (rs != null) {
                rs.close();
            }
        } catch (SQLException ex) {
            log.error(ex.getMessage(), ex);
        }
    }
}

Ответы [ 2 ]

1 голос
/ 17 марта 2020

Возможно, вы прочитали общий совет «используйте подготовленные заявления для защиты от SQL инъекции». Но этот совет - только половина правды.

Полная истина заключается в том, что вы должны использовать параметры запроса , чтобы отделить ненадежный контент от вашего запроса. Просто случается, что использование параметров запроса требует использования подготовленных операторов, поэтому вы можете отделить шаг подготовки от шага выполнения и связать параметры с подготовленным запросом между этими двумя шагами.

Это помогает защитить от SQL инъекция, потому что подготовка - это когда ваш запрос анализируется. Если вы храните ненадежное содержимое отдельно от запроса до тех пор, пока оно не будет проанализировано, то ненадежное содержимое не может ввести SQL инъекцию.

В вашем запросе нет параметров-заполнителей. Вы конкатенируете свой ненадежный контент в утверждение, как и раньше, что означает, что оно все еще имеет уязвимость SQL.

String queryStatement = "SELECT * FROM jobs WHERE description like '%" + query + "%'";

Должно быть:

String queryStatement = "SELECT * FROM jobs WHERE description like ?";

Поскольку ваш запрос не имеет параметров-заполнителей, при попытке привязки к нему должна быть ошибка:

    stmt.setString(1, query);

Выдает ли это исключение? Кажется, вы регистрируете его, поэтому проверьте ваш журнал.

1 голос
/ 17 марта 2020

Вы пропустили сущность подготовленного утверждения. При его использовании вы подставляете все переменные с заполнителями , например

String queryStatement = "SELECT * FROM jobs WHERE description like ?";

, и затем можете связать переменную запроса, как вы это сделали. Просто добавьте эти проценты сначала

stmt.setString(1, "%" + query + "%");
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...