cfn-vpn 0.5.1 → 1.1.0

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.
Files changed (42) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/build-gem.yml +25 -0
  3. data/.github/workflows/release-gem.yml +31 -0
  4. data/.github/workflows/release-image.yml +33 -0
  5. data/Gemfile.lock +30 -38
  6. data/README.md +1 -247
  7. data/cfn-vpn.gemspec +3 -2
  8. data/docs/README.md +44 -0
  9. data/docs/certificate-users.md +89 -0
  10. data/docs/getting-started.md +87 -0
  11. data/docs/modifying.md +67 -0
  12. data/docs/routes.md +82 -0
  13. data/docs/scheduling.md +32 -0
  14. data/docs/sessions.md +27 -0
  15. data/lib/cfnvpn.rb +31 -27
  16. data/lib/cfnvpn/{client.rb → actions/client.rb} +5 -6
  17. data/lib/cfnvpn/{embedded.rb → actions/embedded.rb} +15 -15
  18. data/lib/cfnvpn/actions/init.rb +130 -0
  19. data/lib/cfnvpn/actions/modify.rb +149 -0
  20. data/lib/cfnvpn/actions/params.rb +73 -0
  21. data/lib/cfnvpn/{revoke.rb → actions/revoke.rb} +6 -6
  22. data/lib/cfnvpn/actions/routes.rb +144 -0
  23. data/lib/cfnvpn/{sessions.rb → actions/sessions.rb} +5 -5
  24. data/lib/cfnvpn/{share.rb → actions/share.rb} +10 -10
  25. data/lib/cfnvpn/actions/subnets.rb +78 -0
  26. data/lib/cfnvpn/certificates.rb +5 -5
  27. data/lib/cfnvpn/clientvpn.rb +34 -68
  28. data/lib/cfnvpn/compiler.rb +23 -0
  29. data/lib/cfnvpn/config.rb +34 -78
  30. data/lib/cfnvpn/{cloudformation.rb → deployer.rb} +47 -19
  31. data/lib/cfnvpn/log.rb +26 -26
  32. data/lib/cfnvpn/s3.rb +4 -4
  33. data/lib/cfnvpn/string.rb +29 -0
  34. data/lib/cfnvpn/templates/helper.rb +14 -0
  35. data/lib/cfnvpn/templates/vpn.rb +344 -0
  36. data/lib/cfnvpn/version.rb +1 -1
  37. metadata +55 -22
  38. data/lib/cfnvpn/cfhighlander.rb +0 -49
  39. data/lib/cfnvpn/init.rb +0 -109
  40. data/lib/cfnvpn/modify.rb +0 -103
  41. data/lib/cfnvpn/routes.rb +0 -84
  42. data/lib/cfnvpn/templates/cfnvpn.cfhighlander.rb.tt +0 -27
@@ -1,49 +0,0 @@
1
- require 'cfhighlander.publisher'
2
- require 'cfhighlander.factory'
3
- require 'cfhighlander.validator'
4
-
5
- require 'cfnvpn/version'
6
-
7
- module CfnVpn
8
- class CfHiglander
9
-
10
- def initialize(region, name, config, output_dir)
11
- @component_name = name
12
- @region = region
13
- @config = config
14
- @cfn_output_format = 'yaml'
15
- ENV['CFHIGHLANDER_WORKDIR'] = output_dir
16
- end
17
-
18
- def render()
19
- component = load_component(@component_name)
20
- compiled = compile_component(component)
21
- validate_component(component,compiled.cfn_template_paths)
22
- cfn_template_paths = compiled.cfn_template_paths
23
- return cfn_template_paths.select { |path| path.match(@component_name) }.first
24
- end
25
-
26
- private
27
-
28
- def load_component(component_name)
29
- factory = Cfhighlander::Factory::ComponentFactory.new
30
- component = factory.loadComponentFromTemplate(component_name)
31
- component.config = @config
32
- component.version = CfnVpn::VERSION
33
- component.load()
34
- return component
35
- end
36
-
37
- def compile_component(component)
38
- component_compiler = Cfhighlander::Compiler::ComponentCompiler.new(component)
39
- component_compiler.compileCloudFormation(@cfn_output_format)
40
- return component_compiler
41
- end
42
-
43
- def validate_component(component,template_paths)
44
- component_validator = Cfhighlander::Cloudformation::Validator.new(component)
45
- component_validator.validate(template_paths, @cfn_output_format)
46
- end
47
-
48
- end
49
- end
data/lib/cfnvpn/init.rb DELETED
@@ -1,109 +0,0 @@
1
- require 'thor'
2
- require 'fileutils'
3
- require 'cfnvpn/cloudformation'
4
- require 'cfnvpn/certificates'
5
- require 'cfnvpn/cfhighlander'
6
- require 'cfnvpn/cloudformation'
7
- require 'cfnvpn/log'
8
- require 'cfnvpn/clientvpn'
9
- require 'cfnvpn/globals'
10
-
11
- module CfnVpn
12
- class Init < Thor::Group
13
- include Thor::Actions
14
- include CfnVpn::Log
15
-
16
- argument :name
17
-
18
- class_option :profile, aliases: :p, desc: 'AWS Profile'
19
- class_option :region, aliases: :r, default: ENV['AWS_REGION'], desc: 'AWS Region'
20
- class_option :verbose, desc: 'set log level to debug', type: :boolean
21
-
22
- class_option :server_cn, required: true, desc: 'server certificate common name'
23
- class_option :client_cn, desc: 'client certificate common name'
24
- class_option :easyrsa_local, type: :boolean, default: false, desc: 'run the easyrsa executable from your local rather than from docker'
25
- class_option :bucket, required: true, desc: 's3 bucket'
26
-
27
- class_option :subnet_id, required: true, desc: 'subnet id to associate your vpn with'
28
- class_option :cidr, default: '10.250.0.0/16', desc: 'cidr from which to assign client IP addresses'
29
- class_option :dns_servers, desc: 'DNS Servers to push to clients.'
30
-
31
- class_option :split_tunnel, type: :boolean, default: false, desc: 'only push routes to the client on the vpn endpoint'
32
- class_option :internet_route, type: :boolean, default: true, desc: 'create a default route to the internet'
33
- class_option :protocol, type: :string, default: 'udp', enum: ['udp','tcp'], desc: 'set the protocol for the vpn connections'
34
-
35
-
36
- def self.source_root
37
- File.dirname(__FILE__)
38
- end
39
-
40
- def set_loglevel
41
- Log.logger.level = Logger::DEBUG if @options['verbose']
42
- end
43
-
44
- def create_build_directory
45
- @build_dir = "#{CfnVpn.cfnvpn_path}/#{@name}"
46
- Log.logger.debug "creating directory #{@build_dir}"
47
- FileUtils.mkdir_p(@build_dir)
48
- end
49
-
50
- def initialize_config
51
- @config = {}
52
- @config['parameters'] = {}
53
- @config['parameters']['EnvironmentName'] = @name
54
- @config['parameters']['AssociationSubnetId'] = @options['subnet_id']
55
- @config['parameters']['ClientCidrBlock'] = @options['cidr']
56
- @config['parameters']['DnsServers'] = @options['dns_servers']
57
- @config['parameters']['SplitTunnel'] = @options['split_tunnel'].to_s
58
- @config['parameters']['InternetRoute'] = @options['internet_route'].to_s
59
- @config['parameters']['Protocol'] = @options['protocol']
60
- @config['template_version'] = '0.2.0'
61
- end
62
-
63
- def stack_exist
64
- @cfn = CfnVpn::Cloudformation.new(@options['region'],@name)
65
- if @cfn.does_cf_stack_exist()
66
- Log.logger.error "#{@name}-cfnvpn stack already exists in this account in region #{@options['region']}"
67
- exit 1
68
- end
69
- end
70
-
71
- # create certificates
72
- def generate_server_certificates
73
- Log.logger.info "Generating certificates using openvpn easy-rsa"
74
- cert = CfnVpn::Certificates.new(@build_dir,@name,@options['easyrsa_local'])
75
- @client_cn = @options['client_cn'] ? @options['client_cn'] : "client-vpn.#{@options['server_cn']}"
76
- cert.generate_ca(@options['server_cn'],@client_cn)
77
- end
78
-
79
- def upload_certificates
80
- cert = CfnVpn::Certificates.new(@build_dir,@name,@options['easyrsa_local'])
81
- @config['parameters']['ServerCertificateArn'] = cert.upload_certificates(@options['region'],'server','server',@options['server_cn'])
82
- @config['parameters']['ClientCertificateArn'] = cert.upload_certificates(@options['region'],@client_cn,'client')
83
- s3 = CfnVpn::S3.new(@options['region'],@options['bucket'],@name)
84
- s3.store_object("#{@build_dir}/certificates/ca.tar.gz")
85
- end
86
-
87
- def deploy_vpn
88
- template('templates/cfnvpn.cfhighlander.rb.tt', "#{@build_dir}/#{@name}.cfhighlander.rb", @config, force: true)
89
- Log.logger.debug "Generating cloudformation from #{@build_dir}/#{@name}.cfhighlander.rb"
90
- cfhl = CfnVpn::CfHiglander.new(@options['region'],@name,@config,@build_dir)
91
- template_path = cfhl.render()
92
- Log.logger.debug "Cloudformation template #{template_path} generated and validated"
93
- Log.logger.info "Launching cloudformation stack #{@name}-cfnvpn in #{@options['region']}"
94
- cfn = CfnVpn::Cloudformation.new(@options['region'],@name)
95
- change_set, change_set_type = cfn.create_change_set(template_path, @config['parameters'])
96
- cfn.wait_for_changeset(change_set.id)
97
- cfn.execute_change_set(change_set.id)
98
- cfn.wait_for_execute(change_set_type)
99
- Log.logger.debug "Changeset #{change_set_type} complete"
100
- end
101
-
102
- def finish
103
- vpn = CfnVpn::ClientVpn.new(@name,@options['region'])
104
- @endpoint_id = vpn.get_endpoint_id()
105
- Log.logger.info "Client VPN #{@endpoint_id} created. Run `cfn-vpn config #{@name}` to setup the client config"
106
- end
107
-
108
- end
109
- end
data/lib/cfnvpn/modify.rb DELETED
@@ -1,103 +0,0 @@
1
- require 'thor'
2
- require 'fileutils'
3
- require 'cfnvpn/cloudformation'
4
- require 'cfnvpn/certificates'
5
- require 'cfnvpn/cfhighlander'
6
- require 'cfnvpn/cloudformation'
7
- require 'cfnvpn/log'
8
- require 'cfnvpn/clientvpn'
9
- require 'cfnvpn/globals'
10
-
11
- module CfnVpn
12
- class Modify < Thor::Group
13
- include Thor::Actions
14
- include CfnVpn::Log
15
-
16
- argument :name
17
-
18
- class_option :profile, aliases: :p, desc: 'AWS Profile'
19
- class_option :region, aliases: :r, default: ENV['AWS_REGION'], desc: 'AWS Region'
20
- class_option :verbose, desc: 'set log level to debug', type: :boolean
21
-
22
- class_option :subnet_id, desc: 'subnet id to associate your vpn with'
23
- class_option :cidr, desc: 'cidr from which to assign client IP addresses'
24
- class_option :dns_servers, desc: 'DNS Servers to push to clients.'
25
-
26
- class_option :split_tunnel, type: :boolean, desc: 'only push routes to the client on the vpn endpoint'
27
- class_option :internet_route, type: :boolean, desc: 'create a default route to the internet'
28
- class_option :protocol, type: :string, enum: ['udp','tcp'], desc: 'set the protocol for the vpn connections'
29
-
30
- def self.source_root
31
- File.dirname(__FILE__)
32
- end
33
-
34
- def set_loglevel
35
- Log.logger.level = Logger::DEBUG if @options['verbose']
36
- end
37
-
38
- def create_build_directory
39
- @build_dir = "#{CfnVpn.cfnvpn_path}/#{@name}"
40
- Log.logger.debug "creating directory #{@build_dir}"
41
- FileUtils.mkdir_p(@build_dir)
42
- end
43
-
44
- def initialize_config
45
- @config = {}
46
- @config['parameters'] = {}
47
- @config['parameters']['AssociationSubnetId'] = @options['subnet_id'] unless @options['subnet_id'].nil?
48
- @config['parameters']['ClientCidrBlock'] = @options['cidr'] unless @options['cidr'].nil?
49
- @config['parameters']['DnsServers'] = @options['dns_servers'] unless @options['dns_servers'].nil?
50
- @config['parameters']['SplitTunnel'] = @options['split_tunnel'].to_s unless @options['split_tunnel'].nil?
51
- @config['parameters']['InternetRoute'] = @options['internet_route'].to_s unless @options['internet_route'].nil?
52
- @config['parameters']['Protocol'] = @options['protocol'] unless @options['protocol'].nil?
53
- @config['template_version'] = '0.2.0'
54
- end
55
-
56
- def stack_exist
57
- @cfn = CfnVpn::Cloudformation.new(@options['region'],@name)
58
- if !@cfn.does_cf_stack_exist()
59
- Log.logger.error "#{@name}-cfnvpn stack doesn't exists in this account in region #{@options['region']}\n Try running `cfn-vpn init #{@name}` to setup the stack"
60
- exit 1
61
- end
62
- end
63
-
64
- def deploy_vpn
65
- template('templates/cfnvpn.cfhighlander.rb.tt', "#{@build_dir}/#{@name}.cfhighlander.rb", @config, force: true)
66
- Log.logger.debug "Generating cloudformation from #{@build_dir}/#{@name}.cfhighlander.rb"
67
- cfhl = CfnVpn::CfHiglander.new(@options['region'],@name,@config,@build_dir)
68
- template_path = cfhl.render()
69
- Log.logger.debug "Cloudformation template #{template_path} generated and validated"
70
-
71
- Log.logger.info "Modifying cloudformation stack #{@name}-cfnvpn in #{@options['region']}"
72
- cfn = CfnVpn::Cloudformation.new(@options['region'],@name)
73
- change_set, change_set_type = cfn.create_change_set(template_path,@config['parameters'])
74
- cfn.wait_for_changeset(change_set.id)
75
- changes = cfn.get_change_set(change_set.id)
76
-
77
- Log.logger.warn("The following changes to the cfnvpn stack will be made")
78
- changes.changes.each do |change|
79
- Log.logger.warn("ID: #{change.resource_change.logical_resource_id} Action: #{change.resource_change.action}")
80
- change.resource_change.details.each do |details|
81
- Log.logger.warn("Name: #{details.target.name} Attribute: #{details.target.attribute} Cause: #{details.causing_entity}")
82
- end
83
- end
84
-
85
- continue = yes? "Continue?", :green
86
- if !continue
87
- Log.logger.error("Cancelled cfn-vpn modifiy #{@name}")
88
- exit 1
89
- end
90
-
91
- cfn.execute_change_set(change_set.id)
92
- cfn.wait_for_execute(change_set_type)
93
- Log.logger.debug "Changeset #{change_set_type} complete"
94
- end
95
-
96
- def finish
97
- vpn = CfnVpn::ClientVpn.new(@name,@options['region'])
98
- @endpoint_id = vpn.get_endpoint_id()
99
- Log.logger.info "Client VPN #{@endpoint_id} modified."
100
- end
101
-
102
- end
103
- end
data/lib/cfnvpn/routes.rb DELETED
@@ -1,84 +0,0 @@
1
- require 'thor'
2
- require 'cfnvpn/log'
3
- require 'cfnvpn/s3'
4
- require 'cfnvpn/globals'
5
-
6
- module CfnVpn
7
- class Routes < Thor::Group
8
- include Thor::Actions
9
- include CfnVpn::Log
10
-
11
- argument :name
12
-
13
- class_option :profile, aliases: :p, desc: 'AWS Profile'
14
- class_option :region, aliases: :r, default: ENV['AWS_REGION'], desc: 'AWS Region'
15
- class_option :verbose, desc: 'set log level to debug', type: :boolean
16
-
17
- class_option :add, desc: 'add cidr to route through the client vpn'
18
- class_option :del, desc: 'delete cidr route from the client vpn'
19
- class_option :desc, desc: 'description of the route'
20
-
21
- def self.source_root
22
- File.dirname(__FILE__)
23
- end
24
-
25
- def set_loglevel
26
- Log.logger.level = Logger::DEBUG if @options['verbose']
27
- end
28
-
29
- def set_directory
30
- @build_dir = "#{CfnVpn.cfnvpn_path}/#{@name}"
31
- end
32
-
33
- def add_route
34
- if !@options['add'].nil?
35
- if @options['desc'].nil?
36
- Log.logger.error "--desc option must be provided if adding a new route"
37
- exit 1
38
- end
39
-
40
- vpn = CfnVpn::ClientVpn.new(@name,@options['region'])
41
-
42
- if vpn.route_exists?(@options['add'])
43
- Log.logger.error "route #{@options['add']} already exists in the client vpn"
44
- exit 1
45
- end
46
-
47
- Log.logger.info "Adding new route for #{@options['add']}"
48
- vpn.add_route(@options['add'],@options['desc'])
49
- end
50
- end
51
-
52
- def del_route
53
- if !@options['del'].nil?
54
- vpn = CfnVpn::ClientVpn.new(@name,@options['region'])
55
-
56
- if !vpn.route_exists?(@options['del'])
57
- Log.logger.error "route #{@options['del']} doesn't exist in the client vpn"
58
- exit 1
59
- end
60
- delete = yes? "Delete route #{@options['del']}?", :yellow
61
- if delete
62
- Log.logger.info "Deleting route for #{@options['del']}"
63
- vpn.del_route(@options['del'])
64
- end
65
- end
66
- end
67
-
68
- def get_routes
69
- vpn = CfnVpn::ClientVpn.new(@name,@options['region'])
70
- @routes = vpn.get_routes()
71
- end
72
-
73
- def display_routes
74
- rows = @routes.collect do |s|
75
- [ s.destination_cidr, s.description, s.status.code, s.target_subnet, s.type, s.origin ]
76
- end
77
- table = Terminal::Table.new(
78
- :headings => ['Route', 'Description', 'Status', 'Target', 'Type', 'Origin'],
79
- :rows => rows)
80
- puts table
81
- end
82
-
83
- end
84
- end
@@ -1,27 +0,0 @@
1
- CfhighlanderTemplate do
2
-
3
- Parameters do
4
- ComponentParam 'EnvironmentName'
5
- ComponentParam 'AssociationSubnetId'
6
- ComponentParam 'ClientCidrBlock'
7
- ComponentParam 'DnsServers'
8
- ComponentParam 'SplitTunnel'
9
- ComponentParam 'InternetRoute'
10
- ComponentParam 'Protocol'
11
- ComponentParam 'ServerCertificateArn'
12
- ComponentParam 'ClientCertificateArn'
13
- end
14
-
15
- Component template: 'client-vpn@<%= @config['template_version'] %>', name: 'vpn', render: Inline do
16
- parameter name: 'EnvironmentName', value: Ref('EnvironmentName')
17
- parameter name: 'AssociationSubnetId', value: Ref('AssociationSubnetId')
18
- parameter name: 'ClientCidrBlock', value: Ref('ClientCidrBlock')
19
- parameter name: 'DnsServers', value: Ref('DnsServers')
20
- parameter name: 'SplitTunnel', value: Ref('SplitTunnel')
21
- parameter name: 'InternetRoute', value: Ref('InternetRoute')
22
- parameter name: 'Protocol', value: Ref('Protocol')
23
- parameter name: 'ServerCertificateArn', value: Ref('ServerCertificateArn')
24
- parameter name: 'ClientCertificateArn', value: Ref('ClientCertificateArn')
25
- end
26
-
27
- end