2011-05-11 69 views
1

在postgres中使用CREATE SCHEMA schema_name時,如果需要用戶輸入,如何防止schema_name參數的SQL注入?SQL注入和Postgres「CREATE SCHEMA」

schema_name不能被引用的值,因此例如ActiveRecord::Base.sanitize()將不起作用。 (如果你使用導軌)。

回答

1

我知道這可能不是您正在尋找的答案,但如果您的設計讓用戶決定您的架構名稱,但您不信任您的用戶,那麼您確實需要重新設計。讓用戶決定模式名稱類似於要求用戶決定類和函數名稱。

如果你確實想要這樣做,我會使用正則表達式來限制類似於16個字母數字字符的地方,在被強制爲小寫字母(/^[az] [a-z0 -9] {1,15} $ /)。您還需要顯式過濾出「public」作爲模式名稱,information_schema(如果您還允許使用下劃線)以及其他內置模式名稱。

同樣,我敢打賭,你真的不想這樣做,並且有更好的方法來解決你的潛在問題。

+0

不錯,簡單的答案。 – SooDesuNe 2011-05-24 00:19:26

2

允許用戶創建模式(通常用於執行DDL)是相當不尋常的(甚至是可怕的)。你確定要這麼做嗎?在任何情況下,你都可以做一些常用的事情:或者清理你的輸入(我猜如果你允許用戶至少創建schames,你可以限制允許的名字 - 例如只有字母數字等等),和/或使用準備好的語句,綁定模式名稱(這取決於您的語言/環境)。

+0

也許這是一個不同的問題,但爲什麼會這樣可怕允許用戶創建一個模式? – SooDesuNe 2011-05-11 03:20:08

1

用戶不應該擁有DDL權限,他們不需要它,並且它給了他們太多的權力。

你可以使用一個SQL函數中使用quote_ident,創建一個模式,並避免SQL注入:

CREATE OR REPLACE FUNCTION new_schema(IN _schemaname TEXT) 
    RETURNS bool 
    LANGUAGE plpgsql 
    AS 
    $$ 
    BEGIN; 
     EXECUTE 'CREATE SCHEMA ' || quote_ident(_schemaname); 

     RETURN true; 
    END; 
    $$ 
    SECURITY DEFINER; 

-- test: 
SELECT new_schema('Frank; drop database template1');