Module: Ruqqus
- Defined in:
- lib/ruqqus.rb,
lib/ruqqus/token.rb,
lib/ruqqus/client.rb,
lib/ruqqus/routes.rb,
lib/ruqqus/version.rb,
lib/ruqqus/types/post.rb,
lib/ruqqus/types/user.rb,
lib/ruqqus/types/badge.rb,
lib/ruqqus/types/guild.rb,
lib/ruqqus/types/title.rb,
lib/ruqqus/types/comment.rb,
lib/ruqqus/types/item_base.rb,
lib/ruqqus/types/submission.rb
Overview
Top-level namespace of the Ruqqus gem.
Defined Under Namespace
Modules: Routes Classes: Badge, Client, Comment, Error, Guild, ItemBase, Post, Submission, Title, Token, User
Constant Summary collapse
- HOME =
The base Ruqqus URL.
'https://ruqqus.com'.freeze
- VALID_USERNAME =
A regular expression used for username validation.
/^[a-zA-Z0-9_]{5,25}$/.freeze
- VALID_PASSWORD =
A regular expression used for password validation.
/^.{8,100}$/.freeze
- VALID_GUILD =
A regular expression used for guild name validation.
/^[a-zA-Z0-9][a-zA-Z0-9_]{2,24}$/.freeze
- VALID_POST =
A regular expression used for post/comment ID validation.
/[A-Za-z0-9]+/.freeze
- POST_REGEX =
Captures the ID of a post from a Ruqqus URL
/\/post\/([A-Za-z0-9]+)\/?.*/.freeze
- COMMENT_REGEX =
Captures the ID of a comment from a Ruqqus URL
/\/post\/.+\/.+\/([A-Za-z0-9]+)\/?/.freeze
- VERSION =
The Ruqqus gem version. Version changes implement the following versioning system:
MAJOR
Corresponds to the native Ruqqus API major versionMINOR
Indicates possible breaking API changes for existing codeREVISION
Added functionality, bug-fixes, and other non-breaking alterations
'1.1.5'.freeze
Class Attribute Summary collapse
-
.proxy ⇒ URI?
The URI of the proxy server in use, or
nil
if none has been set.
Class Method Summary collapse
-
.authorize_url(client_id, redirect, scopes, permanent = true, csrf = nil) ⇒ Object
Generates a URL for the user to navigate to that will allow them to authorize an application.
-
.guild_available?(guild_name) ⇒ Boolean
Checks if the specified guild name is available to be created.
-
.imgur_upload(client_id, image_path, **opts) ⇒ String
Helper function to automate uploading images to Imgur anonymously and returning the direct image link.
-
.open_browser(url) ⇒ void
Opens a URL in the system's default web browser, using the appropriate command for the host platform.
-
.proxy_list(anon: :elite, country: nil) ⇒ Array<URI>
Obtains a list of URIs of free proxy servers that can be used to route network traffic through.
-
.username_available?(username) ⇒ Boolean
Checks if the specified username is available to be created.
-
.wait_for_code(port, timeout = 30) ⇒ String?
If using a
localhost
address for your application's OAuth redirect, this method can be used to open a socket and listen for a request, returning the authorization code once it arrives.
Class Attribute Details
.proxy ⇒ URI?
Returns the URI of the proxy server in use, or nil
if none has been set.
|
# File 'lib/ruqqus.rb', line 51
|
Class Method Details
.authorize_url(client_id, redirect, scopes, permanent = true, csrf = nil) ⇒ Object
Generates a URL for the user to navigate to that will allow them to authorize an application.
160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 |
# File 'lib/ruqqus.rb', line 160 def self.(client_id, redirect, scopes, permanent = true, csrf = nil) raise(ArgumentError, 'invalid redirect URI') unless URI.regexp =~ redirect raise(ArgumentError, 'scopes cannot be empty') unless scopes && !scopes.empty? scopes = scopes.map(&:to_sym) raise(ArgumentError, "invalid scopes specified") unless scopes.all? { |s| Client::SCOPES.include?(s) } if scopes.any? { |s| [:create, :update, :guildmaster].include?(s) } && !scopes.include?(:identity) # Add identity permission if missing, which is obviously required for a few other permissions scopes << :identity end url = 'https://ruqqus.com/oauth/authorize' url << "?client_id=#{client_id || raise(ArgumentError, 'client ID cannot be nil')}" url << "&redirect_uri=#{redirect}" url << "&scope=#{scopes.join(',')}" url << "&state=#{csrf || Base64.encode64(SecureRandom.uuid).chomp}" url << "&permanent=#{permanent}" url end |
.guild_available?(guild_name) ⇒ Boolean
Checks if the specified guild name is available to be created.
119 120 121 122 123 124 125 126 127 128 |
# File 'lib/ruqqus.rb', line 119 def self.guild_available?(guild_name) begin response = RestClient.get("#{Routes::GUILD_AVAILABLE}#{guild_name}") json = JSON.parse(response.body, symbolize_names: true) return json[:available] rescue puts 'err' return false end end |
.imgur_upload(client_id, image_path, **opts) ⇒ String
To obtain a free Imgur client ID, visit https://api.imgur.com/oauth2/addclient
No authentication is required for anonymous image upload, though rate limiting (very generous) applies.
Helper function to automate uploading images to Imgur anonymously and returning the direct image link.
100 101 102 103 104 105 106 107 108 109 110 111 |
# File 'lib/ruqqus.rb', line 100 def self.imgur_upload(client_id, image_path, **opts) #noinspection RubyResolve raise(Errno::ENOENT, image_path) unless File.exist?(image_path) raise(ArgumentError, 'client_id cannot be nil or empty') if client_id.nil? || client_id.empty? header = { 'Content-Type': 'application/json', 'Authorization': "Client-ID #{client_id}" } params = { image: File.new(image_path), type: 'file', title: opts[:title], description: opts[:description] } response = RestClient.post('https://api.imgur.com/3/upload', params, header) json = JSON.parse(response.body, symbolize_names: true) json[:data][:link] end |
.open_browser(url) ⇒ void
This method returns an undefined value.
Opens a URL in the system's default web browser, using the appropriate command for the host platform.
188 189 190 191 192 193 194 195 196 197 198 |
# File 'lib/ruqqus.rb', line 188 def self.open_browser(url) cmd = case RbConfig::CONFIG['host_os'] when /mswin|mingw|cygwin/ then "start \"\"#{url}\"\"" when /darwin/ then "open '#{url}'" when /linux|bsd/ then "xdg-open '#{url}'" else raise(Ruqqus::Error, 'unable to determine how to open URL for current platform') end system(cmd) end |
.proxy_list(anon: :elite, country: nil) ⇒ Array<URI>
These proxies are free, keep that in mind. They are refreshed frequently, can go down unexpectedly, be slow, and other manners of inconvenience that can be expected with free services.
Obtains a list of URIs of free proxy servers that can be used to route network traffic through.
65 66 67 68 69 70 71 72 73 74 75 76 |
# File 'lib/ruqqus.rb', line 65 def self.proxy_list(anon: :elite, country: nil) raise(ArgumentError, 'invalid anonymity value') unless %i(transparent anonymous elite).include?(anon.to_sym) url = "https://www.proxy-list.download/api/v1/get?type=https&anon=#{anon}" url << "&country=#{country}" if country RestClient.get(url) do |resp| break if resp.code != 200 return resp.body.split.map { |proxy| URI.parse("https://#{proxy}") } end Array.new end |
.username_available?(username) ⇒ Boolean
Checks if the specified username is available to be created.
136 137 138 139 140 141 142 143 144 |
# File 'lib/ruqqus.rb', line 136 def self.username_available?(username) begin response = RestClient.get("#{Routes::USERNAME_AVAILABLE}#{username}") json = JSON.parse(response.body) return json[username] rescue return false end end |
.wait_for_code(port, timeout = 30) ⇒ String?
This method is blocking, and will not return until a connection is made and data is received on the specified port, or the timeout is reached.
If using a localhost
address for your application's OAuth redirect, this method can be used to open a socket and
listen for a request, returning the authorization code once it arrives.
210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 |
# File 'lib/ruqqus.rb', line 210 def self.wait_for_code(port, timeout = 30) thread = Thread.new do sleep(timeout) TCPSocket.open('localhost', port) { |s| s.puts } end params = {} TCPServer.open('localhost', port) do |server| session = server.accept request = session.gets match = /^GET [\/?]+(.*) HTTP.*/.match(request) Thread.kill(thread) return nil unless match $1.split('&').each do |str| key, value = str.split('=') next unless key && value params[key.to_sym] = value end session.puts "HTTP/1.1 200\r\n" session.puts "Content-Type: text/html\r\n" session.puts "\r\n" session.puts create_response(!!params[:code]) session.close end params[:code] end |