ExportLogsService.java

  1package eu.siacs.conversations.services;
  2
  3import android.app.NotificationManager;
  4import android.app.Service;
  5import android.content.Context;
  6import android.content.Intent;
  7import android.os.IBinder;
  8import android.support.v4.app.NotificationCompat;
  9
 10import eu.siacs.conversations.R;
 11import eu.siacs.conversations.entities.Account;
 12import eu.siacs.conversations.entities.Conversation;
 13import eu.siacs.conversations.entities.Message;
 14import eu.siacs.conversations.persistance.DatabaseBackend;
 15import eu.siacs.conversations.persistance.FileBackend;
 16import eu.siacs.conversations.xmpp.jid.Jid;
 17
 18import java.io.BufferedWriter;
 19import java.io.File;
 20import java.io.FileWriter;
 21import java.io.IOException;
 22import java.text.SimpleDateFormat;
 23import java.util.Date;
 24import java.util.List;
 25import java.util.concurrent.atomic.AtomicBoolean;
 26
 27public class ExportLogsService extends Service {
 28
 29	private static final SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
 30	private static final String DIRECTORY_STRING_FORMAT = FileBackend.getConversationsFileDirectory() + "/logs/%s";
 31	private static final String MESSAGE_STRING_FORMAT = "(%s) %s: %s\n";
 32	private static final int NOTIFICATION_ID = 1;
 33	private static AtomicBoolean running = new AtomicBoolean(false);
 34
 35	@Override
 36	public int onStartCommand(Intent intent, int flags, int startId) {
 37		if (running.compareAndSet(false, true)) {
 38			new Thread(
 39					new Runnable() {
 40						DatabaseBackend databaseBackend = DatabaseBackend.getInstance(getBaseContext());
 41						List<Account> accounts = databaseBackend.getAccounts();
 42
 43						@Override
 44						public void run() {
 45							List<Conversation> conversations = databaseBackend.getConversations(Conversation.STATUS_AVAILABLE);
 46							conversations.addAll(databaseBackend.getConversations(Conversation.STATUS_ARCHIVED));
 47
 48							NotificationManager mNotifyManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
 49							NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(getBaseContext());
 50							mBuilder.setContentTitle(getString(R.string.notification_export_logs_title))
 51									.setSmallIcon(R.drawable.ic_notification)
 52									.setProgress(conversations.size(), 0, false);
 53							startForeground(NOTIFICATION_ID, mBuilder.build());
 54
 55							int progress = 0;
 56							for (Conversation conversation : conversations) {
 57								writeToFile(conversation);
 58								progress++;
 59								mBuilder.setProgress(conversations.size(), progress, false);
 60								mNotifyManager.notify(NOTIFICATION_ID, mBuilder.build());
 61							}
 62
 63							running.set(false);
 64							stopForeground(true);
 65						}
 66
 67						private void writeToFile(Conversation conversation) {
 68							Jid accountJid = resolveAccountUuid(conversation.getAccountUuid());
 69							Jid contactJid = conversation.getJid();
 70
 71							File dir = new File(String.format(DIRECTORY_STRING_FORMAT,
 72									accountJid.toBareJid().toString()));
 73							dir.mkdirs();
 74
 75							BufferedWriter bw = null;
 76							try {
 77								for (Message message : databaseBackend.getMessagesIterable(conversation)) {
 78									if (message.getType() == Message.TYPE_TEXT || message.hasFileOnRemoteHost()) {
 79										String date = simpleDateFormat.format(new Date(message.getTimeSent()));
 80										if (bw == null) {
 81											bw = new BufferedWriter(new FileWriter(
 82													new File(dir, contactJid.toBareJid().toString() + ".txt")));
 83										}
 84										String jid = null;
 85										switch (message.getStatus()) {
 86											case Message.STATUS_RECEIVED:
 87												jid = getMessageCounterpart(message);
 88												break;
 89											case Message.STATUS_SEND:
 90											case Message.STATUS_SEND_RECEIVED:
 91											case Message.STATUS_SEND_DISPLAYED:
 92												jid = accountJid.toBareJid().toString();
 93												break;
 94										}
 95										if (jid != null) {
 96											String body = message.hasFileOnRemoteHost() ? message.getFileParams().url.toString() : message.getBody();
 97											bw.write(String.format(MESSAGE_STRING_FORMAT, date, jid,
 98													body.replace("\\\n", "\\ \n").replace("\n", "\\ \n")));
 99										}
100									}
101								}
102							} catch (IOException e) {
103								e.printStackTrace();
104							} finally {
105								try {
106									if (bw != null) {
107										bw.close();
108									}
109								} catch (IOException e1) {
110									e1.printStackTrace();
111								}
112							}
113						}
114
115						private Jid resolveAccountUuid(String accountUuid) {
116							for (Account account : accounts) {
117								if (account.getUuid().equals(accountUuid)) {
118									return account.getJid();
119								}
120							}
121							return null;
122						}
123
124						private String getMessageCounterpart(Message message) {
125							String trueCounterpart = (String) message.getContentValues().get(Message.TRUE_COUNTERPART);
126							if (trueCounterpart != null) {
127								return trueCounterpart;
128							} else {
129								return message.getCounterpart().toString();
130							}
131						}
132					}).start();
133		}
134		return START_STICKY;
135	}
136
137	@Override
138	public IBinder onBind(Intent intent) {
139		return null;
140	}
141}