Page 1 of 1

Saving/Loading to/from a file using Flash (Now a tutorial!!)

Posted: 2008.11.24 (22:49)
by Exüberance
OK, I know (as you see later, I may be wrong) Flash, for whatever reason, has no good build-in way of simply reading and writing plain text files. I know you need to have some kind of external program to send information to, which in turn writes the text file, but I have no idea where to find one, or how to do it (though I could probably figure out the later via trial and error). I know that N uses a .sol file, but that works when your offline and, as far as I can see, there are no other files required in order for Flash to access the file, so there must be some way to do in in Flash, but I can't find it. The documentation was really only useful for XML, which I don't want to do.

So, anyways, I want to know how to read and write either an SOL or TXT file using Flash (TXT file is much preffered since I can encrypt and decrypt it. Then again, if you can break into an SOL, you can probably also decompile a SWF and find the cypher, but that would be more work)

Any insight on this would be greatly appreciated.

Nevermind, I figured it out. For other people who want to know how to do this, look up SharedObject in your Flash API.
For an example of how to save an SOL file, see my code in the 4th post

EDIT: I'll post my tutorial right here:


~~~Exüberance's Mini-Tutorial:~~~

Let's start by writing to an SOL file. Let's do it by example, and you should be able to see how it works.

Code: Select all

var awryArray:Array = new Array(42, 88, Math.PI);
var isExuberant:Boolean = true;
var namezorz:String = "Exüberance";

var my_so:SharedObject = SharedObject.getLocal("SOLtest"); //This indicates the filename (SOL will be saved as SOLtest.sol)
my_so.data.awryArray = items_array; //next 3 lines are the data saved to the SOL
my_so.data.isExuberant = currentUserIsAdmin;
my_so.data.namezorz = currentUserName;
my_so.flush(); //the flush command actually writes the information to the file

Now look for the SOL file where your N SOL normally is, plus a few folders that correspond with where the file is saved on your computer. The code above generates a file that will appear like this when oppened in notepad: (well somewhat like this. The characters will look different in different browsers since you're trying to open a file that is not plain text in notepad)
¿ ~TCSO SOLtest itemNumbers 0 @E 1 @V 2 @ !ûTD- adminPrivileges userName Exüberance

And here's another version which does the same thing, but now displays if the process was completed or if Flash failed writing the file.

Code: Select all

var awryArray:Array = new Array(42, 88, Math.PI);
var isExuberant:Boolean = true;
var namezorz:String = "Exüberance";

var my_so:SharedObject = SharedObject.getLocal("SOLtest"); //This indicates the filename (SOL will be saved as SOLtest.sol)
my_so.data.awryArray = items_array; //next 3 lines are the data saved to the SOL
my_so.data.isExuberant = currentUserIsAdmin;
my_so.data.namezorz = currentUserName;
switch(my_so.flush()) {
	case 'pending': trace("Writing to file..."); break;
	case true: trace("W00T! File saved successfully!"); break;
	default: trace("Uh oh! An error occurs writing the file. You are eaten by a grue."); break;
}
So far, so good. Now let's get info from a file! Now let's add this code to our file to retreive the data!

Code: Select all

//Well, input worked good... as far as we know. But, did it really write the data correctly?
//Let's find out by retreiving the data... lolcat style!

var I_can_has_data:SharedObject = SharedObject.getLocal("SOLtest"); //opens up the file to read
for (var my_varz:String in I_can_has_data) { //recall that the changing variable in a for..in loop is a string containing the name of the variable in the object, not that value itself
	trace("I has a " + typeof(I_can_has_data[my_varz]) + ". It has a " + I_can_has_data[my_varz]);
}
//note how this returns a single object. This is because the data is parsed as a single Data type object, rather than serpatate entries as it appears when writing data to the SOL
//Now let's get the data from that object
/* Commented out for reasons below
for (var mah_objekt:String in I_can_has_data) {
	for (var my_varz:String in I_can_has_data[mah_objekt]) {
		trace(I_can_has_data[mah_objekt][my_varz]);
	}
}
*/
//but wait, we don't need to do this. We know that I_can_has_data will only ever have 1 element, and it will be data. Instead, let's use
for (var my_varz:String in I_can_has_data.data) {
        trace(I_can_has_data["data"][my_varz]);
}

//The output to the above 3 lines should be:
/*
Exüberance
true
42,88,3.14159265358979
/*
//I'm in ur code, getin ur dataz.
//Look's like we got all the data! Now you know the basics of using SOLs. Happy coding!
//But, what's this? You say you want to get specific data, not just all the data. Easy! Instead of using the for..in loop, just replace [my_vars] with ["namezorz"] or .namezorz or whatever the name is.
There you go!

Notice how, you use the same command to open an SOL for reading as you do writing. Isn't flash nice?

A little bit on encryption (no, not RSA. That would be kind of pointless since you're sending the info to yourself)

Now, if you want to encrypt your file so people can't read it, you might want to use a simple form of encryption in which the data is converted to a string, then you shift the ordinal values of the strings around to get different characters. Of course you don't just shift everything up 5, you would shift each number up by a different pre-defined number (ex with numbers instead of letters: Message: 1337 Key: 8532, Encrypted Message: (1+8) (3+5) (3+3) (7+2) = 9869. Notice how the first and last number encrypted are the same, but the first digits of the original number are not. Also, the middle 2 numbers of the original message are the same, but not when encrypted. If the key is as long as the message. (you would "wrap-around" using modulo, of course, and make sure that you never get ordinal value 0 (null character) or bad things happen.) It's impossible to decode unless you KNOW either what the original message is, or you know a range of things the original message could be and you have a lot of time on your hands. Obviously, this won't be secure if you're encrypting a single digit number, so instead you would generate a random number of non-number characters with the number stuck in a random position there, then encrypt that. When you decrypt it, just look for the things that's a number. As I said before, if the person KNOWS the original message, they can hack the key. (ie, if they know their score in the game is 1337, then they see "Score: 9869" in the file, they can easily crack the code. One thing you could do is name score "jskdfhskj" instead of "score", but a patient hacker could still easily figure out which one is the score, by going into the game and only changing the score. But there's lots of simple, easy things you can do that make breaking the code much much harder. But, this is a tutorial about saving and loading files, not basic encryption. One fun thing you could do to prevent the trial-and-error method of breaking the key is make the file wipe all of it's contents if it received invalid input. Also, instead of using the same key all the time, you could generate a key that depends on something like the number of characters in the file, then add some meaningless variable whose sole purpose is to change the length of the file. Nothing is really fool-proof, but you can make it so hard that no one would ever care to do it. It would be easier to decompile the SWF.

Re: Saving/Loading to/from a file using Flash

Posted: 2008.11.25 (00:24)
by smartalco
Flash can write to .sol files and .sol files alone, and .sol's aren't encrypted, they are really just plain text files with a different extension.
How to use them, I don't know.

Re: Saving/Loading to/from a file using Flash

Posted: 2008.11.25 (00:29)
by Exüberance
smartalco wrote:Flash can write to .sol files and .sol files alone, and .sol's aren't encrypted, they are really just plain text files with a different extension.
How to use them, I don't know.
Actually, I believe SOL files are more like INI files, where they have sections containing key-value pairs. Or maybe they just have key-value pairs. Either way, they are not plain text. Just look at N's SOL. (Well, that tells you that it's either encrypted or not a text file, but since you can download programs to modify SOL files, it's obviously not encrypted, so it's just not a TXT file format.)

EDIT: Well, I was basically right, but it's not a bunch of key-value pairs. It's one whole SharedObject type data, which contains a Data type object, which contains the variables and values.

Re: Saving/Loading to/from a file using Flash

Posted: 2008.11.25 (07:01)
by smartalco
Exüberance wrote:Just look at N's SOL.
Yes, please do, you can read every character. (The strings of numbers? thats just how N saves replay data, its obfuscated so people can't make up their own replay data to have perfect runs, has nothing to do with flash encrypting it)

Saving/Loading to/from a file using Flash (Now a tutorial!)

Posted: 2008.11.25 (18:30)
by Exüberance
smartalco wrote:
Exüberance wrote:Just look at N's SOL.
Yes, please do, you can read every character. (The strings of numbers? thats just how N saves replay data, its obfuscated so people can't make up their own replay data to have perfect runs, has nothing to do with flash encrypting it)
You can make out some characters like password and level data, but you couldn't actually create it in, say, notepad because of the way the data is stored. Yes, you can find some bits of information, but you can't really figure out where it's stored. Just that something has that value. Usually, you can make out the variable names too, but you'll notice characters that are valid ASCII characters, but don't appear on your keyboard. I'm pretty sure that typing those characters into notepad, then converting to an .sol won't work. I can't say for sure, but cases where that works are very very very very rare, since if it's intended to be plain text, all the characters should have ordinal values less than 128. (Edit: nope, not plain text)
EDIT: After experimenting with SOL's, you actually lose a LOT of information looking at it in notepad. It doesn't work at all. Sorry, SOL hackers, but it's not THAT easy!

EDIT: After googling, wikipediaing, and rooting around Flash's documentation, I've discovered the secrets of the elusive .SOL file (Local Shared Object. Don't ask me why it's SOL and not LSO. I didn't make it up). If anyone else has trouble with it, search for "Local Shared Object" in the Flash API, and if you still can't figure out it, you could always google it or something.

Problem resolved. This makes life soooo much easier.

EXAMPLE CODE:
EDIT: Moved to first post.

Re: Saving/Loading to/from a file using Flash (Now a tutorial!!)

Posted: 2008.11.26 (03:46)
by mattk210
I'm not sure how useful it is to make tutorials that are freely available on the internet already, but it's well written. I understand you can do file I/O properly online using PHP (but I'm not really a web guy so I can't elaborate), and offline there's an excellent wrapper called SWF studio that's totally awesome and needs your support. You just put stuff like ssCore.writefile() or whatever in your flash and run it through the magical swf studio compiler. You can make your own too I guess but SWF studio is simple to use and also has lots of other stuff, like real encryption for example. And then there's AIR of course, but I don't like the way it's all integrated into Adobe's manager.

smartalco: I'm pretty sure xuberance is right about SOLs. It's overall formatted ASCII-ful but there's binary bits in there too.

Re: Saving/Loading to/from a file using Flash (Now a tutorial!!)

Posted: 2008.11.26 (19:59)
by Exüberance
mattk210 wrote:I'm not sure how useful it is to make tutorials that are freely available on the internet already, but it's well written.
Thanks. I'll probably come back and tidy it up a bit too later. I couldn't find this anywhere online, because I was looking in the wrong places. All I could find was saving thing on servers for highscores and such, but not saving things locally.