Connecting to TCP server from flash socket on local environment - actionscript-3

I have made a swf file for distribution version to clients to use on their computer.
and I have a TCP server connected from that swf file.
before testing it, I have read some articles related to policy file on adobe website
I tried to test that, and have used the nodejs and swf file for that
but I failed. here is how it looks like.
crossdomain.xml on root
<?xml version="1.0"?>
<!DOCTYPE cross-domain-policy SYSTEM "http://www.adobe.com/xml/dtds/cross-domain-policy.dtd">
<cross-domain-policy>
<allow-access-from domain="*" to-ports="3000" />
</cross-domain-policy>
tcp_server.js
var sys = require("sys"),
net = require("net");
var server = net.createServer(function(stream) {
stream.addListener("connect", function() {
sys.puts("Client connected");
stream.write("hello\r\n");
});
stream.addListener("data", function(data) {
sys.puts("Received from client: " + data);
stream.write(data);
});
stream.addListener("end", function() {
sys.puts("Client disconnected");
stream.write("goodbye\r\n");
stream.end();
});
});
server.listen(3000, "localhost");
swf file on local
import flash.net.Socket;
var socket:Socket = new Socket();
trace(socket);
trace("a socket is created");
socket.connect("localhost", 3000);
It seems like a long code, anyway
I tested it, and got this error
for wrong code, the policy file at xmlsocket://localhost:843 will be ignored
I can't find what is wrong with my code,
If you know that, Please let me know
Thanks for who reads this question
Have a nice day.

Flash Player checks for a policy file server (port 843 by default), or if necessary, on the socket you're opening (for you, port 3000).
A policy file server is a socket which responds to a with a valid policy file. What's happening with your message is likely that it's sending its request and getting something other than a policy file back, hence invalid syntax from port 3000.
Programming socket to return your crossdomain.xml file over the socket when it got a <policy-file-request/> message.
more http://www.adobe.com/devnet/flashplayer/articles/socket_policy_files.html

Related

In AS3 how to make a socket connection

i have a ServerSocket listening for a ServerSocketConnectEvent.CONNECT event.
serverSocket.bind( 80, "127.0.0.1" );
serverSocket.addEventListener( ServerSocketConnectEvent.CONNECT, onConnect );
serverSocket.listen();
which then listens for a ProgressEvent.SOCKET_DATA event.
private function onConnect( event:ServerSocketConnectEvent ):void
{
clientSocket = event.socket;
clientSocket.addEventListener( ProgressEvent.SOCKET_DATA, onClientSocketData );
}
private function onClientSocketData( event:ProgressEvent ):void
{
var buffer:ByteArray = new ByteArray();
clientSocket.readBytes( buffer, 0, clientSocket.bytesAvailable );
...
Then I'm sending a simple message "hello" from my client.
This works fine when i'm running my client from the IDE.
but when i run the same client as a SWF from my browser i get this message in my buffer:
""<policy-file-request/>""
I've tried trapping this response with code like:
if( buffer.toString().search( "policy-file-request" != -1 ))
{
var str:String = "<?xml version=\"1.0\"?><cross-domain-policy><allow-access-from domain=\"*\" to-ports=\"*\" /></cross-domain-policy>\0";
clientSocket.writeUTFBytes( str );
clientSocket.flush();
}
the code is called but it doesn't work. how do i make the connection?
Please help :)
You need to define a socket policy and serve that xml file to the Flash requests, i.e.
<?xml version="1.0"?>
<!DOCTYPE cross-domain-policy SYSTEM "/xml/dtds/cross-domain-policy.dtd">
<!-- Policy file for xmlsocket://socks.example.com -->
<cross-domain-policy>
<!-- This is a master-policy file -->
<site-control permitted-cross-domain-policies="master-only"/>
<!-- Instead of setting to-ports="*",
administrators can use ranges and commas -->
<!-- This will allow access to ports 123, 456, 457, and 458 -->
<allow-access-from domain="swf.example.com" to-ports="123,456-458" />
</cross-domain-policy>
With the introduction of Adobe Flash Player 9,0,124,0, Flash Player
will not make a socket connection directly to a server without first
obtaining explicit permission from that server. This will require some
systems and networks to open up ports or run new services in order to
support granting permission.
Full samples of policy and server setups at available from:
http://www.adobe.com/devnet/flashplayer/articles/socket_policy_files.html
Flash Player checks for a socket policy file in three places for each IP connection. The checks occur in the following order:
Flash Player first checks port 843 to determine if there is a socket master policy file. If there is no socket master policy file or the socket master policy file has a site-control tag specifying "all", then Flash Player proceeds to the next step. If the site-control tag has a value of "none", then the process stops and the socket is denied a connection.
If an ActionScript Security.loadPolicyFile() command exists within the SWF file, then the Flash Player runtime checks that location. Flash Player checks the destination of the loadPolicyFile() only after it has checked the master policy file on port 843 for permission to acknowledge other policy files. If the developer has not specified a loadPolicyFile() command, then Flash Player checks the destination port of the connection.
The destination port of the connection is the last check made by Flash Player. This check is only performed if the socket master policy file permits Flash Player to check additional locations. If Flash Player still cannot locate a policy file granting permission, then the socket connection is denied.

Register service worker failed with localhost

I have the following error when I try to register a service worker in a basic app served by a node Express V4 server / on Chrome 42:
DOMException: Failed to register a ServiceWorker: A bad HTTP response
code (404) was received when fetching the script. {message: "Failed to
register a ServiceWorker: A bad HTTP res…code (404) was received when
fetching the script.", name: "NetworkError", code: 19, INDEX_SIZE_ERR:
1, DOMSTRING_SIZE_ERR: 2…} code: 19 message: "Failed to
Here is the register code :
if ('serviceWorker' in navigator){
console.log("SW present !!! ");
navigator.serviceWorker.register('worker.js', {
//scope: '/toto/'
}).then(function(registration){
console.log('Service worker registered : ', registration.scope);
})
.catch(function(err){
console.log("Service worker registration failed : ", err);
});
}
I think You are trying to Register non-existent script. In this case this issue comes. Please check your script path and scope path. Maybe you don't have any 'worker.js' in the directory where this script exists. If this is the case, please provide full path or provide worker.js in same directory.
I also had this error when using an express server. It turns out the problem was with the server setup itself, not the service worker registration code. I had told my express app to get index.html as the default root using:
app.get('/', function(req, res) {
res.sendFile(path.join(__dirname + '/index.html'));
});
However I had not told express the location of any other files I wanted it to be able to use. At this stage my only other file was the service worker file which was sitting at the root of the directory so I fixed the problem by adding this line to the server file:
app.use(express.static(__dirname + '/'));
To debug whether your issue is with the server itself you could download Web Server for Chrome and point it at the root directory of your app. Check the server is started and click on the Web Server URL. If your service worker registration now succeeds you'll know it's a problem with your express server setup not your service worker registration code.

Flash Socket connection from SWF hosted by a browser

I am attempting to use TCP Socket from Flash ActionScript. I am using a standard example provided by Adobe. Here is the code:
// Load policy file from remote server.
Security.loadPolicyFile("http://" + serverURL + "/crossdomain.xml");
// Attempt to connect to remote socket server.
try {
msg("Trying to connect to " + serverURL + ":" + portNumber + "\n");
socket.connect(serverURL, portNumber);
} catch (error:Error) {
/*
Unable to connect to remote server, display error
message and close connection.
*/
msg(error.message + "\n");
socket.close();
}
My crossdomain.xml file located on port 80:
<cross-domain-policy xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="http://www.adobe.com/xml/schemas/PolicyFileSocket.xsd">
<allow-access-from domain="*" to-ports="*"/>
</cross-domain-policy>
When I load application, I see in my inspector that it accesses the policy file successfully. However Event.CONNECT is never called. I have tried opening various different ports on various domains including same domain with no luck. Tried different policy files.
What am I missing?
If the allowscriptaccess is false you won't be able to bypass that so what you are missing is the adobe policy server.
http://vvowproject.googlecode.com/svn-history/r41/trunk/server/flashpolicyd.py
On the server open port 843 then use this command
sudo ./flashpolicyd.py --file=crossdomain.xml --port=843
here is the crossdomain.xml
<?xml version="1.0"?>
<!DOCTYPE cross-domain-policy SYSTEM
"http://www.adobe.com/xml/dtds/cross-domain-policy.dtd">
<cross-domain-policy>
<site-control permitted-cross-domain-policies="master-only"/>
<allow-access-from domain="*"/>
<allow-http-request-headers-from domain="*" headers="SOAPAction"/>
</cross-domain-policy>
This will definitely work, i tried it myself with your example.
This is what I know from using TCP/IP Sockets and XML. I've set up a Ruby server with a Flash client successfully, but want to know more about chat servers. I hope some of this is helpful.
You need a Daemon with Flash AS3. Here's the documentation.
http://livedocs.adobe.com/flash/9.0/main/wwhelp/wwhimpl/common/html/wwhelp.htm?context=LiveDocs_Parts&file=00000318.html
alt text http://www.ashcraftband.com/myspace/videodnd/daemonLil.jpg
To create a socket connection, you must create a server-side application to wait for the socket connection request and send a response to the SWF file. This type of server-side application can be written in a programming language such as Java, Python, or Perl. To use the XMLSocket class, the server computer must run a daemon that understands the protocol used by the XMLSocket class. The protocol is described in the following list:
• XML messages are sent over a full-duplex TCP/IP stream socket connection.
• Each XML message is a complete XML document, terminated by a zero (0) byte.
• An unlimited number of XML messages can be sent and received over a single XMLSocket connection.
Understanding the security changes in Flash Player 10
http://www.adobe.com/devnet/flashplayer/articles/fplayer10_security_changes_02.html
XML SECURITY POLICY
<?xml version="1.0"?>
<!DOCTYPE cross-domain-policy SYSTEM
"http://www.adobe.com/xml/dtds/cross-domain-policy.dtd">
<cross-domain-policy>
<site-control permitted-cross-domain-policies="master-only"/>
<allow-access-from domain="*"/>
<allow-http-request-headers-from domain="*" headers="SOAPAction"/>
</cross-domain-policy>
FLASH CLIENT
Remember to set Publish Settings to Access Network Only.
SERVER
Open a separate port for security policy, and keep it running in the background.

Flash+Node.JS+Socket.io stuck at handshake authorized

I'm writing a small game, socket-based obviously. Everything works fine when in localhost, but when I'm running .swf file from my dedicated server, and trying to connect to node.js server, connection is getting stuck at "handshake authorized":
info: Server starting...
info - socket.io started
info: Listening on port 4000
info: Server started.
debug - client authorized
info - handshake authorized _kqPhvoD6jYI-c1Gr7zu
And thats it.
Local SWF File -> Local Node.JS -> works.
Local SWF File -> Remote Node.JS -> works.
Remote SWF File -> Remote Node.js -> doesn't work.
Node version 0.10.12. It's not a firewall or antivirus. Tried running on different ports.
Code example:
//setup express for serving crossdomain on same port as game
var express=require('express');
var app=express();
app.get("/crossdomain.xml", onGetCrossdomain);
var server=require('http').Server(app);
//setup socket io
var socketIo=require('socket.io');
var io=socketIo.listen(server);
//listen on port
server.listen(currentPort);
console.log("Listening on port "+currentPort);
io.set('transports',
[
'flashsocket'
]);
io.sockets.on('connection', onConnection);
function onGetCrossdomain(req, res)
{
res.sendfile(__dirname+'/crossdomain.xml');
}
function onConnection(socket)
{
console.log("connected");
}
I've installed earlier version of node (0.8.25) using n - node version manager (https://npmjs.org/package/n), and everything started working fine. Thanks funseiki!

How to make my PHP Socket Server send a policy file to flash clients?

My flash game needs to connect to my PHP Socket Server. Because of security things, a policy file has to be send to the flash client when it tries to connect.
The following is what I've done.
In Actionscript / Flex 3 / Flash:
Security.loadPolicyFile("http://[SERVER.IP]:9000/crossdomain.xml");
socket.connect(hostName, port); //connect to the socket
[rest of original code]
To make the socket server respond on the request, I added the following to the server:
elseif (preg_match("/policy-file-request/i", $buffer) or preg_match("/crossdomain/i", $buffer)) {
socket_write($socket, '<?xml version="1.0"?><cross-domain-policy><site-control permitted-cross-domain-policies="all"/><allow-access-from domain="*" to-ports="9000" /></cross-domain-policy>');
unset($read_sockets[array_search($socket, $read_sockets)]);
socket_shutdown($socket, 2);
socket_close($socket);
I however get the following error: "Ignoring policy file at (URL) due to missing Content-Type." So, I tried to fix this by adding a header right above my xml code:
socket_write($socket, "Content-Type: text/xml\n");
Unfortunately, I still get the same error. Am I giving the content type in a wrong way?
You need to return a valid HTTP response if you are going to use:
Security.loadPolicyFile("http://[SERVER.IP]:9000/crossdomain.xml");
If the flash is going to connect to your PHP socket server, just skip the above line and it will try the port itself and expect raw data instead of a HTTP response.
Try sending this:
HTTP/1.1 200 OK\r\nContent-Type: text/xml\r\n\r\n
Make sure nothing is sent before this.
Also, send a \r\n before the socket is closed.
you can load the policyfile from any port of the server using Security.loadPolicyFile() ... maybe you should simply serve it per http on port 80, load it from there and then connect to the server ...
also, by default, i think flashplayer 9 (upwards from some minor version) sends a policyfile request to port 943 by default ... so you might put a server there, to do that ...
a little side note: PHP was never designed for socket servers and is not very good at that ... if you can, try using Java, or NekoVM, that you can use with Haxe ... also Haxe remoting, as well as ThreadedRemotingServer might be of interest to you ... there's some good and clear tutorials on the Haxe site ...
Try it with \r\n after the Content-Type.
socket_write($socket, "Content-Type: text/xml\r\n");
Shouldn't you be using a xmlsocket on port 843?
if(trim($buffer) == '<policy-file-request/>') {
$policy_file =
'<'.'?xml version="1.0" encoding="UTF-8"?'.'>'.
'<cross-domain-policy xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="http://www.adobe.com/xml/schemas/PolicyFileSocket.xsd">'.
'<allow-access-from domain="*" to-ports="*" secure="false" />'.
'<site-control permitted-cross-domain-policies="master-only" />'.
'</cross-domain-policy>';
socket_write($socket, $policy_file.chr(0));
}
works fine for me, the client will request a policy file, disconnect, then reconnect after receiving the policy file