Skip to content

Commit ee617c1

Browse files
committed
change transaction isolation to repeatable read to allow reads within a transaction to succeed (serializable is not allowed)
1 parent dad481a commit ee617c1

File tree

4 files changed

+116
-107
lines changed

4 files changed

+116
-107
lines changed

RelistenApi/Services/DbService.cs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,11 @@ public Task<T> WithWriteConnection<T>(Func<IDbConnection, Task<T>> getData, bool
5151
return WithConnection(getData, longTimeout, readOnly: false);
5252
}
5353

54+
public Task WithWriteConnection(Func<IDbConnection, Task> getData, bool longTimeout = false)
55+
{
56+
return WithConnection(getData, longTimeout, readOnly: false);
57+
}
58+
5459
public async Task<T> WithConnection<T>(Func<IDbConnection, Task<T>> getData, bool longTimeout = false, bool readOnly = true)
5560
{
5661
try

RelistenApi/Services/Importers/ArchiveOrgImporter.cs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -176,7 +176,9 @@ await root.response.docs.AsyncForEachWithProgress(prog, async doc =>
176176
doc.identifier, detailsRoot.metadata.date);
177177
}
178178

179-
using var scope = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled);
179+
using var scope = new TransactionScope(TransactionScopeOption.Required,
180+
new TransactionOptions() { IsolationLevel = IsolationLevel.RepeatableRead },
181+
TransactionScopeAsyncFlowOption.Enabled);
180182

181183
try
182184
{

RelistenApi/Services/Importers/LocalImporter.cs

Lines changed: 55 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -321,13 +321,13 @@ private async Task<Source> ProcessShow(ImportStats stats, Artist artist, string
321321
var tracks = apiShow.tracks.ToList();
322322

323323
taperNotes.AddRange(apiShow.txts);
324-
324+
325325
foreach (var track in tracks)
326326
{
327327
var localTrackPosition = track.tags.track.no;
328328

329329
// we add one to tracksAdded because track positions are not zero-indexed
330-
// they start at 1, but tracksAdded is zero indexed
330+
// they start at 1, but tracksAdded is zero indexed
331331
if (localTrackPosition < tracksAdded + 1) localTrackPosition += tracksAdded;
332332

333333
var st = new SourceTrack
@@ -395,67 +395,68 @@ public async Task<ImportStats> ProcessShows(Artist artist, ArtistUpstreamSource
395395

396396
async Task processDay(string date, IList<LocalShow> shows)
397397
{
398-
using (var scope = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled))
398+
using var scope = new TransactionScope(TransactionScopeOption.Required,
399+
new TransactionOptions() { IsolationLevel = IsolationLevel.RepeatableRead },
400+
TransactionScopeAsyncFlowOption.Enabled);
401+
402+
var firstShow = shows.First();
403+
var dbSource = existingSources.GetValue(date);
404+
var venueUpstreamId = $"{firstShow.venue} {firstShow.city}, {firstShow.state}";
405+
406+
if (dbSource == null)
399407
{
400-
var firstShow = shows.First();
401-
var dbSource = existingSources.GetValue(date);
402-
var venueUpstreamId = $"{firstShow.venue} {firstShow.city}, {firstShow.state}";
408+
dbSource = await ProcessShow(stats, artist, date, shows, src,
409+
new Source
410+
{
411+
updated_at = firstShow.updated_at,
412+
artist_id = artist.id,
413+
venue_id = existingVenues[venueUpstreamId].id,
414+
display_date = date,
415+
upstream_identifier = date,
416+
is_soundboard = false,
417+
is_remaster = false,
418+
description = "",
419+
taper_notes = ""
420+
}, ctx);
403421

404-
if (dbSource == null)
405-
{
406-
dbSource = await ProcessShow(stats, artist, date, shows, src,
407-
new Source
408-
{
409-
updated_at = firstShow.updated_at,
410-
artist_id = artist.id,
411-
venue_id = existingVenues[venueUpstreamId].id,
412-
display_date = date,
413-
upstream_identifier = date,
414-
is_soundboard = false,
415-
is_remaster = false,
416-
description = "",
417-
taper_notes = ""
418-
}, ctx);
419-
420-
existingSources[dbSource.upstream_identifier] = dbSource;
422+
existingSources[dbSource.upstream_identifier] = dbSource;
421423

422-
stats.Created++;
424+
stats.Created++;
423425

424-
await linkService.AddLinksForSource(dbSource,
425-
new[]
426+
await linkService.AddLinksForSource(dbSource,
427+
new[]
428+
{
429+
new Link
426430
{
427-
new Link
428-
{
429-
source_id = dbSource.id,
430-
for_ratings = true,
431-
for_source = false,
432-
for_reviews = true,
433-
upstream_source_id = src.upstream_source_id,
434-
url = "http://phish.net/setlists/?d=" + dbSource.display_date,
435-
label = "View on phish.net"
436-
}
437-
});
438-
}
439-
else if (firstShow.updated_at > dbSource.updated_at)
440-
{
441-
dbSource.updated_at = firstShow.updated_at;
442-
dbSource.venue_id = existingVenues[venueUpstreamId].id;
443-
dbSource.display_date = date;
444-
dbSource.upstream_identifier = date;
445-
dbSource.is_soundboard = firstShow.sbd;
446-
dbSource.is_remaster = firstShow.remastered;
447-
dbSource.description = "";
448-
dbSource.taper_notes = "";
449-
450-
dbSource = await ProcessShow(stats, artist, date, shows, src, dbSource, ctx);
431+
source_id = dbSource.id,
432+
for_ratings = true,
433+
for_source = false,
434+
for_reviews = true,
435+
upstream_source_id = src.upstream_source_id,
436+
url = "http://phish.net/setlists/?d=" + dbSource.display_date,
437+
label = "View on phish.net"
438+
}
439+
});
440+
}
441+
else if (firstShow.updated_at > dbSource.updated_at)
442+
{
443+
dbSource.updated_at = firstShow.updated_at;
444+
dbSource.venue_id = existingVenues[venueUpstreamId].id;
445+
dbSource.display_date = date;
446+
dbSource.upstream_identifier = date;
447+
dbSource.is_soundboard = firstShow.sbd;
448+
dbSource.is_remaster = firstShow.remastered;
449+
dbSource.description = "";
450+
dbSource.taper_notes = "";
451451

452-
existingSources[dbSource.upstream_identifier] = dbSource;
452+
dbSource = await ProcessShow(stats, artist, date, shows, src, dbSource, ctx);
453453

454-
stats.Updated++;
455-
}
454+
existingSources[dbSource.upstream_identifier] = dbSource;
456455

457-
scope.Complete();
456+
stats.Updated++;
458457
}
458+
459+
scope.Complete();
459460
}
460461

461462
return stats;

RelistenApi/Services/Importers/PhishinImporter.cs

Lines changed: 53 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -505,65 +505,66 @@ public async Task<ImportStats> ProcessShows(Artist artist, ArtistUpstreamSource
505505

506506
async Task processShow(PhishinShow show)
507507
{
508-
using (var scope = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled))
508+
using var scope = new TransactionScope(TransactionScopeOption.Required,
509+
new TransactionOptions() { IsolationLevel = IsolationLevel.RepeatableRead },
510+
TransactionScopeAsyncFlowOption.Enabled);
511+
512+
var dbSource = existingSources.GetValue(show.id.ToString());
513+
514+
if (dbSource == null)
509515
{
510-
var dbSource = existingSources.GetValue(show.id.ToString());
516+
dbSource = await ProcessShow(stats, artist, show, src,
517+
new Source
518+
{
519+
updated_at = show.updated_at,
520+
artist_id = artist.id,
521+
venue_id = existingVenues[show.venue.id.ToString()].id,
522+
display_date = show.date,
523+
upstream_identifier = show.id.ToString(),
524+
is_soundboard = show.sbd,
525+
is_remaster = show.remastered,
526+
description = "",
527+
taper_notes = show.taper_notes
528+
}, ctx);
529+
530+
existingSources[dbSource.upstream_identifier] = dbSource;
511531

512-
if (dbSource == null)
513-
{
514-
dbSource = await ProcessShow(stats, artist, show, src,
515-
new Source
516-
{
517-
updated_at = show.updated_at,
518-
artist_id = artist.id,
519-
venue_id = existingVenues[show.venue.id.ToString()].id,
520-
display_date = show.date,
521-
upstream_identifier = show.id.ToString(),
522-
is_soundboard = show.sbd,
523-
is_remaster = show.remastered,
524-
description = "",
525-
taper_notes = show.taper_notes
526-
}, ctx);
527-
528-
existingSources[dbSource.upstream_identifier] = dbSource;
529-
530-
stats.Created++;
531-
532-
stats.Created += (await linkService.AddLinksForSource(dbSource,
533-
new[]
534-
{
535-
new Link
536-
{
537-
source_id = dbSource.id,
538-
for_ratings = false,
539-
for_source = true,
540-
for_reviews = false,
541-
upstream_source_id = src.upstream_source_id,
542-
url = $"https://phish.in/{dbSource.display_date}",
543-
label = "View on phish.in"
544-
}
545-
})).Count();
546-
}
547-
else if (show.updated_at > dbSource.updated_at)
548-
{
549-
dbSource.updated_at = show.updated_at;
550-
dbSource.venue_id = existingVenues[show.venue.id.ToString()].id;
551-
dbSource.display_date = show.date;
552-
dbSource.upstream_identifier = show.id.ToString();
553-
dbSource.is_soundboard = show.sbd;
554-
dbSource.is_remaster = show.remastered;
555-
dbSource.description = "";
556-
dbSource.taper_notes = show.taper_notes;
532+
stats.Created++;
557533

558-
dbSource = await ProcessShow(stats, artist, show, src, dbSource, ctx);
534+
stats.Created += (await linkService.AddLinksForSource(dbSource,
535+
new[]
536+
{
537+
new Link
538+
{
539+
source_id = dbSource.id,
540+
for_ratings = false,
541+
for_source = true,
542+
for_reviews = false,
543+
upstream_source_id = src.upstream_source_id,
544+
url = $"https://phish.in/{dbSource.display_date}",
545+
label = "View on phish.in"
546+
}
547+
})).Count();
548+
}
549+
else if (show.updated_at > dbSource.updated_at)
550+
{
551+
dbSource.updated_at = show.updated_at;
552+
dbSource.venue_id = existingVenues[show.venue.id.ToString()].id;
553+
dbSource.display_date = show.date;
554+
dbSource.upstream_identifier = show.id.ToString();
555+
dbSource.is_soundboard = show.sbd;
556+
dbSource.is_remaster = show.remastered;
557+
dbSource.description = "";
558+
dbSource.taper_notes = show.taper_notes;
559559

560-
existingSources[dbSource.upstream_identifier] = dbSource;
560+
dbSource = await ProcessShow(stats, artist, show, src, dbSource, ctx);
561561

562-
stats.Updated++;
563-
}
562+
existingSources[dbSource.upstream_identifier] = dbSource;
564563

565-
scope.Complete();
564+
stats.Updated++;
566565
}
566+
567+
scope.Complete();
567568
}
568569

569570
return stats;

0 commit comments

Comments
 (0)