2012-03-09 2 views
1

API OnlyAPI Enabledを除き、すべてが無効になっているユーザープロファイルがあります。このユーザープロファイルには、RESTサービスが定義されている一連のクラスにアクセスできるようになっています。Schema.getGlobalDescribe()の呼び出しを、共有しないと宣言されたクラスのシステムコンテキストで実行しないでください。

Schema.getGlobalDescribe()を呼び出すと、非常に奇妙な動作が見られます。すべてのクラスが同じ方法で定義されていても、そのクラスを呼び出すクラスに応じて異なる応答を受け取ります。問題の簡略化されたバージョンは次のとおりです。

global without sharing class WebServiceClass { 

    { 
    System.debug(WebServiceClass.fieldsContainName()); // THIS RETURNS TRUE 
    System.debug(UtilityClass.fieldsContainName()); //THIS RETURNS FALSE! 
    } 

    global static Boolean fieldsContainName() { 
    System.debug(Schema.getGlobalDescribe().get('contact').getDescribe().fields.getMap().keySet().contains('name')); 
    } 
} 

global without sharing class UtilityClass { 
    global static Boolean fieldsContainName() { 
    System.debug(Schema.getGlobalDescribe().get('contact').getDescribe().fields.getMap().keySet().contains('name')); 
    } 
} 

これはなぜでしょうか?

答えて

2

without sharingは共有(つまり、表示できる行)にのみ影響しますが、システムモードとユーザーモードには影響しません。通常、システムモードで起動するのはトリガだけですが、Webサービスのような他の頂点のエントリポイントはユーザモードで実行されます。

+0

'共有しないでください 'は、クラスが共有せずに実行されますが、システムモードではなくユーザーモードで実行されますか?私はなぜSOQL文を実行して(クラスがシステムモードで実行されていることを示唆する)カラムを取得できるのか分かりませんが、 'Database.query()'を使って同じクエリを実行すると、 ?それはなぜでしょうか? – barelyknown

+1

共有とシステムモードは2つの直交状態です。共有はシステムの行にのみ影響し、ユーザーとシステムのモードはどのオブジェクトとフィールドに影響を与えますか。 – superfell

+0

違いを見る特定の例を投稿できますが、動的なsoqlは通常のインラインクエリと同じにする必要があります。 – superfell

1

Schema.getGlobalDescribe()は、(クラスがシステムモードで実行されている場合でも)呼び出しを含むクラスにユーザーがアクセスできない場合、予期しない動作をします。この問題を解決するには、問題のクラスにアクセスできるユーザーのプロファイルをリストに追加します。これで問題は解決します。私はこれがSchema.getGlobalDescribe()のバグであると信じています。

this blog postに基づいて、Schema.getGlobalDescribe()に関連する他の面白い振る舞いがあるように見えます。

関連する問題