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

nsq_to_file: cleanup #1117

Merged
merged 6 commits into from
Jan 5, 2019
Merged

Conversation

mreiferson
Copy link
Member

@mreiferson mreiferson commented Jan 3, 2019

I've long been frustrated with nsq_to_file's codebase, and didn't want to schlep it off onto @mccutchen in #1110, so here goes.

@mreiferson
Copy link
Member Author

(individual commits are probably easier to review than the combined diff)

@mreiferson mreiferson force-pushed the nsq_to_file-cleanup branch 2 times, most recently from 5805d68 to 5c1c4eb Compare January 3, 2019 18:20
@mreiferson
Copy link
Member Author

mreiferson commented Jan 4, 2019

Fixes #880 in 3cbdbe4

@mreiferson mreiferson force-pushed the nsq_to_file-cleanup branch 2 times, most recently from 7c316a2 to 3cbdbe4 Compare January 4, 2019 00:57
@mreiferson
Copy link
Member Author

I think I'm done here, still passes @mccutchen's nice "jepsen lite" test program.

@ploxiln
Copy link
Member

ploxiln commented Jan 4, 2019

All looks pretty good to me.

I guess you probably plan to squash all commits down before merge, but otherwise I see some runs of commits that could be squashed together, leaving 5 or so commits in the sequence that could be merged.

@mreiferson
Copy link
Member Author

I guess you probably plan to squash all commits down before merge

Hah, I wasn't. So I'm all ears to how you think this should be squashed.

@mreiferson
Copy link
Member Author

@jehiah you might be particularly interested in deb7c33

@ploxiln
Copy link
Member

ploxiln commented Jan 4, 2019

If you want my 2c on how to squash, sure ;)

Leave as-is:

  • nsq_to_file: move to go-options; pass Options struct around
  • nsq_to_file: cleanup startup

FileLogger refactor commits could be squashed:

  • nsq_to_file: remove redundant closing var
  • nsq_to_file: cleanup variable names/cfl responsibilities
  • nsq_to_file: drop ConsumerFileLogger; refactor FileLogger

FileLogger cleanup/rename commits could be squashed:

  • nsq_to_file: un-indent FileLogger.Close()
  • nsq_to_file: s/atomicRename/exclusiveRename
  • nsq_to_file: drop superfluous makeOutputPath
  • nsq_to_file: cleanup FileLogger var names
  • nsq_to_file: dead return; whitespace cleanup
  • nsq_to_file: s/needsFileRotate/needsRotation
  • nsq_to_file: s/makeOutputDir/makeDirFromPath

Leave as-is:

  • nsq_to_file: don't open multiple GZIP streams

Gzip/Sync commits could be squashed:

  • nsq_to_file: fsync after GZIP close
  • nsq_to_file: check and exit on errors for file-related operations

Leave as-is:

  • nsq_to_file: refactor confusing Write interface

Finally, logging commits at the end can be squashed

This changes the structure of output files to be continuous GZIP
streams rather than concatenated GZIP streams.

This is likely slightly more compatible and expected.
For ordering correctness, this ensures that any pending GZIP
data is written _before_ the fsync, but is unlikely to
matter under normal operation.

Also check and exit on errors for file-related operations in Close()
@mreiferson mreiferson force-pushed the nsq_to_file-cleanup branch from bea47f3 to 2feed06 Compare January 4, 2019 21:28
@mreiferson
Copy link
Member Author

squashed 💪

@mreiferson mreiferson merged commit cf4a8c8 into nsqio:master Jan 5, 2019
@mreiferson mreiferson deleted the nsq_to_file-cleanup branch January 5, 2019 00:02
f.writer = f.gzipWriter
} else {
err = f.out.Sync()
err := f.gzipWriter.Flush()
Copy link
Member

Choose a reason for hiding this comment

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

I think i'm 👎on this switch, but I acknowledge that it is possible to encounter unexpected issues with a stream of indipendent gzip chunks (i.e. equiv to cat file1.gz file2.gz).

Without separate gzip streams, recovering from a corrupt file (kill -9 w/ partial data written but not sync'd) becomes problematic.

I think it comes down to the fact that Flush does not write a gzip footer which has the checksum. Close does.

Copy link
Member Author

Choose a reason for hiding this comment

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

Unless I’m misunderstanding something, the recoverable section would be equivalent in either case (bound by the configured sync interval)?

You’re suggesting that by writing out closing footers somehow more data would be recoverable? Given gzip’s streamable quality, I assume that a complete block (regardless of a closed stream) would be decompressable?

Copy link
Member

@jehiah jehiah Jan 5, 2019

Choose a reason for hiding this comment

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

I assume that a complete block (regardless of a closed stream) would be decompressable?

decompressable yes, error checkable no. The footer contains the final crc for a stream which you don't get from a sync()

https://www.forensicswiki.org/wiki/Gzip#File_footer

recoverability

With separate streams for each logical sync, I've found it easy to step through the streams of a file (using compress/gzip.Reader.Multistream) and use the valid streams to recover a corrupt file. When you don't have a stream boundary recovery is less precise because you can't disambiguate between written but not sync'd data and written and sync'd data. That increases the risk of including records that were never ack'd back to nsqd which isn't desirable.

Copy link
Member Author

Choose a reason for hiding this comment

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

Nice, that feels like a strong argument to revert, thanks.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants