4

前の質問へのコメントで、誰かが次の sql ステートメントが私を sql インジェクションに導くと言っていました:

select
    ss.*,
    se.name as engine,
    ss.last_run_at + interval ss.refresh_frequency day as next_run_at,
    se.logo_name    
from 
    searches ss join search_engines se on ss.engine_id = se.id
where
    ss.user_id='.$user_id.'
group by ss.id
order by ss.project_id, ss.domain, ss.keywords

変数が適切にエスケープされていると仮定すると、$useridこれによりどのように脆弱になるのでしょうか?また、それを修正するにはどうすればよいでしょうか?

4

7 に答える 7

15

使用する価値のあるすべての SQL インターフェイス ライブラリには、バインド パラメーターに対する何らかのサポートがあります。賢くしようとしないで、ただそれを使ってください。

あなたは本当に、本当に物事を適切にエスケープしたと思っている/望んでいるかもしれませんが、そうしない時間は価値がありません.

また、いくつかのデータベースはプリペアド ステートメント キャッシングをサポートしているため、適切に行うことで効率も向上します。

より簡単に、より安全に、より速く。

于 2008-11-25T04:35:03.197 に答える
6

適切にエスケープされていると仮定すると、脆弱になることはありません。問題は、適切にエスケープすることは一見したよりも難しく、そのようなクエリを実行するたびに適切にエスケープすることを自分自身に非難することです。可能であれば、すべての問題を回避し、準備済みステートメント (またはバインドされたパラメーターまたはパラメーター化されたクエリ) を使用してください。これは、データ アクセス ライブラリが値を適切にエスケープできるようにするためです。

たとえば、PHP でmysqliを使用すると、次のようになります。

$db_connection = new mysqli("localhost", "user", "pass", "db");
$statement = $db_connection->prepare("SELECT thing FROM stuff WHERE id = ?");
$statement->bind_param("i", $user_id); //$user_id is an integer which goes 
                                       //in place of ?
$statement->execute();
于 2008-11-25T04:35:01.870 に答える
2

$user_idがエスケープされている場合、SQL インジェクションに対して脆弱になることはありません。

この場合、 $user_id が数値または整数であることも確認します (必要な正確なタイプによって異なります)。可能な限り最も制限的なタイプにデータを常に制限する必要があります。

于 2008-11-25T04:36:22.290 に答える
1

すべての答えは適切で正しいですが、prepare/executeパラダイムが唯一の解決策ではないことを付け加える必要があると感じています. ライブラリ関数を直接使用するのではなく、データベース抽象化レイヤーを用意する必要があります。そのようなレイヤーは、文字列パラメーターを明示的にエスケープするのに適しprepareています。

于 2008-11-25T05:00:48.167 に答える
1

ここで「適切にエスケープ」がキーワードだと思います。あなたの最後の質問では、あなたのコードが本番コードからコピーペーストされていると仮定しています.3つのテーブル結合について質問したので、適切なエスケープをしなかったと仮定しています. SQL インジェクション攻撃。

ここで多くの人が説明しているように、あなたの質問に答えるために変数が「適切にエスケープ」されている場合、問題はありません。しかし、なぜそんなことをして自分を苦しめるのですか?一部の人々が指摘しているように、適切にエスケープすることは簡単なことではありません。PHP には SQL インジェクションを不可能にするパターンとライブラリがあります。(また、コードが実際には PHP であると意図的に想定しています)。Vinko Vrsalovic の回答は、この問題へのアプローチ方法に関するアイデアを提供する場合があります。

于 2008-11-25T05:09:58.803 に答える
1

適切にエスケープされ、検証されていれば、問題はありません。

この問題は、適切にエスケープまたは検証されていない場合に発生します。これは、ずさんなコーディングまたは見落としによって発生する可能性があります。

問題は特定のインスタンスではなく、パターンにあります。このパターンは SQL インジェクションを可能にしますが、他のパターンは不可能にします。

于 2008-11-25T04:35:53.943 に答える
0

そのようなステートメント自体は実際には問題ではなく、「安全」ですが、これをどのように行っているかはわかりません(APIスタックの1レベル上)。$user_id が文字列操作を使用してステートメントに挿入されている場合 (Php にステートメントを自動的に入力させているかのように)、危険です。

バインディング API を使用して入力されている場合は、準備完了です。

于 2008-11-25T04:35:37.533 に答える