iron_warbler 2.0.7.28 → 2.0.7.30

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b7ca7e6c0657dbafd3a3e9149fbf05f7a0e0aa275b39d183e145d8802cadc175
4
- data.tar.gz: c67d4ee07b9646761ed2de0d1291e68d36d7a794ed6b4db58a2d7f2428d72944
3
+ metadata.gz: 60966c7bde0f338255d7ab0ce24ebca3311dfcba820b9b0fe5409d4b8eb985bf
4
+ data.tar.gz: 16c6761d9302739e6a28f283bfd2471d27aa1cdf620c82f0c4dcd455b20e7f71
5
5
  SHA512:
6
- metadata.gz: ad587c8488a2a3a1f7a269c32129ba879c3fde5fb54e2a32a7e2a2f45132995e7d2566a492e002c9ee72d83cfb40fdbc1c81dc5f7a536cd5b368cdb95bb2a038
7
- data.tar.gz: 4c08a09952620d5339e9f76e5b29ebf5d1134fe0fd20b774f3b7123cd6fe28683b7f517388ac08f1af6142df4edda686d36ab304ff8816c954ce368bdf5a22db
6
+ metadata.gz: 3ff908d7efc4e141159b0494b600cb8074fd231f384600e19f8b4b9208609667db517d89c950a0da787579f070339dcb7020c9c560159c62f010f957049bc71f
7
+ data.tar.gz: 0431c721ac017e981ee375aba955b41a0e360e380431d6c22635189bfbeeaa80ab0443296a0425532e32eed68cd947fbff84f4e3370a92a1e381f67f214fea9c
data/README.txt CHANGED
@@ -11,9 +11,6 @@ calculator: https://www.omnicalculator.com/finance/black-scholes
11
11
 
12
12
  From: https://pythoninoffice.com/calculate-black-scholes-option-price-in-python/
13
13
 
14
- -=---
15
-
16
-
17
- https://api.tdameritrade.com/v1/accounts/232718838/orders/13597943085
18
-
14
+ = swagger =
19
15
 
16
+ * https://developer.schwab.com/products/trader-api--individual
@@ -0,0 +1,9 @@
1
+
2
+ .iro-alerts--index {
3
+ .field {
4
+ label {
5
+ min-width: auto;
6
+ }
7
+ }
8
+ }
9
+
@@ -45,8 +45,8 @@ class Iro::AlertsController < Iro::ApplicationController
45
45
  super
46
46
 
47
47
  # @profiles_list = Wco::Profile.list
48
- @stocks_list = Iro::Stock.list
49
- puts! @stocks_list, '@stocks_list'
48
+ @stocks_list = Iro::Stock.list
49
+ @symbols_list = [[nil,nil]] + Iro::Stock.active.map { |s| [ s.ticker, s.ticker ] }
50
50
  end
51
51
 
52
52
 
@@ -1,8 +1,41 @@
1
1
 
2
+ class Schwab
3
+ include HTTParty
4
+ debug_output $stdout
5
+ end
6
+
2
7
  class Iro::ApiController < ActionController::Base
3
8
  layout false
4
9
 
5
- before_action :decode_jwt
10
+ before_action :decode_jwt, except: [ :oauth2_redirect ]
11
+
12
+ def oauth2_redirect
13
+ out = Schwab.post( "https://api.schwabapi.com/v1/oauth/token", {
14
+ headers: {
15
+ "Content-Type": "application/x-www-form-urlencoded",
16
+ },
17
+ basic_auth: { username: SCHWAB_DATA[:key], password: SCHWAB_DATA[:secret] },
18
+ body: {
19
+ grant_type: 'authorization_code',
20
+ code: params[:code].sub('%40', '@'),
21
+ redirect_uri: SCHWAB_DATA[:redirect_url],
22
+ },
23
+ })
24
+ out = out.parsed_response
25
+
26
+ attrs = {
27
+ schwab_access_token: out['access_token'],
28
+ schwab_refresh_token: out['refresh_token'],
29
+ schwab_id_token: out['id_token'],
30
+ }
31
+ # puts! attrs, 'attrs'
32
+
33
+ profile = Wco::Profile.find_by email: 'piousbox@gmail.com'
34
+ profile.update(attrs)
35
+ profile.save!
36
+
37
+ render json: { status: :ok }
38
+ end
6
39
 
7
40
  ##
8
41
  ## private
@@ -5,15 +5,50 @@ Po ||= Iro::Position
5
5
  O ||= Iro::Option
6
6
  Sto ||= Iro::Stock
7
7
 
8
+ class Schwab
9
+ include HTTParty
10
+ debug_output $stdout
11
+ end
12
+
8
13
  class Iro::ApplicationController < Wco::ApplicationController
9
14
  layout 'iro/application'
10
15
 
11
- before_action :set_lists
16
+ before_action :set_lists, except: %i| schwab_sync |
12
17
 
13
18
  def home
14
19
  authorize! :home, Iro
15
20
  end
16
21
 
22
+ def schwab_sync
23
+ authorize! :shwab_sync, Iro
24
+ profile = Wco::Profile.find_by email: 'piousbox@gmail.com'
25
+
26
+ out = Schwab.post( "https://api.schwabapi.com/v1/oauth/token", {
27
+ headers: {
28
+ "Content-Type": "application/x-www-form-urlencoded",
29
+ },
30
+ basic_auth: { username: SCHWAB_DATA[:key], password: SCHWAB_DATA[:secret] },
31
+ body: {
32
+ grant_type: 'refresh_token',
33
+ refresh_token: profile.schwab_refresh_token
34
+ },
35
+ })
36
+ out = out.parsed_response
37
+ puts! out, 'out'
38
+
39
+ attrs = {
40
+ schwab_access_token: out['access_token'],
41
+ schwab_refresh_token: out['refresh_token'],
42
+ schwab_id_token: out['id_token'],
43
+ }
44
+ puts! attrs, 'attrs'
45
+
46
+ # profile.update(attrs)
47
+ # profile.save!
48
+
49
+ render json: { status: :ok }
50
+ end
51
+
17
52
  ##
18
53
  ## private
19
54
  ##
@@ -42,7 +42,11 @@ class Iro::Alert
42
42
  if ( alert.direction == alert.class::DIRECTION_ABOVE && price >= alert.strike ) ||
43
43
  ( alert.direction == alert.class::DIRECTION_BELOW && price <= alert.strike )
44
44
 
45
- Iro::AlertMailer.stock_alert( alert.id.to_s ).deliver_later
45
+ if Rails.env.production?
46
+ Iro::AlertMailer.stock_alert( alert.id.to_s ).deliver_later
47
+ else
48
+ Iro::AlertMailer.stock_alert( alert.id.to_s ).deliver_now
49
+ end
46
50
  alert.update({ status: alert.class::STATUS_INACTIVE })
47
51
  print '^'
48
52
 
@@ -84,7 +84,7 @@ class Tda::Option
84
84
  end
85
85
  end
86
86
  if params[:expirationDate]
87
- opts[:fromDate] = opts[:toDate] = params[:expirationDate]
87
+ opts[:fromDate] = opts[:toDate] = params[:expirationDate].to_s[0...10]
88
88
  else
89
89
  raise Iro::InputError.new("Invalid input, missing 'date'.")
90
90
  end
@@ -98,11 +98,12 @@ class Tda::Option
98
98
  opts[:strike] = params[:strike]
99
99
  end
100
100
 
101
- query = { apikey: ::TD_AMERITRADE[:apiKey] }.merge opts
101
+ query = { }.merge opts
102
102
  # puts! query, 'input opts'
103
103
 
104
104
  headers = {
105
- Authorize: "Bearer #{::TD_AMERITRADE[:access_token]}",
105
+ accept: 'application/json',
106
+ Authorization: "Bearer #{::SCHWAB_DATA[:access_token]}",
106
107
  }
107
108
 
108
109
 
@@ -13,14 +13,16 @@ class Tda::Stock
13
13
  ## tickers = "GME"
14
14
  ## tickers = "NVDA,GME"
15
15
  def self.get_quotes tickers
16
+ profile = Wco::Profile.find_by email: 'piousbox@gmail.com'
17
+
16
18
  path = "/quotes"
17
19
  headers = {
18
20
  accept: 'application/json',
19
- Authorization: "Bearer #{::SCHWAB_DATA[:access_token]}",
21
+ Authorization: "Bearer #{profile.schwab_access_token}",
20
22
  }
21
23
  inns = self.get path, { headers: headers, query: { symbols: tickers } }
22
24
  inns = inns.parsed_response
23
- # puts! inns, 'parsed response'
25
+ puts! inns, 'parsed response'
24
26
 
25
27
  if [ NilClass, String ].include?( inns.class )
26
28
  return []
@@ -7,6 +7,9 @@
7
7
  .W
8
8
  .d-flex.flex-wrap
9
9
  %ul
10
+ %li
11
+ = link_to "Schwab Login", "https://api.schwabapi.com/v1/oauth/authorize?client_id=#{SCHWAB_DATA[:key]}&redirect_uri=#{SCHWAB_DATA[:redirect_url]}"
12
+ = link_to '[sync]', schwab_sync_path
10
13
  %li
11
14
  = link_to "Stocks (#{Iro::Stock.all.length})", stocks_path
12
15
  = link_to '[sync]', sync_stocks_path
@@ -24,7 +24,7 @@
24
24
  -# = f.text_field :kind
25
25
  .field
26
26
  = f.label :symbol
27
- = f.select :symbol, options_for_select( @stocks_list, selected: alert.symbol )
27
+ = f.select :symbol, options_for_select( @symbols_list, selected: alert.symbol )
28
28
  .field
29
29
  = f.label :direction
30
30
  = f.select :direction, options_for_select([ :ABOVE, :BELOW ], selected: alert.direction)
@@ -1,9 +1,9 @@
1
1
 
2
- .iro-alerts--index.maxwidth
2
+ .iro-alerts--index.padded
3
3
  %h5 Iro Alerts
4
4
 
5
- %ul
5
+ .a
6
6
  - @alerts.each do |alert|
7
- %li
7
+ .a
8
8
  = render 'iro/alerts/form', alert: alert
9
- %li= render 'iro/alerts/form', alert: Iro::Alert.new
9
+ .a= render 'iro/alerts/form', alert: Iro::Alert.new
@@ -18,9 +18,9 @@
18
18
  %label Stock
19
19
  = f.select :stock_id, options_for_select( @stocks_list, selected: position.stock_id )
20
20
 
21
- .field
22
- %label long or short?
23
- = f.select :long_or_short, options_for_select([nil, Iro::Strategy::LONG, Iro::Strategy::SHORT], selected: long_or_short )
21
+ -# .field
22
+ -# %label long or short?
23
+ -# = f.select :long_or_short, options_for_select([nil, Iro::Strategy::LONG, Iro::Strategy::SHORT], selected: long_or_short )
24
24
 
25
25
  %label Strategy
26
26
  = f.select :strategy_id, options_for_select( @strategies_list, selected: position.strategy_id )
data/config/routes.rb CHANGED
@@ -9,14 +9,14 @@ Iro::Engine.routes.draw do
9
9
 
10
10
  resources :option_watches
11
11
 
12
- match 'positions/:id/close', to: 'positions#close', as: :close_position, via: [ :get, :post ]
13
- get 'positions/duplicate/:id', to: 'positions#new', as: :duplicate_position
14
- post 'positions/propose', to: 'positions#propose', as: :propose_position
15
- get 'positions/:id/prepare', to: 'positions#prepare', as: :prepare_to_roll_position, defaults: { template: 'gameui' }
16
- match 'positions/:id/prepare2', to: 'positions#prepare2', as: :prepare2_position, defaults: { template: 'gameui' }, via: [ :get, :post ]
17
- match 'positions/:id/prepare3', to: 'positions#prepare3', as: :prepare3_position, defaults: { template: 'gameui' }, via: [ :get, :post ]
18
- post 'positions/:id/roll', to: 'positions#do_roll', as: :roll_position
19
- get 'positions/:id/sync', to: 'positions#sync', as: :sync_position
12
+ match 'positions/:id/close', to: 'positions#close', as: :close_position, via: [ :get, :post ]
13
+ get 'positions/duplicate/:id', to: 'positions#new', as: :duplicate_position
14
+ post 'positions/propose', to: 'positions#propose', as: :propose_position
15
+ get 'positions/:id/prepare', to: 'positions#prepare', as: :prepare_to_roll_position, defaults: { template: 'gameui' }
16
+ match 'positions/:id/prepare2', to: 'positions#prepare2', as: :prepare2_position, defaults: { template: 'gameui' }, via: [ :get, :post ]
17
+ match 'positions/:id/prepare3', to: 'positions#prepare3', as: :prepare3_position, defaults: { template: 'gameui' }, via: [ :get, :post ]
18
+ post 'positions/:id/roll', to: 'positions#do_roll', as: :roll_position
19
+ get 'positions/:id/sync', to: 'positions#sync', as: :sync_position
20
20
  resources :positions
21
21
  resources :profiles
22
22
 
@@ -24,11 +24,14 @@ Iro::Engine.routes.draw do
24
24
  get 'purses/:id', to: 'purses#show', as: :purse, defaults: { template: 'show' }
25
25
  resources :purses
26
26
 
27
+ get 'schwab/sync', to: 'application#schwab_sync', as: :schwab_sync
28
+
27
29
  get 'stocks/sync', to: 'stocks#sync', as: :sync_stocks
28
30
  resources :stocks
29
31
 
30
32
  resources :strategies
31
33
 
34
+ get 'api/oauth2-redirect.html', to: 'api#oauth2_redirect'
32
35
  namespace :api do
33
36
  get 'stocks', to: 'stocks#index'
34
37
  get 'stocks/:ticker', to: 'stocks#show'
data/lib/iron_warbler.rb CHANGED
@@ -4,3 +4,5 @@ require 'haml'
4
4
  require 'mongoid'
5
5
 
6
6
  require "iro/engine"
7
+
8
+
@@ -62,7 +62,8 @@ namespace :iro do
62
62
  # Wco::Exceptionist.notify(e, 'Error in iro:watch_stocks')
63
63
  end
64
64
 
65
- sleep 15*60 # 15 min
65
+ print '.'
66
+ sleep 15 # *60 # 15 min
66
67
  end
67
68
  end
68
69
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: iron_warbler
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.7.28
4
+ version: 2.0.7.30
5
5
  platform: ruby
6
6
  authors:
7
7
  - Victor Pudeyev
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2024-07-18 00:00:00.000000000 Z
11
+ date: 2024-07-31 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: business_time
@@ -218,6 +218,7 @@ files:
218
218
  - app/assets/javascript/iron_warbler/application.js
219
219
  - app/assets/javascript/iron_warbler/gameui.js
220
220
  - app/assets/stylesheets/iron_warbler/Card.scss
221
+ - app/assets/stylesheets/iron_warbler/alerts.scss
221
222
  - app/assets/stylesheets/iron_warbler/application.css
222
223
  - app/assets/stylesheets/iron_warbler/positions.scss
223
224
  - app/assets/stylesheets/iron_warbler/positions_gameui.scss