localtower 0.2.3 → 0.4.1

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 (53) hide show
  1. checksums.yaml +5 -5
  2. data/README.md +11 -8
  3. data/app/controllers/localtower/pages_controller.rb +17 -0
  4. data/app/views/localtower/pages/logs.html.erb +42 -28
  5. data/config/routes.rb +2 -0
  6. data/lib/localtower/plugins/capture.rb +66 -45
  7. data/lib/localtower/tools.rb +1 -1
  8. data/lib/localtower/version.rb +1 -1
  9. data/lib/localtower.rb +1 -3
  10. data/public/screenshots/v0.1.6/5_capture.png +0 -0
  11. data/spec/dummy/Gemfile +1 -21
  12. data/spec/dummy/Gemfile.lock +104 -146
  13. data/spec/dummy/app/controllers/pages_controller.rb +8 -0
  14. data/spec/dummy/app/views/pages/home.html.erb +1 -0
  15. data/spec/dummy/config/application.rb +0 -9
  16. data/spec/dummy/config/environments/development.rb +0 -7
  17. data/spec/dummy/config/initializers/new_framework_defaults.rb +0 -3
  18. data/spec/dummy/config/routes.rb +2 -0
  19. data/spec/dummy/log/development.log +2 -158
  20. data/spec/dummy/log/localtower.log +1735 -1984
  21. data/spec/dummy/log/test.log +1829 -2183
  22. data/spec/factories/migration.rb +161 -139
  23. data/spec/factories/model.rb +34 -30
  24. data/spec/lib/localtower/generators/model_spec.rb +6 -7
  25. data/spec/lib/localtower/generators/relation_spec.rb +6 -3
  26. data/spec/spec_helper.rb +3 -12
  27. metadata +63 -159
  28. data/spec/dummy/coverage/assets/0.10.0/application.css +0 -799
  29. data/spec/dummy/coverage/assets/0.10.0/application.js +0 -1707
  30. data/spec/dummy/coverage/assets/0.10.0/colorbox/border.png +0 -0
  31. data/spec/dummy/coverage/assets/0.10.0/colorbox/controls.png +0 -0
  32. data/spec/dummy/coverage/assets/0.10.0/colorbox/loading.gif +0 -0
  33. data/spec/dummy/coverage/assets/0.10.0/colorbox/loading_background.png +0 -0
  34. data/spec/dummy/coverage/assets/0.10.0/favicon_green.png +0 -0
  35. data/spec/dummy/coverage/assets/0.10.0/favicon_red.png +0 -0
  36. data/spec/dummy/coverage/assets/0.10.0/favicon_yellow.png +0 -0
  37. data/spec/dummy/coverage/assets/0.10.0/loading.gif +0 -0
  38. data/spec/dummy/coverage/assets/0.10.0/magnify.png +0 -0
  39. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_flat_0_aaaaaa_40x100.png +0 -0
  40. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_flat_75_ffffff_40x100.png +0 -0
  41. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_glass_55_fbf9ee_1x400.png +0 -0
  42. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_glass_65_ffffff_1x400.png +0 -0
  43. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_glass_75_dadada_1x400.png +0 -0
  44. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_glass_75_e6e6e6_1x400.png +0 -0
  45. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_glass_95_fef1ec_1x400.png +0 -0
  46. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-bg_highlight-soft_75_cccccc_1x100.png +0 -0
  47. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-icons_222222_256x240.png +0 -0
  48. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-icons_2e83ff_256x240.png +0 -0
  49. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-icons_454545_256x240.png +0 -0
  50. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-icons_888888_256x240.png +0 -0
  51. data/spec/dummy/coverage/assets/0.10.0/smoothness/images/ui-icons_cd0a0a_256x240.png +0 -0
  52. data/spec/dummy/coverage/index.html +0 -294
  53. data/spec/dummy/tmp/restart.txt +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: cb98edd013a8dd3adffd7ec30785cf4e6371a788
4
- data.tar.gz: '093b0a9efd88f6223b95c22a513217198138df2d'
2
+ SHA256:
3
+ metadata.gz: 775afdc803d752a87109e8942ff71d1e7829ea59f19234933c477aff3956b7c3
4
+ data.tar.gz: 0d856ca281329b65d2cd9c82836077e1cfdd4f6b35625ade9b118628b00c065b
5
5
  SHA512:
6
- metadata.gz: 11fbdc9b9580686adbd0c8c78a3904a753479fb4110ea0e04e1784ce9fcfa240a3d8063769c6da37a4edfc042d8675a9b52f5a0bea42ac91a806ce25a6a6c68f
7
- data.tar.gz: 52ecc1ff573680f0a9879c13b2b5539b0aef4a214b44a2106d385efb83e7196fcc7059756c3468ffd96378bc79eb872f96a2c94d71594b2936e31f6cee78ef0b
6
+ metadata.gz: 3bf27bfb43dc6a7428efa4279d832407749e576877d9813ab0c5c615374558a30617167952f170a2e48e4dda8e893a8871f357bf2c87ae7160a884e6d96dfbf7
7
+ data.tar.gz: e908d290a06fb7493b547b4bb4c3d1ea8a2538d5b13992748b9f41c189104658531d446118e95703106003217ae7a4870e08f92d23d979a344381370501f8107
data/README.md CHANGED
@@ -14,11 +14,12 @@
14
14
  ### Create a migration
15
15
  ![Migrations](https://raw.githubusercontent.com/damln/localtower/master/public/screenshots/v0.1.6/4_migrations.png)
16
16
 
17
+ ### Using the Capture plugin
18
+ ![Capture](https://raw.githubusercontent.com/damln/localtower/master/public/screenshots/v0.1.6/5_capture.png)
17
19
 
18
20
  ## INSTALL
19
21
 
20
- Only tested with Rails 4.2 and Rails 5.1 (should work with any Rails 4.2+ application).
21
- Only tested with PostgreSQL.
22
+ Only tested with Rails 4.2 and Rails 5.1 (should work with any Rails 4.2+ application). Only tested with PostgreSQL.
22
23
 
23
24
  Add to your `Gemfile` file:
24
25
  ```ruby
@@ -63,12 +64,14 @@ You can put this line anywhere in your code:
63
64
 
64
65
  For example:
65
66
 
66
- def my_method
67
- user = User.find(1)
68
- some_data = {foo: "bar"}
67
+ ```ruby
68
+ def my_method
69
+ user = User.find(1)
70
+ some_data = {foo: "bar"}
69
71
 
70
- Localtower::Plugins::Capture.new(self, binding).save
71
- end
72
+ Localtower::Plugins::Capture.new(self, binding).save
73
+ end
74
+ ```
72
75
 
73
76
  Then go to the Localtower intercave here: [http://localhost:3000/localtower/logs](http://localhost:3000/localtower/logs) and you will see the variables `user` and `some_data` in the UI.
74
77
 
@@ -105,6 +108,6 @@ Thanks for reporting issues, I'll do my best.
105
108
 
106
109
  ## Deploy
107
110
 
108
- rm *.gem | gem build localtower.gemspec | gem push localtower-*.gem
111
+ rm *.gem | gem build localtower.gemspec && gem push localtower-*.gem
109
112
 
110
113
 
@@ -10,6 +10,23 @@ module Localtower
10
10
  @logs = Localtower::Plugins::Capture.new.logs
11
11
  end
12
12
 
13
+ def log
14
+ file = Dir["#{Localtower::Plugins::Capture::LOG_PATH.call}/localtower*#{params[:md5]}*"][0]
15
+
16
+ render json: JSON.parse(open(file).read)
17
+ end
18
+
19
+ def log_var
20
+ answer = {}
21
+
22
+ file = Dir["#{Localtower::Plugins::Capture::LOG_PATH.call}/localtower*#{params[:md5]}*"][0]
23
+ data = JSON.parse(open(file).read)
24
+
25
+ answer = data["variables"].select {|i| i["event_name"] == params[:var] }[0]["returned"]
26
+
27
+ render json: answer
28
+ end
29
+
13
30
  def status
14
31
  @data = ::Localtower::Status.new.run
15
32
  end
@@ -14,53 +14,67 @@
14
14
  border: 1px solid #cacaca;
15
15
  line-height: 1.2em;
16
16
  overflow:auto;
17
+ max-height: 800px;
18
+ max-width: 800px;
17
19
  -moz-background-clip: padding;
18
20
  -webkit-background-clip: padding-box;
19
21
  background-clip: padding-box;
20
22
  background-color: #FAFAFB;
21
23
  color: #393939;
22
24
  margin: 0px;
23
- max-width: 800px;
24
25
  display: block;
25
26
  }
26
-
27
27
  </style>
28
-
29
-
30
-
31
28
  <% content_for :title do %>Logs<% end %>
32
-
33
29
  <div class="row">
34
30
  <div class="col-md-12">
35
31
  <div class="card">
36
32
  <div class="header">
37
- <h4 class="title"><pre>Localtower::Plugins::Capture.new(self, binding).save</pre></h4>
33
+ <h4 class="title">
34
+ <pre>Localtower::Plugins::Capture.new(self, binding).save</pre>
35
+ </h4>
38
36
  </div>
39
-
40
37
  <div class="content">
41
38
  <table class="table">
42
39
  <thead>
43
- <th>Variable</th>
44
- <th>Value</th>
45
- <th>Value Type</th>
40
+ <th>TYPE</th>
41
+ <th>IN CLASS</th>
42
+ <th>IN METHOD</th>
43
+ <th>VARIABLE</th>
44
+ <th>VALUE</th>
46
45
  </thead>
47
-
48
- <tbody data-selector="tbody">
49
- <% @logs["variables"].each do |item| %>
50
-
51
- <tr data-selector="tr">
52
- <td class="code">
53
- <%= item["name"] %>
54
- </td>
55
-
56
- <td>
57
- <pre class="value json code"><%= Localtower::Plugins::Capture.printable(item["value"]) %></pre>
58
- </td>
59
-
60
- <td>
61
- <pre class="code"><%= item["klass"] %></pre>
62
- </td>
63
- </tr>
46
+ <tbody>
47
+ <% @logs.each do |log| %>
48
+ <% log["variables"].each do |item| %>
49
+ <tr>
50
+ <td>
51
+ <span class="label label-success">
52
+ <%= item["type"] %>
53
+ </span>
54
+ </td>
55
+ <td>
56
+ <span>
57
+ <a class="code" href="subl://open/?url=file://<%= item["meta"]["sublime_path"] %>">
58
+ <%= item["meta"]["from_klass"] %>
59
+ </a>
60
+ </span>
61
+ </td>
62
+ <td>
63
+ <span class="code">
64
+ <%= item["meta"]["from_method"] %>
65
+ </span>
66
+ </td>
67
+ <td>
68
+ <span class="code">
69
+ <%= item["event_name"] %>
70
+ </span>
71
+ </td>
72
+ <td>
73
+ <a href="<%= log_var_path(log["md5"], item["event_name"]) %>">open</a>
74
+ <pre class="value json code"><%= Localtower::Plugins::Capture.printable(item["returned"]) %></pre>
75
+ </td>
76
+ </tr>
77
+ <% end %>
64
78
  <% end %>
65
79
  </tbody>
66
80
  </table>
data/config/routes.rb CHANGED
@@ -13,6 +13,8 @@ Localtower::Engine.routes.draw do
13
13
 
14
14
  get 'dashboard', to: 'pages#dashboard', as: 'dashboard'
15
15
  get 'logs', to: 'pages#logs', as: 'logs'
16
+ get 'logs/:md5', to: 'pages#log', as: 'log'
17
+ get 'logs/:md5/:var', to: 'pages#log_var', as: 'log_var'
16
18
 
17
19
  root :to => redirect('dashboard')
18
20
  end
@@ -2,6 +2,7 @@ module Localtower
2
2
  module Plugins
3
3
  class Capture
4
4
  LOG_FILE = lambda { "#{Rails.root}/log/localtower_capture.log" }
5
+ LOG_PATH = lambda { "#{Rails.root}/log" }
5
6
  EXCLUDE_INSTANCE_VARIABLES = [
6
7
  "@_action_has_layout",
7
8
  "@_routes",
@@ -21,7 +22,6 @@ module Localtower
21
22
  class << self
22
23
  def printable(content)
23
24
  if content.respond_to?(:to_json)
24
- # content.to_json
25
25
  JSON.pretty_generate(content)
26
26
  else
27
27
  content.to_s
@@ -47,15 +47,14 @@ module Localtower
47
47
  end
48
48
 
49
49
  def logs
50
- if File.exist?(LOG_FILE.call)
51
- content = File.open(LOG_FILE.call).read
52
- else
53
- content = nil
54
- end
50
+ list = []
55
51
 
56
- return {"variables" => []} if not content.present?
52
+ Dir["#{LOG_PATH.call}/localtower_capture_*.json"].each do |file|
53
+ json = JSON.parse(open(file).read)
54
+ list << json
55
+ end
57
56
 
58
- data = JSON.parse(content)
57
+ list
59
58
  end
60
59
 
61
60
  def my_logger
@@ -70,16 +69,24 @@ module Localtower
70
69
  def values
71
70
  hash = {}
72
71
 
73
- a = @context.send(:caller)[1] # xx/xx/app/controllers/clients/events_controller.rb:57:in `new'
72
+ callers = @context.send(:caller)
73
+ a = callers[1] # xx/xx/app/controllers/clients/events_controller.rb:57:in `new'
74
74
  a = a.split(Rails.root.to_s).last # events_controller.rb:57:in `new'
75
75
  a = a.split("\:")
76
76
 
77
+
77
78
  file = a[0].strip
78
79
  line_number = a[1].strip
79
80
  method = a[2].strip.gsub("in \`", "").gsub("\'", "")
80
81
 
82
+ sublime_path = "#{callers[1].split(":")[0]}:#{line_number}"
83
+
81
84
  hash["class"] = self.klass_name
82
- hash["method"] = "#{file}##{method}:#{line_number}"
85
+ hash["file"] = "#{file}##{method}:#{line_number}"
86
+ hash["method"] = method
87
+ hash["md5"] = Digest::MD5.hexdigest(hash["file"])
88
+ hash["type"] = "CAPTURE_METHOD"
89
+ hash["time"] = Time.now.utc.strftime('%Y-%m-%d %H:%M:%S.%L')
83
90
 
84
91
  variables = []
85
92
 
@@ -89,19 +96,28 @@ module Localtower
89
96
  value = @context_binding.local_variable_get(var)
90
97
  klass = self.class.type_of(value)
91
98
 
92
- variables << {
93
- name: var,
94
- value: value,
95
- klass: klass
99
+ data = {
100
+ type: 'CAPTURE',
101
+ time: Time.now.utc.strftime('%Y-%m-%d %H:%M:%S.%L'),
102
+ event_name: var,
103
+ identifier: nil,
104
+ returned: value,
105
+ meta: {
106
+ from_klass: hash["class"],
107
+ from_method: hash["method"],
108
+ klass: klass.to_s,
109
+ method: method.to_s,
110
+ # arguments: data[:arguments],
111
+ callers: callers,
112
+ # table_name: data[:table_name],
113
+ # sql: data[:sql],
114
+ sublime_path: sublime_path,
115
+ file: hash["file"],
116
+ line: line_number
117
+ }
96
118
  }
97
119
 
98
- if value.is_a?(ActiveRecord::AssociationRelation) and value.respond_to?(:count)
99
- variables << {
100
- name: "#{var}_count",
101
- value: value.count,
102
- klass: nil
103
- }
104
- end
120
+ variables << data
105
121
  end
106
122
 
107
123
  @context.instance_variables.each do |var|
@@ -110,19 +126,28 @@ module Localtower
110
126
  value = @context.instance_variable_get(var.to_sym)
111
127
  klass = self.class.type_of(value)
112
128
 
113
- variables << {
114
- name: var,
115
- value: value,
116
- klass: klass
129
+ data = {
130
+ type: 'CAPTURE',
131
+ time: Time.now.utc.strftime('%Y-%m-%d %H:%M:%S.%L'),
132
+ event_name: var,
133
+ identifier: nil,
134
+ returned: value,
135
+ meta: {
136
+ from_klass: hash["class"],
137
+ from_method: hash["method"],
138
+ klass: klass.to_s,
139
+ method: method.to_s,
140
+ # arguments: data[:arguments],
141
+ callers: callers,
142
+ # table_name: data[:table_name],
143
+ # sql: data[:sql],
144
+ sublime_path: sublime_path,
145
+ file: hash["file"],
146
+ line: line_number
147
+ }
117
148
  }
118
149
 
119
- if value.is_a?(ActiveRecord::AssociationRelation) and value.respond_to?(:count)
120
- variables << {
121
- name: "#{var}_count",
122
- value: value.count,
123
- klass: nil
124
- }
125
- end
150
+ variables << data
126
151
  end
127
152
 
128
153
  hash["variables"] = variables
@@ -140,29 +165,25 @@ module Localtower
140
165
  value.to_s
141
166
  end
142
167
 
143
- # def context_caller
144
- # @context.send(:caller)[0]
145
- # end
168
+ def clear
169
+ Dir["#{LOG_PATH.call}/localtower_capture_*.json"].each do |file|
170
+ File.delete(file)
171
+ end
146
172
 
147
- def init
148
- # Clear the logs
149
- File.open(LOG_FILE.call, 'w') { |f| f.write("{}") }
173
+ self
150
174
  end
151
175
 
152
176
  def save
177
+ # We don't want to save logs in production:
153
178
  return nil if Rails.env.production?
154
179
 
155
- self.init
180
+ self.clear
156
181
 
157
182
  data = self.values
158
- data.each do |value|
159
- puts value
160
- end
161
-
162
183
  json = data.to_json
184
+ file = "#{LOG_PATH.call}/localtower_capture_#{data['md5']}.json"
163
185
 
164
- File.open(LOG_FILE.call, 'w') { |f| f.write(json) }
165
- # log "#{json}\n"
186
+ File.open(file, 'w') { |f| f.write(json) }
166
187
  end
167
188
 
168
189
  def log(str)
@@ -154,7 +154,7 @@ module Localtower
154
154
  def perform_raw_cmd(cmd_str, standalone = false, root_dir = false)
155
155
  root_dir ||= ::Rails.root
156
156
 
157
- cmd = standalone ? cmd_str : "cd '#{root_dir}' && #{cmd_str}"
157
+ cmd = standalone ? cmd_str : "cd \"#{root_dir}\" && #{cmd_str}"
158
158
  cmd = cmd.strip
159
159
 
160
160
  self.log("DOING...: #{cmd}")
@@ -1,3 +1,3 @@
1
1
  module Localtower
2
- VERSION = '0.2.3'.freeze
2
+ VERSION = '0.4.1'.freeze
3
3
  end
data/lib/localtower.rb CHANGED
@@ -5,13 +5,11 @@ end
5
5
  require 'thor'
6
6
  require 'active_link_to'
7
7
  require 'zip'
8
- require 'pg'
9
- require 'sqlite3'
10
8
 
11
9
  begin
12
10
  require "pry"
13
11
  rescue Exception => e
14
- puts "No Pry."
12
+ # Nothing
15
13
  end
16
14
 
17
15
  root = File.expand_path(File.dirname(__FILE__))
data/spec/dummy/Gemfile CHANGED
@@ -1,32 +1,12 @@
1
1
  source 'https://rubygems.org'
2
2
 
3
- git_source(:github) do |repo_name|
4
- repo_name = "#{repo_name}/#{repo_name}" unless repo_name.include?("/")
5
- "https://github.com/#{repo_name}.git"
6
- end
7
-
8
- gem 'rails', '~> 5.0.0'
9
- # gem 'rails', '>= 5.0.1'
3
+ gem 'rails', '5.2.0'
10
4
  gem 'pg'
11
5
  gem 'puma'
12
- gem 'sass-rails', '~> 5.0'
13
- gem 'uglifier', '>= 1.3.0'
14
- gem 'coffee-rails', '~> 4.2'
15
- # See https://github.com/rails/execjs#readme for more supported runtimes
16
- # gem 'therubyracer', platforms: :ruby
17
-
18
6
  gem 'jquery-rails'
19
7
  gem 'turbolinks', '~> 5'
20
8
 
21
9
  group :development, :test do
22
- # Access an IRB console on exception pages or by using <%= console %> anywhere in the code.
23
- gem 'listen', '~> 3.0.5'
24
- gem "dotenv-rails"
25
- gem "better_errors"
26
- gem "binding_of_caller"
27
- gem 'require_reloader'
28
- gem 'pry'
29
-
30
10
  localtower_path = File.expand_path(File.join(File.dirname(__FILE__), '..', '..'))
31
11
  gem "localtower", path: localtower_path
32
12
  end