This is a read-only snapshot of the ComputerCraft forums,
taken in April 2020.
Java coder new to computercraft and lua
Started by Salival, 08 December 2014 - 08:15 PMPosted 08 December 2014 - 09:15 PM
I understand that lua is very simple compared to java, but not everything carries over. I'm a bit overwhelmed, actually. I can do all the basic stuff with lua, for example i made a program that will tell me how many minutes its been since program has been executed. What i want to do with computercraft is essentially make a sort of internet out of computercraft. I guess i need pointers to methods i can call when connecting computers. I need a way to be able to remotely send commands to another computer and a way to save and ediit files on that computer remotely. I guess what i'm looking for is apis but i feel like i'm missing some important things in my core understanding. Any pointers?
Posted 08 December 2014 - 11:23 PM
If you're looking to create such a system yourself, ElvishJerricco's links are a good place to start. If you want a ssh-alike program without needing to write it yourself, you may be interested in nsh. Of course, if you're interested in making something yourself, you've come to the right place! We'll be happy to answer questions along the way.
Posted 09 December 2014 - 03:06 AM
I'd like to use bundled cables that have 16 max redstone connections to make a sort of transport bus. I'm essentially just using minecraft as an engaging way to practice new concepts. So i will essentially encode information into 16 bits and decode it out the other end. Thank you for the links, i will make sure to look at them and tinker around. You'll probably be seeing a lot more of me in the following weeks, i love the concept of computercraft and will be coding away!
Ah, was very sad to see the server i am on runs computercraft 1.63, which does not actually support redpowers bundled cables. I don't really want to bother with a cumbersome slave set up, so i'll ask one more question: could i make a seriel bus with rednet?
Ah, was very sad to see the server i am on runs computercraft 1.63, which does not actually support redpowers bundled cables. I don't really want to bother with a cumbersome slave set up, so i'll ask one more question: could i make a seriel bus with rednet?
Posted 09 December 2014 - 07:04 AM
In that case, you might be interested in the really old versions of the built-in rednet API, since it used to include a bundled cable rednet option.
Edit: In regards to you being on 1.63, that version may actually support using the MFR bundled cables. I can't exactly recall whether it does or not.
Edit: In regards to you being on 1.63, that version may actually support using the MFR bundled cables. I can't exactly recall whether it does or not.
Posted 09 December 2014 - 07:19 AM
Bundled cables of all types have been out of order since ComputerCraft 1.6 - you need CC 1.58 (for MC 1.6.4) or earlier to take full advantage of them. There've been partial support patches released here and there, but as far as I'm aware, none that support both read and write access. It's starting to look like this isn't going to change, which is unfortunate.
The modern rednet API (as described through the link EJ posted) can be used to much the same "effect" as redstone bundled cables (at least, as far as computer-to-computer transmissions go), but it removes the timing issues you'd encounter doing things through redstone.
The modern rednet API (as described through the link EJ posted) can be used to much the same "effect" as redstone bundled cables (at least, as far as computer-to-computer transmissions go), but it removes the timing issues you'd encounter doing things through redstone.
Posted 09 December 2014 - 02:01 PM
Alright. i've moved on to a different idea. I'm using the shell api to open tabs of programs to run simultaneously on the same machine. It seems like these programs will sorta just disappear? For example, i'll have a host program sets a computer up for hosting, then it opens a read program in a different tab and moves on to a command line simulator
the tab it makes doesn't last long before it just sorta disappears. Very frustrating as the tab will be handling input from computers of the same protocol and writing them to file.
the tab it makes doesn't last long before it just sorta disappears. Very frustrating as the tab will be handling input from computers of the same protocol and writing them to file.
Posted 10 December 2014 - 01:09 AM
Can't comment without seeing the code in concern, sorry.
Posted 10 December 2014 - 02:18 AM
ahh, alright
when calling a new tab to run the program it will typically run for a bit, then close. regardless of what is in the program.
rednet.open('left')
rednet.host('trans-tec', 'trans-tec_server')
print('Now Hosting')
rednet.broadcast('trans-tec_server host' boot', 'trans-tec')
sleep(3)
rednet.broadcast('trans-tec_server now hosting!')
--shell.openTab('read')
--multishell.setTitle(k, 'user-listener')
shell.run('bg read')
a = 'hi'
while a == 'unhost' == false do
print('enter a command...')
a = io.read()
end
when calling a new tab to run the program it will typically run for a bit, then close. regardless of what is in the program.
Edited on 10 December 2014 - 01:19 AM
Posted 10 December 2014 - 02:25 AM
ahh, alrightrednet.open('left') rednet.host('trans-tec', 'trans-tec_server') print('Now Hosting') rednet.broadcast('trans-tec_server host' boot', 'trans-tec') sleep(3) rednet.broadcast('trans-tec_server now hosting!') --shell.openTab('read') --multishell.setTitle(k, 'user-listener') shell.run('bg read') a = 'hi' while a == 'unhost' == false do print('enter a command...') a = io.read() end
when calling a new tab to run the program it will typically run for a bit, then close. regardless of what is in the program.
There's no program called "read".
Posted 10 December 2014 - 02:31 AM
i created read. Whatever read is, it seems to close automatically after a certain period of time. i am on a server
Posted 10 December 2014 - 03:23 AM
Can we have the code for the read program as well?
Posted 10 December 2014 - 03:31 AM
sure,
In short, it seems like depending on my timeout time it will close the tab. I do not want it to do this, as i need it to wait constantly for input from computers under
the trans-tec protocol and for now print them to a logs file.
while true do
sleep(3)
id, message = rednet.receive('trans-tec', 5)
local file = fs.open('threads', 'w')
file.write('user' ..id ..message)
file.close()
end
In short, it seems like depending on my timeout time it will close the tab. I do not want it to do this, as i need it to wait constantly for input from computers under
the trans-tec protocol and for now print them to a logs file.
Posted 10 December 2014 - 03:45 AM
That's probably because it's trying to concatenate string and nil.
Run your read program without putting it in the background.
The reason it was closing, was because it was erroring, and not showing you the error.
As for the rest of your code in that program, if you're actually wanting to use it entirely, you'll probably want to handle multiple inputs and not wipe them everytime.
Run your read program without putting it in the background.
The reason it was closing, was because it was erroring, and not showing you the error.
As for the rest of your code in that program, if you're actually wanting to use it entirely, you'll probably want to handle multiple inputs and not wipe them everytime.
local file = fs.open("threads","w")
while true do
local id,message = rednet.receive("trans-tec") --#Don't need a timeout, defaults to 0 which is never timeout.
file.write("user "..id.." "..message)
file.flush() --#Keeps the file open, but saves what you've done so far.
end
Edited on 10 December 2014 - 03:06 AM
Posted 10 December 2014 - 04:31 AM
Thank you so much! I can't believe it was just because of the way i was concatenating it. Would it be better to use append if i don't want to overwrite the file with each entry or is flush effectively working like that?
also the reason i wouldn't want a timeout would be so it never runs the next line of code with nil values, correct?
also the reason i wouldn't want a timeout would be so it never runs the next line of code with nil values, correct?
Posted 10 December 2014 - 04:43 AM
Appending. If you want to use run it and not erase the data that was there when you ran it last, yeah you'd want to open in append.
What flush is doing is it's flushing the internal buffer into memory, which means that whatever data you write is never actually saved to the file until it's closed or flushed, it's saved into lets say an internal table that's then kept up with. If it's not saved by closing or flushing, the whole file gets erased. I'm not the best at explaining this as I don't fully know the whole reasoning. Someone else would be better at explaining this. In my experience though, writing a nil value and then flushing, will still break it.
Timeout. Yeah, if it times out, then it's going to have id and message as nil, and thus give you an error. Not having a timeout still pauses the script and then continues ONLY WHEN it receives a message. It also adds a problem with messages maybe being ignored. If you kept the timeout and checked if the values were nil, then you'd have it sleep for the 3 seconds, if any message, valid or otherwise, comes in during that time, it will be ignored.
What flush is doing is it's flushing the internal buffer into memory, which means that whatever data you write is never actually saved to the file until it's closed or flushed, it's saved into lets say an internal table that's then kept up with. If it's not saved by closing or flushing, the whole file gets erased. I'm not the best at explaining this as I don't fully know the whole reasoning. Someone else would be better at explaining this. In my experience though, writing a nil value and then flushing, will still break it.
Timeout. Yeah, if it times out, then it's going to have id and message as nil, and thus give you an error. Not having a timeout still pauses the script and then continues ONLY WHEN it receives a message. It also adds a problem with messages maybe being ignored. If you kept the timeout and checked if the values were nil, then you'd have it sleep for the 3 seconds, if any message, valid or otherwise, comes in during that time, it will be ignored.
Edited on 10 December 2014 - 03:46 AM
Posted 10 December 2014 - 06:28 AM
Good point. It creates a window where messages were being ignored. Because the timeout thing will only run when there is input from an outside source sleep is unnecessary
Posted 10 December 2014 - 07:01 AM
Lua is a whole different ball of wax than Java. But I think you will find (once you get cozy with Lua for a while) that it's actually quite a nice little dynamic language, and has a lot of neat little features that make it very useful for this sort of stuff.
At least, that's how I feel.
Some gotchas (off the top of my head):
* Despite being a rapid-prototyping sort of language, Lua doesn't do a lot of type-coercion on its own. Strings and numbers are about it. For example, when dumping variables to a string, you'll need a "tostring" function around some types (such as booleans), otherwise Lua will barf with an "attempt to concatenate string and boolean" error.
* Since you are a Java person, I imagine you are familiar with OOP. Lua does OOP, but in a somewhat strange method. It does support automatic method binds, but you have to use a semicolon instead of a dot to invoke that method. So, for a pseudo-class called MyClass, instantiated as "myObject", if you wanted to call the method "myMethod", you would need to use myObject:myMethod(). That will perform the hidden internal logic to auto-populate the "self" argument of your method, so you can refer to the table (which represents the instance of your pseudo-class). Doing myObject.myMethod is totally different, and is the same as a class function in other languages. Be careful of swapping : for . in your code. It will lead to all sorts of strangeness.
* Lua assignment defaults to nil. And Lua hates nil. An invalid functional call in on a class-like table is listed as the some vague error of "attempt to index nil", which isn't very useful at times. Since the Lua compiler and interpreter is very basic, it won't catch errors like "receipt" and "reciept" mixed in the same lexical scope. So you have to watch out for not operating on nil data when you expect something to be there.
* Lua scopes to global when the local keyword isn't used. That's was a big gotcha for someone used to a more stricter, static-typed language. (Like me, when I first started using Lua!) It's easy to accidentally pollute the global namespace with unintentional global variables if you are not careful.
* Lua is thankfully a language that treats functions as first-class citizens, so anonymous functions are great. Also, like Java, scope is also per-block and not per-function as with something like JavaScript or Python. (Be warned: Lua compiler will not warn you if you mask a global variable in the current scope, or even a variable that's part of the parent's scope with a local.)
* Just remember at all times the Lua compiler isn't very smart or sophisticated, so be on your toes for coding mistakes.
Anyway, hope that helps! Just some rambling observations from me about Lua.
At least, that's how I feel.
Some gotchas (off the top of my head):
* Despite being a rapid-prototyping sort of language, Lua doesn't do a lot of type-coercion on its own. Strings and numbers are about it. For example, when dumping variables to a string, you'll need a "tostring" function around some types (such as booleans), otherwise Lua will barf with an "attempt to concatenate string and boolean" error.
* Since you are a Java person, I imagine you are familiar with OOP. Lua does OOP, but in a somewhat strange method. It does support automatic method binds, but you have to use a semicolon instead of a dot to invoke that method. So, for a pseudo-class called MyClass, instantiated as "myObject", if you wanted to call the method "myMethod", you would need to use myObject:myMethod(). That will perform the hidden internal logic to auto-populate the "self" argument of your method, so you can refer to the table (which represents the instance of your pseudo-class). Doing myObject.myMethod is totally different, and is the same as a class function in other languages. Be careful of swapping : for . in your code. It will lead to all sorts of strangeness.
* Lua assignment defaults to nil. And Lua hates nil. An invalid functional call in on a class-like table is listed as the some vague error of "attempt to index nil", which isn't very useful at times. Since the Lua compiler and interpreter is very basic, it won't catch errors like "receipt" and "reciept" mixed in the same lexical scope. So you have to watch out for not operating on nil data when you expect something to be there.
* Lua scopes to global when the local keyword isn't used. That's was a big gotcha for someone used to a more stricter, static-typed language. (Like me, when I first started using Lua!) It's easy to accidentally pollute the global namespace with unintentional global variables if you are not careful.
* Lua is thankfully a language that treats functions as first-class citizens, so anonymous functions are great. Also, like Java, scope is also per-block and not per-function as with something like JavaScript or Python. (Be warned: Lua compiler will not warn you if you mask a global variable in the current scope, or even a variable that's part of the parent's scope with a local.)
* Just remember at all times the Lua compiler isn't very smart or sophisticated, so be on your toes for coding mistakes.
Anyway, hope that helps! Just some rambling observations from me about Lua.
Posted 10 December 2014 - 07:31 AM
That post has actually been extremely helpful and i'm going to make sure to refer to this often. Thank you very much.