package com.marverenic.music.data.store;
import android.content.Context;
import android.support.annotation.Nullable;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.marverenic.music.model.AutoPlaylist;
import com.marverenic.music.model.Playlist;
import com.marverenic.music.model.Song;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.List;
import rx.Observable;
import rx.android.schedulers.AndroidSchedulers;
import rx.schedulers.Schedulers;
import rx.subjects.BehaviorSubject;
public class DemoPlaylistStore implements PlaylistStore {
private static final String PLAYLISTS_FILENAME = "library-playlists.json";
private Context mContext;
private Observable<List<Playlist>> mPlaylists;
public DemoPlaylistStore(Context context) {
mContext = context;
}
@Override
public void loadPlaylists() {
// Do nothing. Performance isn't important in the demo app, so just load lazily.
}
@Override
public Observable<Boolean> refresh() {
return Observable.just(true);
}
@Override
public Observable<Boolean> isLoading() {
return Observable.just(false);
}
@Override
public Observable<List<Playlist>> getPlaylists() {
if (mPlaylists == null) {
BehaviorSubject<List<Playlist>> subject = BehaviorSubject.create();
Observable.fromCallable(this::readPlaylists)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(subject);
mPlaylists = subject;
}
return mPlaylists;
}
@SuppressWarnings("ThrowFromFinallyBlock")
private List<Playlist> readPlaylists() throws IOException {
InputStream stream = null;
InputStreamReader reader = null;
try {
File json = new File(mContext.getExternalFilesDir(null), PLAYLISTS_FILENAME);
stream = new FileInputStream(json);
reader = new InputStreamReader(stream);
return new Gson().fromJson(reader, new TypeToken<List<Playlist>>(){}.getType());
} finally {
if (stream != null) stream.close();
if (reader != null) reader.close();
}
}
@Override
public Observable<List<Song>> getSongs(Playlist playlist) {
throw new UnsupportedOperationException("Cannot get playlist contents in a demo library");
}
@Override
public Observable<List<Playlist>> searchForPlaylists(String query) {
return getPlaylists().map(
playlists -> {
List<Playlist> filtered = new ArrayList<>();
for (Playlist playlist : playlists) {
if (playlist.getPlaylistName().contains(query)) {
filtered.add(playlist);
}
}
return filtered;
});
}
@Override
public String verifyPlaylistName(String playlistName) {
// Never return any errors
return null;
}
@Override
public Playlist makePlaylist(String name) {
throw new UnsupportedOperationException("Cannot create playlists in a demo library");
}
@Override
public AutoPlaylist makePlaylist(AutoPlaylist model) {
throw new UnsupportedOperationException("Cannot create playlists in a demo library");
}
@Override
public Playlist makePlaylist(String name, @Nullable List<Song> songs) {
throw new UnsupportedOperationException("Cannot create playlists in a demo library");
}
@Override
public void removePlaylist(Playlist playlist) {
throw new UnsupportedOperationException("Cannot delete fake playlists");
}
@Override
public void editPlaylist(Playlist playlist, List<Song> newSongs) {
throw new UnsupportedOperationException("Cannot edit fake playlists");
}
@Override
public void editPlaylist(AutoPlaylist replacementModel) {
throw new UnsupportedOperationException("Cannot edit fake playlists");
}
@Override
public void addToPlaylist(Playlist playlist, Song song) {
throw new UnsupportedOperationException("Cannot edit fake playlists");
}
@Override
public void addToPlaylist(Playlist playlist, List<Song> songs) {
throw new UnsupportedOperationException("Cannot edit fake playlists");
}
}