Files
server/src/Icons/Models/IconUri.cs
Matt Gibson 4377c7a897 Rewrite Icon fetching (#3023)
* Rewrite Icon fetching

* Move validation to IconUri, Uri, or UriBuilder

* `dotnet format` 🤖

* PR suggestions

* Add not null compiler hint

* Add twitter to test case

* Move Uri manipulation to UriService

* Implement MockedHttpClient

Presents better, fluent handling of message matching and response
building.

* Add redirect handling tests

* Add testing to models

* More aggressively dispose content in icon link

* Format 🤖

* Update icon lockfile

* Convert to cloned stream for HttpResponseBuilder

Content was being disposed when HttResponseMessage was being disposed.
This avoids losing our reference to our content and allows multiple
usages of the same `MockedHttpMessageResponse`

* Move services to extension

Extension is shared by testing and allows access to services from
our service tests

* Remove unused `using`

* Prefer awaiting asyncs for better exception handling

* `dotnet format` 🤖

* Await async

* Update tests to use test TLD and ip ranges

* Remove unused interfaces

* Make assignments static when possible

* Prefer invariant comparer to downcasing

* Prefer injecting interface services to implementations

* Prefer comparer set in HashSet initialization

* Allow SVG icons

* Filter out icons with unknown formats

* Seek to beginning of MemoryStream after writing it

* More appropriate to not return icon if it's invalid

* Add svg icon test
2023-08-08 19:29:40 +00:00

53 lines
1.2 KiB
C#

#nullable enable
using System.Net;
using Bit.Icons.Extensions;
namespace Bit.Icons.Models;
public class IconUri
{
private readonly IPAddress _ip;
public string Host { get; }
public Uri InnerUri { get; }
public string Scheme => InnerUri.Scheme;
public bool IsValid
{
get
{
// Prevent direct access to any ip
if (IPAddress.TryParse(Host, out _))
{
return false;
}
// Prevent non-http(s) and non-default ports
if ((InnerUri.Scheme != "http" && InnerUri.Scheme != "https") || !InnerUri.IsDefaultPort)
{
return false;
}
// Prevent local hosts (localhost, bobs-pc, etc) and IP addresses
if (!Host.Contains('.') || _ip.IsInternal())
{
return false;
}
return true;
}
}
/// <summary>
/// Represents an ip-validated Uri for use in grabbing an icon.
/// </summary>
/// <param name="uriString"></param>
/// <param name="ip"></param>
public IconUri(Uri uri, IPAddress ip)
{
_ip = ip;
InnerUri = uri.ChangeHost(_ip.ToString());
Host = uri.Host;
}
}