2011-02-04 2 views
10

일부 민감한 데이터를 보호하기위한 몇 가지 요구 사항이 있습니다. 데이터는 URL에서 PDF로 다운로드 다음과 같은 코드를 사용하여 응용 프로그램 개인 파일로 저장됩니다 : 이제콘텐츠 제공 업체 URI의 인 텐트?

public File downloadPDF(final Context fileContext, Uri reportUri, final String fileName) 
{ 
    try 
    { 
     HttpGet get = new HttpGet(reportUri.toString()); 

     File file = httpClient.execute(get, new ResponseHandler<File>() 
     { 
      @Override 
      public File handleResponse(HttpResponse response) throws ClientProtocolException, IOException 
      { 
       if (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK) 
       { 
        response.getEntity().writeTo(fileContext.openFileOutput(fileName, Context.MODE_WORLD_READABLE)); 
        return fileContext.getFileStreamPath(fileName); 
       } 
       return null; 
      } 
     }); 

     return file; 
    } 
    catch (IOException e) 
    { 
     Log.e(TAG, "Unable to download report.", e); 
    } 

    return null; 
} 

를, 내가 뭘하려는 Context.MODE_PRIVATE를 사용으로 변경하고, 컨텐트 프로를 만드는 것입니다 그래서 내 응용 프로그램은이 파일을 Adobe Reader와 같은 PDF 판독기로 공유하는 것을 완전히 제어 할 수 있습니다. 이것이 가능한가? 현재 현재 구성된 PDF 리더에 보고서 URI를 전달하기 위해 다음과 같은 코드를 사용합니다.

// Fire up a PDF viewer intent for the URL. 
    Intent intent = new Intent(Intent.ACTION_VIEW); 
    intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 
    intent.setDataAndType(uri, "application/pdf"); 
    startActivity(intent); 

동일하게 ContentProvider 유형 URI를 사용합니까? content : // package/fileid 유형 URI? 내가 할 수 있는지보기 위해 약간의 스파이크를 시도 할 것입니다.하지만 누군가 file : // URI 만 허용된다는 것을 알고 있다면 정말 도움이 될 것입니다. ,

@Override 
public ParcelFileDescriptor openFile(Uri uri, String mode) throws FileNotFoundException 
{ 
    // The filename is the path in the URI without the initial slash. 
    String fileName = uri.getPath().substring(1); 
    File file = getContext().getFileStreamPath(fileName); 
    return ParcelFileDescriptor.open(file, ParcelFileDescriptor.MODE_READ_ONLY); 
} 

그럼, 내가 보는 의도를 해고 :


UPDATE

나는 오버라이드 (override) 다음과 같은 방법으로 컨텐트 프로 서브 클래스를 구현하여 만족스럽게 내 문제를 해결할 수 있었다 그것은 다음과 같이 재 작성됩니다 :

Intent intent = new Intent(Intent.ACTION_VIEW); 
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 
Uri uri = Uri.withAppendedPath(Uri.parse("content://providername/"),filePath); 
intent.setData(uri); 
startActivity(intent); 

그리고 제 경우에는 content:// URI에서 로딩을 적절하게 구현하는 Adobe Reader를 사용합니다.

답변

4

동일하게 ContentProvider 유형 URI를 사용합니까? content : // package/fileid 유형 URI?

해야합니다. ContentProviderapplication/pdfgetType()으로 환불해야합니다. 그리고 일부 PDF 리더는 content://Uri 값을 처리하지 못할 수도 있습니다.

은 무엇 당신이 할 수있는 것은 아무것도 이해할 수 있는지 확인하기 위해 PackageManager를 사용하여 다음의 ContentProvider을 당신의 content://UriACTION_VIEWIntent. 응답이 있으면 설정됩니다. 그렇지 않으면 파일을 세계에서 읽을 수 있고 현재 구현을 사용하도록 만들 수 있습니다. 또는 파일을 세계에서 읽을 수있는 것으로 변경하는 것이 어려울 수 있으므로 ContentProvider이 지원하는 일부 스크랩 Uri을 사용하여 (예 : 앱이 시작될 때) 테스트를 일찍 실행할 수 있으므로 수행 할 때 취할 경로를 알 수 있습니다 귀하의 다운로드.

+0

대단히 감사합니다. 필자는 아침에 컨셉 증명 작업을하면서 내가 일반적으로 사용하는 PDF 리더가 'content : //'URI를 받아들이는지 확인하려고한다. 나는이'PackageManager' 사용법에 대해서 알지 못 했으므로 그것에 대해 읽도록하겠습니다. – Thorinside

+1

예, 그렇게 된 것 같습니다.Adobe Reader의 '출처'에서 'VIEW content : // Intent'의 경우 콘텐츠 리졸버를 사용할 것인지 확인하기 위해 엿보았습니다. 실제로 볼 수 있습니다. 지금 ContentProvider가 다시 호출되지 않는 이유를 알아 내려고하고 있습니다. – Thorinside

+0

그래, 난 그냥 입력 스트림에 대한 Adobe Reader의 요청을 가로 채기 위해 내 ContentProvider 인스턴스에서 openFile 메서드를 재정의해야한다는 것을 알았습니다. 나는 격려 받았다. – Thorinside

1

없음 콘텐츠 제공 업체를 보호하지 않는 파일 사실

은 아마 응용 프로그램은 콘텐츠 공급자로부터 파일과 함께 할 수있는 우선의 캐시 디렉토리에 임시 복사본을 만들 수 있습니다. 나는 당신이 이것을 다시 생각해야한다고 생각합니다.