diff --git a/src/Universalis.DbAccess.Tests/MarketBoard/ListingStoreTests.cs b/src/Universalis.DbAccess.Tests/MarketBoard/ListingStoreTests.cs index ea4db3ea..c1359f28 100644 --- a/src/Universalis.DbAccess.Tests/MarketBoard/ListingStoreTests.cs +++ b/src/Universalis.DbAccess.Tests/MarketBoard/ListingStoreTests.cs @@ -44,23 +44,7 @@ public async Task ReplaceLiveRetrieveLive_Works() Assert.All(currentlyShown.Listings.OrderBy(l => l.PricePerUnit).Zip(results), pair => { var (expected, actual) = pair; - Assert.Equal(expected.ListingId, actual.ListingId); - Assert.Equal(3, actual.ItemId); - Assert.Equal(93, actual.WorldId); - Assert.Equal(expected.Hq, actual.Hq); - Assert.Equal(expected.OnMannequin, actual.OnMannequin); - Assert.Equal(expected.PricePerUnit, actual.PricePerUnit); - Assert.Equal(expected.Quantity, actual.Quantity); - Assert.Equal(expected.RetainerName, actual.RetainerName); - Assert.Equal(expected.RetainerId, actual.RetainerId); - Assert.Equal(expected.RetainerCityId, actual.RetainerCityId); - Assert.Equal(expected.DyeId, actual.DyeId); - Assert.Equal(expected.CreatorId, actual.CreatorId); - Assert.Equal(expected.CreatorName, actual.CreatorName); - Assert.Equal(new DateTimeOffset(expected.LastReviewTime).ToUnixTimeSeconds(), - new DateTimeOffset(actual.LastReviewTime).ToUnixTimeSeconds()); - Assert.Equal(DateTimeKind.Utc, actual.LastReviewTime.Kind); - Assert.Equal(expected.SellerId, actual.SellerId); + AssertEqual(expected, actual); }); } @@ -79,23 +63,7 @@ public async Task ReplaceLiveRetrieveLive_Cached_Works() Assert.All(currentlyShown.Listings.OrderBy(l => l.PricePerUnit).Zip(results), pair => { var (expected, actual) = pair; - Assert.Equal(expected.ListingId, actual.ListingId); - Assert.Equal(3, actual.ItemId); - Assert.Equal(92, actual.WorldId); - Assert.Equal(expected.Hq, actual.Hq); - Assert.Equal(expected.OnMannequin, actual.OnMannequin); - Assert.Equal(expected.PricePerUnit, actual.PricePerUnit); - Assert.Equal(expected.Quantity, actual.Quantity); - Assert.Equal(expected.RetainerName, actual.RetainerName); - Assert.Equal(expected.RetainerId, actual.RetainerId); - Assert.Equal(expected.RetainerCityId, actual.RetainerCityId); - Assert.Equal(expected.DyeId, actual.DyeId); - Assert.Equal(expected.CreatorId, actual.CreatorId); - Assert.Equal(expected.CreatorName, actual.CreatorName); - Assert.Equal(new DateTimeOffset(expected.LastReviewTime).ToUnixTimeSeconds(), - new DateTimeOffset(actual.LastReviewTime).ToUnixTimeSeconds()); - Assert.Equal(DateTimeKind.Utc, actual.LastReviewTime.Kind); - Assert.Equal(expected.SellerId, actual.SellerId); + AssertEqual(expected, actual); }); } @@ -132,25 +100,7 @@ public async Task ReplaceLiveRetrieveLiveMultiple_Works() Assert.All(currentlyShown.Listings.OrderBy(l => l.PricePerUnit).Zip(results), pair => { var (expected, actual) = pair; - Assert.Equal(expected.ListingId, actual.ListingId); - Assert.Equal(5, actual.ItemId); - Assert.Equal(93, actual.WorldId); - Assert.Equal(expected.Hq, actual.Hq); - Assert.Equal(expected.OnMannequin, actual.OnMannequin); - Assert.Equal(expected.PricePerUnit, actual.PricePerUnit); - Assert.Equal(expected.Quantity, actual.Quantity); - Assert.Equal(expected.RetainerName, actual.RetainerName); - Assert.Equal(expected.RetainerId, actual.RetainerId); - Assert.Equal(expected.RetainerCityId, actual.RetainerCityId); - Assert.Equal(expected.DyeId, actual.DyeId); - Assert.Equal(expected.CreatorId, actual.CreatorId); - Assert.Equal(expected.CreatorName, actual.CreatorName); - Assert.Equal(new DateTimeOffset(expected.LastReviewTime).ToUnixTimeSeconds(), - new DateTimeOffset(actual.LastReviewTime).ToUnixTimeSeconds()); - Assert.Equal(DateTimeKind.Utc, actual.LastReviewTime.Kind); - Assert.Equal(expected.SellerId, actual.SellerId); - Assert.Equal(DateTimeKind.Utc, actual.UpdatedAt.Kind); - Assert.Equal(expected.Source, actual.Source); + AssertEqual(expected, actual); }); } } @@ -185,25 +135,7 @@ public async Task ReplaceLiveRetrieveManyLive_Works() Assert.All(expectedListings[i].OrderBy(l => l.PricePerUnit).Zip(results[new WorldItemPair(93, i)]), pair => { var (expected, actual) = pair; - Assert.Equal(expected.ListingId, actual.ListingId); - Assert.Equal(expected.ItemId, actual.ItemId); - Assert.Equal(expected.WorldId, actual.WorldId); - Assert.Equal(expected.Hq, actual.Hq); - Assert.Equal(expected.OnMannequin, actual.OnMannequin); - Assert.Equal(expected.PricePerUnit, actual.PricePerUnit); - Assert.Equal(expected.Quantity, actual.Quantity); - Assert.Equal(expected.RetainerName, actual.RetainerName); - Assert.Equal(expected.RetainerId, actual.RetainerId); - Assert.Equal(expected.RetainerCityId, actual.RetainerCityId); - Assert.Equal(expected.DyeId, actual.DyeId); - Assert.Equal(expected.CreatorId, actual.CreatorId); - Assert.Equal(expected.CreatorName, actual.CreatorName); - Assert.Equal(new DateTimeOffset(expected.LastReviewTime).ToUnixTimeSeconds(), - new DateTimeOffset(actual.LastReviewTime).ToUnixTimeSeconds()); - Assert.Equal(DateTimeKind.Utc, actual.LastReviewTime.Kind); - Assert.Equal(expected.SellerId, actual.SellerId); - Assert.Equal(DateTimeKind.Utc, actual.UpdatedAt.Kind); - Assert.Equal(expected.Source, actual.Source); + AssertEqual(expected, actual); }); } @@ -245,25 +177,7 @@ await store.RetrieveManyLive(new ListingManyQuery Assert.All(expectedListings[i].OrderBy(l => l.PricePerUnit).Zip(results[new WorldItemPair(93, i)]), pair => { var (expected, actual) = pair; - Assert.Equal(expected.ListingId, actual.ListingId); - Assert.Equal(expected.ItemId, actual.ItemId); - Assert.Equal(expected.WorldId, actual.WorldId); - Assert.Equal(expected.Hq, actual.Hq); - Assert.Equal(expected.OnMannequin, actual.OnMannequin); - Assert.Equal(expected.PricePerUnit, actual.PricePerUnit); - Assert.Equal(expected.Quantity, actual.Quantity); - Assert.Equal(expected.RetainerName, actual.RetainerName); - Assert.Equal(expected.RetainerId, actual.RetainerId); - Assert.Equal(expected.RetainerCityId, actual.RetainerCityId); - Assert.Equal(expected.DyeId, actual.DyeId); - Assert.Equal(expected.CreatorId, actual.CreatorId); - Assert.Equal(expected.CreatorName, actual.CreatorName); - Assert.Equal(new DateTimeOffset(expected.LastReviewTime).ToUnixTimeSeconds(), - new DateTimeOffset(actual.LastReviewTime).ToUnixTimeSeconds()); - Assert.Equal(DateTimeKind.Utc, actual.LastReviewTime.Kind); - Assert.Equal(expected.SellerId, actual.SellerId); - Assert.Equal(DateTimeKind.Utc, actual.UpdatedAt.Kind); - Assert.Equal(expected.Source, actual.Source); + AssertEqual(expected, actual); }); } @@ -300,4 +214,27 @@ public async Task RetrieveManyLive_ReturnsEmpty_WhenMissing() Assert.Empty(value); }); } + + private static void AssertEqual(Listing expected, Listing actual) + { + Assert.Equal(expected.ListingId, actual.ListingId); + Assert.Equal(expected.ItemId, actual.ItemId); + Assert.Equal(expected.WorldId, actual.WorldId); + Assert.Equal(expected.Hq, actual.Hq); + Assert.Equal(expected.OnMannequin, actual.OnMannequin); + Assert.Equal(expected.PricePerUnit, actual.PricePerUnit); + Assert.Equal(expected.Quantity, actual.Quantity); + Assert.Equal(expected.RetainerName, actual.RetainerName); + Assert.Equal(expected.RetainerId, actual.RetainerId); + Assert.Equal(expected.RetainerCityId, actual.RetainerCityId); + Assert.Equal(expected.DyeId, actual.DyeId); + Assert.Null(actual.CreatorId); + Assert.Equal(expected.CreatorName, actual.CreatorName); + Assert.Equal(new DateTimeOffset(expected.LastReviewTime).ToUnixTimeSeconds(), + new DateTimeOffset(actual.LastReviewTime).ToUnixTimeSeconds()); + Assert.Equal(DateTimeKind.Utc, actual.LastReviewTime.Kind); + Assert.Null(actual.SellerId); + Assert.Equal(DateTimeKind.Utc, actual.UpdatedAt.Kind); + Assert.Equal(expected.Source, actual.Source); + } } \ No newline at end of file diff --git a/src/Universalis.DbAccess/MarketBoard/ListingStore.cs b/src/Universalis.DbAccess/MarketBoard/ListingStore.cs index 343c2964..87f92ff8 100644 --- a/src/Universalis.DbAccess/MarketBoard/ListingStore.cs +++ b/src/Universalis.DbAccess/MarketBoard/ListingStore.cs @@ -113,10 +113,10 @@ public async Task ReplaceLive(IEnumerable listings, CancellationToken c batch.BatchCommands.Add(new NpgsqlBatchCommand( """ INSERT INTO listing - (listing_id, item_id, world_id, hq, on_mannequin, materia, unit_price, quantity, dye_id, creator_id, - creator_name, last_review_time, retainer_id, retainer_name, retainer_city_id, seller_id, uploaded_at, + (listing_id, item_id, world_id, hq, on_mannequin, materia, unit_price, quantity, dye_id, + creator_name, last_review_time, retainer_id, retainer_name, retainer_city_id, uploaded_at, source) - VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11, $12, $13, $14, $15, $16, $17, $18) + VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11, $12, $13, $14, $15, $16) ON CONFLICT (listing_id) DO NOTHING; """) { @@ -131,13 +131,11 @@ INSERT INTO listing new NpgsqlParameter { TypedValue = listing.PricePerUnit }, new NpgsqlParameter { TypedValue = listing.Quantity }, new NpgsqlParameter { TypedValue = listing.DyeId }, - new NpgsqlParameter { TypedValue = listing.CreatorId }, new NpgsqlParameter { TypedValue = listing.CreatorName }, new NpgsqlParameter { TypedValue = listing.LastReviewTime }, new NpgsqlParameter { TypedValue = listing.RetainerId }, new NpgsqlParameter { TypedValue = listing.RetainerName }, new NpgsqlParameter { TypedValue = listing.RetainerCityId }, - new NpgsqlParameter { TypedValue = listing.SellerId }, new NpgsqlParameter { TypedValue = uploadedAt.UtcDateTime }, new NpgsqlParameter { TypedValue = listing.Source }, }, @@ -147,6 +145,7 @@ INSERT INTO listing try { rowsUpdated += await batch.ExecuteNonQueryAsync(cancellationToken); + await _easyCachingProvider.RemoveAsync(ListingsKey(worldID, itemID), cancellationToken); } catch (Exception e) { @@ -176,9 +175,9 @@ public async Task> RetrieveLive(ListingQuery query, await using var command = _dataSource.CreateCommand( """ SELECT t.listing_id, t.item_id, t.world_id, t.hq, t.on_mannequin, t.materia, - t.unit_price, t.quantity, t.dye_id, t.creator_id, t.creator_name, + t.unit_price, t.quantity, t.dye_id, t.creator_name, t.last_review_time, t.retainer_id, t.retainer_name, t.retainer_city_id, - t.seller_id, t.uploaded_at, t.source + t.uploaded_at, t.source FROM listing t WHERE t.item_id = $1 AND t.world_id = $2 ORDER BY unit_price @@ -205,15 +204,15 @@ ORDER BY unit_price PricePerUnit = reader.GetInt32(6), Quantity = reader.GetInt32(7), DyeId = reader.GetInt32(8), - CreatorId = string.Intern(reader.GetString(9)), - CreatorName = reader.GetString(10), - LastReviewTime = reader.GetDateTime(11), - RetainerId = string.Intern(reader.GetString(12)), - RetainerName = reader.GetString(13), - RetainerCityId = reader.GetInt32(14), - SellerId = string.Intern(reader.GetString(15)), - UpdatedAt = reader.GetDateTime(16), - Source = string.Intern(reader.GetString(17)), + CreatorId = null, + CreatorName = reader.GetString(9), + LastReviewTime = reader.GetDateTime(10), + RetainerId = string.Intern(reader.GetString(11)), + RetainerName = reader.GetString(12), + RetainerCityId = reader.GetInt32(13), + SellerId = null, + UpdatedAt = reader.GetDateTime(14), + Source = string.Intern(reader.GetString(15)), }); } @@ -263,9 +262,9 @@ public async Task>> RetrieveManyLive(L await using var command = _dataSource.CreateCommand( """ SELECT t.listing_id, t.item_id, t.world_id, t.hq, t.on_mannequin, t.materia, - t.unit_price, t.quantity, t.dye_id, t.creator_id, t.creator_name, + t.unit_price, t.quantity, t.dye_id, t.creator_name, t.last_review_time, t.retainer_id, t.retainer_name, t.retainer_city_id, - t.seller_id, t.uploaded_at, t.source + t.uploaded_at, t.source FROM listing t WHERE t.item_id = ANY($1) AND t.world_id = ANY($2) """); @@ -311,16 +310,16 @@ FROM listing t DyeId = reader.GetInt32(8), // Large hashed IDs are interned as they will likely be reused when // the same item is requested again - CreatorId = string.Intern(reader.GetString(9)), - CreatorName = reader.GetString(10), - LastReviewTime = reader.GetDateTime(11), - RetainerId = string.Intern(reader.GetString(12)), - RetainerName = reader.GetString(13), - RetainerCityId = reader.GetInt32(14), - SellerId = string.Intern(reader.GetString(15)), - UpdatedAt = reader.GetDateTime(16), + CreatorId = null, + CreatorName = reader.GetString(9), + LastReviewTime = reader.GetDateTime(10), + RetainerId = string.Intern(reader.GetString(11)), + RetainerName = reader.GetString(12), + RetainerCityId = reader.GetInt32(13), + SellerId = null, + UpdatedAt = reader.GetDateTime(14), // Small strings, but with only a few possible values - Source = string.Intern(reader.GetString(17)), + Source = string.Intern(reader.GetString(15)), }); } } diff --git a/src/Universalis.DbAccess/Migrations/0014_DeleteIdentifyingColumns.cs b/src/Universalis.DbAccess/Migrations/0014_DeleteIdentifyingColumns.cs new file mode 100644 index 00000000..1ad5957e --- /dev/null +++ b/src/Universalis.DbAccess/Migrations/0014_DeleteIdentifyingColumns.cs @@ -0,0 +1,20 @@ +using FluentMigrator; + +namespace Universalis.DbAccess.Migrations; + +[Migration(14)] +public class DeleteIdentifyingColumns : Migration +{ + public override void Up() + { + Delete.Column("creator_id").FromTable("listing"); + Delete.Column("seller_id").FromTable("listing"); + } + + public override void Down() + { + Alter.Table("listing") + .AddColumn("creator_id").AsString().Nullable() + .AddColumn("seller_id").AsString().NotNullable().WithDefaultValue(""); + } +} \ No newline at end of file