Topic: Crossdomain.xml

Even after reading every message I can find about crossdomain.xml, there is obviously something I just don't understand because I cannot get a widget to work.

I have a private weather station in my backyard that feeds data to a linux server in my basement once every 5 minutes.  The server hosts apache and is visible to the internet (as www.thehargroves.com).  There is a php script that generates a poorman's RSS feed on demand (www.thehargroves.com/weather/currentwx.php).

I've developed a very simple-minded widget based on the sample RSS widget on the site here that reads my feed to display a few weather stats on my Chumby.  I'm using Flash CS3 for development, and the locally-published .swf file works perfectly.

I created a crossdomain.xml file based upon the sample from Duane and placed it in the root of my webserver (www.thehargroves.com/crossdomain.xml).

I uploaded the widget and added it to a channel -- but it is not successfully retrieving the XML weather data from my website.  I think I don't understand exactly what the crossdomain.xml needs to contain to allow access from my Chumby.  Mine crossdomain.xml says:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE cross-domain-policy SYSTEM "http://www.macromedia.com/xml/dtds/cros … policy.dtd">
<cross-domain-policy>
  <allow-access-from domain="*.chumby.com"/>
</cross-domain-policy>

Is this correct?  --or does the <allow-access-from> tag need to specify something different?

Thanks,

-M.

Re: Crossdomain.xml

The crossdomain.xml file appears to be correct.

My suggestion is that you SSH into the chumby and do the following commands:

stop_control_panel
start_control_panel

The console will then output a lot of debug information, and you'll be able to see what's going on when your widget is being run, including any accesses to your server.  Hopefully that will help you debug this.

Re: Crossdomain.xml

To simplify, I removed all of my other widgets. 

I'm not exactly sure what all I'm seeing, but here is what I think is the relevant part of the trace output:

2007-12-29 19:43:36 TRACE: Processing widget instance
2007-12-29 19:43:36 TRACE: Clearing advance timer handler
2007-12-29 19:43:36 TRACE: Playing widget instance (current play mode "playing")
2007-12-29 19:43:36 TRACE: Loading widget instance into player
2007-12-29 19:43:36 TRACE: - loading widget movie "Elms Neighboorhood Weather" from http://widgets.chumby.com/xml/movies/C6 … 156009DD9B
2007-12-29 19:43:36 kStopSlave: no slave running or slave mismatch for instance id -1
2007-12-29 19:43:36 ClientObject::StartSlaveCommon() starting slave 'http://widgets.chumby.com/xml/movies/C6 … 156009DD9B'
2007-12-29 19:43:36 ClientObject::StartSlaveCommon() created new settings instance 0x00235bb8 to be freed when slave dies
2007-12-29 19:43:36 ClientObject::ClientObject(this=0x001a8050) asynch load = Y
2007-12-29 19:43:36 ClientObject(5) mmobj=0x40a2b5d4, PlatformPlayer=0x40a33d98
2007-12-29 19:43:36 DisplayObject::<constructor>() UDMA is disabled, falling back to /dev/fb[#]
2007-12-29 19:43:36 FrameBuffer::<constructor>(0,320X240) 640 bytes per line, 153600 == buffer size
2007-12-29 19:43:36 FrameBuffer::AssureFrameBuffer() file for /dev/fb0 is 0x235830 (fileno 8)
2007-12-29 19:43:36 FrameBuffer::AssureFrameBuffer() m_frame_buffer=0x40a6c000
2007-12-29 19:43:36 FrameBuffer::GetFrameBuffer(0, 320X240) - creating new FrameBuffer instance 2357c8
2007-12-29 19:43:36 DisplayObject::<constructor> got fb=002357c8 for 320X240 idx=0 153600 bytes
2007-12-29 19:43:36 SoundObject::SoundObject[b](0x002359a0 mmobj=0x40a2b5d4): initializing audio, buffers=16, bpb=2048
2007-12-29 19:43:36 SoundObject::Add[b](this=0x002359a0, mmobj=0x40a2b5d4)
2007-12-29 19:43:36 StreamSoundObject::StreamSoundObject(this=0x002359a0, mmobj=0x40a2b5d4==0x40a2b5d4): setting up audio
2007-12-29 19:43:36 KeyboardObject::<ctor>(this=0x001a81d8 mmobj=0x40a2b5d4) next=0x00228390
2007-12-29 19:43:36 ClientObject::Initialize() - successfully set vector font data for 24991 bytes
2007-12-29 19:43:36 KeyboardObject::AssureEventInterface() unable to open /sys/class/input/event1
2007-12-29 19:43:36 KeyboardObject::AssureEventInterface() unable to open /sys/class/input/event2
2007-12-29 19:43:36 ClientObject::LoadSwfToMemFromURL(http://widgets.chumby.com/xml/movies/C6B05ECE-B667-11DC-A690-00156009DD9B) - instantiating http object, async=Y, timeout = 60 sec
2007-12-29 19:43:36 FrameBuffer::GetFrameBuffer(1, 320X240) - adding ref to existing FrameBuffer instance 228758 with ref count 1
2007-12-29 19:43:36 DisplayObject::SwitchActiveDisplay(1) previous frame buffer was 1
2007-12-29 19:43:36 kStartSlave: Object origin=(null), length = 0, interface count = 0, first=0x701fd6f0
2007-12-29 19:43:36 TRACE: - using widget instance timing:
2007-12-29 19:43:36 TRACE:  - timeout, 30000 ms
2007-12-29 19:43:36 TRACE: - running the widget for 30 seconds
2007-12-29 19:43:36 TRACE: - expires at Sat Dec 29 19:44:06 GMT-0700 2007
2007-12-29 19:43:36 TRACE: Setting advance timer handler
2007-12-29 19:43:36 TRACE:  - next profile scheduled to load at Sat Dec 29 19:53:36 GMT-0700 2007
2007-12-29 19:43:36 ClientObject::WidgetLoadPump() loaded 8304 bytes
2007-12-29 19:43:36 ClientObject::WidgetLoadPump(http://widgets.chumby.com/xml/movies/C6B05ECE-B667-11DC-A690-00156009DD9B) - successfully opened widget, elapsed time=0 sec
2007-12-29 19:43:36 ClientObject::SWFValidateCommon(url=http://widgets.chumby.com/xml/movies/C6B05ECE-B667-11DC-A690-00156009DD9B,size=8304) validate result 1
2007-12-29 19:43:36 ClientObject::Initialize() - preloading 1 class libraries
2007-12-29 19:43:36 TRACE: preload.swf v1.02
2007-12-29 19:43:36 ClientObject::Initialize() successfully loaded 1 preinstalled libraries
2007-12-29 19:43:36 ClientObject::WidgetLoadPump(http://widgets.chumby.com/xml/movies/C6B05ECE-B667-11DC-A690-00156009DD9B) validation result 1, deferred var count = 12
2007-12-29 19:43:36 NetStreamRequest::Open(1): Opening protocol 'http://' host 'www.thehargroves.com' port 80 location '/crossdomain.xml'
2007-12-29 19:43:36 NetStreamRequest::Open(1) opened http object id 6
2007-12-29 19:43:41 TRACE: (Advance timer heartbeat)
2007-12-29 19:43:45 TRACE: (Bend sensor heartbeat)
2007-12-29 19:43:46 TRACE: (Master heartbeat)
2007-12-29 19:43:47 TRACE: (Advance timer heartbeat)
2007-12-29 19:43:47 ClientObject::HeartBeat(9589540) elapsed 15.070s previous high 15.020s
2007-12-29 19:43:52 TRACE: (Advance timer heartbeat)
2007-12-29 19:43:56 TRACE: (Bend sensor heartbeat)
2007-12-29 19:43:57 TRACE: (Advance timer heartbeat)
2007-12-29 19:44:02 TRACE: (Master heartbeat)
2007-12-29 19:44:02 ClientObject::HeartBeat(9604570) elapsed 15.030s previous high 15.070s
2007-12-29 19:44:03 TRACE: (Advance timer heartbeat)
2007-12-29 19:44:03 Start time: 2007-12-29 19:43:29
2007-12-29 19:44:03 End time  : 2007-12-29 19:44:03

I see that the crossdomain.xml file gets accessed, but then nothing else happens -- the widget times out after 30 seconds and the whole process starts over.

Do you see anything of use here?

Thanks,

-M.

Re: Crossdomain.xml

maybe you are changing this as I am writing this but I just tried hitting your crossdomain.xml file with curl to check against mine and got this (yours looked fine in the browser)

$ curl http://www.thehargroves.com/crossdomain.xml
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>404 Not Found</title>
</head><body>
<h1>Not Found</h1>
<p>The requested URL /crossdomain.xml was not found on this server.</p>
</body></html>

$ curl http://www.mindlessabstraction.com/crossdomain.xml
<?xml version="1.0"?>
<!DOCTYPE cross-domain-policy SYSTEM "http://www.macromedia.com/xml/dtds/cross-domain-policy.dtd">
<cross-domain-policy>
   <allow-access-from domain="*" />
   <site-control permitted-cross-domain-policies="all"/>
</cross-domain-policy>

then ran it again to check and it looked good

$ curl http://www.thehargroves.com/crossdomain.xml
<?xml version="1.0" encoding="UTF-8" ?>
<cross-domain-policy>
  <allow-access-from domain="*"/>
</cross-domain-policy>

strange

5 (edited by markhargrove 2007-12-29 22:33:38)

Re: Crossdomain.xml

JVC -- yeah, I was fiddling with it, including removing it for a few minutes.  You must have first hit the site during that small window.

I'm now completely at a loss.  The widget shows up with valid data it in in the "Edit Channel" page on the chumby website -- if I select my widget from the list it previews WITH WEATHER DATA IN THE DISPLAY.  Once I actually add it to the channel, though, neither the virtual chumby nor the real one show any data.

My .fla file looks like this -- it's really nothing more than a pared-down version of the rss reader example:

/*
 * Get weather from local neighborhood weather station and display on the Chumby
 */
 
g_rssURL = 'http://www.thehargroves.com/weather/currentwx.php'; // Get current wx readings

delay = 60000;  // one minute between data refreshes

/*
 some convenience utilities to walk through the XML
*/
//
// creates or appends to an array of childNodes with the given tag
//
Object.prototype.childrenOfType = function(s,a) {
    if (a == undefined) {
        a = new Array();
    }
    var n = this.firstChild;
    while (n) {
        if (n.nodeName==s) {
            a.push(n);
        }
        n = n.nextSibling;
    }
    return a;
}
//
// returns the first child item of an element with the given tag
//
Object.prototype.firstChildOfType = function(s) {
    var n = this.firstChild;
    while (n) {
        if (n.nodeName==s) {
            return n;
        }
        n = n.nextSibling;
    }
    return null;
}
//
// returns the text of first child item of an element with the given tag
//
Object.prototype.firstValueOfType = function(s) {
    var n = this.firstChild;
    while (n) {
        if (n.nodeName==s) {
            return n.firstChild.nodeValue;
        }
        n = n.nextSibling;
    }
    return null;
}
/* We're only using the base URL for this widget
if (this._chumby_base_url==undefined) {
    this._chumby_base_url = "http://www.chumby.com"
}
*/
then = 0; // long, long ago....
this.onEnterFrame = function () {
    now = (new Date()).getTime(); // get current time in ms from the epoch
    if (now-then>delay) { // enough time elapsed since weather reading?
        loadRSS();
        then = now; // and reset the last load time
    }
}


/*
Fetch some RSS from somebody
*/
function loadRSS() {
    this.x = new XML();
    this.x.target = this;
    this.x.onLoad = function() {
        this.target.gotRSS(this);
    }
    this.x.load(g_rssURL);
}

/*
Collect the 'item' elements from the first 'channel' element, and launch the slideshow
*/
function gotRSS(rss) {
    g_items = rss.childrenOfType('CurrentReading');
    g_itemIndex = -1;
    nextItem();
}

/* the following two items are often hooked up to  buttons on the UI */

/*
Show the next item in the slideshow
*/
function nextItem() {
    g_itemIndex = (g_itemIndex+1) % g_items.length;
    showItem();
}

/*
Show the previous item in the slideshow
*/
function prevItem() {
    g_itemIndex = (g_itemIndex-1);
    if (g_itemIndex<0) {
        g_itemIndex = g_items.length-1;
    }
    showItem();
}

function showItem() {
    loadItem(g_items[g_itemIndex]);
}

function loadItem(item) {
    DownArrow._visible = false;
    UpArrow._visible = false;
    Snowflake._visible = false;
    g_currentItem = item;
    
    //
    // fill in the text fields from the RSS item
    //
    var ReadingDate = item.firstValueOfType('Date');
    var ReadingTime = item.firstValueOfType('Time');
    LastReading.text = 'On ' + ReadingDate + ' at ' + ReadingTime;
    Outdoors = item.firstValueOfType('OutdoorTemp');
    if (Outdoors <= 32.0) {
        OutsideTemp.textColor = 0xFFFFFF;
        Snowflake.visible = true;
    }
    if (Outdoors > 32 and Outdoors < 50) {
        OutsideTemp.textColor = 0xFF0000;
    }
    if (Outdoors >= 50 and Outdoors < 80) {
        OutsideTemp.textColor = 0xFF7500;
    }
    if (Outdoors >= 80) {
        OutsideTemp.textColor = 0xFF0000;
    }
    OutsideTemp.text = Outdoors + " °F";
    OutsideHumidity.text = item.firstValueOfType('OutdoorHumidity')+" %";
    Pressure.text = item.firstValueOfType('Barometer');
    var BaromTrend = item.firstValueOfType('BarometerTrend');
    if (BaromTrend == 'Falling') {
        DownArrow._visible = true;
    }
    if (BaromTrend == 'Rising') {
        UpArrow._visible = true;
    }
    Wind = item.firstValueOfType('WindSpeed');
    if (Wind <= 2) {
        Windspeed.text = "Calm";
    } else {
        Windspeed.text = Wind + " mph";
    }
}

This is driving me crazy.

-M.

Re: Crossdomain.xml

I just tried your widget from my chumby at home and it seems to work just fine - it got data and displayed it.

It's possible that the problem is with your router - I had a Linksys router that had a firmware bug that would lock up on accesses to server on the LAN through the public IP. Once I upgraded the firmware, it worked fine.

From your trace, it appears the fetch is not getting a response.  You might want to check your Apache logs to see if the server is getting it.

Re: Crossdomain.xml

Great thought!  The chumby is going through a Netgear WiFi router on the inside of my network (it's really just acting as wireless bridge) and then through a Cisco 2600.  I'll have a look at router logs as well as my Apache logs.  It helps a LOT to know that the problem isn't with the .fla file or the crossdomain.xml.

Any idea why the "widget preview" in the channel editor works, while the virtual and the real thing don't work?

I very much appreciate the help!

-M.

Re: Crossdomain.xml

There is nothing in my router logs and I monitored the Cisco for about 10 minutes while the widget ran -- no DENIED packets during the interval I watched it.

The Apache access_log is more interesting.  Here is the log tail:

24.25.218.17 - - [29/Dec/2007:23:57:44 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
24.25.218.17 - - [29/Dec/2007:23:58:44 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
24.25.218.17 - - [29/Dec/2007:23:59:44 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
24.25.218.17 - - [30/Dec/2007:00:00:44 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
24.25.218.17 - - [30/Dec/2007:00:01:44 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
192.168.100.50 - - [30/Dec/2007:00:34:56 -0700] "GET /crossdomain.xml HTTP/1.1" 304 -
192.168.100.50 - - [30/Dec/2007:00:34:56 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
192.168.100.50 - - [30/Dec/2007:00:35:38 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
74.6.19.122 - - [30/Dec/2007:00:36:06 -0700] "GET /robots.txt HTTP/1.0" 404 208
74.6.27.13 - - [30/Dec/2007:00:36:07 -0700] "GET /crossdomain.xml HTTP/1.0" 200 217
192.168.100.50 - - [30/Dec/2007:00:36:20 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
192.168.100.50 - - [30/Dec/2007:00:37:02 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
192.168.100.50 - - [30/Dec/2007:00:37:44 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
192.168.100.50 - - [30/Dec/2007:00:38:27 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
192.168.100.50 - - [30/Dec/2007:00:39:09 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956
192.168.100.50 - - [30/Dec/2007:00:39:51 -0700] "GET /weather/currentwx.php HTTP/1.1" 200 5956

I presume the 24.25.218.17 address is yours -- it's coming from the San Diego area.  The 192.168.100.50 address is my desktop while I was running the virtual chumby in a browser.  The interesting thing is that the chumby (which lives at 192.168.100.153 inside my network) never appears to even try to access the web server.

Er -- wait a second -- am I correct in assuming that's how the network access works?  Does my chumby running the flash player try to directly resolve 'www.thehargroves.com' and then make the appropriate socket connection to port 80 on the resolved IP address?

-M.

Re: Crossdomain.xml

markhargrove wrote:

Er -- wait a second -- am I correct in assuming that's how the network access works?  Does my chumby running the flash player try to directly resolve 'www.thehargroves.com' and then make the appropriate socket connection to port 80 on the resolved IP address?

Yes - the chumby *should* use your ISP's DNS to resolve your domain name to your public IP.  You can verify this by doing an nslookup on the chumby's console:

nslookup www.thehargroves.com

I get 66.227.28.114 for your IP.  I can fetch a header from your server:

chumby:/mnt/usb# curl -I http://www.thehargroves.com/crossdomain.xml
HTTP/1.1 200 OK
Date: Sun, 30 Dec 2007 08:20:37 GMT
Server: Apache/2.2.0 (Unix) DAV/2 PHP/5.1.2
Last-Modified: Sun, 30 Dec 2007 06:16:49 GMT
ETag: "18d0035-d9-df70d640"
Accept-Ranges: bytes
Content-Length: 217
Content-Type: text/xml

chumby:/mnt/usb#

I'm curious what your chumby does if you try this - if it hangs, then it's very likely your router at fault.

Re: Crossdomain.xml

What is the correct emoticon for 'slapping yourself soundly on the forehead for overlooking the obvious'?

For a couple of obscure reasons (mostly because I have two internet connections to my house to two different ISPs), I have an atypical routing and DNS setup.  Bottom line, the one thing I cannot do is resolve fully-qualified domain names of my own domain from inside my network.  I know this seems dumb, but it's a limitation I've had to live with for several years and it really doesn't get in the way -- and so I forget about it.

Today, it bit me in the, er, the chumby.  :-)

My chumby was trying to resolve www.thehargroves.com -- and it couldn't.  That's why I never saw an access in the apache logs.  I suddenly realized this was probably the problem almost about 5 minutes after I typed my previous question to you.

After adding an appropriate entry into the chumby's /etc/hosts file everything is now working just fine.

Thanks enormously, Duane,  for spending time to help me debug this -- your suggestion that it was something other than the code that was causing the problem got my attention shifted to the network and ultimately helped me figure out what was going on.

Thanks again!

-M

Re: Crossdomain.xml

Just out of curiosity, what domain does the chumby appear to be coming from when it attempts a cross-domain access?  Is it chumby.com?  Can I narrow my crossdomain.xml access to just <allow-access-from domain="*.chumby.com"> and expect all my widgets that access my server to work?

-M.

Re: Crossdomain.xml

Yes, the "security domain" for widgets served by our back end is "*.chumby.com" (at the moment, specifically "widgets.chumby.com", however, that may changes as we grow our service).