Class: Sudhanva::Client
- Inherits:
-
Object
- Object
- Sudhanva::Client
- Defined in:
- lib/sudhanva/client.rb
Constant Summary collapse
- DEFAULT_BASE_URL =
"https://sudhanva.me/api/v1"- USER_AGENT =
"sudhanva-ruby/#{VERSION}"
Instance Method Summary collapse
- #ask(text, limit: 10, mode: "list") ⇒ Object
- #batch(operations) ⇒ Object
- #create_profile_insight(audience:, idempotency_key:, focus: nil) ⇒ Object
-
#initialize(base_url: DEFAULT_BASE_URL, timeout: 10, transport: nil) ⇒ Client
constructor
A new instance of Client.
- #post(slug) ⇒ Object
- #posts(limit: 20, tag: nil, cursor: nil) ⇒ Object
- #profile(locale: "en") ⇒ Object
- #profile_insight(job_id) ⇒ Object
- #wait_for_profile_insight(job_id, timeout: 30, poll_interval: 1) ⇒ Object
Constructor Details
#initialize(base_url: DEFAULT_BASE_URL, timeout: 10, transport: nil) ⇒ Client
Returns a new instance of Client.
25 26 27 28 29 30 31 32 33 34 35 36 37 |
# File 'lib/sudhanva/client.rb', line 25 def initialize(base_url: DEFAULT_BASE_URL, timeout: 10, transport: nil) raise ArgumentError, "timeout must be positive" unless timeout.positive? @base_url = base_url.sub(%r{/+\z}, "") parsed = URI.parse(@base_url) unless %w[http https].include?(parsed.scheme) && parsed.host raise ArgumentError, "base_url must be an absolute HTTP(S) URL" end @site_url = "#{parsed.scheme}://#{parsed.host}#{":#{parsed.port}" unless parsed.default_port == parsed.port}" @timeout = timeout @transport = transport || method(:default_transport) end |
Instance Method Details
#ask(text, limit: 10, mode: "list") ⇒ Object
97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 |
# File 'lib/sudhanva/client.rb', line 97 def ask(text, limit: 10, mode: "list") raise ArgumentError, "text is required" if text.to_s.empty? raise ArgumentError, "limit must be between 1 and 20" unless (1..20).cover?(limit) request( "POST", "/ask", base: @site_url, json: { query: { text: text, site: @site_url, limit: limit }, prefer: { streaming: false, response_format: "conversational_search", mode: mode }, meta: { version: "0.55" } } ) end |
#batch(operations) ⇒ Object
55 56 57 58 59 |
# File 'lib/sudhanva/client.rb', line 55 def batch(operations) raise ArgumentError, "operations must contain between 1 and 20 items" unless (1..20).cover?(operations.length) request("POST", "/batch", json: { operations: operations }) end |
#create_profile_insight(audience:, idempotency_key:, focus: nil) ⇒ Object
61 62 63 64 65 66 67 68 69 70 71 72 |
# File 'lib/sudhanva/client.rb', line 61 def create_profile_insight(audience:, idempotency_key:, focus: nil) raise ArgumentError, "idempotency_key is required" if idempotency_key.to_s.empty? payload = { audience: audience } payload[:focus] = focus if focus request( "POST", "/profile-insights", headers: { "Idempotency-Key" => idempotency_key }, json: payload ) end |
#post(slug) ⇒ Object
49 50 51 52 53 |
# File 'lib/sudhanva/client.rb', line 49 def post(slug) raise ArgumentError, "slug is required" if slug.to_s.empty? request("GET", "/posts/#{URI.encode_www_form_component(slug)}") end |
#posts(limit: 20, tag: nil, cursor: nil) ⇒ Object
43 44 45 46 47 |
# File 'lib/sudhanva/client.rb', line 43 def posts(limit: 20, tag: nil, cursor: nil) raise ArgumentError, "limit must be between 1 and 100" unless (1..100).cover?(limit) request("GET", "/posts", query: { limit: limit, tag: tag, cursor: cursor }) end |
#profile(locale: "en") ⇒ Object
39 40 41 |
# File 'lib/sudhanva/client.rb', line 39 def profile(locale: "en") request("GET", "/profile", query: { locale: locale }) end |
#profile_insight(job_id) ⇒ Object
74 75 76 77 78 |
# File 'lib/sudhanva/client.rb', line 74 def profile_insight(job_id) raise ArgumentError, "job_id is required" if job_id.to_s.empty? request("GET", "/profile-insights/#{URI.encode_www_form_component(job_id)}") end |
#wait_for_profile_insight(job_id, timeout: 30, poll_interval: 1) ⇒ Object
80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 |
# File 'lib/sudhanva/client.rb', line 80 def wait_for_profile_insight(job_id, timeout: 30, poll_interval: 1) unless timeout.positive? && poll_interval >= 0 raise ArgumentError, "timeout must be positive and poll_interval cannot be negative" end deadline = Process.clock_gettime(Process::CLOCK_MONOTONIC) + timeout loop do job = profile_insight(job_id) return job if %w[succeeded failed].include?(job["status"]) if Process.clock_gettime(Process::CLOCK_MONOTONIC) >= deadline raise Timeout::Error, "profile insight #{job_id} did not finish within #{timeout}s" end sleep(poll_interval) end end |