parent
97d4063cf3
commit
a27b6eb63e
@ -0,0 +1,72 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Text.RegularExpressions;
|
||||||
|
using NzbDrone.Common.Exceptions;
|
||||||
|
|
||||||
|
namespace NzbDrone.Core.Restrictions
|
||||||
|
{
|
||||||
|
public static class PerlRegexFactory
|
||||||
|
{
|
||||||
|
private static Regex _perlRegexFormat = new Regex(@"/(?<pattern>.*)/(?<modifiers>[a-z]*)", RegexOptions.Compiled);
|
||||||
|
|
||||||
|
public static bool TryCreateRegex(string pattern, out Regex regex)
|
||||||
|
{
|
||||||
|
var match = _perlRegexFormat.Match(pattern);
|
||||||
|
|
||||||
|
if (!match.Success)
|
||||||
|
{
|
||||||
|
regex = null;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
regex = CreateRegex(match.Groups["pattern"].Value, match.Groups["modifiers"].Value);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Regex CreateRegex(string pattern, string modifiers)
|
||||||
|
{
|
||||||
|
var options = GetOptions(modifiers);
|
||||||
|
|
||||||
|
// For now we simply expect the pattern to be .net compliant. We should probably check and reject perl-specific constructs.
|
||||||
|
return new Regex(pattern, options | RegexOptions.Compiled);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static RegexOptions GetOptions(string modifiers)
|
||||||
|
{
|
||||||
|
var options = RegexOptions.None;
|
||||||
|
|
||||||
|
foreach (var modifier in modifiers)
|
||||||
|
{
|
||||||
|
switch (modifier)
|
||||||
|
{
|
||||||
|
case 'm':
|
||||||
|
options |= RegexOptions.Multiline;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 's':
|
||||||
|
options |= RegexOptions.Singleline;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'i':
|
||||||
|
options |= RegexOptions.IgnoreCase;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'x':
|
||||||
|
options |= RegexOptions.IgnorePatternWhitespace;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'n':
|
||||||
|
options |= RegexOptions.ExplicitCapture;
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
throw new ArgumentException("Unknown or unsupported perl regex modifier: " + modifier);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return options;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,63 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using System.Text.RegularExpressions;
|
||||||
|
using NzbDrone.Common.Cache;
|
||||||
|
|
||||||
|
namespace NzbDrone.Core.Restrictions
|
||||||
|
{
|
||||||
|
public interface ITermMatcher
|
||||||
|
{
|
||||||
|
bool IsMatch(string term, string value);
|
||||||
|
}
|
||||||
|
|
||||||
|
public class TermMatcher : ITermMatcher
|
||||||
|
{
|
||||||
|
private ICached<Predicate<string>> _matcherCache;
|
||||||
|
|
||||||
|
public TermMatcher(ICacheManager cacheManager)
|
||||||
|
{
|
||||||
|
_matcherCache = cacheManager.GetCache<Predicate<string>>(GetType());
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool IsMatch(string term, string value)
|
||||||
|
{
|
||||||
|
return GetMatcher(term)(value);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Predicate<string> GetMatcher(string term)
|
||||||
|
{
|
||||||
|
return _matcherCache.Get(term, () => CreateMatcherInternal(term), TimeSpan.FromHours(24));
|
||||||
|
}
|
||||||
|
|
||||||
|
private Predicate<string> CreateMatcherInternal(string term)
|
||||||
|
{
|
||||||
|
Regex regex;
|
||||||
|
if (PerlRegexFactory.TryCreateRegex(term, out regex))
|
||||||
|
{
|
||||||
|
return regex.IsMatch;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return new CaseInsensitiveTermMatcher(term).IsMatch;
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private sealed class CaseInsensitiveTermMatcher
|
||||||
|
{
|
||||||
|
private readonly string _term;
|
||||||
|
|
||||||
|
public CaseInsensitiveTermMatcher(string term)
|
||||||
|
{
|
||||||
|
_term = term.ToLowerInvariant();
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool IsMatch(string value)
|
||||||
|
{
|
||||||
|
return value.ToLowerInvariant().Contains(_term);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in new issue