trend 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 9a0e816457dabd59905b38ec854e53a3bb565e0a55d76ce87ac0d191a3134a9a
4
+ data.tar.gz: ceefde2ec29a66596f995e5a9a4c8847d5c839a37e4c0fa84a835eba035ee3df
5
+ SHA512:
6
+ metadata.gz: 383959b7c7ba1331b3f4f5607825e410cf74ef047bf299a3e98fbc0c24bf003e2a9753103ea438b65b1a22d8cf4f6274a55dba2aa87b25ed5a28d041456f3ae0
7
+ data.tar.gz: a4c1bf226d83f76f4a1d4bffb431276b1f9a1fda548d05301efd1053dab8a724fe8bdd069f766e0d2d9cdc06a45dd9fe5936e6b258b8fd57d8e481ce05edb714
@@ -0,0 +1,9 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /_yardoc/
4
+ /coverage/
5
+ /doc/
6
+ /pkg/
7
+ /spec/reports/
8
+ /tmp/
9
+ *.lock
@@ -0,0 +1,3 @@
1
+ ## 0.1.0
2
+
3
+ - First release
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "https://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in trend.gemspec
4
+ gemspec
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2018 Andrew Kane
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
@@ -0,0 +1,87 @@
1
+ # Trend
2
+
3
+ Ruby client for [Trend](https://trendapi.org), the time series API
4
+
5
+ ## Getting Started
6
+
7
+ Add this line to your application’s Gemfile:
8
+
9
+ ```ruby
10
+ gem 'trend'
11
+ ```
12
+
13
+ ### Anomalies
14
+
15
+ Detect anomalies in a time series
16
+
17
+ ```ruby
18
+ # generate series
19
+ series = {}
20
+ date = Date.parse("2018-04-01")
21
+ 28.times do
22
+ series[date] = rand(100)
23
+ date += 1
24
+ end
25
+
26
+ # add an anomaly on Apr 21
27
+ series[date - 8] = 999
28
+
29
+ Trend.anomalies(series)
30
+ ```
31
+
32
+ Works great with libraries like [Groupdate](https://github.com/ankane/groupdate)
33
+
34
+ ```ruby
35
+ series = User.group_by_day(:created_at).count
36
+ Trend.anomalies(series)
37
+ ```
38
+
39
+ ### Forecast
40
+
41
+ Get future predictions for a time series
42
+
43
+ ```ruby
44
+ series = {}
45
+ date = Date.parse("2018-04-01")
46
+ 28.times do
47
+ series[date] = date.wday
48
+ date += 1
49
+ end
50
+
51
+ Trend.forecast(series)
52
+ ```
53
+
54
+ Also works great with Groupdate
55
+
56
+ ```ruby
57
+ series = User.group_by_day(:created_at).count
58
+ Trend.forecast(series)
59
+ ```
60
+
61
+ Specify the number of predictions to return
62
+
63
+ ```ruby
64
+ Trend.forecast(series, count: 3)
65
+ ```
66
+
67
+ ## History
68
+
69
+ View the [changelog](https://github.com/ankane/trend/blob/master/CHANGELOG.md)
70
+
71
+ ## Contributing
72
+
73
+ Everyone is encouraged to help improve this project. Here are a few ways you can help:
74
+
75
+ - [Report bugs](https://github.com/ankane/trend/issues)
76
+ - Fix bugs and [submit pull requests](https://github.com/ankane/trend/pulls)
77
+ - Write, clarify, or fix documentation
78
+ - Suggest or add new features
79
+
80
+ To get started with development and testing:
81
+
82
+ ```sh
83
+ git clone https://github.com/ankane/trend.git
84
+ cd trend
85
+ bundle install
86
+ rake test
87
+ ```
@@ -0,0 +1,29 @@
1
+ require "bundler/gem_tasks"
2
+ require "rake/testtask"
3
+
4
+ Rake::TestTask.new(:test) do |t|
5
+ t.libs << "test"
6
+ t.libs << "lib"
7
+ t.test_files = FileList["test/**/*_test.rb"]
8
+ end
9
+
10
+ task :default => :test
11
+
12
+ task :benchmark do
13
+ require "benchmark/ips"
14
+ require "trend"
15
+
16
+ series = {}
17
+ date = Date.parse("2018-01-01")
18
+ 1000.times do
19
+ series[date] = rand(100)
20
+ date += 1
21
+ end
22
+
23
+ Trend.url = "http://localhost:8000"
24
+
25
+ Benchmark.ips do |x|
26
+ x.report("anomalies") { Trend.anomalies(series) }
27
+ x.report("forecast") { Trend.forecast(series) }
28
+ end
29
+ end
@@ -0,0 +1,33 @@
1
+ require "date"
2
+ require "json"
3
+ require "net/http"
4
+ require "time"
5
+
6
+ require "trend/client"
7
+ require "trend/version"
8
+
9
+ module Trend
10
+ class Error < StandardError; end
11
+
12
+ def self.anomalies(*args)
13
+ client.anomalies(*args)
14
+ end
15
+
16
+ def self.forecast(*args)
17
+ client.forecast(*args)
18
+ end
19
+
20
+ def self.url
21
+ @url ||= ENV["TREND_URL"] || "https://trendapi.org"
22
+ end
23
+
24
+ def self.url=(url)
25
+ @url = url
26
+ @client = nil
27
+ end
28
+
29
+ # private
30
+ def self.client
31
+ @client ||= Client.new
32
+ end
33
+ end
@@ -0,0 +1,53 @@
1
+ module Trend
2
+ class Client
3
+ HEADERS = {
4
+ "Content-Type" => "application/json",
5
+ "Accept" => "application/json"
6
+ }
7
+
8
+ def initialize(url: nil)
9
+ url ||= Trend.url
10
+ @uri = URI.parse(url)
11
+ @http = Net::HTTP.new(@uri.host, @uri.port)
12
+ @http.use_ssl = true if @uri.scheme == "https"
13
+ @http.open_timeout = 3
14
+ @http.read_timeout = 5
15
+ end
16
+
17
+ def anomalies(series, params = {})
18
+ resp = make_request("anomalies", series, params)
19
+ resp["anomalies"].map { |v| parse_time(v) }
20
+ end
21
+
22
+ def forecast(series, params = {})
23
+ resp = make_request("forecast", series, params)
24
+ Hash[resp["forecast"].map { |k, v| [parse_time(k), v] }]
25
+ end
26
+
27
+ private
28
+
29
+ def make_request(path, series, params)
30
+ post_data = {
31
+ series: series
32
+ }.merge(params)
33
+
34
+ begin
35
+ response = @http.post("/#{path}", post_data.to_json, HEADERS)
36
+ rescue Errno::ECONNREFUSED, Timeout::Error => e
37
+ raise Trend::Error, e.message
38
+ end
39
+
40
+ parsed_body = JSON.parse(response.body) rescue {}
41
+
42
+ if !response.is_a?(Net::HTTPSuccess)
43
+ raise Trend::Error, parsed_body["error"] || "Server returned #{response.code} response"
44
+ end
45
+
46
+ parsed_body
47
+ end
48
+
49
+ def parse_time(v)
50
+ v.size == 10 ? Date.parse(v) : Time.parse(v)
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,3 @@
1
+ module Trend
2
+ VERSION = "0.1.0"
3
+ end
@@ -0,0 +1,29 @@
1
+
2
+ lib = File.expand_path("../lib", __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require "trend/version"
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "trend"
8
+ spec.version = Trend::VERSION
9
+ spec.authors = ["Andrew Kane"]
10
+ spec.email = ["andrew@chartkick.com"]
11
+
12
+ spec.summary = "Ruby client for Trend, the time series API"
13
+ spec.homepage = "https://github.com/ankane/trend"
14
+ spec.license = "MIT"
15
+
16
+ # Specify which files should be added to the gem when it is released.
17
+ # The `git ls-files -z` loads the files in the RubyGem that have been added into git.
18
+ spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
19
+ `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
20
+ end
21
+ spec.bindir = "exe"
22
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
23
+ spec.require_paths = ["lib"]
24
+
25
+ spec.add_development_dependency "benchmark-ips"
26
+ spec.add_development_dependency "bundler"
27
+ spec.add_development_dependency "rake"
28
+ spec.add_development_dependency "minitest"
29
+ end
metadata ADDED
@@ -0,0 +1,110 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: trend
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Andrew Kane
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2018-05-24 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: benchmark-ips
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: bundler
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rake
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: minitest
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ description:
70
+ email:
71
+ - andrew@chartkick.com
72
+ executables: []
73
+ extensions: []
74
+ extra_rdoc_files: []
75
+ files:
76
+ - ".gitignore"
77
+ - CHANGELOG.md
78
+ - Gemfile
79
+ - LICENSE.txt
80
+ - README.md
81
+ - Rakefile
82
+ - lib/trend.rb
83
+ - lib/trend/client.rb
84
+ - lib/trend/version.rb
85
+ - trend.gemspec
86
+ homepage: https://github.com/ankane/trend
87
+ licenses:
88
+ - MIT
89
+ metadata: {}
90
+ post_install_message:
91
+ rdoc_options: []
92
+ require_paths:
93
+ - lib
94
+ required_ruby_version: !ruby/object:Gem::Requirement
95
+ requirements:
96
+ - - ">="
97
+ - !ruby/object:Gem::Version
98
+ version: '0'
99
+ required_rubygems_version: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ">="
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ requirements: []
105
+ rubyforge_project:
106
+ rubygems_version: 2.7.6
107
+ signing_key:
108
+ specification_version: 4
109
+ summary: Ruby client for Trend, the time series API
110
+ test_files: []