public DatabaseTrackInfo ImportTrack(SafeUri uri) { if (!IsWhiteListedFile(uri.LocalPath)) { return(null); } if (DatabaseTrackInfo.ContainsUri(uri, PrimarySourceIds)) { // TODO add DatabaseTrackInfo.SyncedStamp property, and if the file has been // updated since the last sync, fetch its metadata into the db. return(null); } DatabaseTrackInfo track = null; // TODO note, there is deadlock potential here b/c of locking of shared commands and blocking // because of transactions. Needs to be fixed in HyenaDatabaseConnection. ServiceManager.DbConnection.BeginTransaction(); try { track = new DatabaseTrackInfo(); track.Uri = uri; StreamTagger.TrackInfoMerge(track, StreamTagger.ProcessUri(uri)); track.PrimarySource = trackPrimarySourceChooser(track); bool save_track = true; if (track.PrimarySource is Banshee.Library.LibrarySource) { save_track = track.CopyToLibraryIfAppropriate(force_copy); } if (save_track) { track.Save(false); } ServiceManager.DbConnection.CommitTransaction(); } catch (Exception) { ServiceManager.DbConnection.RollbackTransaction(); throw; } counts[track.PrimarySourceId] = counts.ContainsKey(track.PrimarySourceId) ? counts[track.PrimarySourceId] + 1 : 1; // Reload every 20% or every 250 tracks, whatever is more (eg at most reload 5 times during an import) if (counts[track.PrimarySourceId] >= Math.Max(TotalCount / 5, 250)) { counts[track.PrimarySourceId] = 0; track.PrimarySource.NotifyTracksAdded(); } return(track); }
/// <summary> /// Adds the currently selected item(s) of the active source to the internet radio source /// as new stations. Any session data (as in live365 with activated user login) will previously /// be cleared. /// </summary> /// <param name="o"> /// A <see cref="System.Object"/> -- not used /// </param> /// <param name="e"> /// A <see cref="EventArgs"/> -- not used /// </param> protected void OnAddToInternetRadio(object o, EventArgs e) { PrimarySource internet_radio_source = GetInternetRadioSource (); PrimarySource current_source = ServiceManager.SourceManager.ActiveSource as PrimarySource; if (current_source == null) { Log.Debug ("[LiveRadioSource]<OnAddToInternetRadio> ActiveSource not Primary"); return; } if (internet_radio_source == null) { Log.Debug ("[LiveRadioSource]<OnAddToInternetRadio> Internet Radio not found"); return; } ITrackModelSource active_track_model_source = (ITrackModelSource) current_source; if (active_track_model_source.TrackModel.SelectedItems == null || active_track_model_source.TrackModel.SelectedItems.Count <= 0) { return; } ILiveRadioPlugin current_plugin = null; foreach (ILiveRadioPlugin plugin in plugins) { if (plugin.PluginSource != null && plugin.PluginSource.Equals (current_source)) { current_plugin = plugin; } } foreach (TrackInfo track in active_track_model_source.TrackModel.SelectedItems) { DatabaseTrackInfo station_track = new DatabaseTrackInfo (track as DatabaseTrackInfo); if (station_track != null) { station_track.PrimarySource = internet_radio_source; if (current_plugin != null) station_track.Uri = current_plugin.CleanUpUrl (station_track.Uri); station_track.Save (); } } }
protected override void AddTrackToDevice (DatabaseTrackInfo track, SafeUri fromUri) { if (track.PrimarySourceId == DbId) return; SafeUri new_uri = new SafeUri (GetTrackPath (track, System.IO.Path.GetExtension (fromUri.LocalPath))); // If it already is on the device but it's out of date, remove it //if (File.Exists(new_uri) && File.GetLastWriteTime(track.Uri.LocalPath) > File.GetLastWriteTime(new_uri)) //RemoveTrack(new MassStorageTrackInfo(new SafeUri(new_uri))); if (!File.Exists (new_uri)) { Directory.Create (System.IO.Path.GetDirectoryName (new_uri.LocalPath)); File.Copy (fromUri, new_uri, false); DatabaseTrackInfo copied_track = new DatabaseTrackInfo (track); copied_track.PrimarySource = this; copied_track.Uri = new_uri; // Write the metadata in db to the file on the DAP if it has changed since file was modified // to ensure that when we load it next time, it's data will match what's in the database // and the MetadataHash will actually match. We do this by comparing the time // stamps on files for last update of the db metadata vs the sync to file. // The equals on the inequality below is necessary for podcasts who often have a sync and // update time that are the same to the second, even though the album metadata has changed in the // DB to the feedname instead of what is in the file. It should be noted that writing the metadata // is a small fraction of the total copy time anyway. if (track.LastSyncedStamp >= Hyena.DateTimeUtil.ToDateTime (track.FileModifiedStamp)) { Log.DebugFormat ("Copying Metadata to File Since Sync time >= Updated Time"); bool write_metadata = Metadata.SaveTrackMetadataService.WriteMetadataEnabled.Value; bool write_ratings_and_playcounts = Metadata.SaveTrackMetadataService.WriteRatingsAndPlayCountsEnabled.Value; Banshee.Streaming.StreamTagger.SaveToFile (copied_track, write_metadata, write_ratings_and_playcounts); } copied_track.Save (false); } if (CoverArtSize > -1 && !String.IsNullOrEmpty (CoverArtFileType) && !String.IsNullOrEmpty (CoverArtFileName) && (FolderDepth == -1 || FolderDepth > 0)) { SafeUri cover_uri = new SafeUri (System.IO.Path.Combine (System.IO.Path.GetDirectoryName (new_uri.LocalPath), CoverArtFileName)); string coverart_id = track.ArtworkId; if (!File.Exists (cover_uri) && CoverArtSpec.CoverExists (coverart_id)) { Gdk.Pixbuf pic = null; if (CoverArtSize == 0) { if (CoverArtFileType == "jpg" || CoverArtFileType == "jpeg") { SafeUri local_cover_uri = new SafeUri (Banshee.Base.CoverArtSpec.GetPath (coverart_id)); Banshee.IO.File.Copy (local_cover_uri, cover_uri, false); } else { pic = artwork_manager.LookupPixbuf (coverart_id); } } else { pic = artwork_manager.LookupScalePixbuf (coverart_id, CoverArtSize); } if (pic != null) { try { byte [] bytes = pic.SaveToBuffer (CoverArtFileType); System.IO.Stream cover_art_file = File.OpenWrite (cover_uri, true); cover_art_file.Write (bytes, 0, bytes.Length); cover_art_file.Close (); } catch (GLib.GException){ Log.DebugFormat ("Could not convert cover art to {0}, unsupported filetype?", CoverArtFileType); } finally { Banshee.Collection.Gui.ArtworkManager.DisposePixbuf (pic); } } } } }
public DatabaseTrackInfo ImportTrack (SafeUri uri) { if (!IsWhiteListedFile (uri.AbsoluteUri)) { return null; } if (DatabaseTrackInfo.ContainsUri (uri, PrimarySourceIds)) { // TODO add DatabaseTrackInfo.SyncedStamp property, and if the file has been // updated since the last sync, fetch its metadata into the db. return null; } if (Banshee.IO.File.GetSize (uri) == 0) { throw new InvalidFileException (String.Format ( Catalog.GetString ("File is empty so it could not be imported: {0}"), Path.GetFileName (uri.LocalPath))); } DatabaseTrackInfo track = new DatabaseTrackInfo () { Uri = uri }; using (var file = StreamTagger.ProcessUri (uri)) { StreamTagger.TrackInfoMerge (track, file, false, true, true); } track.Uri = uri; if (FindOutdatedDupe (track)) { return null; } track.PrimarySource = trackPrimarySourceChooser (track); // TODO note, there is deadlock potential here b/c of locking of shared commands and blocking // because of transactions. Needs to be fixed in HyenaDatabaseConnection. ServiceManager.DbConnection.BeginTransaction (); try { bool save_track = true; if (track.PrimarySource is Banshee.Library.LibrarySource) { save_track = track.CopyToLibraryIfAppropriate (force_copy); } if (save_track) { track.Save (false); } ServiceManager.DbConnection.CommitTransaction (); } catch (Exception) { ServiceManager.DbConnection.RollbackTransaction (); throw; } counts[track.PrimarySourceId] = counts.ContainsKey (track.PrimarySourceId) ? counts[track.PrimarySourceId] + 1 : 1; // Reload every 20% or every 250 tracks, whatever is more (eg at most reload 5 times during an import) if (counts[track.PrimarySourceId] >= Math.Max (TotalCount/5, 250)) { counts[track.PrimarySourceId] = 0; track.PrimarySource.NotifyTracksAdded (); } return track; }
/*public override void CopyTrackTo (DatabaseTrackInfo track, SafeUri uri, UserJob job) { Banshee.IO.File.Copy (track.Uri, uri, false); }*/ protected override void AddTrack (DatabaseTrackInfo track) { // Ignore if already have it if (track.PrimarySourceId == DbId) return; PrimarySource source = track.PrimarySource; // If it's from a local primary source, change its PrimarySource if (source.IsLocal || source is LibrarySource) { track.PrimarySource = this; if (!(source is LibrarySource)) { track.CopyToLibraryIfAppropriate (false); } track.Save (false); // TODO optimize, remove this? I think it makes moving items // between local libraries very slow. //source.NotifyTracksChanged (); } else { // Figure out where we should put it if were to copy it var pattern = this.PathPattern ?? MusicLibrarySource.MusicFileNamePattern; string path = pattern.BuildFull (BaseDirectory, track); SafeUri uri = new SafeUri (path); // Make sure it's not already in the library // TODO optimize - no need to recreate this int [] every time if (DatabaseTrackInfo.ContainsUri (uri, new int [] {DbId})) { return; } // Since it's not, copy it and create a new TrackInfo object track.PrimarySource.CopyTrackTo (track, uri, AddTrackJob); // Create a new entry in CoreTracks for the copied file DatabaseTrackInfo new_track = new DatabaseTrackInfo (track); new_track.Uri = uri; new_track.PrimarySource = this; new_track.Save (false); } }
public static void Scan() { Hyena.Log.Debug ("[RippedFileScanner] <Scan> Start"); List<string> current_list = new List<string> (); GetFileNames (current_list, basepath); List<string> new_items = GetNewItems (previous_list, current_list); if (new_items != null && previous_list != null) { foreach (string item in new_items) { DatabaseTrackInfo new_track = new DatabaseTrackInfo (); if (new_track != null) { StreamTagger.TrackInfoMerge (new_track, new SafeUri (item)); // I think here should be a check to database if track is unique Hyena.Log.DebugFormat ("[RippedFileScanner] <Scan> New track found! Artist: {0} Title: {1}", new_track.ArtistName, new_track.TrackTitle); new_track.PrimarySource = Banshee.ServiceStack.ServiceManager.SourceManager.MusicLibrary; new_track.Save (); } } } previous_list = current_list; Hyena.Log.Debug ("[RippedFileScanner] <Scan> End"); }
public override void UpdateMetadata(DatabaseTrackInfo track) { SafeUri new_uri = new SafeUri (GetTrackPath (track, System.IO.Path.GetExtension (track.Uri))); if (new_uri.ToString () != track.Uri.ToString ()) { Directory.Create (System.IO.Path.GetDirectoryName (new_uri.LocalPath)); Banshee.IO.File.Move (track.Uri, new_uri); //to remove the folder if it's not needed anymore: DeleteTrackFile (track); track.Uri = new_uri; track.Save (true, BansheeQuery.UriField); } base.UpdateMetadata (track); }
public DatabaseTrackInfo ImportTrack(SafeUri uri) { if (!IsWhiteListedFile(uri.AbsoluteUri)) { return(null); } if (DatabaseTrackInfo.ContainsUri(uri, PrimarySourceIds)) { // TODO add DatabaseTrackInfo.SyncedStamp property, and if the file has been // updated since the last sync, fetch its metadata into the db. return(null); } if (!Banshee.IO.File.GetPermissions(uri).IsReadable) { throw new InvalidFileException(String.Format( Catalog.GetString("File is not readable so it could not be imported: {0}"), Path.GetFileName(uri.LocalPath))); } if (Banshee.IO.File.GetSize(uri) == 0) { throw new InvalidFileException(String.Format( Catalog.GetString("File is empty so it could not be imported: {0}"), Path.GetFileName(uri.LocalPath))); } DatabaseTrackInfo track = new DatabaseTrackInfo() { Uri = uri }; using (var file = StreamTagger.ProcessUri(uri)) { StreamTagger.TrackInfoMerge(track, file, false, true, true); } track.Uri = uri; if (FindOutdatedDupe(track)) { return(null); } track.PrimarySource = trackPrimarySourceChooser(track); // TODO note, there is deadlock potential here b/c of locking of shared commands and blocking // because of transactions. Needs to be fixed in HyenaDatabaseConnection. ServiceManager.DbConnection.BeginTransaction(); try { bool save_track = true; if (track.PrimarySource is Banshee.Library.LibrarySource) { save_track = track.CopyToLibraryIfAppropriate(force_copy); } if (save_track) { track.Save(false); } ServiceManager.DbConnection.CommitTransaction(); } catch (Exception) { ServiceManager.DbConnection.RollbackTransaction(); throw; } counts[track.PrimarySourceId] = counts.ContainsKey(track.PrimarySourceId) ? counts[track.PrimarySourceId] + 1 : 1; // Reload every 20% or every 250 tracks, whatever is more (eg at most reload 5 times during an import) if (counts[track.PrimarySourceId] >= Math.Max(TotalCount / 5, 250)) { counts[track.PrimarySourceId] = 0; track.PrimarySource.NotifyTracksAdded(); } return(track); }
private void OnItemAdded (FeedItem item) { if (item.Enclosure != null) { DatabaseTrackInfo track = new DatabaseTrackInfo (); track.ExternalId = item.DbId; track.PrimarySource = source; (track.ExternalObject as PodcastTrackInfo).SyncWithFeedItem (); track.Save (false); RefreshArtworkFor (item.Feed); } else { // We're only interested in items that have enclosures item.Delete (false); } }
private void MigrateXspfTrack(Media.Playlists.Xspf.Playlist playlist, Track track) { if (track.LocationCount <= 0) { return; } DatabaseTrackInfo station = new DatabaseTrackInfo (); station.PrimarySource = source; station.IsLive = true; station.Uri = GetSafeUri (track.Locations[0]); if (!String.IsNullOrEmpty (track.Title)) { station.TrackTitle = track.Title; } if (!String.IsNullOrEmpty (track.Creator)) { station.ArtistName = track.Creator; } if (!String.IsNullOrEmpty (track.Annotation)) { station.Comment = track.Annotation; } if (!String.IsNullOrEmpty (playlist.Title)) { station.Genre = playlist.Title; } if (track.Info != null) { station.MoreInfoUri = GetSafeUri (track.Info); } station.Save (); }
/// <summary> /// Adds a track to is source. Does not actually set the tracks source. /// </summary> /// <param name="track"> /// A <see cref="DatabaseTrackInfo"/> -- the track to be added to its set source /// </param> public override void AddTrack(DatabaseTrackInfo track) { track.CanSaveToDatabase = false; track.PrimarySource = this; track.Save (); }