The "Security sandbox violation" message is a common problem for any Flash developer who try to do a Snapshot of an RTMP Stream. There was a couple of workaround but they stopped working since Flash Player 9.0.115 as it was considered as a possible bug. So, now how to do a proper snapshot of an RTMP stream ? The answer is simple but you’ll need to have the control on the streaming server, whatever it is FMS or Red5.
Flash use a non documented part of the RTMP protocol. When the client connect to an RTMP stream, the server send a packet that will indicate to the client if it can allow access to the bitmap data (pixels) or/and the raw audio data.
Wireshark - Packet capture RtmpSampleAccess
Fix with FMS
I think what is working here for FMS is also working for Wowza servers but I never tried. To fix your problem with Flash Media Server, you can add this two simple line of code inside the application.onConnect function :
appClient.audioSampleAccess = "/"; appClient.videoSampleAccess = "/";
It seem that you can also just edit your application.xml file to add the following inside the Application node :
<AudioSampleAccess enabled="true">/</AudioSampleAccess> <VideoSampleAccess enabled="true">/</VideoSampleAccess>
Beaware that using "/" will allow snapshot on all your streams, you can restrict it accordingly to your needs.
Fix with Red5
On last April I posted a patch to Red5 community that let you handle the problem in the same way that FMS does (Ticket #APPSERVER-315 #498). So, to let your client access the stream, you will need to edit the red5-web.xml of your application :
<bean id="rtmpSampleAccess" class="org.red5.server.stream.RtmpSampleAccess"> <property name="audioAllowed" value="true"/> <property name="videoAllowed" value="true"/> </bean>
All the Red5 project is designed to use beans which make this application quite flexible. So, in the same way, you can implement your own class and add every security check you want before allowing the access to your RTMP streams. All you need to do is implementing a new class with the IRtmpSampleAccess interface and create a bean using your class.
Even with those changes, you could still get the error message if the stream buffer is empty. So be sure to use a proper try/catch in your client application and also to listen for the "NetStatusEvent.NET_STATUS" event. You can start capturing data when the NET_STATUS event return an event.info.code as "NetStream.Buffer.Full" and stop capturing data on "NetStream.Buffer.Empty".