This is a read-only snapshot of the ComputerCraft forums, taken in April 2020.
applesauce10189's profile picture

read("*")/rednet.open() Help.

Started by applesauce10189, 28 January 2014 - 08:53 AM
applesauce10189 #1
Posted 28 January 2014 - 09:53 AM
I'm making a password program and I also have a house control program, I plan on having both a password and using a wireless modem to open it when I want to. Password for people allowed in 24/7 and wireless modem for when I'm okay with visitors.

Here's what I have so far.

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
term.setTextColor(colors.white)
while true do
  if read("*") or rednet.recieve(1) == "open door" then
	rs.setOutput("left", true)
	sleep(2)
	rs.setOutput("left", false)
  end
end
Edited on 28 January 2014 - 08:54 AM
CometWolf #2
Posted 28 January 2014 - 09:56 AM

if read("*") or rednet.recieve(1) == "open door" then
lol, this won't work as these both block until they are finished, as in take all events. rednet.receive won't be ran until you hit enter on the read funciton.
You'll either have to make your own read function or use the parallel api.
applesauce10189 #3
Posted 28 January 2014 - 10:15 AM
Okay, took your advice and used the parallel API, I know almost nothing of it so I may have used it wrong.

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
while true do
  parallel.waitForAny(local x = read("*"), local password = rednet.receive()) --Unexpected symbol.
  if x or password == "open door" then
    rs.setOutput("left", true)
    sleep(2)
    rs.setOutput("left", false)
  end
end
CometWolf #4
Posted 28 January 2014 - 10:29 AM
You can't pass arguments to the functions called with the parallel api. You'll either have to define them as their own functions with the arguments already passed then pass those functions to the parallel api, or define them as anonymous functions passed to the parallel api.

local password = "derp"
while true do
  local acess = false
  parallel.waitForAny(
    function()
	  if read("*") ==password then
	    acess = true
	  end
    end,
    function()
	  if rednet.receive() == password then
	    acess = true
	  end
    end
  )
  if acess then
    rs.setOutput("left", true)
    sleep(2)
    rs.setOutput("left", false)
  end
end
applesauce10189 #5
Posted 28 January 2014 - 10:40 AM
You can't pass arguments to the functions called with the parallel api. You'll either have to define them as their own functions with the arguments already passed then pass those functions to the parallel api, or define them as anonymous functions passed to the parallel api.

local password = "derp"
while true do
  local acess = false
  parallel.waitForAny(
	function()
	  if read("*") ==password then
		acess = true
	  end
	end,
	function()
	  if rednet.receive() == password then
		acess = true
	  end
	end
  )
  if acess then
	rs.setOutput("left", true)
	sleep(2)
	rs.setOutput("left", false)
  end
end
I always forget you can start a parenthesis on one line and end it on another. Just doesn't feel natural to me.
surferpup #6
Posted 28 January 2014 - 10:44 AM
Change:


parallel.waitForAny(local x = read("*"), local password = rednet.receive()) --Unexpected symbol.

To:


local x,password  
parallel.waitForAny(function() x = read("*") end, function() _,password = rednet.receive() end)

The parallel.waitForAny is expecting functions as arguments. I replaced your assignments with two inline functions. Also, the first return value for rednet.receive() is the senderID, the second is the message. You want the message. I ignored the first return value of rednet.receive() so I could get the message ( _,password = rednet.receive() ). You will have trouble if you don't do that.

Edit: CometWolf was answering this at the same time I was testing my answer. His answer is better developed, although he did not address the problem with your call to rednet.receive()​. I edited mine to emphasize the change I made to your code here.
Edited on 28 January 2014 - 09:53 AM
CometWolf #7
Posted 28 January 2014 - 10:50 AM
I didn't test mine, but looking at yours now i realized the rednet on mine would fail as it's checking the ID for the password :P/>
Edited on 28 January 2014 - 09:54 AM
applesauce10189 #8
Posted 28 January 2014 - 10:57 AM
Okay, I did as you said and now it says I need a ( to close the ) on line 11.


rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")

local password = "open door"
access = false

while true do
  parallel.waitForAny(

  function()
	local x = read("*")
	if x == password then
	  access = true
	end
  end

  function()
	local signal = rednet.receive()
	if id,message == password then
	  access = true
	end
  end
  )
end
EDIT: Didn't see the 2 posts above this. Editting code then going to post it again.
ANOTHER EDIT: All I did was add/change one word. Just going to edit this code to avoid useless posts.
Edited on 28 January 2014 - 10:01 AM
surferpup #9
Posted 28 January 2014 - 10:59 AM
I test mine or I will be taken to the woodshed. Besides, I wanted to check out the use of:


if x or password == "open door" then

I thought this would evaluate to if true == "open door" then… but it turns out it works fine. Not sure exactly why this works, but it does. Learn something new all the time.


This is incorrect. It does not work. You need to change it to:


[if x=="open door" or password == open door" then[/color]
[/code][/color]

[color=#FF0000]I will correct my other posts as well.  This was an error in my test routine when I was checking this.  Sorry. [/color]
Edited on 28 January 2014 - 10:34 AM
CometWolf #10
Posted 28 January 2014 - 10:59 AM
You forgot the "," to seperate the arguments. Put one at the end closing the first function you're passing to the parallel api.
surferpup #11
Posted 28 January 2014 - 11:00 AM
Okay, I did as you said and now it says I need a ( to close the ) on line 11.

You are missing a ,

end
,
function()

I'm signing off this thread – CometWolf, you got this.
Edited on 28 January 2014 - 10:01 AM
CometWolf #12
Posted 28 January 2014 - 11:03 AM
lol, imma ninja!

if x or password == "open door" then
I thought this would evaluate to if true == "open door" then… but it turns out it works fine. Not sure exactly why this works, but it does. Learn something new all the time.
if you'd have done (x or password) then it would use x to compare, if it was not nil or false, and otherwise use password. However what it's doing without the parenthese is this

if x == true
or password == "open door" then
surferpup #13
Posted 28 January 2014 - 11:11 AM
However what it's doing without the parenthese is this

if x == true
or password == "open door" then

I tested that. What I found was that it essentially converted it to this:

if (x=="open door") or (password =="open door") then


What you are suggesting is that it is doing a nil check on x (it is not nil) and a value comparison on password. I am actually pretty impressed that these two logical statements are equivalent:

x or password == "open door"

x == "open door" or password == "open door"


Edit: This post is incorrect. These are not equivalent. The second one is what should be used.


x or password == "open door"  < -- this will not evaluate correctly

x == "open door" or password == "open door"  <-- this will evaluate correctly
Edited on 28 January 2014 - 10:46 AM
applesauce10189 #14
Posted 28 January 2014 - 11:13 AM
Okay here's the final version of my code. It works but one question I have that's some-what unrelated, when I terminate the program I get "Parallel: 22 Terminated" or something like that I don't remember word for word, quick edit. I assume the "Parallel" means the problem occured in the parallel API.


rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")

local password = "open door"
access = false

while true do
  parallel.waitForAny(

  function()
	local x = read("*")
	if x == password then
	  access = true
	end
  end

  ,

  function()
	local id,message = rednet.receive()
	if message == password then
	  access = true
	end
  end
  )

  if access then
	rs.setOutput("left", true)
	sleep(2)
	rs.setOutput("left", false)
  end
end
EDIT: Not sure if anybody saw that but I accidentally posted it without the code. Sorry. Lol.
Edited on 28 January 2014 - 10:16 AM
surferpup #15
Posted 28 January 2014 - 11:21 AM
It is because you did not gracefully exit. The code is waiting for a parallel event when you pressed ctrl-T Note you will get some kind of terminated message any time you ctrl-t a program. You have not given any kind of graceful exit condition. Here is one which will exit when the user types exit or when the rednet message is exit:


while true do
  local x,password  
  parallel.waitForAny(function() x = read("*") end, function() _,password = rednet.receive() end)
  if x == "open door" or password == "open door" then
	--what you already do
  elseif x == "exit" or password == "exit" then
	break;
  end
end
rednet.close("back")

Edit – corrected logical comparison in if statements.
Edited on 28 January 2014 - 10:36 AM
TechMasterGeneral #16
Posted 28 January 2014 - 11:31 AM
Try this…


rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
term.setTextColor(colors.white)
while true do
local cmd = read("*")
local evt, p1, p2, p3 = os.pullEvent("rednet_message")
  if cmd == "open door" or  p2 == "open door" then
		rs.setOutput("left", true)
		sleep(2)
		rs.setOutput("left", false)
  end
end


Ignore this.. I'm night quite sure why it won't work
Edited on 28 January 2014 - 11:16 AM
CometWolf #17
Posted 28 January 2014 - 11:34 AM
Try this…


rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
term.setTextColor(colors.white)
while true do
local cmd = read("*")
local evt, p1, p2, p3 = os.pullEvent("rednet_message")
  if cmd == "open door" or if p1 == 1 and p2 == "open door" then
		rs.setOutput("left", true)
		sleep(2)
		rs.setOutput("left", false)
  end
end
Why this won't work has already been explained…

Lol surf, i was about to ask you about that, but when i qouted the post it was crossed out.
surferpup #18
Posted 28 January 2014 - 11:45 AM
I was
Lol surf, i was about to ask you about that, but when i qouted the post it was crossed out.

I was busy making sure I flagged my error to correct the info. The original logical test used in this code as posted by applesauce10189 will fail. I think I show that now. I really dislike it when I post inaccurate info, I don't want to mislead others.

A for my solution for the graceful exit, that will work fine with the edit I made.

And – yes, you are a ninja.
TechMasterGeneral #19
Posted 28 January 2014 - 12:18 PM
Try this…


rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
term.setTextColor(colors.white)
while true do
local cmd = read("*")
local evt, p1, p2, p3 = os.pullEvent("rednet_message")
  if cmd == "open door" or if p1 == 1 and p2 == "open door" then
		rs.setOutput("left", true)
		sleep(2)
		rs.setOutput("left", false)
  end
end
Why this won't work has already been explained…

Lol surf, i was about to ask you about that, but when i qouted the post it was crossed out.

Why won't it work…
cus i've done stuff similar to that… i'm not sure… oh well then
surferpup #20
Posted 28 January 2014 - 12:44 PM
Why won't it work…
cus i've done stuff similar to that… i'm not sure… oh well then

Take a careful look at what it is doing in the while loop:
  • wait for user input AND THEN
  • wait for rednet message AND THEN
  • do stuff AND THEN
  • go back to while
These are serially performed tasks. What you want to do is wait for EITHER user inout OR a rednet message and then do stuff.
The parallel.waitForAny function does is precisely that. It will wait for any of the functions to yield and then continue. Do you see the difference?
CometWolf #21
Posted 28 January 2014 - 12:45 PM

if read("*") or rednet.recieve(1) == "open door" then
lol, this won't work as these both block until they are finished, as in take all events. rednet.receive won't be ran until you hit enter on the read funciton.
You'll either have to make your own read function or use the parallel api.
Same thing applies to your code. If you receive the rednet message while the user input is active, it will be missed. If you attempt to input the password while waiting for the rednet message, you can't.

Edit: This time i got ninjaed! lol
Edited on 28 January 2014 - 11:46 AM
TechMasterGeneral #22
Posted 28 January 2014 - 12:52 PM
Why won't it work…
cus i've done stuff similar to that… i'm not sure… oh well then

Take a careful look at what it is doing in the while loop:
  • wait for user input AND THEN
  • wait for rednet message AND THEN
  • do stuff AND THEN
  • go back to while
These are serially performed tasks. What you want to do is wait for EITHER user inout OR a rednet message and then do stuff.
The parallel.waitForAny function does is precisely that. It will wait for any of the functions to yield and then continue. Do you see the difference?
Ohhh…
Ok yah i see… thank you for explaining that… i may need to use that for one of my programs…
applesauce10189 #23
Posted 28 January 2014 - 01:58 PM
New problem! I want to use os.pullEvent = os.pullEventRaw but at the same time I want to end/edit the program whenever I want. How do I end the program? Here's what I have so far.

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")

local password = "yoloswag"
access = false

while true do
  parallel.waitForAny(

  function()
    local x = read("*")
    if x == password then
      access = true
    elseif x == "adminPassword" then
       return
    end
  end

  ,

  function()
    local id,message = rednet.receive()
    if message == password then
      access = true
    end
  end
  )

  if access then
    rs.setOutput("left", true)
    sleep(2)
    rs.setOutput("left", false)
    os.reboot()
  end
end
TechMasterGeneral #24
Posted 28 January 2014 - 02:12 PM
New problem! I want to use os.pullEvent = os.pullEventRaw but at the same time I want to end/edit the program whenever I want. How do I end the program? Here's what I have so far.

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")

local password = "yoloswag"
access = false

while true do
  parallel.waitForAny(

  function()
	local x = read("*")
	if x == password then
	  access = true
	elseif x == "adminPassword" then
	   return
	end
  end

  ,

  function()
	local id,message = rednet.receive()
	if message == password then
	  access = true
	end
  end
  )

  if access then
	rs.setOutput("left", true)
	sleep(2)
	rs.setOutput("left", false)
	os.reboot()
  end
end

do you want to end it using a certain key or phrase? if you want to end using a word add this:

else
if x == "quit" then
return false
-- Add this after the check for passwords in the first function
why do you want os.pullEvent to be equal to os.pullEventRaw?
Edited on 28 January 2014 - 01:18 PM
CometWolf #25
Posted 28 January 2014 - 02:26 PM
He wants to overwrite os.pullEvent with os.pullEventRaw to prevent termination with ctrl+t. Doing so and implementing what you suggested should yield the desired result. Though not within the first function. As that will simply end the input function, which will just start up again.
Edited on 28 January 2014 - 01:27 PM
TechMasterGeneral #26
Posted 28 January 2014 - 02:34 PM
Ahhh… here is something that may help…
http://computercraft.info/wiki/Raw_key_events
CometWolf #27
Posted 28 January 2014 - 02:49 PM
That is irrelephant to him unless he intends to create his own read function, which he does not. A quick and dirty way to acheiv what he wants would be to just throw an error when the acess code is input.

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
local password = "yoloswag"
access = false
while true do
  parallel.waitForAny(
  function()
	    local x = read("*")
	    if x == password then
		  access = true
	    elseif x == "adminPassword" then
		   error"Admin acess granted"
	    end
  end
  ,
  function()
	    local id,message = rednet.receive()
	    if message == password then
		  access = true
	    end
  end
  )
  if access then
	    rs.setOutput("left", true)
	    sleep(2)
	    rs.setOutput("left", false)
	    os.reboot()
  end
end
The proper way however, would be to check the input outside of the parallel function and use return from there, like this

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
local password = "yoloswag"
local adminpass = "derpderp"
while true do
  local input = ""
  parallel.waitForAny(
    function()
	  input = read("*")
    end
  ,
  function()
    local _id
	 _id,input = rednet.receive()
  end
  )
  if input == password then
    rs.setOutput("left", true)
    sleep(2)
    rs.setOutput("left", false)
  elseif input == adminpass then
    return
  end
end
applesauce10189 #28
Posted 28 January 2014 - 03:13 PM
That is impossibly far from what I want to do.
Ahhh… here is something that may help…
http://computercraft.&#46;&#46;/Raw_key_events

Comet: I'm going to go with option one out of pure lazyness.

EDIT: It actually looks kind of cool. An error with an error code of "Admin access granted". I like it.
Edited on 28 January 2014 - 02:17 PM
surferpup #29
Posted 28 January 2014 - 03:16 PM
It is because you did not gracefully exit. The code is waiting for a parallel event when you pressed ctrl-T Note you will get some kind of terminated message any time you ctrl-t a program. You have not given any kind of graceful exit condition. Here is one which will exit when the user types exit or when the rednet message is exit:


while true do
  local x,password  
  parallel.waitForAny(function() x = read("*") end, function() _,password = rednet.receive() end)
  if x == "open door" or password == "open door" then
	--what you already do
  elseif x == "exit" or password == "exit" then
	break;
  end
end
rednet.close("back")

So how is that different from what I recommended earlier??
CometWolf #30
Posted 28 January 2014 - 03:21 PM
It is indeed the same. Didn't even cross my mind, sorry about that.
applesauce10189 #31
Posted 28 January 2014 - 03:52 PM
Yet another problem! It isn't opening the door as it should. More specifically. It worked before when I was testing around. I want rednet to open the door as well when I want to temporarily allow visitors. Basically rednet sends "open door" and I turn "open door" into whatever the password is before checking if it's equal to the password. Before, "open door" was the password so it worked but now it doesn't.

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")

local password = "yoloswag"
access = false

while true do
  parallel.waitForAny(

  function()
    local x = read("*")
    if x == password then
      access = true
    elseif x == "adminPassword" then
       error"Admin access granted"
    end
  end

  ,

  function()
    local id,message = rednet.receive()
    if message == "open door" then
      message = password  --Used to be "open door". Changing it to the password.
    end
    if message == password then --Should work but isn't?
      access = true
    end
  end
  )

  if access then
    rs.setOutput("left", true)
    sleep(2)
    rs.setOutput("left", false)
    os.reboot()
  end
end
CometWolf #32
Posted 28 January 2014 - 03:56 PM
idk why it dosen't work, but do this instead

  function()
	local id,message = rednet.receive()
	if message == "open door" then
	  access = true
	end
  end
Also you should define access locally as false within the loop, this way it will revert to false after the doors been opened, and you can get rid of the os.reboot.
Edited on 28 January 2014 - 02:58 PM
applesauce10189 #33
Posted 28 January 2014 - 04:30 PM
Thanks for the help. Also, I need the os.reboot(). This is a door password program. Also it's startup. One more thing, most of the reason I have it say os.reboot() instead of just continuing with the while true do loop is so you don't see a bunch of *'s in the computer.

EDIT: Still doesn't work.

Found the problem. I tried putting os.pullEvent = os.pullEventRaw before changing the password so I needed a disk drive with a different startup and I had to break the computer so I could edit the original startup which caused the id to be raised by 1. I'm using rednet for this area of the program so that explains why it didn't work.
Edited on 28 January 2014 - 03:26 PM
applesauce10189 #34
Posted 28 January 2014 - 04:51 PM
How many problems am I going to have with this program today? Let's find out! Let's +1 that number with this one!
parallel.waitForAny() Is being mean to me >: ( It says unexpected symbol when I close the parenthesis but when I get rid of the parenthesis like it says, then it tells me that it's expecting one at the very end of the code. Which would give me an error because the last section of the code isn't a function.


rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
local potato = fs.open("swag", "r")
local password = potato.readLine()
potato.close()

local access = false

while true do
  parallel.waitForAny(

  function()
	local x = read("*")
	if x == password then
	  access = true
	elseif x == "whynot" then
	   error"Admin access granted"
	end
  end

  ,

  function()
	local id,message = rednet.receive()
	if message == "open door" then
	  access = true
	end
  end

  ,

  function()
	if x == "changepass" then
	  potato.open("swag", "w")
	  local swaggamuffin = read("*")
	  potato.writeLine(swaggamuffin)
	  potato.close()
	end
   )


  if access then
	rs.setOutput("left", true)
	sleep(2)
	rs.setOutput("left", false)
	os.reboot()
  end
end
Edited on 28 January 2014 - 03:51 PM
CometWolf #35
Posted 28 January 2014 - 05:08 PM
you're missing the end to close the last parallel function. Also, you could just do term.clear after an input…
lookin at your code, this will also never happen

	    if x == "changepass" then
as x in the code you posted is a variable local to the funciton you use to read input. As such, it should also be checked in the same function. Or outside the parallel alltogether, like has been previously suggested,
Edited on 28 January 2014 - 04:15 PM
applesauce10189 #36
Posted 28 January 2014 - 05:26 PM
you're missing the end to close the last parallel function. Also, you could just do term.clear after an input…
lookin at your code, this will also never happen

		if x == "changepass" then
as x in the code you posted is a variable local to the funciton you use to read input. As such, it should also be checked in the same function. Or outside the parallel alltogether, like has been previously suggested,
Still doesn't work. I fixed the things you mentioned and it doesn't work.
surferpup #37
Posted 28 January 2014 - 05:34 PM
What he meant, applesauce, was that you need an end here:

function()
        if x == "changepass" then
          potato.open("swag", "w")
          local swaggamuffin = read("*")
          potato.writeLine(swaggamuffin)
          potato.close()
        end
end <-- this is where the end was missing
applesauce10189 #38
Posted 28 January 2014 - 05:41 PM
What he meant, applesauce, was that you need an end here:

function()
		if x == "changepass" then
		  potato.open("swag", "w")
		  local swaggamuffin = read("*")
		  potato.writeLine(swaggamuffin)
		  potato.close()
		end
end <-- this is where the end was missing
Maybe I wasn't clear enough. I fixed it. The problem is at line 8. More specifically

local password = potato.readLine()
Edited on 28 January 2014 - 04:43 PM
applesauce10189 #39
Posted 28 January 2014 - 07:06 PM
I have a password program which is startup. I'm using the fs API to store/change the password. My problem is line 9. Attempt to index ?. I assume I spelled something wrong. I have absolutely no clue what it is though.

rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
local password = 1
local potato = fs.open("swag", "r")
password = potato.readLine()
potato.close()

local access = false

while true do
  parallel.waitForAny(

  function()
	local x = read("*")
	if x == password then
	  access = true
	elseif x == "my2kittys" then
	   error"Admin access granted"
	end
  end

  ,

  function()
	local id,message = rednet.receive()
	if message == "open door" then
	  access = true
	end
  end

  ,

  function()
	local x = read("*")
	if x == "changepass" then
	  potato.open("swag", "w")
	  local swaggamuffin = read("*")
	  potato.writeLine(swaggamuffin)
	  potato.close()
	end
  end

  )

  if access then
	rs.setOutput("left", true)
	sleep(2)
	rs.setOutput("left", false)
	os.reboot()
  end
end
Edited on 28 January 2014 - 06:09 PM
Bomb Bloke #40
Posted 28 January 2014 - 07:43 PM
Line 9:

potato.close()

This attempts to get the index "close" from the "potato" table. Given that it had no trouble getting "readLine" out of it on the line above, I'm guessing you've got the line numbers mixed up?

fs.open() may not be able to get a file handle if eg something else is using the file in concern or the file does not exist. This in itself won't crash your script, but it may lead to a crash if you try to make use of the returned object without checking it first.

Bear in mind that in this particular example, the file "swag" must exist on the root of the computer's drive. If the script is in a sub-folder and you want it to read "swag" from that same subfolder, use:

potato = fs.open(shell.resolve(".").."/swag", "r")
applesauce10189 #41
Posted 28 January 2014 - 07:48 PM
Well I read somewhere else that using fs.open either read/wrote to the file or created the file had it not been there.
http://www.computerc...6871-data-save/
Edited on 28 January 2014 - 06:56 PM
Bomb Bloke #42
Posted 28 January 2014 - 08:02 PM
CometWolf's example uses write mode to potentially write a new file, but you're telling Lua to read an existing one - and in read mode, why would it do any writing?

See the details on the fs.open() wiki page for more info.
applesauce10189 #43
Posted 28 January 2014 - 08:11 PM
Problem solved! Turns out just write creates a new file.
applesauce10189 #44
Posted 29 January 2014 - 11:15 AM
Bomb just to let you know when I made that last post I didn't see yours.
applesauce10189 #45
Posted 29 January 2014 - 03:04 PM
I have a password program which I made 2 other posts about actually but this is a new problem. I'm using the fs API to store/change the password variable. I think the read part works where it reads the password and changes the variable to that but my problem is changing the password. It opens the file and stuff and it doesn't write the new one though, here's my program


rednet.open("back")
term.clear()
term.setCursorPos(1,1)
term.setTextColor(colors.purple)
print("AppleOS v0.1")
local password = 1
local potato = fs.open("swag", "r")
password = potato.readLine()
potato.close()

local access = false

while true do
  parallel.waitForAny(

  function()
    local x = read("*")
    if x == password then
      access = true
    elseif x == "adminpass" then
       error"Admin access granted"
    end
  end

  ,

  function()
    local id,message = rednet.receive()
    if message == "open door" then
      access = true
    end
  end

  ,

  function()
    local x = read("*")
    if x == "changepass" then
      local potato = fs.open("swag", "w")
      local swaggamuffin = read("*")
      potato.writeLine(swaggamuffin)
      potato.close()
    end
  end

  )

  if access then
    rs.setOutput("left", true)
    sleep(2)
    rs.setOutput("left", false)
    os.reboot()
  end
end
OReezy #46
Posted 29 January 2014 - 03:09 PM
Still doesn't work. I fixed the things you mentioned and it doesn't work.

What doesn't work? If its not matching, check whats in your file. If you put "password" (with quotes) in the file, readLine() returns "\"password\"" .

Also what they are telling you about that function is that x is out of scope when you call it.
local x = 5  --variables local to program can be seen/used by anything in program

local function printStuff()
  local x = 10  --variable local to this function can only be seen in this function
  print(x)
end

local function printMore()
  print(x)  --there is no x local to this function so it finds the x local to the program
end

printStuff() -->10
printMore() -->5

So if that block of code has no local variable, it looks for a higher variable. If there isn't one it will get nil.

An easier way to have it change the password would be to add onto the if statement in the first function.

EDIT: Was typing this up when you made a new post
Edited on 29 January 2014 - 02:15 PM
Lyqyd #47
Posted 29 January 2014 - 03:42 PM
I've merged these threads. Please stick to one topic for all questions on a given piece of code. It is much easier for the people trying to help you to provide good help.
applesauce10189 #48
Posted 29 January 2014 - 05:09 PM
Well with the posts merged I am now 100% confused. The last code I posted is the current code. This program is a password program. You put one password and it will open a door adjacent to the computer. You put another password it will give you access to the computer itself as in running/making programs etc. If you put the final password it will allow you to change the password. My problem is the password. I'm trying to use the fs API to store the password so it can be changed and when the program restarts the password will still be what it's been changed to.
Edited on 29 January 2014 - 04:10 PM
TechMasterGeneral #49
Posted 29 January 2014 - 05:32 PM
I've been having problems with that as well… right now all i've been able to do i read, but then it return as a table id with no string data…
you can check out some of my dev code and see if you can figure out a solution from what i have wrote so far…
here
applesauce10189 #50
Posted 29 January 2014 - 05:55 PM
Note: I'm testing this program on a survival server and haven't 100% tested everything after recent changes. Turns out the first function isn't properly working. And by that I mean it isn't opening the door when the password is provided.
Bomb Bloke #51
Posted 29 January 2014 - 06:48 PM
Are you sure there's a password stored in your "swag" file at the moment? Didn't you say it opened the file for writing (which would've deleted the contents), but then didn't write anything in its place?

This is an untested attempt at improving the code somewhat:

Spoiler
rednet.open("back")
term.setTextColor(colors.purple)
local potato = fs.open("swag", "r")
local password = potato.readLine()
potato.close()

local access = false

while true do
  term.clear()
  term.setCursorPos(1,1)
  print("AppleOS v0.1")
  print("Enter password:")

  parallel.waitForAny(

  function()
    local x = read("*")
    if x == password then
      print("Access granted, door opening...")
      access = true
    elseif x == "adminpass" then
       error("Admin access granted. Returning to shell...")
    elseif x == "changepass" then     -- No need for a third function for this, as OReezy pointed out.
      print("Enter new password:")
      password = read("*")            -- Password variable can be updated "right now".
      local potato = fs.open("swag", "w")
      potato.writeLine(password)
      potato.close()
    else
      print("Incorrect!")
      sleep(5)
    end
  end

  ,

  function()
    while not access do  -- This should be looped, in case someone starts spamming eg random rednet broadcasts.
      local id,message = rednet.receive()
      if message == "open door" then access = true end
    end
  end

  )

  if access then
    rs.setOutput("left", true)
    sleep(2)
    rs.setOutput("left", false)  -- Rebooting isn't the best method of looping.
    access = false               -- We just need to revert "access" and make sure "password" is up to date.
  end

  print("")
end
Edited on 29 January 2014 - 05:50 PM
surferpup #52
Posted 29 January 2014 - 10:23 PM
Bomb Bloke's code works fine, except the rednet function is wrong in your current code.

Change this:


function()
    while not access do  -- This should be looped, in case someone starts spamming eg random rednet broadcasts.
      local id,message = rednet.receive()
      if message == "open door" then access = true end
    end
  end

To this:



function()
    repeat -- This should be looped, in case someone starts spamming eg random rednet broadcasts.
      local id,message = rednet.receive()
    until (message == "open door")
    access= true
  end

I have confirmed that this works the way you have discussed it, complete with changing passwords, admin password and rednet functionality.