или false; - qacode.ru" />

Выполняется запрос MySQL, возвращает словарь или false;


Я занимаюсь C# и ASP.NET и работают на несколько более масштабный проект, чем я в настоящее время используется для. Я уверен, что есть ужасные вещи неправильно с этим кодом, что я узнаю позднее, а предпочел бы получить некоторые входные на нем сейчас.

Одна из вещей, я озабочен, так это тем, что RunSelectCommand может возвращать значение false, если в базе не удается подключиться, или если запрос не возвращает ничего.

В настоящее время, для того, чтобы проверить, что я делаю if (!(data is bool)) и если это не я предполагаю, что есть данные для работы, и я вернуть ошибки от веб-сервера, если нет.

Если больше информации необходимо, пожалуйста, дайте мне знать! Я очень рад для некоторых реальных рецензируемых код.

public object RunSelectCommand(MySqlCommand command, List<MySqlParameter> parameterCollection = null)
{
    using (MySqlConnection conn = new MySqlConnection(connectionString))
    using (var cmd = conn.CreateCommand())
    {
        try
        {
            conn.Open();
        }
        catch (MySqlException ex)
        {
            return ex;
        }
        cmd.CommandText = command.CommandText;
        if (parameterCollection != null) // if parameters for query are specified, add them here.
        {
            cmd.Parameters.AddRange(parameterCollection.ToArray());
        }
        using (var reader = cmd.ExecuteReader())
        {
            if (reader.Read())
            {
                Dictionary<string, string> data = new Dictionary<string, string>(); // This is designed for returning only 1 row at a time
                for (int i = 0; i < (reader.FieldCount - 1); i++) // TODO seperate SelectAll command
                {
                    data.Add(reader.GetName(i), reader[i].ToString()); // Iterates through reader and adds data to Dictionary for output to JSON
                }
                conn.Close();
                return data;
            }
            else
            {
                conn.Close();
                return false;
            }
        }
    }
}

Пример использования:

[HttpGet("checkapi/{text}")] 
    public object CheckApi(string text) // returning object automatically converts to JSon
    {
        MySqlCommand C = new MySqlCommand("SELECT * FROM api WHERE apikey = @apikey");
        List<MySqlParameter> collection = new List<MySqlParameter>()
        {
            new MySqlParameter() { ParameterName = "@apikey", Value = text }
        };
        return mysqlWrapper.RunSelectCommand(C, collection);
    }


720
4
задан 10 февраля 2018 в 03:02 Источник Поделиться
Комментарии
1 ответ

Как вы и подозревали, этот код очень плох. Вы возвращаете здесь три разных типа данных. Просто, не.

1)


try
{
conn.Open();
}
catch (MySqlException ex)
{
return ex;
}

Не вернуть исключение, повторно бросать и ловить его в звонившего.

try
{
conn.Open();
}
catch (MySqlException ex)
{
throw;
}

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

try
{
return mysqlWrapper.RunSelectCommand(C, collection);
}
catch (Exception ex)
{
return ex;
}

Однако, теперь вы подвергаете свой стек вызовов пользователя, которое вы не хотите делать. Эту информацию может предоставить подсказки, которые кто-то пытается проникнуть в вашу систему, и не допускается при некоторых протоколов безопасности (СПЦ 2, например). Вместо возвращения всего исключение, построить новый кусок данных и возвращает только соответствующие биты (или если просто нужно один кусок, затем просто вернуть этот кусок).

2)

Не вернуть false. Либо вернуть пустой объект (если звонящий не волнует, если не было результатов), или бросить исключение. Поочередно, вы могли бы использовать ValueTuple и вернуться (bool success, Dictionary<string, string> data) из метода. Первый успешный путь вернется (true, {data}) а второй вернется (false, null).

3)

Возможно, атаки с внедрением SQL происходит. Проверить, что произойдет, если клиент отправляет запрос с параметром текст "Test' или 1 = 1 --". Похоже, что результирующий запрос может быть SELECT * FROM api WHERE apikey = 'test' or 1 = 1 --'но я не знаю это достаточно хорошо, чтобы быть уверенным.

1
ответ дан 13 февраля 2018 в 04:02 Источник Поделиться