5

私が書いているサーバーは、すべての人と直接接触するわけではありませんが、さまざまな人によって実行されると予想されます。サーバーはクラスター内で相互に通信します。サーバーの機能の一部には、潜在的に非常に大きなテーブルから行の小さなサブセットを選択することが含まれます。どの行を選択するかを正確に選択するには、ある程度の調整が必要です。また、クラスターを実行している人 (例えば、私自身) が選択基準を更新できることが重要であり、すべてのサーバー管理者に新しいバージョンのサーバーをデプロイしてもらう必要はありません。 .

実行時に任意の Python コードをダウンロードして実行するサーバーをインストールしたいと思う人はいないため、単純に Python で関数を記述することは実際には選択肢ではありません。

私が必要としているのは、この目標を達成するためにドメイン固有言語を実装する最も簡単な方法に関する提案です。この言語は、単純な式の評価だけでなく、テーブル インデックスのクエリと返された行の反復処理も実行できる必要があります。言語の書きやすさと読みやすさは、実装のしやすさに次ぐものです。また、クエリ オプティマイザー全体を作成する必要がないことも望んでいるため、クエリするインデックスを明示的に指定するものが理想的です。

これをコンパイルする必要があるインターフェースは、App Engine データストアがエクスポートするものと同様の機能を備えています。テーブルの任意のインデックスで連続した範囲を照会できます (たとえば、より小さい、より大きい、範囲、等値のクエリ)。 、次に、返された行をブール式でフィルタリングします。複数の独立した結果セットを連結することもできます。

この質問は、私が SQL を求めているように聞こえると思います。ただし、このデータを支えるデータストアがリレーショナル データベースであることを要求したくはありません。また、SQL を自分で再実装しようとするオーバーヘッドも必要ありません。また、既知のスキーマを持つ単一のテーブルのみを扱っています。最後に、結合は必要ありません。はるかに単純なものがはるかに望ましいでしょう。

編集:いくつかの誤解を解消するために説明を拡張しました。

4

9 に答える 9

4

Python によって解釈される DSL の構築。

ステップ 1. ランタイム クラスとオブジェクトをビルドします。これらのクラスには、すべてのカーソル ループと SQL ステートメント、およびそのすべてのアルゴリズム処理がメソッドに組み込まれています。CommandStrategyの設計パターンを多用して、これらのクラスを作成します。ほとんどのものはコマンドであり、オプションと選択肢はプラグイン戦略です。Apache Ant のTask API の設計を見てください。これは良い例です。

ステップ 2. このオブジェクトのシステムが実際に機能することを検証します。デザインがシンプルで完全であることを確認してください。テストでは Command オブジェクトと Strategy オブジェクトを構築し、最上位の Command オブジェクトを実行します。Command オブジェクトがその作業を行います。

この時点で、おおむね完了です。ランタイムは、上記のドメインから作成されたオブジェクトの単なる構成です。[これは思ったほど簡単ではありません。インスタンス化できる一連のクラスを定義し、アプリケーションの作業を行うために「互いに対話」するには、ある程度の注意が必要です。]

必要なのは宣言だけであることに注意してください。手続き型の何が問題になっていますか?手続き型要素を含む DSL を書き始めると、Python を別の構文で書くまで、ますます多くの機能が必要であることがわかります。良くない。

さらに、手続き型言語インタープリターは単純に書くのが難しいです。実行の状態と参照の範囲を管理するのは単純に困難です。

ネイティブの Python を使用でき、「サンドボックスから抜け出す」ことを心配する必要はありません。実際、これが、短い Python スクリプトを使用してオブジェクトを作成することで、すべてのユニット テストを行う方法です。Python が DSL になります。

[「でも待って」、「Python を DSL として単純に使用すると、人々は任意のことを実行できる」と言うでしょう。PYTHONPATH と sys.path の内容によって異なります。利用可能なものを制御する方法については、サイトモジュールを参照してください。]

宣言型 DSL は最も単純です。それは完全に表現の練習です。一部の変数の値を設定するだけの Python のブロックは便利です。それがDjangoが使用するものです。

ConfigParserを、オブジェクトのランタイム構成を表す言語として使用できます。

オブジェクトのランタイム構成を表す言語として、JSONまたはYAMLを使用できます。既製のパーサーは完全に利用可能です。

XML も使用できます。設計と解析が難しくなりますが、うまく機能します。人々はそれを愛しています。これが、Ant と Maven (および他の多くのツール) が宣言構文を使用してプロシージャーを記述する方法です。言葉遣いが頭を悩ませるのでお勧めしません。単純に Python を使用することをお勧めします。

または、ディープ エンドから離れて、独自の構文を発明し、独自のパーサーを作成することもできます。

于 2008-09-26T22:14:14.890 に答える
1

ここでもう少し情報が必要になると思います。次のいずれかが誤った仮定に基づいている場合はお知らせください。

まず第一に、あなたが指摘したように、任意のテーブルから行を選択するための DSL が既に存在します - それは「SQL」と呼ばれます。SQL を再発明したくないので、固定形式の 1 つのテーブルからのみクエリを実行する必要があると想定しています。

この場合、おそらく DSL を実装する必要はありません (ただし、それは確かに 1 つの方法です)。オブジェクト指向に慣れている場合は、Filter オブジェクトを作成する方が簡単かもしれません。

具体的には、1 つ以上の SelectionCriterion オブジェクトを保持する「Filter」コレクションです。これらを実装して、選択のタイプ (Range、LessThan、ExactMatch、Like など) を表す 1 つ以上の基本クラスから継承できます。これらの基本クラスが配置されると、その列に適した列固有の継承バージョンを作成できます。 . 最後に、サポートするクエリの複雑さに応じて、さまざまな基準間の AND および OR および NOT リンケージを処理するために、何らかの結合剤を実装する必要があります。

気が向いたら、簡単な GUI を作成してコレクションをロードできます。他に何も考えていなければ、Excel でのフィルタリングをモデルとして検討します。

最後に、この Collection の内容を対応する SQL に変換し、それをデータベースに渡すのは簡単です。

ただし、シンプルさが求められていて、ユーザーが SQL を理解している場合は、WHERE 句の内容を入力するようにユーザーに依頼し、残りのクエリをプログラムで作成することができます。セキュリティの観点から、選択した列と FROM 句をコードで制御でき、データベースのアクセス許可が適切に設定されていて、ユーザーからの文字列に対して何らかの健全性チェックを行っている場合、これは比較的安全なオプションです。

于 2008-09-26T15:35:16.627 に答える
1

「ドメイン固有言語を実装する」

「実行時に任意の Python コードをダウンロードして実行するサーバーをインストールしたいと思う人はいないでしょう」

DSL が必要ですが、Python をその DSL にしたくありません。わかった。この DSL をどのように実行しますか? Python でない場合、どのランタイムが許容されますか?

Python インタープリターを埋め込んだ C プログラムがある場合はどうなりますか? それは受け入れられますか?

そして -- もし Python が受け入れられないランタイムであるなら -- なぜこれには Python タグが付いているのでしょうか?

于 2008-09-26T20:46:31.187 に答える
0

「コンパイル」時に SQL やデータストアが必要とするクエリ言語を生成する言語を作成してみませんか?

基本的に、永続化レイヤーに抽象化を作成します。

于 2008-09-26T15:02:56.707 に答える
0

あなたはPythonに言及しました。なぜ Python を使わないのですか? DSL で式を「入力」できる人は、Python で入力できます。

式の構造に関するいくつかの規則が必要になりますが、それは何か新しいものを実装するよりもはるかに簡単です。

于 2008-09-26T15:07:03.933 に答える
0

本当に SQL のように聞こえますが、シンプルに保ちたい場合は、SQLite を試してみる価値があるのではないでしょうか?

于 2008-09-26T15:39:40.877 に答える
0

DSL ではなく文法を作成したいようです。テキストを解釈して特定のコマンドに変換する特定のパーサーを作成できるANTLRを調べます。ANTLR は、Python、SQL、Java、C++、C、C# などのライブラリを提供します。

また、 C# で作成された ANTLR計算エンジンの良い例を次に示します。

于 2008-09-26T21:05:15.197 に答える
0

あなたは、実行時に任意のコードをダウンロードして実行するサーバーをインストールしたいと思う人はいないと言いました。ただし、それはまさにDSLが(最終的に)行うことなので、おそらくそれほど大きな違いはありません. データに対して非常に具体的なことをしている場合を除き、DSL がそれほど多くの利益をもたらすとは思いませんし、SQL に精通しているユーザーを苛立たせることになるでしょう。引き受けるタスクのサイズを過小評価しないでください。

ただし、質問に答えるには、言語の文法を考え出す必要があります。テキストを解析してツリーをたどり、コードを発行したり、作成した API を呼び出したりする必要があります。まだいくつかのコードを出荷する必要があります)。

ネット上には、参照できる数式の文法に関する教育テキストがたくさんあります。これはかなり簡単です。ANTLR や Yacc などのパーサー ジェネレーター ツールを使用して、パーサーを生成する (または Lisp/Scheme などの言語を使用して 2 つを組み合わせる) ことができる場合があります。妥当な SQL 文法を考え出すのは簡単ではありません。ただし、「BNF SQL」をグーグルで検索して、思いついたものを確認してください。

幸運を祈ります。

于 2008-09-26T15:29:21.667 に答える