2012-08-31 29 views
7

私と同じ制限を求める投稿は見つかりませんでした。コンテンツプロバイダへのアクセスを制限する

私は、コンテンツプロバイダ(メインアプリケーションと呼ぶ)を他のアプリケーション(クライアントアプリケーションと呼ぶ)に提供するアプリケーションを持っています。クライアントアプリケーションからのコンテンツプロバイダへのアクセスを制限するには、と、のクエリのメソッドのみをサポートします。

私はしたくないもの:主な目的は、クライアントアプリケーションにデータベースを提供することであるため

  • は、コンテンツプロバイダは、プライベートください。
  • クライアントアプリケーションの署名付きアクセスを制限するには、メインアプリケーションプラットフォームを使用するクライアントアプリケーションを作成できる必要があります。

私が見る最も明白な解決策は、2つのコンテンツプロバイダ、1つはメインアプリケーションのプライベートアクセスと1つの制限付き公開の両方を書くことです。しかし、これは間違いなく適切な方法だと私は思う。

このGoogle groups postによれば、コンテンツプロバイダの呼び出しでBinder.getCallingUid()を使用して、呼び出しがメインアプリケーションから来たものかどうかを検出することを考えています。だから私はの更新メソッドを呼び出しても、メインアプリケーションからの呼び出しでない場合は何もできません。

メインアプリケーションを取得する方法UIDを比較するには?可能であれば、このソリューションは安全ですか?

ご協力いただきありがとうございます。

+0

私が正しく理解すれば、コンテンツプロバイダコンポーネントを含むアプリケーションは、書き込みアクセス権を持つ唯一のものでなければなりません。その理由から、コンテンツプロバイダのインターフェイスを経由せずにその機能を使用できないのはなぜですか?その場合、コンテンツプロバイダはクエリインタフェースのみをサポートします。 – Sameer

+0

残念ながら、クライアントアプリケーションが必要とする主なアクセスは挿入です。彼らはまた、書き込みアクセスを持つ必要があります。しかし、主なアプリケーションはコンテンツプロバイダを使用する必要はありませんが、複雑さと保守性があまりにも高くなります。 – FabiF

+0

よく、まだ同じポイント。メインアプリケーションは、コンテンツプロバイダインタフェースを介さずに、挿入、更新、削除を直接行うことができます。コンテンツプロバイダは、挿入およびクエリインタフェースのみを提供します。 – Sameer

答えて

8

はのProtectionLevel署名で以下のようなパーミッションを定義し、このWRITE権限は、その後のContentProviderタグ使用中の許可タグを読み書き同じ秘密鍵

<permission android:name="com.yourapp.WRITE.PERMISSION" 
    android:protectionLevel="signature" 
     android:label="@string/permission_label" 
     android:description="@string/permission_desc"> 
</permission> 

<permission android:name="com.yourapp.READ.PERMISSION" 
     android:label="@string/permission_label" 
     android:description="@string/permission_desc"> 
</permission> 

で署名されているだけのアプリケーションに制限されます。 あなたが許可を読んだり、あなたは完全に

android:readPermission="com.yourapp.READ.PERMISSION" 
android:writePermission="com.yourapp.WRITE.PERMISSION" 

だから、同じ署名で署名されている唯一のアプリが

編集して、コンテンツプロバイダを使用することができ、それを削除することができ強制することができ、次のいずれか

たぶん、あなたはこの

を使用することができます
private Collection<String> getCallingPackages() { 
    int caller = Binder.getCallingUid(); 
    if (caller == 0) { 
     return null; 
    } 
    return Lists.newArrayList(mContext.getPackageManager().getPackagesForUid(caller)); 
} 

あなたのパッケージ名がこのリストに含まれているかどうかを確認してください。私はそれが安全だと思う

+0

私はこの解決策を知っていますが、私の場合、クライアントアプリケーションは*データを挿入できなければならないので、書き込みアクセスも必要です。 – FabiF

+0

何を制限したいですか? packagenameのクライアントアプリケーションはほんのわずかですか? – nandeesh

+0

あなたのアプリケーションがデータを必要とするならば、sqlitedbhelperを通してそれを行い、contentproviderを通してアクセスを減らしてください。 – nandeesh

関連する問題