iron_warbler 2.0.7.39 → 2.0.7.41

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
  SHA256:
3
- metadata.gz: 706bc42f34e116f0071a21611468365ac0a6a2b76fc722c812a9d0158380898b
4
- data.tar.gz: 670933ff9f081f0c7d31a32a1a99e4af6b933e4d1b019c51b5923d3efd244395
3
+ metadata.gz: 00d253e5183bd431fc4f47681007d9ce860d7ea71ec825247db81d3f56224d4f
4
+ data.tar.gz: 8600938ea2f61303da8f2eae2a4775e13b177cb976211a1911a4f5d9d09b1aba
5
5
  SHA512:
6
- metadata.gz: 7e3039883ab46c0a8231500f29fffba931f2ba8fb45529ea139464246c1657940d97279f1b4f61f9d8a563640384874096c87949cb617c0e96aa34c6e978d946
7
- data.tar.gz: b0b80caa5be42c0062836150043e89ef719df3caac02b4535887b17ea8e6b7d180073b2585db7195f83b0adec264ab4421f7f3fcc830fcf2394657081d2fde40
6
+ metadata.gz: 3867a03b4d259f27256a09eda9047b688f3410301429ea9d8a321875e9d753db9028cadf93fb02f2ea1617e0370ad6e920346d68ae5d673ebaacf8e953c389e2
7
+ data.tar.gz: 6cdc0b4e80653ae44fa231e18007a829f6216a348b4fb6a5279dbf13f88caa7b50ed8d3053344c20680463f3aa5d2d681c6aa0edea48fd3452b8e916ac6ddaf5
@@ -1,6 +1,6 @@
1
1
 
2
2
  class Iro::Api::StocksController < Iro::ApiController
3
- before_action :set_stock, only: [:show, :edit, :update, :destroy]
3
+ before_action :set_stock, only: [:destroy, :edit, :max_pain, :show, :update ]
4
4
 
5
5
  def index
6
6
  @stocks = Iro::Stock.active
@@ -12,6 +12,21 @@ class Iro::Api::StocksController < Iro::ApiController
12
12
  end
13
13
  end
14
14
 
15
+ def max_pain
16
+ authorize! :max_pain, @stock
17
+
18
+ hash = Tda::Option.get_chains({ ticker: @stock.ticker })
19
+ # hash = JSON.parse File.read './trash.json'
20
+ @max_pain = Iro::Option.max_pain hash
21
+
22
+ respond_to do |format|
23
+ format.html
24
+ format.json do
25
+ render layout: false
26
+ end
27
+ end
28
+ end
29
+
15
30
  def show
16
31
  authorize! :show, @stock
17
32
  end_on = Time.now.to_date.in_time_zone('UTC')
@@ -49,4 +49,14 @@ class Iro::ApiController < ActionController::Base
49
49
  sign_in user
50
50
  end
51
51
 
52
+ def set_stock
53
+ begin
54
+ @stock = Iro::Stock.find(params[:id])
55
+ rescue Mongoid::Errors::DocumentNotFound => e
56
+ @stock = Iro::Stock.find_by ticker: params[:id]
57
+ end
58
+ @stocks_list = Iro::Stock.tickers_list
59
+ end
60
+
61
+
52
62
  end
@@ -3,7 +3,7 @@
3
3
  ## https://www.macrotrends.net/stocks/charts/META/meta-platforms/stock-price-history
4
4
  ##
5
5
  class Iro::StocksController < Iro::ApplicationController
6
- before_action :set_stock, only: [:show, :edit, :update, :destroy]
6
+ before_action :set_stock, only: [:destroy, :edit, :show, :update ]
7
7
 
8
8
  def create
9
9
  @stock = Iro::Stock.new(stock_params)
@@ -38,6 +38,8 @@ class Iro::StocksController < Iro::ApplicationController
38
38
  end
39
39
  end
40
40
 
41
+
42
+
41
43
  def new
42
44
  @stock = Iro::Stock.new
43
45
  authorize! :new, @stock
@@ -64,6 +66,25 @@ class Iro::StocksController < Iro::ApplicationController
64
66
  symbol: @stock.ticker,
65
67
  }).order_by({ date: :desc }).limit(100)
66
68
 
69
+ filename = "./data/schwab/#{Time.now.to_date.to_s}-#{@stock.ticker}-chains.json"
70
+ if File.exists? filename
71
+ hash = JSON.parse File.read filename
72
+ else
73
+ hash = Tda::Option.get_chains({ ticker: @stock.ticker })
74
+ File.write filename, hash.to_json
75
+ end
76
+ @max_pain = Iro::Option.max_pain hash
77
+ @max_pain_summary = {}
78
+ @max_pain.each do |date, types|
79
+ all = types['all']
80
+ @max_pain_summary[date] = all.keys[0]
81
+ all.each do |strike, amount|
82
+ if amount < all[@max_pain_summary[date]]
83
+ @max_pain_summary[date] = strike
84
+ end
85
+ end
86
+ end
87
+
67
88
  respond_to do |format|
68
89
  format.html
69
90
  format.json do
@@ -18,8 +18,14 @@ class Iro::Datapoint
18
18
  KIND_TREASURY = 'TREASURY'
19
19
 
20
20
  field :symbol ## ticker, but use 'symbol' here
21
- SYMBOL_BTC = 'BTC'
22
- SYMBOL_ETH = 'ETH'
21
+ ## crypto
22
+ SYMBOL_BTC = 'BTC'
23
+ SYMBOL_ETH = 'ETH'
24
+ ## currencies
25
+ SYMBOL_JPY = 'JPY'
26
+ SYMBOL_COP = 'COP'
27
+ SUMBOL_EUR = 'EUR'
28
+ ## treasuries
23
29
  SYMBOL_T1MO = 'T1MO'
24
30
  SYMBOL_T2MO = 'T2MO'
25
31
  SYMBOL_T3MO = 'T3MO'
@@ -73,6 +73,7 @@ class Iro::Option
73
73
  self[:symbol]
74
74
  end
75
75
 
76
+ before_save :sync, if: ->() { !Rails.env.test? } ## do not sync in test
76
77
  def sync
77
78
  out = Tda::Option.get_quote({
78
79
  contractType: put_call,
@@ -86,6 +87,53 @@ class Iro::Option
86
87
  # self.save
87
88
  end
88
89
 
89
- before_save :sync, if: ->() { !Rails.env.test? } ## do not sync in test
90
+ def self.max_pain hash
91
+ outs = {}
92
+
93
+ %w| put call |.each do |contractType|
94
+ dates = hash["#{contractType}ExpDateMap"]
95
+ dates.each do |_date, strikes| ## _date="2023-02-10:5"
96
+ date = _date.split(':')[0].to_date.to_s
97
+ outs[date] ||= {
98
+ 'all' => {},
99
+ 'put' => {},
100
+ 'call' => {},
101
+ }
102
+
103
+ strikes.each do |_strike, _v| ## _strike="18.5"
104
+ strike = _strike.to_f
105
+
106
+ ## calls
107
+ mem_c = 0
108
+ strikes.keys.reverse.each do |_key|
109
+ if _key == _strike
110
+ break
111
+ end
112
+ key = _key.to_f
113
+ tmp = hash["callExpDateMap"][_date][_key][0]['openInterest'] * ( key - strike )
114
+ mem_c += tmp
115
+ end
116
+ outs[date]['call'][_strike] = mem_c
117
+
118
+ ## puts
119
+ mem_p = 0
120
+ strikes.keys.each do |_key|
121
+ if _key == _strike
122
+ break
123
+ end
124
+ key = _key.to_f
125
+ tmp = hash["putExpDateMap"][_date][_key][0]['openInterest'] * ( strike - key )
126
+ mem_p += tmp
127
+ end
128
+ outs[date]['put'][_strike] = mem_p
129
+ outs[date]['all'][_strike] = mem_c + mem_p
130
+
131
+ end
132
+ end
133
+ end
134
+
135
+ return outs
136
+ end
137
+
90
138
 
91
139
  end
@@ -11,6 +11,7 @@ class Iro::Priceitem
11
11
  ## PUT, CALL, STOCK
12
12
  field :putCall, type: String ## kind
13
13
  field :symbol, type: String
14
+ field :description, type: String
14
15
  field :ticker, type: String
15
16
  # belongs_to :stock, inverse_of: :priceitems
16
17
 
@@ -33,7 +34,12 @@ class Iro::Priceitem
33
34
  field :exchangeName, type: String
34
35
  field :volatility, type: Float
35
36
 
36
- field :expires_on, type: :date
37
+ field :expirationDate, type: :date
38
+ field :delta, type: Float
39
+ field :gamma, type: Float
40
+ field :theta, type: Float
41
+ field :openInterest, type: Integer
42
+ field :strikePrice, type: Float
37
43
 
38
44
  def self.my_find props={}
39
45
  lookup = { '$lookup': {
@@ -35,23 +35,32 @@ class Tda::Option
35
35
  }
36
36
  path = "/chains"
37
37
  out = self.get path, {
38
- basic_auth: { username: SCHWAB_DATA[:key], password: SCHWAB_DATA[:secret] },
39
38
  headers: headers,
40
39
  query: query }
41
40
  timestamp = DateTime.parse out.headers['date']
42
- out = out.parsed_response.deep_symbolize_keys
41
+ out = out.parsed_response
43
42
 
44
- byebug
43
+ # byebug
45
44
 
46
45
  outs = []
47
46
  %w| put call |.each do |contractType|
48
- tmp_sym = "#{contractType}ExpDateMap".to_sym
49
- _out = out[tmp_sym]
47
+ _out = out["#{contractType}ExpDateMap"]
50
48
  _out.each do |date, vs| ## date="2023-02-10:5"
51
49
  vs.each do |strike, _v| ## strike="18.5"
52
- v = _v[0] ## v={} many attrs
53
- v = v.except( :lastSize, :optionDeliverablesList, :settlementType,
54
- :deliverableNote, :pennyPilot, :mini )
50
+ _v = _v[0] ## weird, keep
51
+ # puts! _v, '_v'
52
+
53
+ v = {
54
+ putCall: _v['putCall'],
55
+ symbol: _v['symbol'],
56
+ bid: _v['bid'],
57
+ ask: _v['ask'],
58
+ last: _v['last'],
59
+ totalVolume: _v['totalVolume'],
60
+ openInterest: _v['openInterest'],
61
+ strikePrice: _v['strikePrice'],
62
+ expirationDate: _v['expirationDate'],
63
+ }
55
64
  v.each do |k, i|
56
65
  if i == 'NaN'
57
66
  v[k] = nil
@@ -66,11 +75,13 @@ class Tda::Option
66
75
  end
67
76
 
68
77
  outs.each do |out|
69
- opi = ::Iro::PriceItem.create( out )
78
+ opi = ::Iro::Priceitem.create( out )
70
79
  if !opi.persisted?
71
- puts! opi.errors.full_messages, "Cannot create OptionPriceItem"
80
+ puts! opi.errors.full_messages, "Cannot create PriceItem"
72
81
  end
73
82
  end
83
+
84
+ return out
74
85
  end
75
86
 
76
87
  ##
@@ -0,0 +1,18 @@
1
+
2
+ json.ticker @stock.ticker
3
+ json.last @stock.last
4
+
5
+ json.max_pain do
6
+ @max_pain.each do |date, maps|
7
+ json.set! date do
8
+ json.all do
9
+ json.array! maps['all'] do |strike, value|
10
+ json.strike strike
11
+ json.value value
12
+ end
13
+ end
14
+ end
15
+ end
16
+ end
17
+
18
+
@@ -24,4 +24,6 @@
24
24
  %b 1 yr volatility <br />
25
25
  = @stock.volatility
26
26
 
27
- %h4 Max Pain
27
+ %h4 Max Pain
28
+ %pre
29
+ = JSON.pretty_generate @max_pain_summary
data/config/routes.rb CHANGED
@@ -35,13 +35,14 @@ Iro::Engine.routes.draw do
35
35
 
36
36
  get 'api/oauth2-redirect.html', to: 'api#oauth2_redirect'
37
37
  namespace :api do
38
- get 'stocks', to: 'stocks#index'
39
- get 'stocks/:ticker', to: 'stocks#show'
40
- get 'stocks/:ticker/period/:period', to: 'stocks#show'
41
- get 'stocks/:ticker/from/:begin_on', to: 'stocks#show'
42
- get 'stocks/:ticker/begin_on/:begin_on', to: 'stocks#show'
43
- get 'stocks/:ticker/from/:begin_on/to/:end_on', to: 'stocks#show'
38
+ get 'stocks', to: 'stocks#index'
39
+ get 'stocks/:ticker', to: 'stocks#show'
40
+ get 'stocks/:ticker/begin_on/:begin_on', to: 'stocks#show'
44
41
  get 'stocks/:ticker/begin_on/:begin_on/end_on/:end_on', to: 'stocks#show'
42
+ get 'stocks/:ticker/from/:begin_on', to: 'stocks#show'
43
+ get 'stocks/:ticker/from/:begin_on/to/:end_on', to: 'stocks#show'
44
+ get 'stocks/:ticker/max-pain', to: 'stocks#max_pain'
45
+ get 'stocks/:ticker/period/:period', to: 'stocks#show'
45
46
  end
46
47
 
47
48
  end
data/lib/iron_warbler.rb CHANGED
@@ -25,6 +25,35 @@ class Iro::Iro
25
25
  end
26
26
  end
27
27
 
28
+ def self.get_currencies
29
+ out = HTTParty.get "https://api.currencyfreaks.com/v2.0/rates/latest?apikey=#{CURRENCYFREAKS[:key]}&symbols=COP,EUR,JPY"
30
+ out = out.parsed_response.deep_symbolize_keys!
31
+ out[:rates].each do |currency, value|
32
+
33
+ # opi = OPI.new({
34
+ # putCall: 'CURRENCY',
35
+ # symbol: currency,
36
+ # ticker: currency,
37
+ # exchangeName: 'currencyfreaks',
38
+ # mark: value,
39
+ # lastPrice: value,
40
+ # timestamp: Time.now.to_date,
41
+ # })
42
+ # opi.save!
43
+
44
+ datapoint = Iro::Datapoint.new({
45
+ date: Time.now.to_date,
46
+ quote_at: Time.now,
47
+ kind: Iro::Datapoint::KIND_CURRENCY,
48
+ symbol: currency,
49
+ value: value,
50
+ })
51
+ datapoint.save!
52
+
53
+ print '^'
54
+ end
55
+ end
56
+
28
57
  def self.get_treasuries
29
58
  response = HTTParty.get( "https://home.treasury.gov/resource-center/data-chart-center/interest-rates/daily-treasury-rates.csv/all/#{Time.now.strftime('%Y%m')}?type=daily_treasury_yield_curve&field_tdr_date_value_month=#{Time.now.strftime('%Y%m')}&page&_format=csv")
30
59
  outs = CSV.parse( response.body, { headers: true })
@@ -1,6 +1,14 @@
1
1
 
2
2
  namespace :test do
3
3
 
4
+ desc 'max pain'
5
+ task max_pain: :environment do
6
+ hash = JSON.parse File.read './trash.json'
7
+ puts! hash.keys, '+++ +++ parsed hash'
8
+ outs = Iro::Option.max_pain hash
9
+ byebug
10
+ end
11
+
4
12
  desc 'stock#volatility_mo'
5
13
  task stock_vol_mo: :environment do
6
14
  out = Iro::Stock.find_by( ticker: 'NVDA' ).volatility_from_mo
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.39
4
+ version: 2.0.7.41
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-08-09 00:00:00.000000000 Z
11
+ date: 2024-08-21 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: business_time
@@ -260,6 +260,7 @@ files:
260
260
  - app/views/iro/alerts/_form.haml
261
261
  - app/views/iro/alerts/index.haml
262
262
  - app/views/iro/api/stocks/index.json.jbuilder
263
+ - app/views/iro/api/stocks/max_pain.json.jbuilder
263
264
  - app/views/iro/api/stocks/show.json.jbuilder
264
265
  - app/views/iro/api/stocks/show.json.jbuilder-bk
265
266
  - app/views/iro/application/home.haml