Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rename and recreate un-initialized cycle file instead of overwriting #1314

Merged
merged 2 commits into from
Mar 10, 2023

Conversation

alamar
Copy link
Contributor

@alamar alamar commented Mar 7, 2023

closes #1313

@@ -70,6 +67,7 @@
public class SingleChronicleQueue extends AbstractCloseable implements RollingChronicleQueue {

public static final String SUFFIX = ".cq4";
public static final String DISCARD_FILE_SUFFIX = ".discard";

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would suggest a sequence or timestamp-based decoration is a better/more flexible option

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Timestamp-based decoraton means we may copy a single cycle an arbitrary number of times, which in case of high performance system might as well be tens of thousands times which will exhaust inodes and-or current directory files limit. That's why I advise we use predictable discard name and avoid this issue entirely. If it's not successful after first try it's probably too dangerous to continue - what do you think @rogersimmons ?

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, I agree with the concern, and it is something we should be in a position to mitigate.
Having a sequence/time-based decoration helps rather than impedes that, and at the same time gives us more control options in future if needed

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't know how we could mitigate this right now, whereas the current solution is indeed limited but is predictable and completely understood, and we can reason about its behavior.

I suggest that maybe we add time-based decoration together with the change that protects about creating the same cycle file unbounded number of times.

@alamar alamar requested a review from rogersimmons March 8, 2023 09:16
@@ -108,7 +106,7 @@ public void appropriateExceptionIsThrownWhenLockCannotBeAcquiredForRecovery() th
assertTrue(readingDocument.isPresent());
}
}
assertThrows(IOException.class, tailer::readingDocument);
assertEquals(false, tailer.readingDocument().isPresent());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

perhaps rename the test also (now an exception is not thrown)

// Rename un-acquirable segment file to make sure no data is lost to try and recreate the segment
private boolean backupCycleFile(File cycleFile) {
File cycleFileDiscard = new File(cycleFile.getParentFile(), cycleFile.getName() + DISCARD_FILE_SUFFIX);
boolean success = cycleFile.renameTo(cycleFileDiscard);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it possible that multiple processes get here and think they moved the existing file (i.e is the move atomic), and would that cause chaos later if they both attempted to create the replacement file? I notice Files.move allows you to specify an atomic move (and define the behaviour when an existing file is there), not sure if that would be more appropriate here.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Only one of these process succeeds and this one gets to recreate the file from scratch - other ones retry opening this file without createIfAbsent flag. I find the behavior of File.renameTo() more consistent than the described atomic move, but when we rename file in the current directory it should almost always be atomic yes or no operation.

Copy link
Contributor

@nicktindall nicktindall left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approved pending resolution of the discussion around timestamped backups

@sonarcloud
Copy link

sonarcloud bot commented Mar 10, 2023

Kudos, SonarCloud Quality Gate passed!    Quality Gate passed

Bug A 0 Bugs
Vulnerability A 0 Vulnerabilities
Security Hotspot A 0 Security Hotspots
Code Smell A 0 Code Smells

80.0% 80.0% Coverage
0.0% 0.0% Duplication

@alamar alamar merged commit 4d02a90 into develop Mar 10, 2023
@alamar alamar deleted the Queue1313 branch March 10, 2023 14:43
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants