1 /*
2  * Copyright (C) 2017 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License
15  */
16 
17 package com.android.settingslib.applications;
18 
19 import android.app.usage.StorageStats;
20 import android.app.usage.StorageStatsManager;
21 import android.content.Context;
22 import android.content.pm.PackageManager;
23 import android.os.UserHandle;
24 
25 import androidx.annotation.VisibleForTesting;
26 
27 import java.io.IOException;
28 
29 /**
30  * StorageStatsSource wraps the StorageStatsManager for testability purposes.
31  */
32 public class StorageStatsSource {
33     private StorageStatsManager mStorageStatsManager;
34 
StorageStatsSource(Context context)35     public StorageStatsSource(Context context) {
36         mStorageStatsManager = context.getSystemService(StorageStatsManager.class);
37     }
38 
getExternalStorageStats(String volumeUuid, UserHandle user)39     public StorageStatsSource.ExternalStorageStats getExternalStorageStats(String volumeUuid,
40             UserHandle user) throws IOException {
41         return new StorageStatsSource.ExternalStorageStats(
42                 mStorageStatsManager.queryExternalStatsForUser(volumeUuid, user));
43     }
44 
getStatsForUid(String volumeUuid, int uid)45     public StorageStatsSource.AppStorageStats getStatsForUid(String volumeUuid, int uid)
46             throws IOException {
47         return new StorageStatsSource.AppStorageStatsImpl(
48                 mStorageStatsManager.queryStatsForUid(volumeUuid, uid));
49     }
50 
getStatsForPackage( String volumeUuid, String packageName, UserHandle user)51     public StorageStatsSource.AppStorageStats getStatsForPackage(
52             String volumeUuid, String packageName, UserHandle user)
53             throws PackageManager.NameNotFoundException, IOException {
54         return new StorageStatsSource.AppStorageStatsImpl(
55                 mStorageStatsManager.queryStatsForPackage(volumeUuid, packageName, user));
56     }
57 
getCacheQuotaBytes(String volumeUuid, int uid)58     public long getCacheQuotaBytes(String volumeUuid, int uid) {
59         return mStorageStatsManager.getCacheQuotaBytes(volumeUuid, uid);
60     }
61 
62     /**
63      * Static class that provides methods for querying the amount of external storage available as
64      * well as breaking it up into several media types.
65      */
66     public static class ExternalStorageStats {
67         public long totalBytes;
68         public long audioBytes;
69         public long videoBytes;
70         public long imageBytes;
71         public long appBytes;
72 
73         /** Convenience method for testing. */
74         @VisibleForTesting
ExternalStorageStats( long totalBytes, long audioBytes, long videoBytes, long imageBytes, long appBytes)75         public ExternalStorageStats(
76                 long totalBytes, long audioBytes, long videoBytes, long imageBytes, long appBytes) {
77             this.totalBytes = totalBytes;
78             this.audioBytes = audioBytes;
79             this.videoBytes = videoBytes;
80             this.imageBytes = imageBytes;
81             this.appBytes = appBytes;
82         }
83 
84         /**
85          * Creates an ExternalStorageStats from the system version of ExternalStorageStats. They are
86          * identical other than the utility method created for test purposes.
87          * @param stats The stats to copy to wrap.
88          */
ExternalStorageStats(android.app.usage.ExternalStorageStats stats)89         public ExternalStorageStats(android.app.usage.ExternalStorageStats stats) {
90             totalBytes = stats.getTotalBytes();
91             audioBytes = stats.getAudioBytes();
92             videoBytes = stats.getVideoBytes();
93             imageBytes = stats.getImageBytes();
94             appBytes = stats.getAppBytes();
95         }
96     }
97 
98     /**
99      * Interface that exists to simplify testing. The platform {@link StorageStats} is too new and
100      * robolectric cannot see it. It simply wraps a StorageStats object and forwards method calls
101      * to the real object
102      */
103     public interface AppStorageStats {
getCodeBytes()104         long getCodeBytes();
getDataBytes()105         long getDataBytes();
getCacheBytes()106         long getCacheBytes();
getTotalBytes()107         long getTotalBytes();
108     }
109 
110     /**
111      * Simple implementation of AppStorageStats that will allow you to query the StorageStats object
112      * passed in for storage information about an app.
113      */
114     public static class AppStorageStatsImpl implements
115             StorageStatsSource.AppStorageStats {
116         private StorageStats mStats;
117 
AppStorageStatsImpl(StorageStats stats)118         public AppStorageStatsImpl(StorageStats stats) {
119             mStats = stats;
120         }
121 
getCodeBytes()122         public long getCodeBytes() {
123             return mStats.getAppBytes();
124         }
125 
getDataBytes()126         public long getDataBytes() {
127             return mStats.getDataBytes();
128         }
129 
getCacheBytes()130         public long getCacheBytes() {
131             return mStats.getCacheBytes();
132         }
133 
getTotalBytes()134         public long getTotalBytes() {
135             return mStats.getAppBytes() + mStats.getDataBytes();
136         }
137     }
138 }