Class: Snapsync::SyncTarget

Inherits:
Object
  • Object
show all
Defined in:
lib/snapsync/sync_target.rb

Defined Under Namespace

Classes: InvalidTargetPath, InvalidUUIDError, NoUUIDError

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(dir, create_if_needed: true) ⇒ SyncTarget

Returns a new instance of SyncTarget.

Parameters:



44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
# File 'lib/snapsync/sync_target.rb', line 44

def initialize(dir, create_if_needed: true)
    if !dir.directory?
        raise ArgumentError, "#{dir} does not exist"
    end
    @dir = dir

    begin
        read_config
    rescue NoUUIDError
        if !create_if_needed
            raise
        end
        @uuid = SecureRandom.uuid
        @sync_policy = DefaultSyncPolicy.new
        @cleanup = nil
        @enabled = true
        @autoclean = true
        write_config
    end
end

Instance Attribute Details

#cleanupCleanup (readonly)

The cleanup object

Returns:



17
18
19
# File 'lib/snapsync/sync_target.rb', line 17

def cleanup
  @cleanup
end

#dirObject (readonly)

This target’s directory



9
10
11
# File 'lib/snapsync/sync_target.rb', line 9

def dir
  @dir
end

#sync_policyDefaultSyncPolicy (readonly)

The target sync policy

Returns:



13
14
15
# File 'lib/snapsync/sync_target.rb', line 13

def sync_policy
  @sync_policy
end

#uuidString (readonly)

The target’s UUID

Returns:

  • (String)


6
7
8
# File 'lib/snapsync/sync_target.rb', line 6

def uuid
  @uuid
end

Class Method Details

.parse_policy(type, options) ⇒ (#filter_snapshots,#filter_snapshots)

Parse a policy specification as provided on the command line or saved in the config file into sync and cleanup policy objects

Parameters:

  • type (String)

    the policy type, either default, timeline or last

  • options (Array<String>)

    to be passed to the #from_config method on the underlying policy classes

Returns:

  • ((#filter_snapshots,#filter_snapshots))

    the sync policy and the cleanup policy. The cleanup policy might be nil

Raises:

See Also:



142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
# File 'lib/snapsync/sync_target.rb', line 142

def self.parse_policy(type, options)
    case type
    when 'default'
        sync_policy = DefaultSyncPolicy
        cleanup     = nil
    when 'timeline'
        sync_policy = TimelineSyncPolicy
        cleanup     = TimelineSyncPolicy
    when 'last'
        sync_policy = SyncLastPolicy
        cleanup     = SyncLastPolicy
    else
        raise InvalidConfiguration, "synchronization policy '#{type}' does not exist"
    end
    sync_policy = sync_policy.from_config(options)
    cleanup =
        if cleanup
            Cleanup.new(cleanup.from_config(options))
        end
    return sync_policy, cleanup
end

.valid_policy?(type, options) ⇒ Boolean

Verifies that the given policy type and options are valid

Returns:

  • (Boolean)


165
166
167
168
169
170
# File 'lib/snapsync/sync_target.rb', line 165

def self.valid_policy?(type, options)
    parse_policy(type, options)
    true
rescue InvalidConfiguration
    false
end

Instance Method Details

#autoclean?Boolean

Whether the target should be autocleaned on synchronization

Defaults to true

Returns:

  • (Boolean)


33
# File 'lib/snapsync/sync_target.rb', line 33

def autoclean?; !!@autoclean end

#change_policy(type, options) ⇒ Object



172
173
174
175
# File 'lib/snapsync/sync_target.rb', line 172

def change_policy(type, options)
    @sync_policy, @cleanup =
        self.class.parse_policy(type, options)
end

#config_pathPathname

Path to the target’s configuration file

Returns:



127
128
129
# File 'lib/snapsync/sync_target.rb', line 127

def config_path
    dir + "snapsync.config"
end

#delete(s, dry_run: false) ⇒ Object

Parameters:



178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
# File 'lib/snapsync/sync_target.rb', line 178

def delete(s, dry_run: false)
    btrfs = Btrfs.get(s.subvolume_dir)

    Snapsync.info "Removing snapshot #{s.num} #{s.date.to_time} at #{s.subvolume_dir}"
    return if dry_run

    begin
        btrfs.run("subvolume", "delete", s.subvolume_dir.path_part)
    rescue Btrfs::Error
        Snapsync.warn "failed to remove snapshot at #{s.subvolume_dir}, keeping the rest of the snapshot"
        return
    end

    s.snapshot_dir.rmtree
end

#descriptionObject



39
40
41
# File 'lib/snapsync/sync_target.rb', line 39

def description
    "local:#{dir}"
end

#disableObject

Disable this target, i.e. remove it from the auto synchronization and cleanup commands



28
# File 'lib/snapsync/sync_target.rb', line 28

def disable; @enabled = false; self end

#each_snapshot {|snapshot| ... } ⇒ Object

Yield Parameters:



70
71
72
# File 'lib/snapsync/sync_target.rb', line 70

def each_snapshot(&block)
    Snapshot.each(dir, &block)
end

#each_snapshot_raw(&block) ⇒ Object



65
66
67
# File 'lib/snapsync/sync_target.rb', line 65

def each_snapshot_raw(&block)
    Snapshot.each_snapshot_raw(dir, &block)
end

#enableObject

Enable this target, i.e. add it to the auto synchronization and cleanup commands



24
# File 'lib/snapsync/sync_target.rb', line 24

def enable; @enabled = true; self end

#enabled?Boolean

Whether this target is enabled or not

Returns:

  • (Boolean)


20
# File 'lib/snapsync/sync_target.rb', line 20

def enabled?; @enabled end

#parse_config(config) ⇒ Object



106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
# File 'lib/snapsync/sync_target.rb', line 106

def parse_config(config)
    uuid = config['uuid']
    if uuid.length != 36
        raise InvalidUUIDError, "uuid in #{uuid_path} was expected to be 36 characters long, but is #{uuid.length}"
    end
    @uuid = uuid

    @enabled = config.fetch('enabled', true)
    @autoclean = config.fetch('autoclean', true)

    if policy_config = config['policy']
        change_policy(policy_config['type'], policy_config['options'] || Array.new)
    else
        @sync_policy = DefaultSyncPolicy.new
        @cleanup = nil
    end
end

#read_configObject



93
94
95
96
97
98
99
100
101
102
103
104
# File 'lib/snapsync/sync_target.rb', line 93

def read_config
    Snapsync.debug "SyncTarget #{dir} read_config"
    begin
        if !(raw_config = YAML.load(config_path.read))
            raise NoUUIDError, "empty configuration file found in #{config_path}"
        end

    rescue Errno::ENOENT => e
        raise NoUUIDError, e.message, e.backtrace
    end
    parse_config(raw_config)
end

#write_configObject



74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
# File 'lib/snapsync/sync_target.rb', line 74

def write_config
    Snapsync.debug "SyncTarget #{dir} write_config"
    config = Hash['uuid' => uuid, 'policy' => Hash.new]
    config['policy']['type'] =
        case sync_policy
        when TimelineSyncPolicy then 'timeline'
        when SyncLastPolicy then 'last'
        when DefaultSyncPolicy then 'default'
        end
    config['policy']['options'] =
        sync_policy.to_config
    config['enabled'] = enabled?
    config['autoclean'] = autoclean?

    config_path.open('w') do |io|
        YAML.dump(config, io)
    end
end