adminix 0.1.20 → 0.1.21

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 4fce5280ad2ceecf739d281d46809592b5522ce2
4
- data.tar.gz: e211660507d932a0e66c3894511cd8e527b98ab8
3
+ metadata.gz: 298f9880a3d767fef666c2dd901cc9aefe81948b
4
+ data.tar.gz: 2ad5aebb4b569cbc4f92ecfefaa5a3a69763111b
5
5
  SHA512:
6
- metadata.gz: cecb9b52aaa4a956ae666463c83d257cf7dc549d11031b3596de470b41fdf7c2b530a8f790e8d0c0c4c9da3e86811d3bc5a1c6c207f215d90c3fcbd3d862490f
7
- data.tar.gz: 0ee3575d07b9ebb066496bb8effc92b7e45d9d4e4830d54de231d02c5f72a225adb161a29847fd5dcdda9ceb2627b376a619843d8d1364015054ef67750cda26
6
+ metadata.gz: ee3dcaaf7a68736dbcc9c2e9cf8e9b132b0efa9ff639e79b77563b1c91d4e2e981a8e1b5014450249360423c260f00760eb70cb6afd5ada6a925c1bdc44bd3ee
7
+ data.tar.gz: 515e255bcf71308ea6753445deb2b5c4e8f9e9f0344263ac33ae0fbe14b85948047d2589143f41f8ef65fbda65eff4510af5d17bdfcedd13d22c99a2d8c9d0f2
data/adminix.gemspec CHANGED
@@ -30,10 +30,9 @@ Gem::Specification.new do |spec|
30
30
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
31
31
  spec.require_paths = ["lib"]
32
32
 
33
- #spec.add_dependency "daemons", "~> 1.2.4"
34
- #spec.add_dependency "action_cable_client", "~> 1.3", ">= 1.3.4"
35
33
  spec.add_dependency "eventmachine", "1.2.3"
36
34
  spec.add_dependency "em-websocket-client", "0.1.2"
35
+ spec.add_dependency "sinatra", "1.4.8"
37
36
 
38
37
  spec.add_development_dependency "bundler", "~> 1.14"
39
38
  spec.add_development_dependency "rake", "~> 10.0"
data/exe/adminix CHANGED
@@ -43,16 +43,26 @@ parsers[options[:action].to_sym].parse!(ARGV) rescue nil
43
43
 
44
44
  unless options[:action] == "help"
45
45
  require'adminix'
46
- Adminix::Config.instance.secret_key = options[:secret_key]
47
- Adminix::Config.instance.service_id = options[:service_id]
48
- Adminix::Config.instance.daemon = options[:daemonize]
46
+ config = Adminix::Config.instance
47
+
48
+ config.secret_key = options[:secret_key]
49
+ config.service_id = options[:service_id]
50
+ config.daemon = options[:daemonize]
51
+ if !config.credentials_defined? && config.creds_file_exists?
52
+ config.read_creds_file
53
+ end
49
54
  end
50
55
 
51
56
  case options[:action]
52
- when "env"
57
+ when "env"
53
58
  puts Adminix::Service.instance.options_to_envs
54
59
  when "watch"
55
- puts Adminix::Watcher.run!(options)
60
+ if config.credentials_defined?
61
+ puts Adminix::Watcher.run!(options)
62
+ else
63
+ puts 'Credentials are not defined, running setup server'
64
+ require 'adminix/setup'
65
+ end
56
66
  when "version"
57
67
  puts "adminix version #{Adminix::VERSION}"
58
68
  else
@@ -1,19 +1,40 @@
1
1
  require 'singleton'
2
+ require 'json'
2
3
 
3
4
  module Adminix
4
5
  class Config
5
6
  include Singleton
6
7
 
7
8
  DEFAULT_HOST = 'http://api.adminix.io'.freeze
9
+ DEFAULT_SETUP_SERVER_PORT = '8080'
8
10
 
9
- attr_accessor :service_id, :secret_key, :host, :commands, :daemon
11
+ attr_accessor :service_id, :secret_key, :host, :commands, :daemon, :setup_server_port
10
12
 
11
13
  def initialize
12
- #self.service_id = ENV['ADMINIX_SERVICE_ID']
13
- #self.secret_key = ENV['ADMINIX_SECRET_KEY']
14
- self.host = ENV['ADMINIX_HOST'] || DEFAULT_HOST
14
+ self.host = ENV['ADMINIX_HOST'] || DEFAULT_HOST
15
+ self.setup_server_port = ENV['ADMINIX_SETUP_SERVER_PORT'] || DEFAULT_SETUP_SERVER_PORT
15
16
  self.commands = []
16
17
  end
18
+
19
+ def read_creds_file
20
+ file_content = IO.read("#{ENV['HOME']}/.adminix")
21
+ data = JSON.parse(file_content) rescue nil
22
+
23
+ unless data.nil?
24
+ self.service_id ||= data['service_id']
25
+ self.secret_key ||= data['secret_key']
26
+ end
27
+
28
+ true
29
+ end
30
+
31
+ def creds_file_exists?
32
+ File.exists?("#{ENV['HOME']}/.adminix")
33
+ end
34
+
35
+ def credentials_defined?
36
+ !service_id.nil? && !secret_key.nil?
37
+ end
17
38
  end
18
39
  end
19
40
 
@@ -0,0 +1,108 @@
1
+ require 'sinatra/base'
2
+
3
+ module Adminix::Setup
4
+ class Routes < Sinatra::Base
5
+ get '/' do
6
+ render('root')
7
+ end
8
+
9
+ get '/login' do
10
+ render('login')
11
+ end
12
+
13
+ post '/login' do
14
+ result = Services.create_session(params[:session])
15
+ case result[0]
16
+ when :ok
17
+ redirect "/create-service?t=#{result[1]}"
18
+ when :error
19
+ errors = result[1]
20
+ render('login', session: params[:session], errors: errors)
21
+ end
22
+ end
23
+
24
+ get '/sign-up' do
25
+ render('sign_up')
26
+ end
27
+
28
+ post '/sign-up' do
29
+ result = Services.create_user(params[:user])
30
+ case result[0]
31
+ when :ok
32
+ redirect "/create-service?t=#{result[1]}"
33
+ when :error
34
+ errors = result[1]
35
+ render('sign_up', user: params[:user], errors: errors)
36
+ end
37
+ end
38
+
39
+ get '/create-service' do
40
+ if params[:t]
41
+ case (result = Services.get_existing_services(params[:t]))[0]
42
+ when :ok
43
+ render('create_service', token: params[:t], service_exists: result[1] != 0)
44
+ when :error
45
+ render('error')
46
+ end
47
+ else
48
+ redirect '/sign-up'
49
+ end
50
+ end
51
+
52
+ post '/create-service' do
53
+ if params[:t]
54
+ case (result = Services.create_service(params[:t], params[:service]))[0]
55
+ when :ok
56
+ redirect "/complete?t=#{params[:t]}&id=#{result[1]['id']}"
57
+ when :error
58
+ render('error')
59
+ end
60
+ else
61
+ redirect '/sign-up'
62
+ end
63
+ end
64
+
65
+ get '/connect-service' do
66
+ if params[:t]
67
+ case (result = Services.get_existing_services(params[:t]))[0]
68
+ when :ok
69
+ render('connect_service', token: params[:t], services: result[1])
70
+ when :error
71
+ render('error')
72
+ end
73
+ else
74
+ redirect '/sign-up'
75
+ end
76
+ end
77
+
78
+ post '/connect-service' do
79
+ redirect "/complete?t=#{params[:t]}&id=#{params[:service][:id]}"
80
+ end
81
+
82
+ get '/complete' do
83
+ if params[:t] && params[:id]
84
+ id_is_valid = Services.verify_service_id(params[:t], params[:id])
85
+ secret_key = Services.get_secret_key(params[:t])
86
+ if id_is_valid && !secret_key.nil?
87
+ Services.import_settings(secret_key, params[:id])
88
+ render('complete')
89
+ else
90
+ render('error')
91
+ end
92
+ else
93
+ render('error')
94
+ end
95
+ end
96
+
97
+ private
98
+
99
+ def render(view_name, assigns={})
100
+ Views.send("#{view_name}_view", assigns)
101
+ end
102
+
103
+ set :port, Adminix::Config.instance.setup_server_port
104
+
105
+ run!
106
+ end
107
+ end
108
+
@@ -0,0 +1,138 @@
1
+ require 'net/http'
2
+ require 'json'
3
+
4
+ module Adminix::Setup
5
+ module Services
6
+ def self.create_session(payload)
7
+ uri = URI.parse("#{config.host}/v1/profile/session")
8
+ request = Net::HTTP::Post.new(uri)
9
+ request['Content-Type'] = 'application/json'
10
+ request.body = {
11
+ session: {
12
+ connect_type: 'email',
13
+ connect_data: {
14
+ email: payload[:email],
15
+ password: payload[:password]
16
+ }
17
+ }
18
+ }.to_json
19
+ opts = { use_ssl: uri.scheme == 'https' }
20
+
21
+ response = Net::HTTP.start(uri.hostname, uri.port, opts) do |http|
22
+ http.request(request)
23
+ end
24
+
25
+ data = JSON.parse(response.body)
26
+
27
+ data['success'] == true ? [:ok, data['result']['token']] : [:error, { email: ['Invalid credentials'] }]
28
+ end
29
+
30
+ def self.create_user(payload)
31
+ uri = URI.parse("#{config.host}/v1/profile")
32
+ request = Net::HTTP::Post.new(uri)
33
+ request['Content-Type'] = 'application/json'
34
+ request.body = {
35
+ profile: {
36
+ connect_type: 'email',
37
+ connect_data: {
38
+ email: payload[:email],
39
+ first_name: payload[:first_name],
40
+ last_name: payload[:last_name],
41
+ password: payload[:password],
42
+ locale: 'en'
43
+ }
44
+ }
45
+ }.to_json
46
+ opts = { use_ssl: uri.scheme == 'https' }
47
+
48
+ response = Net::HTTP.start(uri.hostname, uri.port, opts) do |http|
49
+ http.request(request)
50
+ end
51
+
52
+ data = JSON.parse(response.body)
53
+
54
+ data['success'] == true ? [:ok, data['result']['token']] : [:error, data['result']]
55
+ end
56
+
57
+ def self.create_service(access_token, payload)
58
+ uri = URI.parse("#{config.host}/v1/services")
59
+ request = Net::HTTP::Post.new(uri)
60
+ request['Content-Type'] = 'application/json'
61
+ request['X-Auth-Token'] = access_token
62
+ request.body = {
63
+ service: {
64
+ name: payload[:name]
65
+ }
66
+ }.to_json
67
+ opts = { use_ssl: uri.scheme == 'https' }
68
+
69
+ response = Net::HTTP.start(uri.hostname, uri.port, opts) do |http|
70
+ http.request(request)
71
+ end
72
+
73
+ data = JSON.parse(response.body)
74
+
75
+ data['success'] == true ? [:ok, data['result']] : [:error, data['result']]
76
+ end
77
+
78
+ def self.get_existing_services(access_token)
79
+ uri = URI.parse("#{config.host}/v1/services")
80
+ request = Net::HTTP::Get.new(uri)
81
+ request["X-Auth-Token"] = access_token
82
+ opts = { use_ssl: uri.scheme == 'https' }
83
+
84
+ response = Net::HTTP.start(uri.hostname, uri.port, opts) do |http|
85
+ http.request(request)
86
+ end
87
+
88
+ data = JSON.parse(response.body) rescue {}
89
+
90
+ data['success'] == true ? [:ok, data['result']] : [:error, []]
91
+ end
92
+
93
+ def self.get_secret_key(access_token)
94
+ uri = URI.parse("#{config.host}/v1/profile/session")
95
+ request = Net::HTTP::Get.new(uri)
96
+ request["X-Auth-Token"] = access_token
97
+ opts = { use_ssl: uri.scheme == 'https' }
98
+
99
+ response = Net::HTTP.start(uri.hostname, uri.port, opts) do |http|
100
+ http.request(request)
101
+ end
102
+
103
+ data = JSON.parse(response.body) rescue {}
104
+
105
+ data['result']['user']['secret_key'] rescue nil
106
+ end
107
+
108
+ def self.verify_service_id(access_token, service_id)
109
+ uri = URI.parse("#{config.host}/v1/services/#{service_id}")
110
+ request = Net::HTTP::Get.new(uri)
111
+ request["X-Auth-Token"] = access_token
112
+ opts = { use_ssl: uri.scheme == 'https' }
113
+
114
+ response = Net::HTTP.start(uri.hostname, uri.port, opts) do |http|
115
+ http.request(request)
116
+ end
117
+
118
+ data = JSON.parse(response.body) rescue {}
119
+
120
+ data['success'] == true
121
+ end
122
+
123
+ private
124
+
125
+ def self.config
126
+ Adminix::Config.instance
127
+ end
128
+
129
+ def self.import_settings(secret_key, service_id)
130
+ open("#{ENV['HOME']}/.adminix", 'w') do |f|
131
+ f.puts({ secret_key: secret_key, service_id: service_id }.to_json)
132
+ end
133
+
134
+ true
135
+ end
136
+ end
137
+ end
138
+
@@ -0,0 +1,183 @@
1
+ module Adminix::Setup
2
+ module Views
3
+ def self.root_view(_assigns)
4
+ layout do
5
+ %{
6
+ <div class="row">
7
+ <div class="col-md-6 col-md-offset-3">
8
+ <br/>
9
+ <a href="http://adminix.io" title="Adminix website" target="_blank">
10
+ <img src="http://www.adminix.io/images/logo_square.jpg" alt="Adminix logo" class="img-responsive center-block" style="width: 130px" />
11
+ </a>
12
+ <br/>
13
+ <p>Thank you for using Adminix image!</p>
14
+ <p>Your application is almost deployed, please click on "Continue" button to finish setup process.</p>
15
+ <button type="button" class="btn btn-primary" onclick="location.href='/sign-up';">Continue</button>
16
+ <br/><br/>
17
+ <a href="http://adminix.io" title="Adminix website" target="_blank">Click to visit our website</a>
18
+ </div>
19
+ </div>
20
+ }
21
+ end
22
+ end
23
+
24
+ def self.login_view(assigns)
25
+ session = assigns[:session] || {}
26
+ errors = assigns[:errors] || []
27
+ layout do
28
+ panel(title: 'Login') do
29
+ %{
30
+ <form method="POST" action="/login">
31
+ #{form_group('email', type: 'email', name: 'session[email]', label: 'Email', placeholder: 'Please enter your email', value: session[:email])}
32
+ #{form_group('password', type: 'password', name: 'session[password]', label: 'Password', placeholder: 'Please enter your password')}
33
+ #{errors.count != 0 ? render_errors(errors) : ''}
34
+ <button type="submit" class="btn btn-primary">Login</button>
35
+ <br/><br/>
36
+ <a href="/sign-up" title="Sign up">New to Adminix? Create a FREE account</a>
37
+ </form>
38
+ }
39
+ end
40
+ end
41
+ end
42
+
43
+ def self.sign_up_view(assigns)
44
+ user = assigns[:user] || {}
45
+ errors = assigns[:errors] || []
46
+ layout do
47
+ panel(title: 'Create a FREE Adminix account') do
48
+ %{
49
+ <form method="POST" action="/sign-up">
50
+ #{form_group('first_name', type: 'text', name: 'user[first_name]', label: 'First name', placeholder: 'Please enter your first name', value: user[:first_name])}
51
+ #{form_group('last_name', type: 'text', name: 'user[last_name]', label: 'Last name', placeholder: 'Please enter your last name', value: user[:last_name])}
52
+ #{form_group('email', type: 'email', name: 'user[email]', label: 'Email', placeholder: 'Please enter your email', value: user[:email])}
53
+ #{form_group('password', type: 'password', name: 'user[password]', label: 'Password', placeholder: 'Please enter your password')}
54
+ #{errors.count != 0 ? render_errors(errors) : ''}
55
+ <button type="submit" class="btn btn-primary">Sign up</button>
56
+ <br/><br/>
57
+ <a href="/login" title="Login">Already have an account? Login</a>
58
+ </form>
59
+ }
60
+ end
61
+ end
62
+ end
63
+
64
+ def self.create_service_view(assigns)
65
+ layout do
66
+ panel(title: 'Create service') do
67
+ %{
68
+ <form method="POST" action="/create-service?t=#{assigns[:token]}">
69
+ #{form_group('name', type: 'text', name: 'service[name]', label: 'Service name', placeholder: 'Please enter your service name')}
70
+ <button type="submit" class="btn btn-primary" onclick="location.href='/complete';">Launch your service</button>
71
+ <br/><br/>
72
+ #{assigns[:service_exists] ? "<a href=\"/connect-service?t=#{assigns[:token]}\" title=\"Connect service\">Already have an existing service? Choose it</a>" : ''}
73
+ </form>
74
+ }
75
+ end
76
+ end
77
+ end
78
+
79
+ def self.connect_service_view(assigns)
80
+ layout do
81
+ panel(title: 'Connect existing service') do
82
+ %{
83
+ <form method="POST" action="/connect-service?t=#{assigns[:token]}">
84
+ <div class="form-group">
85
+ <label for="service_id">Please select service to connect</label>
86
+ <select class="form-control" name="service[id]" id="service_id">
87
+ #{(assigns[:services].map { |s| "<option value='#{s['id']}'>#{s['name']}</option>" }).join('')}
88
+ </select>
89
+ </div>
90
+ <button type="submit" class="btn btn-primary">Launch your service</button>
91
+ <br/><br/>
92
+ <a href="/create-service?t=#{assigns[:token]}" title="Connect service">Want to create a new one? Create service</a>
93
+ </form>
94
+ }
95
+ end
96
+ end
97
+ end
98
+
99
+ def self.complete_view(_assigns)
100
+ layout do
101
+ panel(title: 'Application setup process completed') do
102
+ %{
103
+ <p>Your application setup is completed.
104
+ }
105
+ end
106
+ end
107
+ end
108
+
109
+ def self.error_view(_assigns)
110
+ layout do
111
+ panel(title: 'Something went wrong') do
112
+ %{
113
+ <p>Something went wrong please retry a process.</p>
114
+ }
115
+ end
116
+ end
117
+ end
118
+
119
+ private
120
+
121
+ def self.layout
122
+ %{
123
+ <html>
124
+ <head>
125
+ <title>Adminix setup</title>
126
+ <link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
127
+ </head>
128
+ <body>
129
+ <div class="container">
130
+ #{yield}
131
+ </div>
132
+ <script src="https://code.jquery.com/jquery-3.2.1.min.js" integrity="sha256-hwg4gsxgFZhOsEEamdOYGBf13FyQuiTwlAQgxVSNgt4=" crossorigin="anonymous"></script>
133
+ <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js" integrity="sha384-Tc5IQib027qvyjSMfHjOMaLkfuWVxZxUPnCJA7l2mCWNIpG9mGCD8wGNIcPD7Txa" crossorigin="anonymous"></script>
134
+ </body>
135
+ </html>
136
+ }
137
+ end
138
+
139
+ def self.panel(assigns)
140
+ %{
141
+ <div class="row">
142
+ <div class="col-md-offset-2 col-md-8">
143
+ <div class="panel panel-default">
144
+ <div class="panel-heading clearfix">
145
+ <i class="icon-calendar"></i>
146
+ <h3 class="panel-title">#{assigns[:title]}</h3>
147
+ </div>
148
+ <div class="panel-body">
149
+ <div class="row">
150
+ <div class="col-md-6 col-md-offset-3">
151
+ #{yield}
152
+ </div>
153
+ </div>
154
+ </div>
155
+ </div>
156
+ </div>
157
+ }
158
+ end
159
+
160
+ def self.render_errors(errors)
161
+ flash (errors.map { |k,v| "#{v}<br/>" }).join('<br/>')
162
+ text = errors.map do |attr, errors|
163
+ (errors.map { |err| "#{attr} #{err}" }).join('<br/>')
164
+ end.join('<br/>')
165
+
166
+ flash(text)
167
+ end
168
+
169
+ def self.flash(text, type='danger')
170
+ %{<div class="alert alert-#{type}">#{text}</div>}
171
+ end
172
+
173
+ def self.form_group(id, assigns)
174
+ %{
175
+ <div class="form-group">
176
+ <label for="#{id}">#{assigns[:label]}</label>
177
+ <input type="#{assigns[:type]}" name="#{assigns[:name]}" value="#{assigns[:value]}" class="form-control" id="#{id}" placeholder="#{assigns[:placeholder]}">
178
+ </div>
179
+ }
180
+ end
181
+ end
182
+ end
183
+
@@ -0,0 +1,3 @@
1
+ require 'adminix/setup/views'
2
+ require 'adminix/setup/services'
3
+ require 'adminix/setup/routes'
@@ -1,3 +1,3 @@
1
1
  module Adminix
2
- VERSION = "0.1.20"
2
+ VERSION = "0.1.21"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: adminix
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.20
4
+ version: 0.1.21
5
5
  platform: ruby
6
6
  authors:
7
7
  - Christian Dyl
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2017-04-19 00:00:00.000000000 Z
11
+ date: 2017-04-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: eventmachine
@@ -38,6 +38,20 @@ dependencies:
38
38
  - - '='
39
39
  - !ruby/object:Gem::Version
40
40
  version: 0.1.2
41
+ - !ruby/object:Gem::Dependency
42
+ name: sinatra
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - '='
46
+ - !ruby/object:Gem::Version
47
+ version: 1.4.8
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - '='
53
+ - !ruby/object:Gem::Version
54
+ version: 1.4.8
41
55
  - !ruby/object:Gem::Dependency
42
56
  name: bundler
43
57
  requirement: !ruby/object:Gem::Requirement
@@ -144,6 +158,10 @@ files:
144
158
  - lib/adminix/.service.rb.swn
145
159
  - lib/adminix/config.rb
146
160
  - lib/adminix/service.rb
161
+ - lib/adminix/setup.rb
162
+ - lib/adminix/setup/routes.rb
163
+ - lib/adminix/setup/services.rb
164
+ - lib/adminix/setup/views.rb
147
165
  - lib/adminix/system.rb
148
166
  - lib/adminix/version.rb
149
167
  - lib/adminix/watcher.rb