Android(java)学习笔记191:ContentProvider使用之利用ContentProvider备份和还原手机短信(掌握)
1. 通过阅读系统源码我们知道:
短信的内容提供者:
content://sms/ 系统短信的内容提供者的路径
2. 利用ContentProvider备份和还原手机短信:
(1)新建一个Android工程,命名为"短信备份助手",如下:
(2)我们先实现UI布局,activity_main.xml,如下:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context="com.himi.smsbackup.MainActivity" > <Button
android:onClick="smsBackup"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="备份" />
<Button
android:onClick="smsRestores"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="还原" /> </LinearLayout>
布局效果如下:
(3)编写MainActivity,如下:
package com.himi.smsbackup; import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream; import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlSerializer; import android.app.Activity;
import android.app.AlertDialog;
import android.app.AlertDialog.Builder;
import android.content.ContentResolver;
import android.content.ContentValues;
import android.content.DialogInterface;
import android.content.DialogInterface.OnClickListener;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.util.Xml;
import android.view.View;
import android.widget.Toast; public class MainActivity extends Activity { @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
} /**
* 短信备份
* @param view
*/
public void smsBackup(View view) {
try {
// 系统短信数据库是私有的,不能访问,只能使用内容提供者ContentProvider去访问
ContentResolver resolver = getContentResolver();
// 指定Uri
Uri uri = Uri.parse("content://sms/");
Cursor cursor = resolver.query(uri, new String[] { "address",
"date", "type", "body" }, null, null, null);
// 存储为xml文件,跨平台
// 获取一个xml的序列化器serializer
XmlSerializer serializer = Xml.newSerializer();
// 初始化设置xml序列化器serializer
File file = new File(Environment.getExternalStorageDirectory(),
"backup.xml");
FileOutputStream os = new FileOutputStream(file);
serializer.setOutput(os, "utf-8"); // 写xml文件的头
serializer.startDocument("utf-8", true);
serializer.startTag(null, "root");
while (cursor.moveToNext()) {
serializer.startTag(null, "sms"); serializer.startTag(null, "address");
String address = cursor.getString(0);
serializer.text(address);
serializer.endTag(null, "address"); serializer.startTag(null, "date");
String date = cursor.getString(1);
serializer.text(date);
serializer.endTag(null, "date"); serializer.startTag(null, "type");
String type = cursor.getString(2);
serializer.text(type);
serializer.endTag(null, "type"); serializer.startTag(null, "body");
String body = cursor.getString(3);
serializer.text(body);
serializer.endTag(null, "body"); serializer.endTag(null, "sms");
}
cursor.close();
serializer.endTag(null, "root");
serializer.endDocument();
os.close();
Toast.makeText(this, "备份成功", 0).show();
} catch (Exception e) {
// TODO 自动生成的 catch 块
e.printStackTrace();
Toast.makeText(this, "备份失败", 0).show();
}
} /**
* 还原用户的备份的短信数据
* 还原之前要提醒用户是否要覆盖旧的数据
* @param view
*/
public void smsRestores(View view) {
File file = new File(Environment.getExternalStorageDirectory(),
"backup.xml");
//file.lastModified();获取文件上一次备份时间
AlertDialog.Builder builder = new Builder(this);
builder.setTitle("提醒");
builder.setMessage("是否清除旧的短信?");
builder.setPositiveButton("确实清除", new OnClickListener() { public void onClick(DialogInterface dialog, int which) {
Uri uri = Uri.parse("content://sms/");
getContentResolver().delete(uri, null, null);
restore(); }
});
builder.setNegativeButton("不清楚数据", new OnClickListener() { public void onClick(DialogInterface dialog, int which) {
restore(); }
}); builder.show();
} public void restore() {
try { File file = new File(Environment.getExternalStorageDirectory(),
"backup.xml");
FileInputStream is = new FileInputStream(file);
//获取xml的pull解析器
XmlPullParser parser = Xml.newPullParser();
//初始化设置xml的pull解析器
parser.setInput(is, "utf-8");
int type = parser.getEventType(); String address = null;
String date = null;
String smstype = null;
String body = null;
while(type != XmlPullParser.END_DOCUMENT) {
switch (type) {
case XmlPullParser.START_TAG:
//开始解析标签
if("address".equals(parser.getName())) {
address = parser.nextText();
}else if ("date".equals(parser.getName())){
date = parser.nextText();
}else if ("type".equals(parser.getName())){
smstype = parser.nextText();
}else if ("body".equals(parser.getName())){
body = parser.nextText();
} break; case XmlPullParser.END_TAG:
if ("sms".equals(parser.getName())) {
// 结束解析标签,把短信的数据加入到系统短信应用数据库中
ContentResolver resolver = getContentResolver();
Uri uri = Uri.parse("content://sms/");
ContentValues values = new ContentValues();
values.put("address", address);
values.put("date", date);
values.put("type", smstype);
values.put("body", body);
resolver.insert(uri, values);
}
break;
}
type = parser.next();//指向下一待解析的标签
}
Toast.makeText(this, "还原成功", 0).show();
} catch (Exception e) {
// TODO 自动生成的 catch 块
e.printStackTrace();
Toast.makeText(this, "还原失败", 0).show();
} }
}
上面使用到要存取数据到SD卡,要添加相应的权限。同时读取系统短信应用也需要相应的权限,AndroidMainfest.xml,如下:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.himi.smsbackup"
android:versionCode="1"
android:versionName="1.0" > <uses-sdk
android:minSdkVersion="15"
android:targetSdkVersion="17" />
<uses-permission android:name="android.permission.READ_SMS"/>
<uses-permission android:name="android.permission.WRITE_SMS"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> <application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme" >
<activity
android:name=".MainActivity"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application> </manifest>
(4)布署程序到模拟器上,如下:
•我们先在模拟器上模拟发送和接收几条短信,如下:
•回到上面我们编写的应用程序中,点击"备份",提示备份成功,如下:
•查看Sd保存路径,如下图,导出这个backup.xml文件到桌面,然后使用IE打开这个backup.xml文件,如下:
•这个时候,我们去删除模拟器上的短信,如下:
•回到编写的应用程序中,点击"还原",如下:
•回到系统短信页面,看到:
Android(java)学习笔记191:ContentProvider使用之利用ContentProvider备份和还原手机短信(掌握)的更多相关文章
- Android(java)学习笔记247:ContentProvider使用之利用ContentProvider备份和还原手机短信(掌握)
1.通过阅读系统源码我们知道: 短信的内容提供者: content://sms/ 系统短信的内容提供者的路径 2. 利用ContentProvider备份和还原手机短信: (1) ...
- [知了堂学习笔记]_Java代码实现MySQL数据库的备份与还原
通常在MySQL数据库的备份和恢复的时候,多是采用在cmd中执行mysql命令来实现. 例如: mysqldump -h127.0.0.1 -uroot -ppass test > d:/tes ...
- 0028 Java学习笔记-面向对象-Lambda表达式
匿名内部类与Lambda表达式示例 下面代码来源于:0027 Java学习笔记-面向对象-(非静态.静态.局部.匿名)内部类 package testpack; public class Test1{ ...
- 《Java学习笔记(第8版)》学习指导
<Java学习笔记(第8版)>学习指导 目录 图书简况 学习指导 第一章 Java平台概论 第二章 从JDK到IDE 第三章 基础语法 第四章 认识对象 第五章 对象封装 第六章 继承与多 ...
- Android动画学习笔记-Android Animation
Android动画学习笔记-Android Animation 3.0以前,android支持两种动画模式,tween animation,frame animation,在android3.0中 ...
- Java学习笔记:语言基础
Java学习笔记:语言基础 2014-1-31 最近开始学习Java,目的倒不在于想深入的掌握Java开发,而是想了解Java的基本语法,可以阅读Java源代码,从而拓展一些知识面.同时为学习An ...
- Android 数字签名学习笔记
Android 数字签名学习笔记 在Android系统中,所有安装到系统的应用程序都必有一个数字证书,此数字证书用于标识应用程序的作者和在应用程序之间建立信任关系,如果一个permission的pro ...
- 【Java学习笔记之二十六】深入理解Java匿名内部类
在[Java学习笔记之二十五]初步认知Java内部类中对匿名内部类做了一个简单的介绍,但是内部类还存在很多其他细节问题,所以就衍生出这篇博客.在这篇博客中你可以了解到匿名内部类的使用.匿名内部类要注意 ...
- 20145316许心远《Java学习笔记(第8版)》课程总结
20145316许心远<Java学习笔记(第8版)>课程总结 每周读书笔记链接汇总 ▪ 第一周读书笔记 ▪ 第二周读书笔记 ▪ 第三周读书笔记 ▪ 第四周读书笔记 ▪ 第五周读书笔记 ▪ ...
随机推荐
- Latex 3: 解决LaTeX编译卡顿问题
1.问题: 最近在编译latex时,老是在tulmr.fd处编译很久,但是以前不这样啊,那肯定就是我最近做了什么导致这样的了,是什么呢? 2.解决: 后来google下发现了解决办法,原来是我新安装了 ...
- Linux下使用putty进行UART串口调试【转】
本文转载自:http://blog.csdn.net/xzongyuan/article/details/11593101 版权声明:本文为博主原创文章,未经博主允许不得转载. 使用putty进行串口 ...
- jQuery 与 AJAX 实现失去焦点验证用户名是否合格
JSP页面 <tr onmouseover="currentcolor=this.style.backgroundColor;this.style.backgroundColor='# ...
- 【idea】idea快捷键
Alt+回车 导入包,自动修正 alt+shift+↑ 向上sout输出 psvm主函数 fori for Ctrl+N 查找类Ctrl+Shift+N 查找文件Ctrl+Alt+L 格式化代 ...
- C# WinForm开发系列 - Form/Window
Form是WinForm开发中非常重要的一个控件, 本文将包含如何制作一个关于对话框,系统载入提示窗体, 创建类似于QQ提示框以及创建不规则窗体等(文章及相关代码搜集自网络,仅供学习参考,版权属于原作 ...
- bzoj 4543 HOTEL 加强版
题目大意: 求树上取三个点这三个点两两距离相等的方案数 思路: 远古时候的$n^2$做法是换根 但那样无法继续优化了 学习了一波长链剖分 考虑如何在一棵树上进行dp 设$f[i][j]$表示以$i$为 ...
- 【WIP】Ruby JSON
创建: 2018/03/22 以后有空补上 注: JSON.generate 参数只能是Obejct或者Array, 不可以是Hash https://docs.ruby-lang.org/ja/la ...
- python 面向对象六 类属性和实例属性
一.实例属性 Python是动态语言,根据类创建的实例可以任意绑定属性. >>> class Student(object): ... def __init__(self, name ...
- bzoj 2132 圈地计划【最小割+dinic】
对于网格图,尤其是这种要求相邻各自不同的,考虑黑白染色 对于这张染色后图来说: 对于每个黑格: 表示初始时选择商业区: s点向它连商业区收益的流量,它向t点连工业区收益的流量: 割断S侧的边说明反悔, ...
- Logstash读取文本信息并写入到ES
Logstash读取文本信息并写入到ES 前提是ELK安装没问题 进入到logstash安装目录下的bin目录(我的logstash安装目录:/usr/local/) [root@es1 bin]# ...