2012-05-04 11 views
2

IPアドレスは、次のいずれかの方法でテーブルに格納されます。テーブル内のIPアドレスのリストに対してユーザーのIPアドレスを検証するにはどうすればよいですか?

192.12.34.12 
192.12.#.12 
192.#.34.12 

私のアプリケーションでは、このテーブルに対して、.netコードを使用してログインしたユーザーのIPアドレスを自動的に取得して検証したいと考えています。

は今、ユーザーIPが

192.12.34.12 
192.12.45.12 

192.56.34.12-- it should be valid. 
191.12.34.12-- Invalid 

ある場合はどのようにSQLクエリまたはこのテーブルに対するユーザーのIPアドレスにログインして検証するストアドプロシージャを作成することができますか?

答えて

1

お客様の訪問者IPの番号を各位置(ドットの間)に「#」で置き換え、通常のWHERE句を実行するという記述ができます。したがって、5つの比較を含むwhere節を持つ文が得られます(直接一致の場合は1つ、各位置の場合は#が4つあります)。

CHARINDEXを使用してドットを検索し、SUBSTRINGを使用して比較用のvarcharsを構築できます。

+3

幸運我々は、IPv6への移行時に、笑。 – Styxxy

+0

また、私はこの例が単純化されており、5つ以上の比較が必要であると思われます。多分... heh –

+0

あなたは#####と一致する必要はないと仮定して、15でなければなりません。 –

4

このように、LIKE演算子を使用してみてください:あなたは(それがどのインデックスを使用することはできません)あなたのテーブル内のレコードをたくさん持っている場合

SELECT * 
FROM IPRecords 
WHERE @UsersIp like replace(IP, '#', '%') 

しかし、このアプローチは非常に問題のパフォーマンスワイズすることができます。

パフォーマンスは本当に問題になる場合は、別のアプローチをすることができます。

  • は、(例えば、あなたの最後のルールは、192, null, 34, 12なる4つの数値列ワイルドカードを示すために
  • 使用null間でIPを分割しましたクライアント上の)
  • 、対応する4つの部分にIPを分割し、などの条件を使用:

    WHERE ([email protected] OR IP1 is null) AND ([email protected] OR IP2 is null) AND ...

この方法では、必要に応じて4つの列のインデックスを使用して高速化することができます。

3

PARSENAME機能を使用して、IPアドレス値を4つの部分に分割して個別に比較することができます。

テストデータスクリプトを作成し、移入:

CREATE TABLE ipaddresses 
( 
    ip VARCHAR(20) NOT NULL 
); 

INSERT INTO ipaddresses (ip) VALUES 
    ('192.12.34.12'), 
    ('192.12.#.12'), 
    ('192.#.34.12'); 

シナリオ#1

DECLARE @userip VARCHAR(20) 
SET  @userip = '192.56.34.12' 

;WITH ips AS 
(
    SELECT REPLACE(ip, '#', '%') AS ip 
    FROM ipaddresses 
) 
SELECT COUNT(ip) AS validcount 
FROM ips 
WHERE PARSENAME(@userip, 1) LIKE PARSENAME(ip, 1) 
AND  PARSENAME(@userip, 2) LIKE PARSENAME(ip, 2) 
AND  PARSENAME(@userip, 3) LIKE PARSENAME(ip, 3) 
AND  PARSENAME(@userip, 4) LIKE PARSENAME(ip, 4); 

VALIDCOUNT 
---------- 
    1 

シナリオ#2

DECLARE @userip VARCHAR(20) 
SET  @userip = '191.12.34.12' 

;WITH ips AS 
(
    SELECT REPLACE(ip, '#', '%') AS ip 
    FROM ipaddresses 
) 
SELECT COUNT(ip) AS validcount 
FROM ips 
WHERE PARSENAME(@userip, 1) LIKE PARSENAME(ip, 1) 
AND  PARSENAME(@userip, 2) LIKE PARSENAME(ip, 2) 
AND  PARSENAME(@userip, 3) LIKE PARSENAME(ip, 3) 
AND  PARSENAME(@userip, 4) LIKE PARSENAME(ip, 4); 

VALIDCOUNT 
---------- 
    0 
関連する問題