3

私が関わってきた多くのWebアプリケーションプロジェクトは、

  1. アプリケーションは、永続化されたデータが特定の形式であることを想定しています

  2. 永続化されたデータがその形式から逸脱した場合、アプリケーションはバーフします

  3. 古い「ミステリーコード」は悪い形式でデータを保持しています

これにより、通常、アプリケーション開発者は多くの検証条件でモデルコードを乱雑にします。あれは

function save()
{
    if($model->getSomeProp() == 'bad value')
    {
        $model->setSomeProp('good default value');
    }

    return parent::save();
}        

これらの状況に対処するためのより良いパターンおよび/またはシステムはありますか?前述のパターンおよび/またはシステムは、開発者がリリースごとに完全な移行スクリプトおよび/または検証コードを作成することに依存していませんか?私が特に興味を持っているのは、他の開発者がこの種の(私の経験では)一般的な長期的な問題のクリーンアップにどのように取り組むかです。

特にLAMPスタック/PHPソリューションを探していますが、他の一般的なミドルウェア言語/プラットフォーム(Ruby、Pythonなど)からのソリューションとアプローチは大歓迎です。

4

2 に答える 2

2

少なくとも、dbの相互作用にできるだけ近いこのタイプの動作を処理しているので、コードベースにこれらのタイプのチェックが散らばっている場合は、さらに悪化する可能性があります。

この種の問題を解決する必要がある場合、最初に行うことは、カスタム例外コードをスローするメソッドを設定することだと思います。そうすれば、呼び出し元のコードをログに記録して、アプリケーションのどの部分でデータをフォーマットしているかを確認できます。間違った方法。

たとえば、次のようなことができます。

class CustomException extends Exception
{
    const CODE_BAD_FORMAT = 1;

    protected code;

    public function setCode($code)
    {
        $this->code = $code;
    }

    public function getCode()
    {
        return $this->code;
    }
}

class Model extends ParentModel
{
    function save()
    {
        if ($model->getSomeProp() == 'bad value') {
            $badValueFound = true;
            $model->setSomeProp('good default value');
        }

        // Now that you are using try/catches you don't need a return value
        parent::save();

        if ($badValueFound) {

            $e = new CustomException();
            $e->setCode(CustomException::CODE_BAD_FORMAT);

            throw $e;
        }
    }
}

// Calling code
try {
    $model = new Model();

    $model->setSomeProp('ohnoes im bad format');

    $model->save();

} catch (Exception $e) {

    if ($e->getCode() === CustomException::CODE_BAD_FORMAT) {
        error_log(__METHOD__ . ': Called save with bad format'); 
    } else {
        throw $e; // Some other exception occurred b/c the code() didn't line up so bubble up
    }
}

// All is well b/c made it through the try / catch block... so onto the next logic

これで、save()を呼び出すことができます。不正な形式が検出された場合は、例外をスローして呼び出しからコードを確認できます。コードが一致する場合(予想される不正な形式)、ロギングトラック呼び出しを実装できます。コードポイント。

さらに、保存は引き続き行われるため、プロセスで何も中断しませんが、save()の呼び出しがtry / catchブロックでラップされていることを確認する必要があります。そうしないと、キャッチされない場合に例外が発生します。ちゃんと。

別のアイデアは、モデルクラスの不正な形式の構成を追跡して、同じ文字列をあちこちにコピーすることにならないようにすることです。

class Model
{
    const BAD_FORMAT_MALFORMED_NAME = 'format for a malformed name';
    const BAD_FORMAT_MALFORMED_ADDRESS = 'format for malformed address';
}

....
if($model->getSomeProp() === self::BAD_FORMAT_MALFORMED_NAME) {
....
于 2011-12-13T05:17:20.287 に答える
2

処理されたすべてのアイテムに対して実行する必要があるステップの構成ファイル提供リストを使用します。これにより、検証、データのわずかな変更、ルックアップ、外部ソースからの特定の属性の取得とマージなどが可能になります。

現在は、抽象を実装する一連のRubyクラスに基づいており、Stepyaml構成に従って動作しますが、次の書き換えでは、純粋なRubyDSLを使用すると思います。

したがって、最後に、次のようなものになります。

HealingProcessor.on(impure_data) {
  replace_bad_value :field => :some_prop, :bad_value => 'bad value', :good_value => 'good_default_value'
  # etc
}
于 2011-12-13T00:33:49.297 に答える