0

Pythonを使用してDjangoアプリケーションを構築していますが、アプリケーションは大量のデータを受信することが予想されます。パフォーマンスを向上させることができるいくつかのPL/PGSQLプロシージャに取り組んできました。これらのプロシージャはファイルに保存されているので、データベースに作成したくありません。

postgresql_psycopg2を使用してそれらを実行できるようにしたいだけです。別のトリッキーな部分は、実行前にファイル内のいくつかのパラメーターを変更できるようにしたいということです。

これが私のPythonコードです

        pg_script = os.path.join(getattr(settings, 'BASE_DIR'),'myapp/apps/rating/sql/rating_create_article_rating.sql')

        cursor = connection.cursor()
        cursor.execute("run script %s" % pg_script)

これがrating_create_article_rating.sqlです

DECLARE
    article_rec   publication_article%ROWTYPE;
    user_rec      auth_user%ROWTYPE;
    up            integer := 1;
    down          integer := -1;
    l_counter     integer := 0; -- local counter
    cnt           integer;
    p_content_type_id integer;
BEGIN



    LOOP
        -- RANDOM ARTICLE
        SELECT *
        INTO article_rec
        FROM publication_article
        order by random()
        LIMIT  1;

        -- RANDOM USER
        SELECT *
        INTO user_rec
        FROM auth_user
        order by random()
        LIMIT  1;

        BEGIN
          INSERT INTO rating_rate (rated_by_id, rated_at, content_type_id, object_id, rate, language)
          VALUES (user_rec.id, now(), p_content_type_id, article_rec.id, 1, 'en');
          l_counter := l_counter+1;
        EXCEPTION
              WHEN unique_violation THEN

        END;



        EXIT WHEN l_counter>cnt;
    END LOOP;


    RETURN;
END;
$$ LANGUAGE plpgsql;

上記のコードは、ストアド関数として実行すると機能します。そうでない場合、実行スクリプトが機能しないと、次のエラーが発生します。

ERROR:  syntax error at or near "run" at character 1
STATEMENT:  run script /Users/mo/Projects/pythonic/myapp-env/myapp/myapp/apps/rating/sql/rating_create_article_rating.sql

パラメータをファイルに渡してpl/pgsqlから処理する方法があるかどうかも疑問に思っていますか?

どうもありがとう

4

1 に答える 1

1

まず、私はこれらのものを関数に入れることを好みます。重要な理由の1つは、これによりSQLコードとアプリケーションコードが分離され、必要なものを読みやすく見つけやすくなることです。関数で発生する可能性のあるいくつかの最適化もあります。

これで不十分な場合は、DOブロックを使用してください。ただし、DOブロックにはいくつかの重要な制限があります。たとえば、結果を返すことはできません。つまり、挿入物などに関する有用な情報を返したい場合は、それを行うことはできません。

DO戻り型のない無名関数を作成します。関数本体をDO LANGUAGE PLPGSQL $$ .. $$;ブロックに含めると、すぐに実行されます。

于 2013-04-20T15:09:03.617 に答える