From bdf560352c24e58a371ed878cb96105b69c347b5 Mon Sep 17 00:00:00 2001 From: Scott Jackson Date: Fri, 17 Aug 2018 18:16:03 -0700 Subject: Fixes #872 use native serialization so Auto doesn't crash on entries --- .../daneren2005/dsub/domain/MusicDirectory.java | 41 ++++++++ .../dsub/service/AutoMediaBrowserService.java | 107 ++++++++++++--------- .../github/daneren2005/dsub/util/Constants.java | 1 + .../dsub/util/compat/RemoteControlClientLP.java | 8 ++ 4 files changed, 112 insertions(+), 45 deletions(-) diff --git a/app/src/main/java/github/daneren2005/dsub/domain/MusicDirectory.java b/app/src/main/java/github/daneren2005/dsub/domain/MusicDirectory.java index 5f7b2412..bd7928fd 100644 --- a/app/src/main/java/github/daneren2005/dsub/domain/MusicDirectory.java +++ b/app/src/main/java/github/daneren2005/dsub/domain/MusicDirectory.java @@ -25,6 +25,13 @@ import android.media.MediaMetadataRetriever; import android.os.Build; import android.util.Log; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.ObjectInput; +import java.io.ObjectInputStream; +import java.io.ObjectOutput; +import java.io.ObjectOutputStream; import java.text.Collator; import java.util.ArrayList; import java.util.Iterator; @@ -628,6 +635,40 @@ public class MusicDirectory implements Serializable { public String toString() { return title; } + + public byte[] toByteArray() throws IOException { + ByteArrayOutputStream bos = new ByteArrayOutputStream(); + ObjectOutput out = null; + try { + out = new ObjectOutputStream(bos); + out.writeObject(this); + out.flush(); + return bos.toByteArray(); + } finally { + try { + bos.close(); + } catch (IOException ex) { + // ignore close exception + } + } + } + + public static Entry fromByteArray(byte[] byteArray) throws IOException, ClassNotFoundException { + ByteArrayInputStream bis = new ByteArrayInputStream(byteArray); + ObjectInput in = null; + try { + in = new ObjectInputStream(bis); + return (Entry) in.readObject(); + } finally { + try { + if (in != null) { + in.close(); + } + } catch (IOException ex) { + // ignore close exception + } + } + } } public static class EntryComparator implements Comparator { diff --git a/app/src/main/java/github/daneren2005/dsub/service/AutoMediaBrowserService.java b/app/src/main/java/github/daneren2005/dsub/service/AutoMediaBrowserService.java index 83af2cad..d4e544c6 100644 --- a/app/src/main/java/github/daneren2005/dsub/service/AutoMediaBrowserService.java +++ b/app/src/main/java/github/daneren2005/dsub/service/AutoMediaBrowserService.java @@ -30,6 +30,7 @@ import android.service.media.MediaBrowserService; import android.support.annotation.Nullable; import android.util.Log; +import java.io.IOException; import java.util.ArrayList; import java.util.List; @@ -279,18 +280,22 @@ public class AutoMediaBrowserService extends MediaBrowserService { // music files for(Entry entry: indexes.getEntries()) { - entry.setBookmark(null); // don't resume from a bookmark in a browse listing - Bundle extras = new Bundle(); - extras.putSerializable(Constants.INTENT_EXTRA_ENTRY, entry); - extras.putString(Constants.INTENT_EXTRA_NAME_CHILD_ID, entry.getId()); + try { + entry.setBookmark(null); // don't resume from a bookmark in a browse listing + Bundle extras = new Bundle(); + extras.putByteArray(Constants.INTENT_EXTRA_ENTRY_BYTES, entry.toByteArray()); + extras.putString(Constants.INTENT_EXTRA_NAME_CHILD_ID, entry.getId()); - MediaDescription description = new MediaDescription.Builder() - .setTitle(entry.getTitle()) - .setMediaId(entry.getId()) - .setExtras(extras) - .build(); + MediaDescription description = new MediaDescription.Builder() + .setTitle(entry.getTitle()) + .setMediaId(entry.getId()) + .setExtras(extras) + .build(); - mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + } catch(IOException e) { + Log.e(TAG, "Failed to add entry", e); + } } result.sendResult(mediaItems); @@ -324,19 +329,23 @@ public class AutoMediaBrowserService extends MediaBrowserService { mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_BROWSABLE)); } else { - // mark individual songs as directly playable - entry.setBookmark(null); // don't resume from a bookmark in a browse listing - Bundle extras = new Bundle(); - extras.putSerializable(Constants.INTENT_EXTRA_ENTRY, entry); - extras.putString(Constants.INTENT_EXTRA_NAME_CHILD_ID, entry.getId()); - - description = new MediaDescription.Builder() - .setTitle(entry.getTitle()) - .setMediaId(entry.getId()) - .setExtras(extras) - .build(); - - mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + try { + // mark individual songs as directly playable + entry.setBookmark(null); // don't resume from a bookmark in a browse listing + Bundle extras = new Bundle(); + extras.putByteArray(Constants.INTENT_EXTRA_ENTRY_BYTES, entry.toByteArray()); + extras.putString(Constants.INTENT_EXTRA_NAME_CHILD_ID, entry.getId()); + + description = new MediaDescription.Builder() + .setTitle(entry.getTitle()) + .setMediaId(entry.getId()) + .setExtras(extras) + .build(); + + mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + } catch (IOException e) { + Log.e(TAG, "Failed to add entry", e); + } } } result.sendResult(mediaItems); @@ -411,19 +420,23 @@ public class AutoMediaBrowserService extends MediaBrowserService { List mediaItems = new ArrayList<>(); for(Entry entry: podcasts.getChildren(false, true)) { - PodcastEpisode podcast = (PodcastEpisode) entry; - Bundle podcastExtras = new Bundle(); - podcastExtras.putSerializable(Constants.INTENT_EXTRA_ENTRY, podcast); - podcastExtras.putString(Constants.INTENT_EXTRA_NAME_PODCAST_ID, podcast.getId()); - - MediaDescription description = new MediaDescription.Builder() - .setTitle(podcast.getTitle()) - .setSubtitle(Util.formatDate(downloadService, podcast.getDate(), false)) - .setMediaId(PODCAST_PREFIX + podcast.getId()) - .setExtras(podcastExtras) - .build(); + try { + PodcastEpisode podcast = (PodcastEpisode) entry; + Bundle podcastExtras = new Bundle(); + podcastExtras.putByteArray(Constants.INTENT_EXTRA_ENTRY_BYTES, podcast.toByteArray()); + podcastExtras.putString(Constants.INTENT_EXTRA_NAME_PODCAST_ID, podcast.getId()); + + MediaDescription description = new MediaDescription.Builder() + .setTitle(podcast.getTitle()) + .setSubtitle(Util.formatDate(downloadService, podcast.getDate(), false)) + .setMediaId(PODCAST_PREFIX + podcast.getId()) + .setExtras(podcastExtras) + .build(); - mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + } catch(IOException e) { + Log.e(TAG, "Failed to add podcast", e); + } } result.sendResult(mediaItems); @@ -445,18 +458,22 @@ public class AutoMediaBrowserService extends MediaBrowserService { List mediaItems = new ArrayList<>(); for(Entry entry: bookmarkList.getChildren(false, true)) { - Bundle extras = new Bundle(); - extras.putSerializable(Constants.INTENT_EXTRA_ENTRY, entry); - extras.putString(Constants.INTENT_EXTRA_NAME_CHILD_ID, entry.getId()); + try { + Bundle extras = new Bundle(); + extras.putByteArray(Constants.INTENT_EXTRA_ENTRY_BYTES, entry.toByteArray()); + extras.putString(Constants.INTENT_EXTRA_NAME_CHILD_ID, entry.getId()); - MediaDescription description = new MediaDescription.Builder() - .setTitle(entry.getTitle()) - .setSubtitle(Util.formatDuration(entry.getBookmark().getPosition() / 1000)) - .setMediaId(entry.getId()) - .setExtras(extras) - .build(); + MediaDescription description = new MediaDescription.Builder() + .setTitle(entry.getTitle()) + .setSubtitle(Util.formatDuration(entry.getBookmark().getPosition() / 1000)) + .setMediaId(entry.getId()) + .setExtras(extras) + .build(); - mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + mediaItems.add(new MediaBrowser.MediaItem(description, MediaBrowser.MediaItem.FLAG_PLAYABLE)); + } catch(IOException e) { + Log.e(TAG, "Failed to add entry", e); + } } result.sendResult(mediaItems); diff --git a/app/src/main/java/github/daneren2005/dsub/util/Constants.java b/app/src/main/java/github/daneren2005/dsub/util/Constants.java index e0a1e164..7f5ff3f1 100644 --- a/app/src/main/java/github/daneren2005/dsub/util/Constants.java +++ b/app/src/main/java/github/daneren2005/dsub/util/Constants.java @@ -68,6 +68,7 @@ public final class Constants { public static final String INTENT_EXTRA_SHOW_ALL = "showAll"; public static final String INTENT_EXTRA_PLAY_LAST = "playLast"; public static final String INTENT_EXTRA_ENTRY = "passedEntry"; + public static final String INTENT_EXTRA_ENTRY_BYTES = "passedEntryBytes"; // Preferences keys. public static final String PREFERENCES_KEY_SERVER_KEY = "server"; diff --git a/app/src/main/java/github/daneren2005/dsub/util/compat/RemoteControlClientLP.java b/app/src/main/java/github/daneren2005/dsub/util/compat/RemoteControlClientLP.java index 816a071d..9f1d5ebd 100644 --- a/app/src/main/java/github/daneren2005/dsub/util/compat/RemoteControlClientLP.java +++ b/app/src/main/java/github/daneren2005/dsub/util/compat/RemoteControlClientLP.java @@ -39,6 +39,7 @@ import android.support.v7.media.MediaRouter; import android.util.Log; import android.view.KeyEvent; +import java.io.IOException; import java.util.ArrayList; import java.util.List; @@ -584,6 +585,13 @@ public class RemoteControlClientLP extends RemoteControlClientBase { boolean shuffle = extras.getBoolean(Constants.INTENT_EXTRA_NAME_SHUFFLE, false); boolean playLast = extras.getBoolean(Constants.INTENT_EXTRA_PLAY_LAST, false); Entry entry = (Entry) extras.getSerializable(Constants.INTENT_EXTRA_ENTRY); + if(extras.containsKey(Constants.INTENT_EXTRA_ENTRY_BYTES)) { + try { + entry = Entry.fromByteArray(extras.getByteArray(Constants.INTENT_EXTRA_ENTRY_BYTES)); + } catch(Exception e) { + Log.e(TAG, "Failed to deserialize from entry: ", e); + } + } String playlistId = extras.getString(Constants.INTENT_EXTRA_NAME_PLAYLIST_ID, null); if(playlistId != null) { -- cgit v1.2.3