• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2006 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 android.provider;
18 
19 import com.android.internal.telephony.CallerInfo;
20 import com.android.internal.telephony.Connection;
21 
22 import android.content.ContentResolver;
23 import android.content.ContentValues;
24 import android.content.Context;
25 import android.database.Cursor;
26 import android.net.Uri;
27 import android.text.TextUtils;
28 
29 /**
30  * The CallLog provider contains information about placed and received calls.
31  */
32 public class CallLog {
33     public static final String AUTHORITY = "call_log";
34 
35     /**
36      * The content:// style URL for this provider
37      */
38     public static final Uri CONTENT_URI =
39         Uri.parse("content://" + AUTHORITY);
40 
41     /**
42      * Contains the recent calls.
43      */
44     public static class Calls implements BaseColumns {
45         /**
46          * The content:// style URL for this table
47          */
48         public static final Uri CONTENT_URI =
49                 Uri.parse("content://call_log/calls");
50 
51         /**
52          * The content:// style URL for filtering this table on phone numbers
53          */
54         public static final Uri CONTENT_FILTER_URI =
55                 Uri.parse("content://call_log/calls/filter");
56 
57         /**
58          * The default sort order for this table
59          */
60         public static final String DEFAULT_SORT_ORDER = "date DESC";
61 
62         /**
63          * The MIME type of {@link #CONTENT_URI} and {@link #CONTENT_FILTER_URI}
64          * providing a directory of calls.
65          */
66         public static final String CONTENT_TYPE = "vnd.android.cursor.dir/calls";
67 
68         /**
69          * The MIME type of a {@link #CONTENT_URI} sub-directory of a single
70          * call.
71          */
72         public static final String CONTENT_ITEM_TYPE = "vnd.android.cursor.item/calls";
73 
74         /**
75          * The type of the call (incoming, outgoing or missed).
76          * <P>Type: INTEGER (int)</P>
77          */
78         public static final String TYPE = "type";
79 
80         public static final int INCOMING_TYPE = 1;
81         public static final int OUTGOING_TYPE = 2;
82         public static final int MISSED_TYPE = 3;
83 
84         /**
85          * The phone number as the user entered it.
86          * <P>Type: TEXT</P>
87          */
88         public static final String NUMBER = "number";
89 
90         /**
91          * The date the call occured, in milliseconds since the epoch
92          * <P>Type: INTEGER (long)</P>
93          */
94         public static final String DATE = "date";
95 
96         /**
97          * The duration of the call in seconds
98          * <P>Type: INTEGER (long)</P>
99          */
100         public static final String DURATION = "duration";
101 
102         /**
103          * Whether or not the call has been acknowledged
104          * <P>Type: INTEGER (boolean)</P>
105          */
106         public static final String NEW = "new";
107 
108         /**
109          * The cached name associated with the phone number, if it exists.
110          * This value is not guaranteed to be current, if the contact information
111          * associated with this number has changed.
112          * <P>Type: TEXT</P>
113          */
114         public static final String CACHED_NAME = "name";
115 
116         /**
117          * The cached number type (Home, Work, etc) associated with the
118          * phone number, if it exists.
119          * This value is not guaranteed to be current, if the contact information
120          * associated with this number has changed.
121          * <P>Type: INTEGER</P>
122          */
123         public static final String CACHED_NUMBER_TYPE = "numbertype";
124 
125         /**
126          * The cached number label, for a custom number type, associated with the
127          * phone number, if it exists.
128          * This value is not guaranteed to be current, if the contact information
129          * associated with this number has changed.
130          * <P>Type: TEXT</P>
131          */
132         public static final String CACHED_NUMBER_LABEL = "numberlabel";
133 
134         /**
135          * Adds a call to the call log.
136          *
137          * @param ci the CallerInfo object to get the target contact from.  Can be null
138          * if the contact is unknown.
139          * @param context the context used to get the ContentResolver
140          * @param number the phone number to be added to the calls db
141          * @param presentation the number presenting rules set by the network for
142          *        "allowed", "payphone", "restricted" or "unknown"
143          * @param callType enumerated values for "incoming", "outgoing", or "missed"
144          * @param start time stamp for the call in milliseconds
145          * @param duration call duration in seconds
146          *
147          * {@hide}
148          */
addCall(CallerInfo ci, Context context, String number, int presentation, int callType, long start, int duration)149         public static Uri addCall(CallerInfo ci, Context context, String number,
150                 int presentation, int callType, long start, int duration) {
151             final ContentResolver resolver = context.getContentResolver();
152 
153             // If this is a private number then set the number to Private, otherwise check
154             // if the number field is empty and set the number to Unavailable
155             if (presentation == Connection.PRESENTATION_RESTRICTED) {
156                 number = CallerInfo.PRIVATE_NUMBER;
157                 if (ci != null) ci.name = "";
158             } else if (presentation == Connection.PRESENTATION_PAYPHONE) {
159                 number = CallerInfo.PAYPHONE_NUMBER;
160                 if (ci != null) ci.name = "";
161             } else if (TextUtils.isEmpty(number)
162                     || presentation == Connection.PRESENTATION_UNKNOWN) {
163                 number = CallerInfo.UNKNOWN_NUMBER;
164                 if (ci != null) ci.name = "";
165             }
166 
167             ContentValues values = new ContentValues(5);
168 
169             values.put(NUMBER, number);
170             values.put(TYPE, Integer.valueOf(callType));
171             values.put(DATE, Long.valueOf(start));
172             values.put(DURATION, Long.valueOf(duration));
173             values.put(NEW, Integer.valueOf(1));
174             if (ci != null) {
175                 values.put(CACHED_NAME, ci.name);
176                 values.put(CACHED_NUMBER_TYPE, ci.numberType);
177                 values.put(CACHED_NUMBER_LABEL, ci.numberLabel);
178             }
179 
180             if ((ci != null) && (ci.person_id > 0)) {
181                 ContactsContract.Contacts.markAsContacted(resolver, ci.person_id);
182             }
183 
184             Uri result = resolver.insert(CONTENT_URI, values);
185 
186             removeExpiredEntries(context);
187 
188             return result;
189         }
190 
191         /**
192          * Query the call log database for the last dialed number.
193          * @param context Used to get the content resolver.
194          * @return The last phone number dialed (outgoing) or an empty
195          * string if none exist yet.
196          */
getLastOutgoingCall(Context context)197         public static String getLastOutgoingCall(Context context) {
198             final ContentResolver resolver = context.getContentResolver();
199             Cursor c = null;
200             try {
201                 c = resolver.query(
202                     CONTENT_URI,
203                     new String[] {NUMBER},
204                     TYPE + " = " + OUTGOING_TYPE,
205                     null,
206                     DEFAULT_SORT_ORDER + " LIMIT 1");
207                 if (c == null || !c.moveToFirst()) {
208                     return "";
209                 }
210                 return c.getString(0);
211             } finally {
212                 if (c != null) c.close();
213             }
214         }
215 
removeExpiredEntries(Context context)216         private static void removeExpiredEntries(Context context) {
217             final ContentResolver resolver = context.getContentResolver();
218             resolver.delete(CONTENT_URI, "_id IN " +
219                     "(SELECT _id FROM calls ORDER BY " + DEFAULT_SORT_ORDER
220                     + " LIMIT -1 OFFSET 500)", null);
221         }
222     }
223 }
224