1. Run the update program on a computer above a disk drive (with a disk in it).
- This grabs all the pastes from your account and saves them (under the same name as on pastebin) in a folder (named after your username)
2. Place your turtle/computer next to the disk drive, open it
3. You'll be prompted to add a label (if it's not labelled) and set a startup program (leave blank to not set one)
4. Fully updated comp/turtle!
This is the program I use all the time, more than anything else. It allows you to edit your code outside of minecraft and easily transfer everything in-game so easily!
Update: https://pastebin.com/BB7dQGu2
Spoiler
local arg = { ... } if #arg < 2 then -- Check to see if there are saved login details if fs.exists("credentials") then local h = fs.open("credentials", "r") local data = h.readAll() h.close() local data = textutils.unserialize(data) api_user_name = data[1] api_user_password = data[2] else term.clear() term.setCursorPos(1,1) error("Login credentials not specified. Usage: update <username> <password> [-s:save credentials locally]", 0) end else api_user_name = arg[1] api_user_password = arg[2] if fs.exists("username") ~= true then local h = fs.open("username", "w") h.write(api_user_name) h.close() if arg[3] == "-s" then local h = fs.open("credentials", "w") h.write(textutils.serialize({api_user_name, api_user_password})) h.close() end end -- You need to put your api_dev_key here local api_dev_key = "dfe49e216beea148e6acf8d5149d93f1" -- e.g., "cfe49e216beea143e6acf8h5149d93f1" -- Authenticates with Pastebin. -- Example: local agente382 = pastebin.login("AgentE382", "thisisnotmypassword") -- -- Returns user key for use with other API functions. function login(api_user_name, api_user_password) assert(type(api_user_name) == "string" and type(api_user_password) == "string", "Both arguments are required and must be strings!") return http.post( "https://pastebin.com/api/api_login.php", "api_dev_key="..api_dev_key.."&".. "api_user_name="..textutils.urlEncode(api_user_name).."&".. "api_user_password="..textutils.urlEncode(api_user_password) ).readAll() end -- Internal function that parses the pastebin XML response. local function parse(response) local objs = {} for prefix, objstr in string.gmatch(response, "<(.-)>(.-)</%1>") do local obj = {} for key, value in string.gmatch(objstr, "<"..prefix.."_(.-)>(.-)</"..prefix.."_%1>") do obj[key] = value end objs[#objs+1] = obj end return objs end -- Used to be a custom function, but I realized CC-Lua had one already. local url_encode = textutils.urlEncode -- Fetches a paste from Pastebin. -- Example: local rc4 = pastebin.get("Rxe673BJ") -- -- Returns requested paste as a string or an error message. function get(api_paste_key) assert(type(api_paste_key) == "string", "Enter a valid paste key as a string!") local response = http.get("https://pastebin.com/raw.php?i="..url_encode(api_paste_key)) return response and response.readAll() end -- Lists data about all of a user's pastes. Uses user key from login(). Note that this makes it impossible to get data about random people's pastes. -- Example: local allpastes = pastebin.list(agente382, 1000) -- -- Returns a list of data about all pastes associated with a user's account, using the table format described at the end of the document. function list(api_user_key, api_results_limit) assert(type(api_user_key) == "string", "Enter a valid user key as a string!") local urlstr = {"api_dev_key=", url_encode(api_dev_key), "&api_user_key=", url_encode(api_user_key), "&api_option=list"} if api_results_limit then if type(api_results_limit) == "number" then if api_results_limit > 1000 then api_results_limit = 1000 elseif api_results_limit < 1 then api_results_limit = 1 end local len = #urlstr urlstr[len+1] = "&api_results_limit=" urlstr[len+2] = url_encode(api_results_limit) else io.stderr:write("Results limit must be a number!\n") end end local response = http.post("https://pastebin.com/api/api_post.php", table.concat(urlstr)).readAll() if string.find(response,"<") then return parse(response) else return response end end -- Table Format: -- Pastes: -- { -- [1] = { -- date = "1297953260", -- format_short = "javascript", -- key = "0b42rwhf", -- size = "15", -- hits = "15", -- format_long = "JavaScript", -- url = "https://pastebin.com/0b42rwhf", -- title = "javascript test", -- private = "0", -- 0:Public - 1:Unlisted - 2:Private -- expire_date = "1297956860" -- }, -- [2] = { -- date = "1297694343", -- format_short = "text", -- key = "0C343n0d", -- size = "490", -- hits = "65", -- format_long = "None", -- url = "https://pastebin.com/0C343n0d", -- title = "Welcome To Pastebin V3", -- private = "0", -- 0:Public - 1:Unlisted - 2:Private -- expire_date = "0" -- } -- } ------------------------ term.clear() term.setCursorPos(1,1) print("Preparing to update programs...") user_data = login(api_user_name, api_user_password) local allPastes = list(user_data) --"put all pastes in a table" local folderName = api_user_name if peripheral.isPresent("bottom") and peripheral.getType("bottom") == "drive" then print("Disk drive found, updating to disk.") sleep(1) if fs.exists("/disk/" ..folderName.. "/updates") then --"remove the old updates folder" fs.delete("/disk/" ..folderName.. "/updates") end if fs.exists("/disk/" ..folderName) then --"remove the old folder" fs.delete("/disk/" ..folderName) end fs.makeDir("disk/" ..folderName) --"make a new updates folder" downloadDir = "disk/" ..folderName.. "/" else print("Updating computer.") sleep(1) if fs.exists("/" ..folderName.. "/updates") then --"remove the old updates folder" fs.delete("/" ..folderName.. "/updates") end fs.makeDir("/" ..folderName) --"make a new updates folder" downloadDir = folderName.. "/" end for i,v in ipairs(allPastes) do --"for each of my pastes download it and save it (with the name it has on pastebin)" code = http.get("https://pastebin.com/raw.php?i="..allPastes[i]["key"]) if code then h = fs.open(downloadDir..allPastes[i]["title"],"w") h.write(code.readAll()) h.close() term.setCursorPos(1,4) print("\""..allPastes[i]["title"].."\" successfully downloaded ") else print(allPastes[i]["title"] "failed to download") end end term.setCursorPos(1,4) print("Successfully updated "..#allPastes.." programs.") if downloadDir == "disk/" ..folderName then fs.delete("/" ..folderName) fs.copy("disk/" ..folderName, folderName) print("Successfully updated computer.") end if downloadDir == "disk/" ..folderName.. "/" then print("Setting disk startup program.") if fs.exists("/disk/startup") then fs.delete("/disk/startup") end fs.copy("disk/" ..folderName.. "/refresh", "disk/startup") print("Done.") end
Refresh: https://pastebin.com/9mTVTruQ
Spoiler
local start = nil local label = nil if fs.exists("username") then local h = fs.open("username", "r") local api_user_name = h.readAll() h.close() end term.clear() term.setCursorPos(1,1) if os.computerLabel() == nil then print("What label do you want to give this device?") label = io.read() os.setComputerLabel(label) else label = os.computerLabel() end if fs.exists("startup") then fs.delete("/startup") end if os.computerLabel() == "compressor" then start = api_user_name.."/compressor" elseif os.computerLabel() == "cComp" then start = "" shell.run("disk/"..api_user_name.."/update") else print("What program do you want to set as startup?") start = io.read() end if start ~= "" then h = fs.open("startup", "w") h.write("shell.run\(\""..start.."\"\)") h.close() end if fs.exists(api_user_name) then fs.delete("/"..api_user_name) end fs.copy("/disk/"..api_user_name,"/"..api_user_name) print("Device '"..label.."' has been updated") if start ~= "" then print("Startup program set to "..start) else print("No startup program set") end
Edited by campicus, 11 October 2018 - 01:07 AM.