diff options
author | Chris Schlaeger <chris@linux.com> | 2017-11-11 22:05:12 +0100 |
---|---|---|
committer | Chris Schlaeger <chris@linux.com> | 2017-11-11 22:05:12 +0100 |
commit | 30f754df20e08dd8162cdf5b0df54fba037a719e (patch) | |
tree | 79dc042e3b708a9953ac8d45fa41b0d6cd230472 /lib | |
parent | d3c9294451b0a3c2e47fbf9ce10ed245394babac (diff) | |
download | postrunner-30f754df20e08dd8162cdf5b0df54fba037a719e.zip |
New: Store hash of imported FIT files to speed up import
Garmin devices typically keep older activity FIT files on the device.
Parsing a FIT file can be costly at scale. Postrunner now stores the
MD5 sums of recently importet files and checks against that list
before parsing the FIT file.
Diffstat (limited to 'lib')
-rw-r--r-- | lib/postrunner/FFS_Device.rb | 7 | ||||
-rw-r--r-- | lib/postrunner/FitFileStore.rb | 18 |
2 files changed, 25 insertions, 0 deletions
diff --git a/lib/postrunner/FFS_Device.rb b/lib/postrunner/FFS_Device.rb index 06e1fc8..6ea6890 100644 --- a/lib/postrunner/FFS_Device.rb +++ b/lib/postrunner/FFS_Device.rb @@ -93,6 +93,13 @@ module PostRunner entities << entity entities.sort! + md5sums = @store['fit_file_md5sums'] + md5sums << FitFileStore.calc_md5_sum(fit_file_name) + # We only store the 512 most recently added FIT files. This should be + # more than a device can store. This will allow us to skip the already + # imported FIT files quickly instead of having to parse them each time. + md5sums.shift if md5sums.length > 512 + # Scan the activity for any potential new personal records and register # them. if entity.is_a?(FFS_Activity) diff --git a/lib/postrunner/FitFileStore.rb b/lib/postrunner/FitFileStore.rb index 981da6d..6ee484f 100644 --- a/lib/postrunner/FitFileStore.rb +++ b/lib/postrunner/FitFileStore.rb @@ -10,6 +10,7 @@ # published by the Free Software Foundation. # +require 'digest' require 'fit4ruby' require 'perobs' @@ -54,6 +55,9 @@ module PostRunner # safely to another directory. @store['config']['devices_dir'] = @devices_dir create_directory(@devices_dir, 'devices') + unless @store['fit_file_md5sums'] + @store['fit_file_md5sums'] = @store.new(PEROBS::Array) + end # Define which View objects the HTML output will consist of. This # doesn't really belong in this class but for now it's the best place @@ -76,6 +80,12 @@ module PostRunner # @return [FFS_Activity or FFS_Monitoring] Corresponding entry in the # FitFileStore or nil if file could not be added. def add_fit_file(fit_file_name, fit_entity = nil, overwrite = false) + md5sum = FitFileStore.calc_md5_sum(fit_file_name) + if @store['fit_file_md5sums'].include?(md5sum) + # The FIT file is already stored in the DB. + return nil unless overwrite + end + # If we the file hasn't been read yet, read it in as a # Fit4Ruby::Activity or Fit4Ruby::Monitoring entity. unless fit_entity @@ -420,6 +430,14 @@ module PostRunner puts MonitoringStatistics.new(monitoring_files).monthly(day) end + def FitFileStore::calc_md5_sum(file_name) + begin + Digest::MD5.hexdigest File.read(file_name) + rescue IOError + return 0 + end + end + private def read_fit_file(fit_file_name) |