Merge pull request #2313 from MediaBrowser/dev

Dev
This commit is contained in:
Luke 2016-11-27 14:42:25 -05:00 committed by GitHub
commit 58cff1aca8
13 changed files with 140 additions and 68 deletions

View File

@ -397,16 +397,34 @@ namespace Emby.Common.Implementations.IO
private FileAccess GetFileAccess(FileAccessMode mode)
{
var val = (int)mode;
return (FileAccess)val;
switch (mode)
{
case FileAccessMode.ReadWrite:
return FileAccess.ReadWrite;
case FileAccessMode.Write:
return FileAccess.Write;
case FileAccessMode.Read:
return FileAccess.Read;
default:
throw new Exception("Unrecognized FileAccessMode");
}
}
private FileShare GetFileShare(FileShareMode mode)
{
var val = (int)mode;
return (FileShare)val;
switch (mode)
{
case FileShareMode.ReadWrite:
return FileShare.ReadWrite;
case FileShareMode.Write:
return FileShare.Write;
case FileShareMode.Read:
return FileShare.Read;
case FileShareMode.None:
return FileShare.None;
default:
throw new Exception("Unrecognized FileShareMode");
}
}
public void SetHidden(string path, bool isHidden)

View File

@ -551,7 +551,7 @@ namespace Emby.Server.Core
DisplayPreferencesRepository = displayPreferencesRepo;
RegisterSingleInstance(DisplayPreferencesRepository);
var itemRepo = new SqliteItemRepository(ServerConfigurationManager, JsonSerializer, LogManager.GetLogger("SqliteItemRepository"), MemoryStreamFactory, assemblyInfo, FileSystemManager, EnvironmentInfo);
var itemRepo = new SqliteItemRepository(ServerConfigurationManager, JsonSerializer, LogManager.GetLogger("SqliteItemRepository"), MemoryStreamFactory, assemblyInfo, FileSystemManager, EnvironmentInfo, TimerFactory);
ItemRepository = itemRepo;
RegisterSingleInstance(ItemRepository);

View File

@ -88,11 +88,14 @@ namespace Emby.Server.Implementations.Data
var queries = new List<string>
{
"PRAGMA temp_store = memory",
//"PRAGMA journal_mode=WAL"
//"PRAGMA cache size=-10000"
};
if (EnableTempStoreMemory)
{
queries.Add("PRAGMA temp_store = memory");
}
//var cacheSize = CacheSize;
//if (cacheSize.HasValue)
//{
@ -116,7 +119,7 @@ namespace Emby.Server.Implementations.Data
db.ExecuteAll(string.Join(";", queries.ToArray()));
}
}
else
else if (queries.Count > 0)
{
db.ExecuteAll(string.Join(";", queries.ToArray()));
}
@ -124,6 +127,14 @@ namespace Emby.Server.Implementations.Data
return db;
}
protected virtual bool EnableTempStoreMemory
{
get
{
return false;
}
}
protected virtual int? CacheSize
{
get

View File

@ -63,8 +63,8 @@ namespace Emby.Server.Implementations.Data
string[] queries = {
"create table if not exists userdisplaypreferences (id GUID, userId GUID, client text, data BLOB)",
"create unique index if not exists userdisplaypreferencesindex on userdisplaypreferences (id, userId, client)"
"create table if not exists userdisplaypreferences (id GUID, userId GUID, client text, data BLOB)",
"create unique index if not exists userdisplaypreferencesindex on userdisplaypreferences (id, userId, client)"
};
connection.RunQueries(queries);
@ -107,10 +107,10 @@ namespace Emby.Server.Implementations.Data
private void SaveDisplayPreferences(DisplayPreferences displayPreferences, Guid userId, string client, IDatabaseConnection connection)
{
using (var statement = connection.PrepareStatement("replace into userdisplaypreferences (id, userid, client, data) values (@id, @userid, @client, @data)"))
{
var serialized = _jsonSerializer.SerializeToBytes(displayPreferences, _memoryStreamProvider);
var serialized = _jsonSerializer.SerializeToBytes(displayPreferences, _memoryStreamProvider);
using (var statement = connection.PrepareStatement("replace into userdisplaypreferences (id, userid, client, data) values (@id, @userId, @client, @data)"))
{
statement.TryBind("@id", displayPreferences.Id.ToGuidParamValue());
statement.TryBind("@userId", userId.ToGuidParamValue());
statement.TryBind("@client", client);

View File

@ -30,6 +30,7 @@ using MediaBrowser.Server.Implementations.Playlists;
using MediaBrowser.Model.Reflection;
using SQLitePCL.pretty;
using MediaBrowser.Model.System;
using MediaBrowser.Model.Threading;
namespace Emby.Server.Implementations.Data
{
@ -68,11 +69,13 @@ namespace Emby.Server.Implementations.Data
private readonly IMemoryStreamFactory _memoryStreamProvider;
private readonly IFileSystem _fileSystem;
private readonly IEnvironmentInfo _environmentInfo;
private readonly ITimerFactory _timerFactory;
private ITimer _shrinkMemoryTimer;
/// <summary>
/// Initializes a new instance of the <see cref="SqliteItemRepository"/> class.
/// </summary>
public SqliteItemRepository(IServerConfigurationManager config, IJsonSerializer jsonSerializer, ILogger logger, IMemoryStreamFactory memoryStreamProvider, IAssemblyInfo assemblyInfo, IFileSystem fileSystem, IEnvironmentInfo environmentInfo)
public SqliteItemRepository(IServerConfigurationManager config, IJsonSerializer jsonSerializer, ILogger logger, IMemoryStreamFactory memoryStreamProvider, IAssemblyInfo assemblyInfo, IFileSystem fileSystem, IEnvironmentInfo environmentInfo, ITimerFactory timerFactory)
: base(logger)
{
if (config == null)
@ -89,6 +92,7 @@ namespace Emby.Server.Implementations.Data
_memoryStreamProvider = memoryStreamProvider;
_fileSystem = fileSystem;
_environmentInfo = environmentInfo;
_timerFactory = timerFactory;
_typeMapper = new TypeMapper(assemblyInfo);
_criticReviewsPath = Path.Combine(_config.ApplicationPaths.DataPath, "critic-reviews");
@ -119,6 +123,14 @@ namespace Emby.Server.Implementations.Data
}
}
protected override bool EnableTempStoreMemory
{
get
{
return true;
}
}
private SQLiteDatabaseConnection _backgroundConnection;
protected override void CloseConnection()
{
@ -129,6 +141,12 @@ namespace Emby.Server.Implementations.Data
_backgroundConnection.Dispose();
_backgroundConnection = null;
}
if (_shrinkMemoryTimer != null)
{
_shrinkMemoryTimer.Dispose();
_shrinkMemoryTimer = null;
}
}
/// <summary>
@ -364,13 +382,35 @@ namespace Emby.Server.Implementations.Data
connection.RunQueries(postQueries);
//SqliteExtensions.Attach(_connection, Path.Combine(_config.ApplicationPaths.DataPath, "userdata_v2.db"), "UserDataDb");
//await Vacuum(_connection).ConfigureAwait(false);
}
userDataRepo.Initialize(WriteLock);
_backgroundConnection = CreateConnection(true);
_shrinkMemoryTimer = _timerFactory.Create(OnShrinkMemoryTimerCallback, null, TimeSpan.FromMinutes(1), TimeSpan.FromMinutes(30));
}
private void OnShrinkMemoryTimerCallback(object state)
{
try
{
using (WriteLock.Write())
{
using (var connection = CreateConnection())
{
connection.RunQueries(new string[]
{
"pragma shrink_memory"
});
}
}
}
catch (Exception ex)
{
Logger.ErrorException("Error running shrink memory", ex);
}
}
private readonly string[] _retriveItemColumns =
@ -666,7 +706,7 @@ namespace Emby.Server.Implementations.Data
{
var requiresReset = false;
var statements = db.PrepareAll(string.Join(";", new string[]
var statements = db.PrepareAll(string.Join(";", new string[]
{
GetSaveItemCommandText(),
"delete from AncestorIds where ItemId=@ItemId",

View File

@ -84,6 +84,14 @@ namespace Emby.Server.Implementations.Data
}
}
protected override bool EnableTempStoreMemory
{
get
{
return true;
}
}
private void ImportUserDataIfNeeded(IDatabaseConnection connection)
{
if (!_fileSystem.FileExists(_importFile))

View File

@ -735,7 +735,7 @@ namespace Emby.Server.Implementations.HttpServer
/// <returns><c>true</c> if [is not modified] [the specified cache key]; otherwise, <c>false</c>.</returns>
private bool IsNotModified(IRequest requestContext, Guid? cacheKey, DateTime? lastDateModified, TimeSpan? cacheDuration)
{
var isNotModified = true;
//var isNotModified = true;
var ifModifiedSinceHeader = requestContext.Headers.Get("If-Modified-Since");
@ -745,18 +745,23 @@ namespace Emby.Server.Implementations.HttpServer
if (DateTime.TryParse(ifModifiedSinceHeader, out ifModifiedSince))
{
isNotModified = IsNotModified(ifModifiedSince.ToUniversalTime(), cacheDuration, lastDateModified);
if (IsNotModified(ifModifiedSince.ToUniversalTime(), cacheDuration, lastDateModified))
{
return true;
}
}
}
var ifNoneMatchHeader = requestContext.Headers.Get("If-None-Match");
// Validate If-None-Match
if (isNotModified && (cacheKey.HasValue || !string.IsNullOrEmpty(ifNoneMatchHeader)))
if ((cacheKey.HasValue || !string.IsNullOrEmpty(ifNoneMatchHeader)))
{
Guid ifNoneMatch;
if (Guid.TryParse(ifNoneMatchHeader ?? string.Empty, out ifNoneMatch))
ifNoneMatchHeader = (ifNoneMatchHeader ?? string.Empty).Trim('\"');
if (Guid.TryParse(ifNoneMatchHeader, out ifNoneMatch))
{
if (cacheKey.HasValue && cacheKey.Value == ifNoneMatch)
{

View File

@ -83,6 +83,14 @@ namespace Emby.Server.Implementations.Sync
}
}
protected override bool EnableTempStoreMemory
{
get
{
return true;
}
}
private const string BaseJobSelectText = "select Id, TargetId, Name, Profile, Quality, Bitrate, Status, Progress, UserId, ItemIds, Category, ParentId, UnwatchedOnly, ItemLimit, SyncNewContent, DateCreated, DateLastModified, ItemCount from SyncJobs";
private const string BaseJobItemSelectText = "select Id, ItemId, ItemName, MediaSourceId, JobId, TemporaryPath, OutputPath, Status, TargetId, DateCreated, Progress, AdditionalFiles, MediaSource, IsMarkedForRemoval, JobItemIndex, ItemDateModifiedTicks from SyncJobItems";

View File

@ -257,7 +257,7 @@ namespace MediaBrowser.Api.Playback.Hls
// add when stream copying?
// -avoid_negative_ts make_zero -fflags +genpts
var args = string.Format("{0} {1} {2} -map_metadata -1 -threads {3} {4} {5} -sc_threshold 0 {6} -hls_time {7} -start_number {8} -hls_list_size {9}{10} -y \"{11}\"",
var args = string.Format("{0} {1} {2} -map_metadata -1 -threads {3} {4} {5} -fflags +genpts -sc_threshold 0 {6} -hls_time {7} -start_number {8} -hls_list_size {9}{10} -y \"{11}\"",
itsOffset,
inputModifier,
GetInputArgument(state),

View File

@ -369,7 +369,6 @@ namespace MediaBrowser.Model.IO
Append = 6
}
[Flags]
public enum FileAccessMode
{
//
@ -388,7 +387,6 @@ namespace MediaBrowser.Model.IO
ReadWrite = 3
}
[Flags]
public enum FileShareMode
{
//
@ -417,16 +415,7 @@ namespace MediaBrowser.Model.IO
// or another process) will fail until the file is closed. However, even if this
// flag is specified, additional permissions might still be needed to access the
// file.
ReadWrite = 3,
//
// Summary:
// Allows subsequent deleting of a file.
Delete = 4,
//
// Summary:
// Makes the file handle inheritable by child processes. This is not directly supported
// by Win32.
Inheritable = 16
ReadWrite = 3
}
}

View File

@ -32,7 +32,6 @@ namespace MediaBrowser.Model.LiveTv
public LiveTvOptions()
{
EnableMovieProviders = true;
EnableRecordingSubfolders = true;
TunerHosts = new List<TunerHostInfo>();
ListingProviders = new List<ListingsProviderInfo>();
MediaLocationsCreated = new string[] { };

View File

@ -78,16 +78,15 @@ namespace MediaBrowser.Providers.Manager
bool hasRefreshedMetadata = true;
bool hasRefreshedImages = true;
var isFirstRefresh = item.DateLastRefreshed == default(DateTime);
// Next run metadata providers
if (refreshOptions.MetadataRefreshMode != MetadataRefreshMode.None)
{
var providers = GetProviders(item, refreshOptions, requiresRefresh)
var providers = GetProviders(item, refreshOptions, isFirstRefresh, requiresRefresh)
.ToList();
var dateLastRefresh = item.DateLastRefreshed;
if (providers.Count > 0 || dateLastRefresh == default(DateTime))
if (providers.Count > 0 || isFirstRefresh)
{
if (item.BeforeMetadataRefresh())
{
@ -110,11 +109,7 @@ namespace MediaBrowser.Providers.Manager
var result = await RefreshWithProviders(metadataResult, id, refreshOptions, providers, itemImageProvider, cancellationToken).ConfigureAwait(false);
updateType = updateType | result.UpdateType;
if (result.Failures == 0)
{
hasRefreshedMetadata = true;
}
else
if (result.Failures > 0)
{
hasRefreshedMetadata = false;
}
@ -138,19 +133,13 @@ namespace MediaBrowser.Providers.Manager
var result = await itemImageProvider.RefreshImages(itemOfType, libraryOptions, providers, refreshOptions, config, cancellationToken).ConfigureAwait(false);
updateType = updateType | result.UpdateType;
if (result.Failures == 0)
{
hasRefreshedImages = true;
}
else
if (result.Failures > 0)
{
hasRefreshedImages = false;
}
}
}
var isFirstRefresh = item.DateLastRefreshed == default(DateTime);
var beforeSaveResult = await BeforeSave(itemOfType, isFirstRefresh || refreshOptions.ReplaceAllMetadata || refreshOptions.MetadataRefreshMode == MetadataRefreshMode.FullRefresh || requiresRefresh, updateType).ConfigureAwait(false);
updateType = updateType | beforeSaveResult;
@ -373,15 +362,18 @@ namespace MediaBrowser.Providers.Manager
/// Gets the providers.
/// </summary>
/// <returns>IEnumerable{`0}.</returns>
protected IEnumerable<IMetadataProvider> GetProviders(IHasMetadata item, MetadataRefreshOptions options, bool requiresRefresh)
protected IEnumerable<IMetadataProvider> GetProviders(IHasMetadata item, MetadataRefreshOptions options, bool isFirstRefresh, bool requiresRefresh)
{
// Get providers to refresh
var providers = ((ProviderManager)ProviderManager).GetMetadataProviders<TItemType>(item).ToList();
var dateLastRefresh = item.DateLastRefreshed;
var metadataRefreshMode = options.MetadataRefreshMode;
// Run all if either of these flags are true
var runAllProviders = options.ReplaceAllMetadata || options.MetadataRefreshMode == MetadataRefreshMode.FullRefresh || dateLastRefresh == default(DateTime) || requiresRefresh;
var runAllProviders = options.ReplaceAllMetadata ||
metadataRefreshMode == MetadataRefreshMode.FullRefresh ||
(isFirstRefresh && metadataRefreshMode >= MetadataRefreshMode.Default) ||
(requiresRefresh && metadataRefreshMode >= MetadataRefreshMode.Default);
if (!runAllProviders)
{
@ -404,6 +396,9 @@ namespace MediaBrowser.Providers.Manager
}
else
{
var anyRemoteProvidersChanged = providersWithChanges.OfType<IRemoteMetadataProvider>()
.Any();
providers = providers.Where(i =>
{
// If any provider reports a change, always run local ones as well
@ -412,9 +407,6 @@ namespace MediaBrowser.Providers.Manager
return true;
}
var anyRemoteProvidersChanged = providersWithChanges.OfType<IRemoteMetadataProvider>()
.Any();
// If any remote providers changed, run them all so that priorities can be honored
if (i is IRemoteMetadataProvider)
{

View File

@ -911,17 +911,14 @@ namespace MediaBrowser.XbmcMetadata.Savers
var image = item.GetImageInfo(ImageType.Primary, 0);
if (image != null && image.IsLocalFile)
if (image != null)
{
writer.WriteElementString("poster", GetPathToSave(image.Path, libraryManager, config));
writer.WriteElementString("poster", GetImagePathToSave(image, libraryManager, config));
}
foreach (var backdrop in item.GetImages(ImageType.Backdrop))
{
if (backdrop.IsLocalFile)
{
writer.WriteElementString("fanart", GetPathToSave(backdrop.Path, libraryManager, config));
}
writer.WriteElementString("fanart", GetImagePathToSave(backdrop, libraryManager, config));
}
writer.WriteEndElement();
@ -1012,9 +1009,9 @@ namespace MediaBrowser.XbmcMetadata.Savers
var personEntity = libraryManager.GetPerson(person.Name);
var image = personEntity.GetImageInfo(ImageType.Primary, 0);
if (image != null && image.IsLocalFile)
if (image != null)
{
writer.WriteElementString("thumb", GetPathToSave(image.Path, libraryManager, config));
writer.WriteElementString("thumb", GetImagePathToSave(image, libraryManager, config));
}
}
catch (Exception)
@ -1026,9 +1023,14 @@ namespace MediaBrowser.XbmcMetadata.Savers
}
}
private static string GetPathToSave(string path, ILibraryManager libraryManager, IServerConfigurationManager config)
private static string GetImagePathToSave(ItemImageInfo image, ILibraryManager libraryManager, IServerConfigurationManager config)
{
return libraryManager.GetPathAfterNetworkSubstitution(path);
if (!image.IsLocalFile)
{
return image.Path;
}
return libraryManager.GetPathAfterNetworkSubstitution(image.Path);
}
private static bool IsPersonType(PersonInfo person, string type)