Not a member of Pastebin yet?
                        Sign Up,
                        it unlocks many cool features!                    
                - local clientAssignmentDirectory = "usr/"
 - local userList = "user_list"
 - local adminUser = "KillaVanilla"
 - local adminPass = "something"
 - local lastAccessTimes = {}
 - local logfile = "server.log"
 - local logServ = 117
 - function log(stuff)
 - local lHandle = fs.open(logfile, "a")
 - lHandle.writeLine(stuff)
 - lHandle.close()
 - end
 - local function spec_print(...)
 - local args2 = {...}
 - local str = ""
 - for i,v in ipairs(args2) do
 - str = str..v
 - end
 - rednet.send(logServ, textutils.serialize({"LOGSERV", "GradeServ", str}))
 - if http then
 - local wHandle = http.get("http://timeapi.org/utc/now")
 - if wHandle then
 - str = "[ RL TIME: "..wHandle.readAll().." UTC] "..str
 - else
 - str = "[ MC TIME: Day "..os.day().." @ "..textutils.formatTime(os.time()).."} "..str
 - end
 - end
 - print(str)
 - log(str)
 - end
 - local successMsg = textutils.serialize({"assignment", "return_code", "success"})
 - assert(fs.exists(userList), userList.." does not exist!")
 - for i,v in ipairs(rs.getSides()) do
 - if peripheral.getType(v) == "modem" then
 - rednet.open(v)
 - end
 - end
 - if not fs.exists(clientAssignmentDirectory) then
 - fs.makeDir(clientAssignmentDirectory)
 - end
 - local handle = io.open(userList, "r")
 - local cred_table = {}
 - for line in handle:lines() do
 - string.gsub(line, "([%a%p%d]+)%s+([%a%p%d]+)", function(user, pass) cred_table[user] = pass if not fs.exists(fs.combine(clientAssignmentDirectory, user)) then fs.makeDir(fs.combine(clientAssignmentDirectory, user)) end end)
 - end
 - cred_table[adminUser] = adminPass
 - handle:close()
 - local function runTests(inputFile) -- run a simple pair of tests designed to catch (lazy) cheaters and weed out obviously-wrong answers.
 - if not fs.exists(inputFile) then
 - spec_print("Attempted to run test on nonexistent file: "..input)
 - return "false", "File does not exist"
 - end
 - local iHandle = fs.open(inputFile, "r")
 - local input = iHandle.readAll()
 - iHandle.close()
 - for i,v in ipairs(fs.list(clientAssignmentDirectory)) do
 - if fs.isDir(fs.combine(clientAssignmentDirectory, v)) then
 - for i,file in ipairs(fs.list(fs.combine(clientAssignmentDirectory, v))) do
 - if file ~= "SanityTests.log" then
 - local handle = fs.open(fs.combine(fs.combine(clientAssignmentDirectory, v), file), "r")
 - if handle.readAll() == input then
 - handle.close()
 - return "false" -- cheater!
 - end
 - handle.close()
 - end
 - end
 - end
 - end
 - local ok, err = pcall(loadstring(input))
 - return tostring(ok)
 - end
 - local function getLoginCredent(id)
 - for i,v in pairs(lastAccessTimes) do
 - if v[2] == id then
 - return true, i
 - end
 - end
 - end
 - local function runSanityTests()
 - for userID,user in ipairs(fs.list(clientAssignmentDirectory)) do
 - if fs.isDir(fs.combine(clientAssignmentDirectory, user)) then
 - local sanityLog = fs.open(fs.combine(fs.combine(clientAssignmentDirectory, user), "SanityTests.log"), "w")
 - for fileID, fileName in ipairs(fs.list(fs.combine(clientAssignmentDirectory, user))) do
 - if fileName ~= "SanityTests.log" then
 - sanityLog.writeLine(fileName..": "..runTests(fs.combine(fs.combine(clientAssignmentDirectory, user), fileName)))
 - end
 - end
 - sanityLog.close()
 - end
 - end
 - end
 - local function listenerThread()
 - while true do
 - local id, msg = rednet.receive()
 - msg = textutils.unserialize(msg)
 - if msg then
 - local hasLoggedIn, user = getLoginCredent(id)
 - local isAdmin = false
 - if hasLoggedIn then
 - isAdmin = (user == adminUser)
 - end
 - if msg[1] == "assignment" then
 - if msg[2] == "login" then
 - if cred_table[msg[3]] == msg[4] then
 - if msg[3] == adminUser then
 - spec_print("ID "..id.." logged in as "..msg[3]..". (admin account)")
 - else
 - spec_print("ID "..id.." logged in as "..msg[3]..". (student account)")
 - end
 - lastAccessTimes[msg[3]] = {os.clock(), id}
 - rednet.send(id, successMsg)
 - end
 - elseif hasLoggedIn then
 - if msg[2] == "logout" then
 - spec_print("ID "..id.." ("..user..") logged out.")
 - lastAccessTimes[user] = nil
 - rednet.send(id, successMsg)
 - elseif msg[2] == "submit" then
 - if not fs.exists(fs.combine(clientAssignmentDirectory..user, msg[3])) then
 - local file = fs.open(fs.combine(clientAssignmentDirectory..user, msg[3]), "w")
 - file.write(msg[4])
 - file.close()
 - spec_print("ID "..id.." ("..user..") submitted an assignment as file "..msg[3].." ("..fs.getSize(fs.combine(clientAssignmentDirectory..user, msg[3])).." bytes written).")
 - rednet.send(id, successMsg)
 - end
 - lastAccessTimes[user][1] = os.clock()
 - elseif msg[2] == "get_results" then
 - spec_print("ID "..id.." ("..user..") downloaded his/her test results.")
 - local file = fs.open(fs.combine(clientAssignmentDirectory..user, "SanityTests.log"), "r")
 - rednet.send(id, textutils.serialize({"assignment", "results", file.readAll()}))
 - file.close()
 - lastAccessTimes[user][1] = os.clock()
 - elseif isAdmin then
 - local fullFileName = fs.combine(clientAssignmentDirectory, msg[3])
 - if msg[2] == "get" then
 - if fs.exists(fullFileName) then
 - spec_print("ID "..id.." ("..user..") downloaded file "..fullFileName..".")
 - local handle = fs.open(fullFileName, "r")
 - rednet.send(id, textutils.serialize({"assignment", "file", msg[3], handle.readAll()}))
 - handle.close()
 - end
 - elseif msg[2] == "list" then
 - spec_print("ID "..id.." ("..user..") requested directory listing for "..fullFileName..".")
 - if fs.exists(fullFileName) and fs.isDir(fullFileName) then
 - rednet.send(id, textutils.serialize({"assignment", "list", msg[3], fs.list(fullFileName)}))
 - end
 - elseif msg[2] == "put" then
 - local handle = fs.open(fullFileName, "w")
 - handle.write(msg[4])
 - handle.close()
 - spec_print("ID "..id.." ("..user..") uploaded file "..fullFileName.." ("..fs.getSize(fullFileName).." bytes written).")
 - rednet.send(id, successMsg)
 - elseif msg[2] == "delete" then
 - if fs.exists(fullfileName) then
 - fs.delete(fullFileName)
 - spec_print("ID "..id.." ("..user..") deleted file "..fullFileName..".")
 - end
 - end
 - end
 - end
 - end
 - end
 - end
 - end
 - local function timedEventThread()
 - local sanityTestItr = 0
 - while true do
 - local lastAccessTimes_clone = {}
 - for i,v in pairs(lastAccessTimes) do
 - if os.clock() < v[1]+300 then
 - lastAccessTimes_clone[i] = v
 - else
 - spec_print("Automatically logging out ID "..v[2].." ("..i..") due to inactivity.")
 - end
 - end
 - lastAccessTimes = lastAccessTimes_clone
 - sanityTestItr = sanityTestItr+1
 - if sanityTestItr >= 30 then
 - runSanityTests()
 - sanityTestItr = 0
 - end
 - os.sleep(1)
 - end
 - end
 - spec_print("GradeServ V1.2 is ONLINE!")
 - parallel.waitForAll(listenerThread, timedEventThread)
 
Advertisement
 
                    Add Comment                
                
                        Please, Sign In to add comment