Class: SQA::Ticker

Inherits:
Object
  • Object
show all
Defined in:
lib/sqa/ticker.rb

Overview

sqa/lib/sqa/ticker.rb

Stock ticker symbol validation and lookup using the dumbstockapi.com service. Downloads and caches a CSV file containing ticker symbols, company names, and exchanges.

Examples:

Validating a ticker

SQA::Ticker.valid?('AAPL')  # => true
SQA::Ticker.valid?('FAKE')  # => false

Looking up ticker info

info = SQA::Ticker.lookup('AAPL')
info[:name]      # => "Apple Inc"
info[:exchange]  # => "NASDAQ"

Constant Summary collapse

FILENAME_PREFIX =

Returns Prefix for downloaded CSV filenames.

Returns:

  • (String)

    Prefix for downloaded CSV filenames

"dumbstockapi"
CONNECTION =

Returns Connection to dumbstockapi.com.

Returns:

  • (Faraday::Connection)

    Connection to dumbstockapi.com

Faraday.new(url: "https://dumbstockapi.com")

Class Method Summary collapse

Class Method Details

.dataHash{String => Hash}

Returns the cached ticker data, loading it if necessary.

Returns:

  • (Hash{String => Hash})

    Hash mapping ticker symbols to info hashes



92
93
94
95
# File 'lib/sqa/ticker.rb', line 92

def data
  @data ||= {}
  @data.empty? ? load : @data
end

.download(country = "US") ⇒ Integer

Downloads ticker data from dumbstockapi.com and saves to data directory.

Examples:

SQA::Ticker.download("US")  # => 200

Parameters:

  • country (String) (defaults to: "US")

    Country code for ticker list (default: “US”)

Returns:

  • (Integer)

    HTTP status code from the download request



31
32
33
34
35
36
37
38
39
40
41
# File 'lib/sqa/ticker.rb', line 31

def download(country="US")
  response = CONNECTION.get("/stock?format=csv&countries=#{country.upcase}").to_hash

  if 200 == response[:status]
    filename = response[:response_headers]["content-disposition"].split('=').last.gsub('"','')
    out_path = Pathname.new(SQA.config.data_dir) + filename
    out_path.write response[:body]
  end

  response[:status]
end

.loadHash{String => Hash}

Loads ticker data from cached CSV or downloads if not available. Retries download up to 3 times if no cached file exists.

Returns:

  • (Hash{String => Hash})

    Hash mapping ticker symbols to info hashes



47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
# File 'lib/sqa/ticker.rb', line 47

def load
  tries = 0
  found = false

  until(found || tries >= 3) do
    files     = Pathname.new(SQA.config.data_dir).children.select{|c| c.basename.to_s.start_with?(FILENAME_PREFIX)}.sort
    if files.empty?
      begin
        download
      rescue StandardError => e
        warn "Warning: Could not download ticker list: #{e.message}" if $VERBOSE
      end
      tries += 1
    else
      found = true
    end
  end

  if files.empty?
    warn "Warning: No ticker validation data available. Proceeding without validation." if $VERBOSE
    return {}
  end

  load_from_csv files.last
end

.load_from_csv(csv_path) ⇒ Hash{String => Hash}

Loads ticker data from a specific CSV file.

Parameters:

  • csv_path (Pathname, String)

    Path to CSV file

Returns:

  • (Hash{String => Hash})

    Hash mapping ticker symbols to info hashes



77
78
79
80
81
82
83
84
85
86
87
# File 'lib/sqa/ticker.rb', line 77

def load_from_csv(csv_path)
  @data ||= {}
  CSV.foreach(csv_path, headers: true) do |row|
    @data[row["ticker"]] = {
      name:     row["name"],
      exchange: row["exchange"]
    }
  end

  @data
end

.lookup(ticker) ⇒ Hash?

Looks up information for a specific ticker symbol.

Examples:

SQA::Ticker.lookup('AAPL')  # => { name: "Apple Inc", exchange: "NASDAQ" }
SQA::Ticker.lookup('FAKE')  # => nil

Parameters:

  • ticker (String, nil)

    Ticker symbol to look up

Returns:

  • (Hash, nil)

    Hash with :name and :exchange keys, or nil if not found



106
107
108
109
# File 'lib/sqa/ticker.rb', line 106

def lookup(ticker)
  return nil if ticker.nil? || ticker.to_s.empty?
  data[ticker.to_s.upcase]
end

.reset!Hash

Resets the cached ticker data. Useful for testing to force a fresh load.

Returns:

  • (Hash)

    Empty hash



129
130
131
# File 'lib/sqa/ticker.rb', line 129

def reset!
  @data = {}
end

.valid?(ticker) ⇒ Boolean

Checks if a ticker symbol is valid (exists in the data).

Examples:

SQA::Ticker.valid?('AAPL')  # => true
SQA::Ticker.valid?(nil)     # => false

Parameters:

  • ticker (String, nil)

    Ticker symbol to validate

Returns:

  • (Boolean)

    true if ticker exists, false otherwise



120
121
122
123
# File 'lib/sqa/ticker.rb', line 120

def valid?(ticker)
  return false if ticker.nil? || ticker.to_s.empty?
  data.key?(ticker.to_s.upcase)
end