Last active
January 16, 2021 19:21
-
-
Save IS2511/e4c6a6f638609fcfa733ceeb432cfced to your computer and use it in GitHub Desktop.
catbox.lua - catbox.moe api in lua for OpenComputers (https://pastebin.com/kuGkdm53)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
--[[ | |
Catbox https://gist.github.com/IS2511/e4c6a6f638609fcfa733ceeb432cfced | |
An implementation of CatBox.moe API in Lua | |
Pastebin: https://pastebin.com/kuGkdm53 | |
Author: IS2511 | |
parg library | |
https://gist.github.com/IS2511/96847fe185278b457505218b1c141f9d | |
Special thanks to fingercomp | |
]]-- | |
-- Libs, components | |
local shell = require("shell") | |
local fs = require("filesystem") | |
local io = require("io") | |
local print = print -- Bring print() to local so redef not global | |
local os = require("os") | |
local comp = require("computer") | |
if not require("component").isAvailable("internet") then error("No internet card found!") end | |
local compRequest = require("component").internet.request | |
local CONFIG_FILE = fs.concat(os.getenv("HOME"), ".catbox") | |
local HOST = "https://catbox.moe/user/api.php" | |
local ok, parg = pcall(require, "parg") | |
if not ok then | |
print("Library \"parg\" not found!") | |
print("Installing...") | |
if not fs.isDirectory("/usr/lib") then fs.makeDirectory("/usr/lib") end | |
shell.execute("pastebin get nSgXWHtp /usr/lib/parg.lua") | |
print("Done installing!") | |
end | |
local parg = require("parg") | |
-- Command-line arguments | |
local anon, requestTimeout, yesToAll | |
parg.register({"help", "h"}, "flag") | |
parg.register({"anonymous", "a"}, "flag", | |
function (count) anon = (count > 0) or (not fs.exists(CONFIG_FILE)) end) | |
parg.register({"timeout", "t"}, "value", | |
function (value) requestTimeout = tonumber(value) or 10 end) | |
parg.register({"yes", "y"}, "flag", | |
function (count) yesToAll = (count > 0) end) | |
parg.register({"quite", "q"}, "flag", | |
function (count) | |
if count > 0 then | |
print = function (...) end | |
end | |
end) | |
local args = parg( {...} ) | |
if args.quite > 0 then yesToAll = true end | |
-- Helper functions | |
local Multipart = {} | |
function Multipart.generateBorder(str) | |
local border = tostring({}):sub(14) -- 10? | |
local longestOccurence = nil | |
for match in str:gmatch("%-*"..border) do | |
if (not longestOccurence) or (#match > #longestOccurence) then | |
longestOccurence = match | |
end | |
end | |
return longestOccurence and ("-" .. longestOccurence) or border | |
end | |
function Multipart:formData() | |
local border = "" | |
for i, v in ipairs(self.data) do | |
border = border..Multipart.generateBorder(v.value) | |
end | |
local data = "" | |
for i, v in ipairs(self.data) do | |
local params = "" | |
if v.params then | |
for k, vv in pairs(v.params) do | |
params = params.."; "..k.."=\""..vv.."\"" | |
end | |
end | |
data = data..([[--%s | |
Content-Disposition: form-data; name="%s"%s | |
%s | |
]]):format(border, v.name, params, v.value) | |
end | |
data = data.."--"..border.."--" | |
-- data:gsub("\n", "\r\n") -- Nope | |
return data, ("multipart/form-data; boundary="..border) -- data, Content-Type | |
end | |
function Multipart.new() | |
return { | |
formData = Multipart.formData, | |
data = {} | |
} | |
end | |
local function urlEncode(str) | |
if str then | |
str = str:gsub("\n", "\r\n") | |
str = str:gsub("([^%w %-%_%.%~])", function(c) | |
return ("%%%02X"):format(string.byte(c)) | |
end) | |
str = str:gsub(" ", "+") | |
end | |
return str | |
end | |
local function dataUrlEncode(t) | |
local data = "" | |
for k, v in pairs(t) do | |
data = data..k.."="..urlEncode(v).."&" | |
end | |
data = data:sub(1, #data-1) | |
return data | |
end | |
local function request(url, body, headers, method, timeout) | |
local handle, err = compRequest(url, body, headers, method) | |
if not handle then | |
return nil, ("request failed: %s"):format(err or "unknown error") | |
end | |
local start = comp.uptime() | |
while true do | |
local status, err = handle.finishConnect() | |
if status then break end | |
if status == nil then | |
return nil, ("request failed: %s"):format(err or "unknown error") | |
end | |
if comp.uptime() >= start + timeout then | |
handle.close() | |
return nil, "request failed: connection timed out" | |
end | |
os.sleep(0.05) | |
end | |
return handle | |
end | |
-- Main functions | |
local function catboxRequest (reqtype, arg, data) | |
local handle, err | |
if reqtype == "fileupload" then | |
handle, err = request(HOST, data.data, {["Content-Type"] = data.contentType}, "POST", requestTimeout) | |
else | |
handle, err = request(HOST, dataUrlEncode(data), {["Content-Type"] = "application/x-www-form-urlencoded; charset=UTF-8"}, "POST", requestTimeout) | |
end | |
data = nil form = nil contentType = nil -- Clearing memory | |
for i=1, 10 do os.sleep(0) end -- Collect garbadge | |
if handle == nil then | |
print("Request error \""..arg.."\": "..tostring(err)) | |
else | |
local result = "" | |
while true do | |
local chunk, err = handle.read() | |
if not chunk then break end | |
result = result..chunk | |
end | |
if handle.response() == 200 then -- Response code == 200 OK | |
if (result:sub(1, 25) == "https://files.catbox.moe/") or (result:sub(1, 19) == "https://catbox.moe/") then | |
if result:sub(1, 21) == "https://catbox.moe/c/" then -- "createalbum" ? | |
print("Album short: "..result:sub(22)) | |
end | |
print("Link: "..result) | |
else | |
print("Success! "..result) | |
end | |
else | |
print("Catbox error \""..arg.."\": "..result) | |
end | |
end | |
end | |
local function usage (album) | |
if album then | |
print([[ | |
Usage: catbox album <command> [arguments] | |
Every command here needs userhash so be sure you have set it up! | |
Every title or discription must be written in "" if you want to write more than one word! | |
Commands: | |
create <title> <description> <file(s)> - Create album | |
edit <short> <title> <description> [file(s)] - Edit album | |
add <short> <file(s)> - Add files to album | |
remove <short> <file(s)> - Remove files from album | |
delete <short> - Delete album]]) | |
else | |
print([[ | |
Usage: catbox <command> [arguments] | |
Commands: | |
user [userhash] - Get or set current userhash. | |
Pass 'off' to forget set userhash | |
file <filename(s)> - Upload files to catbox.moe | |
url <url(s)> - Upload files from URLs to catbox.moe | |
delete <filenames(s)> - Delete files from catbox.moe. Requires userhash | |
album - Album Managment ('catbox album' for help) | |
-a, --anonymous - Ignore userhash, upload anonymously | |
-h, --help - Print this message | |
-y, --yes - Yes to everything, skip all checks | |
-q, --quite - Suppress all output (except sys err) and --yes]]) | |
end | |
end | |
local function Hash (hash) | |
if hash then | |
local file, err = io.open(CONFIG_FILE, "w") | |
if not file then error(err) end | |
file:write(hash) | |
file:close() | |
hash = true | |
else | |
if anon or (not fs.exists(CONFIG_FILE)) then | |
return nil | |
end | |
local file, err = io.open(CONFIG_FILE, "r") | |
if not file then error(err) end | |
hash = file:read("*l") | |
end | |
return hash | |
end | |
-- Program start | |
if #args == 0 or (args.help > 0) then | |
usage(args[1] == "album") | |
return | |
elseif args[1] == "user" then -- NOTE: user | |
if not args[2] then | |
if fs.exists(CONFIG_FILE) then | |
print("Your current userhash is: "..Hash()) | |
else | |
print("No userhash is currently set, so you are anonymous") | |
end | |
else | |
if args[2] ~= "off" then | |
Hash(args[2]) | |
print("Userhash "..args[2].." set in "..CONFIG_FILE) | |
else | |
fs.remove(CONFIG_FILE) | |
print("You are now Anonymous!") | |
end | |
end | |
elseif args[1] == "file" then -- NOTE: file | |
if #args == 1 then | |
print("Usage: catbox file <filename> [<filename>...] - Uploads files to CatBox.moe") | |
return | |
end | |
if anon then | |
print("Uploading anonymously...") | |
else | |
print("Uploading with userhash...") | |
end | |
for i=2, #args do | |
local path = fs.concat(fs.path(args[0]), args[i]) | |
if fs.exists(path) and (not fs.isDirectory(path)) then | |
local form = Multipart.new() | |
table.insert(form.data, {name = "reqtype", value = "fileupload"}) | |
if not anon then table.insert(form.data, {name = "userhash", value = Hash()}) end | |
table.insert(form.data, { | |
name = "fileToUpload", | |
params = { filename = fs.name(path) }, | |
value = io.open(path):read("*a") }) | |
local data, contentType = form:formData() | |
-- print("DEBUG:") print(data) print(contentType) | |
catboxRequest("fileupload", path, {data = data, contentType = contentType}) | |
else | |
print("File "..path.." does not exist or is a directory!") | |
end | |
end | |
print("Done!") | |
elseif args[1] == "url" then -- NOTE: url | |
if #args == 1 then | |
print("Usage: catbox url <url> [<url>...] - Uploads files from urls to CatBox.moe") | |
return | |
end | |
if anon then | |
print("Uploading anonymously...") | |
else | |
print("Uploading with userhash...") | |
end | |
for i=2, #args do | |
local data = { | |
reqtype = "urlupload", | |
userhash = Hash(), -- If anon Hash():nil | |
url = args[i] | |
} | |
catboxRequest("urlupload", args[i], data) | |
end | |
print("Done!") | |
elseif args[1] == "delete" then -- NOTE: delete | |
if #args == 1 then | |
print("Usage: catbox delete <filename> [<filename>...] - Deletes files from your CatBox.moe account") | |
return | |
end | |
if anon then | |
print("Can't delete files! No userhash!") | |
return | |
end | |
print("Deleting files...") | |
for i=2, #args do | |
local data = { | |
reqtype = "deletefiles", | |
userhash = Hash(), | |
files = args[i] -- Deleting 1 file at a time | |
} | |
catboxRequest("deletefiles", args[i], data) | |
end | |
print("Done!") | |
elseif args[1] == "album" then -- NOTE: album | |
if #args == 1 then | |
usage(true) | |
return | |
end | |
if args[2] == "create" then | |
if #args < 5 then | |
print("Usage: catbox album create <title> <description> <filename> [<filename> ...] - Careates an album with given title, discription and files") | |
return | |
end | |
if anon then | |
print("Anonymous albums are permanently disabled in this program.") | |
print("I don't think they are needed anyway. Use userhash for albums.") | |
return | |
end | |
local title, desc, files = args[3], args[4], "" | |
for i=5, #args do | |
files = files..args[i]..((i ~= #args) and " " or "") | |
end | |
print("Creating Album...") | |
print("Title: "..title) | |
print("Description: "..desc) | |
print("Files: "..files) | |
print() | |
if not yesToAll then | |
io.write("Are you sure? [y/N] ") | |
local answer = io.read() -- "*line" (default) | |
if (string.lower(answer) == "no") or (string.lower(answer) == "n") or (answer == "") then | |
print("Aborting.") | |
return | |
end | |
end | |
local data = { | |
reqtype = "createalbum", | |
userhash = Hash(), | |
title = title, | |
desc = desc, | |
files = files | |
} | |
catboxRequest("createalbum", title, data) | |
print("Done!") | |
elseif args[2] == "edit" then | |
if #args < 5 then | |
print("Usage: catbox album edit <short> <title> <description> [<filename> ...] - Edites album") | |
print("Filenames are optional, BUT if none are specified the album WILL BE EMPTY!") | |
return | |
end | |
if anon then | |
print("Can't edit albums! No userhash!") | |
return | |
end | |
local short, title, desc, files = args[3], args[4], args[5], "" | |
for i=6, #args do | |
files = files..args[i]..((i ~= #args) and " " or "") | |
end | |
print("Editing Album...") | |
print("Short: "..short) | |
print("Title: "..title) | |
print("Description: "..desc) | |
print("Files: "..files) | |
print("Filenames are optional, BUT if none are specified the album WILL BE EMPTY!") | |
print() | |
if not yesToAll then | |
io.write("Are you sure? [y/N] ") | |
local answer = io.read() -- "*line" (default) | |
if (string.lower(answer) == "no") or (string.lower(answer) == "n") or (answer == "") then | |
print("Aborting.") | |
return | |
end | |
end | |
local data = { | |
reqtype = "editalbum", | |
userhash = Hash(), | |
short = short, | |
title = title, | |
desc = desc, | |
files = files | |
} | |
catboxRequest("editalbum", short, data) | |
print("Done!") | |
elseif args[2] == "add" then | |
if #args < 4 then | |
print("Usage: catbox album add <short> <filename> [<filename> ...] - Adds files to the specific album") | |
return | |
end | |
if anon then | |
print("Can't add files to albums! No userhash!") | |
return | |
end | |
local short, files = args[3], "" | |
for i=4, #args do | |
files = files..args[i]..((i ~= #args) and " " or "") | |
end | |
print("Adding files to Album...") | |
print("Short: "..short) | |
print("Files: "..files) | |
print() | |
local data = { | |
reqtype = "addtoalbum", | |
userhash = Hash(), | |
short = short, | |
files = files | |
} | |
catboxRequest("addtoalbum", short, data) | |
print("Done!") | |
elseif args[2] == "remove" then | |
if #args < 4 then | |
print("Usage: catbox album remove <short> <filename> [<filename> ...] - Removes files from the specific album") | |
return | |
end | |
if anon then | |
print("Can't remove files from albums! No userhash!") | |
return | |
end | |
local short, files = args[3], "" | |
for i=4, #args do | |
files = files..args[i]..((i ~= #args) and " " or "") | |
end | |
print("Removing files from Album...") | |
print("Short: "..short) | |
print("Files: "..files) | |
print() | |
local data = { | |
reqtype = "removefromalbum", | |
userhash = Hash(), | |
short = short, | |
files = files | |
} | |
catboxRequest("removefromalbum", short, data) | |
print("Done!") | |
elseif args[2] == "delete" then | |
if #args < 3 then | |
print("Usage: catbox album delete <short> [<short> ...] - Deletes album") | |
return | |
end | |
if anon then | |
print("Can't delete albums! No userhash!") | |
return | |
end | |
local short = args[3] | |
print("Deleting Album...") | |
print("Short: "..short) | |
print() | |
if not yesToAll then | |
io.write("Are you sure? [y/N] ") | |
local answer = io.read() -- "*line" (default) | |
if (string.lower(answer) == "no") or (string.lower(answer) == "n") or (answer == "") then | |
print("Aborting.") | |
return | |
end | |
end | |
local data = { | |
reqtype = "deletealbum", | |
userhash = Hash(), | |
short = short | |
} | |
catboxRequest("deletealbum", short, data) | |
print("Done!") | |
else | |
usage(true) | |
end | |
else | |
usage() | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment