sifttter-redux 0.5.4 → 0.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/.travis.yml +5 -1
- data/Gemfile +1 -0
- data/Rakefile +78 -25
- data/bin/srd +74 -63
- data/features/1.ui.feature +7 -0
- data/features/2.initialization.feature +130 -0
- data/features/step_definitions/sifttter-redux_steps.rb +19 -0
- data/features/support/env.rb +20 -0
- data/lib/sifttter-redux/constants.rb +33 -0
- data/lib/{sifttter_redux/date_range_maker.rb → sifttter-redux/date-range-maker.rb} +23 -47
- data/lib/sifttter-redux/dropbox-uploader.rb +64 -0
- data/lib/{sifttter_redux → sifttter-redux}/sifttter.rb +16 -21
- data/lib/sifttter-redux.rb +164 -0
- data/res/preference_prompts.yaml +17 -0
- data/{sifttter_redux.gemspec → sifttter-redux.gemspec} +2 -1
- data/test/date_range_maker_test.rb +1 -1
- data/tmp/srd/.dropbox_uploader +0 -0
- data/tmp/srd/.sifttter_redux +13 -0
- data/tmp/srd/.sifttter_redux_log +10 -0
- metadata +34 -14
- data/lib/sifttter_redux/cli_message.rb +0 -270
- data/lib/sifttter_redux/configuration.rb +0 -89
- data/lib/sifttter_redux/dropbox_uploader.rb +0 -77
- data/lib/sifttter_redux/version.rb +0 -6
- data/lib/sifttter_redux.rb +0 -218
- data/test/cli_message_test.rb +0 -54
- data/test/configuration_test.rb +0 -78
@@ -0,0 +1,19 @@
|
|
1
|
+
Given(/^a file located at "(.*?)"$/) do |filepath|
|
2
|
+
expect(File).to exist(filepath)
|
3
|
+
end
|
4
|
+
|
5
|
+
Given(/^an empty file located at "(.*?)"$/) do |filepath|
|
6
|
+
FileUtils.touch(File.expand_path(filepath))
|
7
|
+
end
|
8
|
+
|
9
|
+
Given(/^a file located at "(.*?)" with the contents:$/) do |filepath, contents|
|
10
|
+
File.open(filepath, 'w') { |f| f.write(contents) }
|
11
|
+
end
|
12
|
+
|
13
|
+
Given(/^no file located at "(.*?)"$/) do |filepath|
|
14
|
+
step %(the file "#{ filepath }" should not exist)
|
15
|
+
end
|
16
|
+
|
17
|
+
When /^I get help for "([^"]*)"$/ do |app_name|
|
18
|
+
step %(I run `#{app_name} --help`)
|
19
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require 'aruba/cucumber'
|
2
|
+
|
3
|
+
ENV['PATH'] = "#{File.expand_path(File.dirname(__FILE__) + '/../../bin')}#{File::PATH_SEPARATOR}#{ENV['PATH']}"
|
4
|
+
LIB_DIR = File.join(File.expand_path(File.dirname(__FILE__)),'..','..','lib')
|
5
|
+
|
6
|
+
Before do
|
7
|
+
@aruba_timeout_seconds = 25
|
8
|
+
@puts = true
|
9
|
+
@original_rubylib = ENV['RUBYLIB']
|
10
|
+
ENV['RUBYLIB'] = LIB_DIR + File::PATH_SEPARATOR + ENV['RUBYLIB'].to_s
|
11
|
+
@original_home = ENV['HOME']
|
12
|
+
ENV['HOME'] = "/tmp/srd"
|
13
|
+
FileUtils.rm_rf "/tmp/srd"
|
14
|
+
FileUtils.mkdir "/tmp/srd"
|
15
|
+
end
|
16
|
+
|
17
|
+
After do
|
18
|
+
ENV['RUBYLIB'] = @original_rubylib
|
19
|
+
ENV['HOME'] = @original_home
|
20
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
module SifttterRedux
|
2
|
+
# The default configuration path for Dropbox Uploader
|
3
|
+
DEFAULT_DBU_CONFIG_FILEPATH = File.join(ENV['HOME'], '.dropbox_uploader')
|
4
|
+
|
5
|
+
# The default local filepath of the Dropbox-Uploader directory
|
6
|
+
DEFAULT_DBU_LOCAL_FILEPATH = '/usr/local/opt'
|
7
|
+
|
8
|
+
# The default message to display when Dropbox Uploader is running
|
9
|
+
DEFAULT_DBU_MESSAGE = 'RUNNING DROPBOX UPLOADER'
|
10
|
+
|
11
|
+
# The default local filepath of the Siftter Redux config file
|
12
|
+
DEFAULT_SRD_CONFIG_FILEPATH = File.join(ENV['HOME'], '.sifttter_redux')
|
13
|
+
|
14
|
+
# The default local filepath of the Siftter Redux log file
|
15
|
+
DEFAULT_SRD_LOG_FILEPATH = File.join(ENV['HOME'], '.sifttter_redux_log')
|
16
|
+
|
17
|
+
# The Gem's description
|
18
|
+
DESCRIPTION = 'A customized IFTTT-to-Day One service that allows for smart installation and automated running on a standalone *NIX device (such as a Raspberry Pi).'
|
19
|
+
|
20
|
+
# The last version to require a config update
|
21
|
+
NEWEST_CONFIG_VERSION = '0.6'
|
22
|
+
|
23
|
+
# Hash of preference files
|
24
|
+
PREF_FILES = {
|
25
|
+
'INIT' => File.join(File.dirname(__FILE__), '..', '..', 'res/preference_prompts.yaml')
|
26
|
+
}
|
27
|
+
|
28
|
+
# The Gem's summary
|
29
|
+
SUMMARY = 'Automated IFTTT to Day One engine.'
|
30
|
+
|
31
|
+
# The Gem's version
|
32
|
+
VERSION = '0.6'
|
33
|
+
end
|
@@ -1,23 +1,15 @@
|
|
1
1
|
require 'chronic'
|
2
2
|
|
3
3
|
module SifttterRedux
|
4
|
-
#
|
5
|
-
#
|
6
|
-
#
|
7
|
-
# Manages any configuration values and the flat file
|
8
|
-
# into which they get stored.
|
9
|
-
# ======================================================
|
4
|
+
# DateRangeMaker Module
|
5
|
+
# Returns a Range of dates based on supplied parameters
|
10
6
|
module DateRangeMaker
|
11
7
|
|
12
|
-
#
|
13
|
-
#
|
14
|
-
#
|
15
|
-
#
|
16
|
-
#
|
17
|
-
# @param num_days The number of days to look back
|
18
|
-
# @param include_today Should today be included?
|
19
|
-
# @return Range
|
20
|
-
# ------------------------------------------------------
|
8
|
+
# Returns a date range for the last N days (including
|
9
|
+
# today's date if specified).
|
10
|
+
# @param [Integer} num_days The number of days to look back
|
11
|
+
# @param [Boolean] include_today Should today be included?
|
12
|
+
# @return [Range]
|
21
13
|
def self.last_n_days(num_days, include_today = false)
|
22
14
|
if num_days < 0
|
23
15
|
error = 'Cannot specify a negative number of days'
|
@@ -31,15 +23,11 @@ module SifttterRedux
|
|
31
23
|
end
|
32
24
|
end
|
33
25
|
|
34
|
-
#
|
35
|
-
#
|
36
|
-
#
|
37
|
-
#
|
38
|
-
#
|
39
|
-
# @param num_days The number of weeks to look back
|
40
|
-
# @param include_today Should today be included?
|
41
|
-
# @return Range
|
42
|
-
# ------------------------------------------------------
|
26
|
+
# Returns a date range for the last N weeks (including
|
27
|
+
# today's date if specified).
|
28
|
+
# @param [Integer] num_days The number of weeks to look back
|
29
|
+
# @param [Boolean] include_today Should today be included?
|
30
|
+
# @return [Range]
|
43
31
|
def self.last_n_weeks(num_weeks = 0, include_today = false)
|
44
32
|
if num_weeks < 0
|
45
33
|
error = 'Cannot specify a negative number of weeks'
|
@@ -60,17 +48,13 @@ module SifttterRedux
|
|
60
48
|
end
|
61
49
|
end
|
62
50
|
|
63
|
-
#
|
64
|
-
#
|
65
|
-
#
|
66
|
-
#
|
67
|
-
#
|
68
|
-
#
|
69
|
-
#
|
70
|
-
# @param end_date The end date
|
71
|
-
# @param options Miscellaneous options hash
|
72
|
-
# @return Range
|
73
|
-
# ------------------------------------------------------
|
51
|
+
# Returns a date range for specified start dates and
|
52
|
+
# end dates. Note that specifying an end date greater
|
53
|
+
# than today's date will force today to be the end date.
|
54
|
+
# @param [Start] start_date The start date
|
55
|
+
# @param [Date] end_date The end date
|
56
|
+
# @param [Hash] options Miscellaneous options
|
57
|
+
# @return [Range]
|
74
58
|
def self.range(start_date, end_date, include_today = false)
|
75
59
|
if start_date.nil? && !end_date.nil?
|
76
60
|
error = "You can't specify -t without specifying -f"
|
@@ -115,22 +99,14 @@ module SifttterRedux
|
|
115
99
|
end
|
116
100
|
end
|
117
101
|
|
118
|
-
#
|
119
|
-
#
|
120
|
-
#
|
121
|
-
# Returns a date range for today
|
122
|
-
# @return Range
|
123
|
-
# ------------------------------------------------------
|
102
|
+
# Returns a date range for today
|
103
|
+
# @return [Range]
|
124
104
|
def self.today
|
125
105
|
(Date.today..Date.today)
|
126
106
|
end
|
127
107
|
|
128
|
-
#
|
129
|
-
#
|
130
|
-
#
|
131
|
-
# Returns a date range for yesterday
|
132
|
-
# @return Range
|
133
|
-
# ------------------------------------------------------
|
108
|
+
# Returns a date range for yesterday
|
109
|
+
# @return [Range]
|
134
110
|
def self.yesterday
|
135
111
|
(Date.today - 1..Date.today - 1)
|
136
112
|
end
|
@@ -0,0 +1,64 @@
|
|
1
|
+
module SifttterRedux
|
2
|
+
# DropboxUploader Class
|
3
|
+
# Wrapper class for the Dropbox Uploader project
|
4
|
+
class DropboxUploader
|
5
|
+
# Stores the local filepath.
|
6
|
+
# @return [String]
|
7
|
+
attr_accessor :local_target
|
8
|
+
|
9
|
+
# Stores the remote filepath.
|
10
|
+
# @return [String]
|
11
|
+
attr_accessor :remote_target
|
12
|
+
|
13
|
+
# Stores the message to display.
|
14
|
+
# @return [String]
|
15
|
+
attr_accessor :message
|
16
|
+
|
17
|
+
# Stores the verbosity level.
|
18
|
+
# @return [Boolean]
|
19
|
+
attr_accessor :verbose
|
20
|
+
|
21
|
+
# Loads the location of dropbox_uploader.sh.
|
22
|
+
# @param [String] dbu_path The local filepath to the script
|
23
|
+
# @param [Logger] A Logger to use
|
24
|
+
# @return [void]
|
25
|
+
def initialize(dbu_path, logger = nil)
|
26
|
+
@dbu = dbu_path
|
27
|
+
@logger = logger
|
28
|
+
end
|
29
|
+
|
30
|
+
# Downloads files from Dropbox (assumes that both
|
31
|
+
# local_target and remote_target have been set).
|
32
|
+
# @return [void]
|
33
|
+
def download
|
34
|
+
if !@local_target.nil? && !@remote_target.nil?
|
35
|
+
if @verbose
|
36
|
+
system "#{ @dbu } download #{ @remote_target } #{ @local_target }"
|
37
|
+
else
|
38
|
+
exec = `#{ @dbu } download #{ @remote_target } #{ @local_target }`
|
39
|
+
end
|
40
|
+
else
|
41
|
+
error_msg = 'Local and remote targets cannot be nil'
|
42
|
+
@logger.error(error_msg) if @logger
|
43
|
+
fail StandardError, error_msg
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
# Uploads files tro Dropbox (assumes that both
|
48
|
+
# local_target and remote_target have been set).
|
49
|
+
# @return [void]
|
50
|
+
def upload
|
51
|
+
if !@local_target.nil? && !@remote_target.nil?
|
52
|
+
if @verbose
|
53
|
+
system "#{ @dbu } upload #{ @local_target } #{ @remote_target }"
|
54
|
+
else
|
55
|
+
exec = `#{ @dbu } upload #{ @local_target } #{ @remote_target }`
|
56
|
+
end
|
57
|
+
else
|
58
|
+
error_msg = 'Local and remote targets cannot be nil'
|
59
|
+
@logger.error(error_msg) if @logger
|
60
|
+
fail StandardError, error_msg
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
64
|
+
end
|
@@ -1,20 +1,13 @@
|
|
1
1
|
module SifttterRedux
|
2
|
-
#
|
3
|
-
#
|
4
|
-
#
|
5
|
-
# Wrapper module for Sifttter itself
|
6
|
-
# ======================================================
|
2
|
+
# Sifttter Module
|
3
|
+
# Wrapper module for Sifttter itself
|
7
4
|
module Sifttter
|
8
|
-
#
|
9
|
-
# run_sifttter method
|
5
|
+
# Modified form of Sifttter
|
10
6
|
#
|
11
|
-
#
|
12
|
-
#
|
13
|
-
#
|
14
|
-
#
|
15
|
-
# @param date The date to use when scanning Sifttter
|
16
|
-
# @return Void
|
17
|
-
# ----------------------------------------------------
|
7
|
+
# Sifttter: An IFTTT-to-Day One Logger by Craig Eley
|
8
|
+
# Based on tp-dailylog.rb by Brett Terpstra 2012
|
9
|
+
# @param [Date] date The date to use when scanning Sifttter
|
10
|
+
# @return [void]
|
18
11
|
def self.run(date)
|
19
12
|
uuid = SecureRandom.uuid.upcase.gsub(/-/, '').strip
|
20
13
|
|
@@ -46,10 +39,12 @@ module SifttterRedux
|
|
46
39
|
date_regex = "(?:#{ date.strftime("%B") } 0?#{ date.strftime("%-d") }, #{ date.strftime("%Y") })"
|
47
40
|
time_regex = "(?:\d{1,2}:\d{1,2}\s?[AaPpMm]{2})"
|
48
41
|
|
49
|
-
files = `find #{
|
42
|
+
files = `find #{ configuration.sifttter_redux[:sifttter_local_filepath] } -type f -name "*.txt" | grep -v -i daily | sort`
|
50
43
|
if files.empty?
|
51
|
-
|
52
|
-
|
44
|
+
messenger.error('No Sifttter files to parse...')
|
45
|
+
messenger.error('Is Dropbox Uploader configured correctly?')
|
46
|
+
messenger.error("Is #{ configuration.sifttter_redux[:sifttter_remote_filepath] } the correct remote filepath?")
|
47
|
+
exit!(1)
|
53
48
|
end
|
54
49
|
|
55
50
|
projects = []
|
@@ -77,7 +72,7 @@ module SifttterRedux
|
|
77
72
|
end
|
78
73
|
|
79
74
|
if projects.length <=0
|
80
|
-
|
75
|
+
messenger.warn('No entries found...')
|
81
76
|
end
|
82
77
|
|
83
78
|
if projects.length > 0
|
@@ -86,12 +81,12 @@ module SifttterRedux
|
|
86
81
|
entrytext += project.gsub(/.txt/, ' ') + "\n\n"
|
87
82
|
end
|
88
83
|
|
89
|
-
Dir.mkdir(
|
84
|
+
Dir.mkdir(configuration.sifttter_redux[:dayone_local_filepath]) if !Dir.exists?(configuration.sifttter_redux[:dayone_local_filepath])
|
90
85
|
|
91
|
-
fh = File.new(File.expand_path(
|
86
|
+
fh = File.new(File.expand_path(configuration.sifttter_redux[:dayone_local_filepath] + '/' + uuid + '.doentry'), 'w+')
|
92
87
|
fh.puts template.result(binding)
|
93
88
|
fh.close
|
94
|
-
|
89
|
+
messenger.success("Entry logged for #{ date_for_title }...")
|
95
90
|
end
|
96
91
|
end
|
97
92
|
end
|
@@ -0,0 +1,164 @@
|
|
1
|
+
require 'sifttter-redux/constants'
|
2
|
+
require 'sifttter-redux/date-range-maker'
|
3
|
+
require 'sifttter-redux/dropbox-uploader'
|
4
|
+
require 'sifttter-redux/sifttter'
|
5
|
+
|
6
|
+
# The SifttterRedux module, which wraps everything
|
7
|
+
# in this gem.
|
8
|
+
module SifttterRedux
|
9
|
+
|
10
|
+
class << self
|
11
|
+
# Stores whether initalization has completed.
|
12
|
+
# @return [Boolean]
|
13
|
+
attr_reader :initialized
|
14
|
+
|
15
|
+
# Stores whether verbose output is turned on.
|
16
|
+
# @return [Boolean]
|
17
|
+
attr_accessor :verbose
|
18
|
+
end
|
19
|
+
|
20
|
+
# Removes temporary directories and their contents
|
21
|
+
# @return [void]
|
22
|
+
def self.cleanup_temp_files
|
23
|
+
dirs = [
|
24
|
+
configuration.sifttter_redux[:dayone_local_filepath],
|
25
|
+
configuration.sifttter_redux[:sifttter_local_filepath]
|
26
|
+
]
|
27
|
+
|
28
|
+
messenger.info_block('Removing temporary local files...') do
|
29
|
+
dirs.each do |d|
|
30
|
+
FileUtils.rm_rf(d)
|
31
|
+
messenger.debug("Removed directory: #{ d }")
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
# Runs a wizard that installs Dropbox Uploader on the
|
37
|
+
# local filesystem.
|
38
|
+
# @param [Boolean] from_scratch
|
39
|
+
# @return [void]
|
40
|
+
def self.dbu_install_wizard(from_scratch = false)
|
41
|
+
valid_path_chosen = false
|
42
|
+
|
43
|
+
messenger.section_block('CONFIGURING DROPBOX UPLOADER...') do
|
44
|
+
until valid_path_chosen
|
45
|
+
# Prompt the user for a location to save Dropbox Uploader.
|
46
|
+
if from_scratch && !configuration.db_uploader[:base_filepath].nil?
|
47
|
+
default = configuration.db_uploader[:base_filepath]
|
48
|
+
else
|
49
|
+
default = DEFAULT_DBU_LOCAL_FILEPATH
|
50
|
+
end
|
51
|
+
path = messenger.prompt('Location for Dropbox-Uploader', default)
|
52
|
+
path = default if path.empty?
|
53
|
+
path.chop! if path.end_with?('/')
|
54
|
+
|
55
|
+
# If the entered directory exists, clone the repository.
|
56
|
+
if Dir.exists?(File.expand_path(path))
|
57
|
+
valid_path_chosen = true
|
58
|
+
|
59
|
+
dbu_path = File.join(path, 'Dropbox-Uploader')
|
60
|
+
executable_path = File.join(dbu_path, 'dropbox_uploader.sh')
|
61
|
+
|
62
|
+
if File.directory?(dbu_path)
|
63
|
+
messenger.warn("Using pre-existing Dropbox Uploader at #{ dbu_path }...")
|
64
|
+
else
|
65
|
+
messenger.info_block("Downloading Dropbox Uploader to #{ dbu_path }...", 'Done.', true) do
|
66
|
+
system "git clone https://github.com/andreafabrizi/Dropbox-Uploader.git #{ dbu_path }"
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
# If the user has never configured Dropbox Uploader, have them do it here.
|
71
|
+
unless File.exists?(DEFAULT_DBU_CONFIG_FILEPATH)
|
72
|
+
messenger.info_block('Initializing Dropbox Uploader...') { system "#{ executable_path }" }
|
73
|
+
end
|
74
|
+
|
75
|
+
configuration.add_section(:db_uploader) unless configuration.data.key?(:db_uploader)
|
76
|
+
configuration.db_uploader.merge!({
|
77
|
+
base_filepath: path,
|
78
|
+
dbu_filepath: dbu_path,
|
79
|
+
exe_filepath: executable_path
|
80
|
+
})
|
81
|
+
else
|
82
|
+
messenger.error("Sorry, but #{ path } isn't a valid directory.")
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
# Creates a date range from the supplied command line
|
89
|
+
# options.
|
90
|
+
# @param [Hash] options GLI command line options
|
91
|
+
# @return [Range]
|
92
|
+
def self.get_dates_from_options(options)
|
93
|
+
messenger.section_block('EXECUTING...') do
|
94
|
+
if options[:c] || options[:n] || options[:w] || options[:y] || options[:f] || options[:t]
|
95
|
+
# Yesterday
|
96
|
+
r = DateRangeMaker.yesterday if options[:y]
|
97
|
+
|
98
|
+
# Current Week
|
99
|
+
r = DateRangeMaker.last_n_weeks(0, options[:i]) if options[:c]
|
100
|
+
|
101
|
+
# Last N Days
|
102
|
+
r = DateRangeMaker.last_n_days(options[:n].to_i, options[:i]) if options[:n]
|
103
|
+
|
104
|
+
# Last N Weeks
|
105
|
+
r = DateRangeMaker.last_n_weeks(options[:w].to_i, options[:i]) if options[:w]
|
106
|
+
|
107
|
+
# Custom Range
|
108
|
+
if (options[:f] || options[:t])
|
109
|
+
_dates = DateRangeMaker.range(options[:f], options[:t], options[:i])
|
110
|
+
|
111
|
+
if _dates.last > Date.today
|
112
|
+
long_message = "Ignoring overextended end date and using today's date (#{ Date.today })..."
|
113
|
+
messenger.warn(long_message)
|
114
|
+
r = (_dates.first..Date.today)
|
115
|
+
else
|
116
|
+
r = (_dates.first.._dates.last)
|
117
|
+
end
|
118
|
+
end
|
119
|
+
else
|
120
|
+
r = DateRangeMaker.today
|
121
|
+
end
|
122
|
+
|
123
|
+
messenger.debug("Date range: #{ r }")
|
124
|
+
r
|
125
|
+
end
|
126
|
+
end
|
127
|
+
|
128
|
+
# Initializes Sifttter Redux by downloading and
|
129
|
+
# collecting all necessary items and info.
|
130
|
+
# @param [Boolean] from_scratch
|
131
|
+
# @return [void]
|
132
|
+
def self.init(from_scratch = false)
|
133
|
+
if from_scratch
|
134
|
+
configuration.reset
|
135
|
+
configuration.add_section(:sifttter_redux)
|
136
|
+
end
|
137
|
+
|
138
|
+
configuration.sifttter_redux.merge!({
|
139
|
+
config_location: configuration.config_path,
|
140
|
+
log_level: 'WARN',
|
141
|
+
version: SifttterRedux::VERSION,
|
142
|
+
})
|
143
|
+
|
144
|
+
# Run the wizard to download Dropbox Uploader.
|
145
|
+
dbu_install_wizard(from_scratch = from_scratch)
|
146
|
+
|
147
|
+
pm = CLIUtils::Prefs.new(SifttterRedux::PREF_FILES['INIT'], configuration)
|
148
|
+
pm.ask
|
149
|
+
configuration.ingest_prefs(pm)
|
150
|
+
|
151
|
+
messenger.debug { "Configuration values after pref collection: #{ configuration.data }" }
|
152
|
+
configuration.save
|
153
|
+
@initialized = true
|
154
|
+
end
|
155
|
+
|
156
|
+
# Notifies the user that the config file needs to be
|
157
|
+
# re-done and does it.
|
158
|
+
# @return [void]
|
159
|
+
def self.update_config_file
|
160
|
+
messenger.info("This version needs to make some config changes. Don't worry; when prompted, your current values for existing config options will be presented (so it'll be easier to fly through the upgrade).")
|
161
|
+
messenger.prompt('Press enter to continue')
|
162
|
+
SifttterRedux.init(true)
|
163
|
+
end
|
164
|
+
end
|