android - 从 url 下载视频文件并限制从应用程序外部下载的文件

标签 android encryption exoplayer

我创建了 Android 应用程序,我使用 exoplayer2 从 url 播放在线视频,为此我引用了这个 Example 。它工作正常,但现在我想添加下载选项,并限制从其他应用程序下载的视频文件(下载的视频文件仅在该应用程序内打开,如 YouTube 下载视频)。 我已阅读 Downloading media 的文档exoplayer提供但未能实现。有人请帮助我满足上述要求。或者告诉我任何其他解决方案来满足我的要求。

我也尝试过Android restricting downloaded files to app ,这工作正常,但不满足要求(下载的视频未在图库或媒体商店中显示,但文件存在于此路径 Android/data/package_name/file_name 上),我们可以从外部轻松访问下载的文件该应用程序。

提前谢谢您。

最佳答案

我找到了解决方案:)

我已使用下载管理器从 url 下载视频并将文件存储在公共(public)路径上。这是代码

public void downloadVideo(String url) {
    Uri Download_Uri = Uri.parse(url);
    DownloadManager.Request request = new DownloadManager.Request(Download_Uri);

    //Restrict the types of networks over which this download may proceed.
    request.setAllowedNetworkTypes(DownloadManager.Request.NETWORK_WIFI | DownloadManager.Request.NETWORK_MOBILE);
    //Set whether this download may proceed over a roaming connection.
    request.setAllowedOverRoaming(false);
    // Visibility of the download Notification
    request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED);
    //Set the title of this download, to be displayed in notifications (if enabled).
    request.setTitle("Downloading");
    //Set a description of this download, to be displayed in notifications (if enabled)
    request.setDescription("Downloading File");

    //Set the local destination for the downloaded file to a path within the application's external files directory
    /*request.setDestinationInExternalFilesDir(MainActivity.this, Environment.DIRECTORY_MOVIES, "Shivam196.mp4");*/ //For private destination

    //Set the local destination for the downloaded file to a path within the application's external files directory
    request.setDestinationInExternalPublicDir(Environment.DIRECTORY_MOVIES, "Shivam196.mp4"); // for public destination

    DownloadManager downloadManager= (DownloadManager) getSystemService(DOWNLOAD_SERVICE);
    downloadID = downloadManager.enqueue(request);// enqueue puts the download request in the queue.
}

成功下载文件后,我通过以下方法传递文件路径来加密该文件:

private void encryptFile(String filePath) throws IOException, NoSuchPaddingException, NoSuchAlgorithmException, InvalidKeyException {
    int read;
    FileInputStream fis = new FileInputStream(new File(filePath));
    File outfile = new File(Environment.getExternalStorageDirectory() + "/" + FOLDER_NAME + "/" + "test2_enc.mp4");
    if(!outfile.exists())
        outfile.createNewFile();

    FileOutputStream fos = new FileOutputStream(outfile);

    Cipher encipher = Cipher.getInstance("AES");

    KeyGenerator kgen = KeyGenerator.getInstance("AES");
    //byte key[] = {0x00,0x32,0x22,0x11,0x00,0x00,0x00,0x00,0x00,0x23,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
    SecretKey skey = kgen.generateKey();

    encipher.init(Cipher.ENCRYPT_MODE, skey);
    CipherInputStream cis = new CipherInputStream(fis, encipher);

    byte[] buffer = new byte[1024]; // buffer can read file line by line to increase speed
    while((read = cis.read(buffer)) >= 0)
    {
        fos.write(buffer, 0, read);
        fos.flush();
    }
    fos.close();
    Toast.makeText(this, "File encrypted", Toast.LENGTH_SHORT).show();

    //call method for decrypt file.
    decryptFile(Environment.getExternalStorageDirectory() + "/" + FOLDER_NAME + "/" + "test_enc.mp4", skey);
}

然后通过将加密的文件路径和 key 传递给以下方法来解密文件:

private void decryptFile(String encryptFilePath, SecretKey secretKey) throws IOException, NoSuchPaddingException, NoSuchAlgorithmException, InvalidKeyException {
    int read;
    File outfile = new File(encryptFilePath);
    File decfile = new File(Environment.getExternalStorageDirectory() + "/" + FOLDER_NAME + "/" + "test_dec.mp4");
    if(!decfile.exists())
        decfile.createNewFile();

    FileOutputStream decfos = new FileOutputStream(decfile);
    FileInputStream encfis = new FileInputStream(outfile);

    Cipher decipher = Cipher.getInstance("AES");

    decipher.init(Cipher.DECRYPT_MODE, secretKey);
    CipherOutputStream cos = new CipherOutputStream(decfos,decipher);

    byte[] buffer = new byte[1024]; // buffer can read file line by line to increase speed
    while((read=encfis.read(buffer)) >= 0)
    {
        cos.write(buffer, 0, read);
        cos.flush();
    }
    cos.close();
    Toast.makeText(this, "File decrypted", Toast.LENGTH_SHORT).show();
}

注意:在后台服务上进行加密和描述操作。

关于android - 从 url 下载视频文件并限制从应用程序外部下载的文件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61835019/

相关文章:

java - 用于记录传感器数据的 Android 按钮

android - 是否可以在android中使用iText库阅读pdf文档

spring - 如何在 Web 应用程序运行时保留用于解密的 key

android - 使用 Exoplayer2,如何始终使用默认插图(即使音频嵌入了插图?)

android - 必需的 com.google.android.gms.GoogleMap 发现无效

android - 如何在android中动态地使形状可拖动和调整大小

algorithm - 密码算法加密作业

java - 如何播放字节数组中的视频?

java - Exoplayer背景: how to set a background for exoplayer

android - 使用 Exoplayer 从 Icecast 流中提取元数据