Giter Club home page Giter Club logo

t1-runtime's Introduction

[UNMAINTAINED] This library does not have a maintainer. The source code and repository will be kept at this URL indefinitely. If you'd like to help maintain this codebase, create an issue on this repo explaining why you'd like to become a maintainer and tag @tessel/maintainers in the body.

Tessel Runtime

This is the runtime and JavaScript engine that runs on Tessel, built on Lua's VM. It can be run independently on PC or embedded.

Building the firmware requires gyp, and ninja, and gcc-arm-embedded when building for embedded.

OS X

To install quickly on a Mac with Brew:

brew tap tessel/tools
brew install gyp ninja
brew install gcc-arm # to build for embedded

Ubuntu 14.04

All dependencies are in the Ubuntu 14.04 repositories:

sudo apt-get install git nodejs npm nodejs-legacy gyp ninja-build
sudo apt-get install gcc-arm-none-eabi # to build for embedded

Building (PC or Embedded)

git clone https://github.com/tessel/runtime.git
cd runtime
make update
make colony
make test

To link globally, run npm link --local. You can now run code on your PC using colony from your command line (e.g. colony hello-world.js). For building firmware, please see the firmware building instructions.

Troubleshooting: If you're updating and have the error fatal: destination path 'deps/colony-luajit' already exists and is not an empty directory., run rm -rf deps/colony-luajit && make update.

Documentation for C

Colony

Colony has support for interacting with the Lua API for handling basic JavaScript primitives. These are included via colony.h.

# void  colony_createarray ( lua_State*  L, int  size )
Creates a new JavaScript array of length size. This sets the object prototype as well as the initial length of the array.

# void  colony_createobj ( lua_State*  L, int  size, int  proto )
Creates a new JavaScript object with an expected (but not required) allocation of size keys. This sets the object prototype as well. If proto is not zero (an invalid stack pointer), it points to an object on the stack to be used as the prototype for the newly created object.

License

MIT or Apache 2.0, at your option.

t1-runtime's People

Contributors

adammagaluk avatar adkron avatar evansimpson avatar frijol avatar hannesvdvreken avatar jiahuang avatar johnnyman727 avatar kevinmehall avatar kevinswiber avatar lhuszko avatar linusu avatar mattsoftware avatar natevw avatar nplus11 avatar nw avatar olegas avatar olsondev avatar paulbernier avatar paulcuth avatar pirumpi avatar pmcote avatar rwaldron avatar tcr avatar tm-rampart avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

t1-runtime's Issues

String.prototype.lastIndexOf's fromIndex parameter ignored

String.prototype.lastIndexOf does not support fromIndex. MDN's example shows this sample code:

"canal".lastIndexOf("a")    // returns  3
"canal".lastIndexOf("a", 2) // returns  1
"canal".lastIndexOf("a", 0) // returns -1
"canal".lastIndexOf("x")    // returns -1

whereas when I test it on the Tessel, this is the output I get:

 3
 3
 3
-1

This is related to #186.

SSL/TLS not supported

Whoops this should be on tessel/beta. Moving the issue.

Using the XMLHttpRequest node module, got error "SSL/TLS is not supported in this version."

My code:

var XMLHttpRequest = require('xmlhttprequest').XMLHttpRequest;
function httpGet(theUrl)
{
  var xmlHttp = null;

  xmlHttp = new XMLHttpRequest();
  xmlHttp.open( "GET", theUrl, false );
  xmlHttp.send( null );
  return xmlHttp.responseText;
}

var res = httpGet('http://api.openweathermap.org/data/2.5/weather?id=5327684&units=imperial');
console.log(res);

Error output:

➜  module-demos git:(master) ✗ tessel run servo-weathervane.js
TESSEL! Connected to TM-00-04-f000da30-00514f3b-38642586.
Bundling directory /Users/timryan/module-demos (~12.14 MB)
Deploying bundle (12.58 MB)...
Running script...
Error: SSL/TLS is not supported in this version.
stack traceback:
    [T]: src/colony/lua/colony-js.lua:759: in function 'f'
    [T]: src/colony/lua/colony-init.lua:414: in function '_new'
    [T]:src/colony/modules/https.js:4: in function 'res'
    [T]: src/colony/lua/colony-node.lua:853: in function 'run'
    [T]: src/colony/lua/colony-node.lua:849: in function 'require'
    ...pp/node_modules/xmlhttprequest/lib/XMLHttpRequest.js:24: in function 'f'
    [T]: src/colony/lua/colony-init.lua:414: in function '_new'
    /app/servo-weathervane.js:28: in function 'httpGet'
    /app/servo-weathervane.js:34: in function 'res'
    [T]: src/colony/lua/colony-node.lua:853: in function 'run'
    [T]: src/colony/lua/colony-node.lua:849: in function 'require'
    /_start.js:3: in function 'res'
    [T]: src/colony/lua/colony-node.lua:853: in function 'run'
    [T]: src/colony/lua/cli.lua:24: in main chunk
    [C]: in function 'require'
    [T]: runtime:1: in main chunk

Node output:

➜  module-demos git:(master) ✗ node servo-weathervane.js
{"coord":{"lon":-122.27,"lat":37.87},"sys":{"message":0.3462,"country":"US","sunrise":1400072341,"sunset":1400123510},"weather":[{"id":800,"main":"Clear","description":"Sky is Clear","icon":"01d"}],"base":"cmc stations","main":{"temp":75.82,"temp_min":75.82,"temp_max":75.82,"pressure":1024.67,"sea_level":1033.3,"grnd_level":1024.67,"humidity":42},"wind":{"speed":3.37,"deg":285.5},"clouds":{"all":0},"dt":1400101368,"id":5327684,"name":"Berkeley","cod":200}

url.parse not consistent with node.js url.parse

While playing with some modules that make use of url.parse for some validation I've noticed the implementation differs a bit. I first noticed .host was missing on the returned object.

AdamMagaluk@f9ce094

My extended test outputs:

λ: ./out/Release/colony test/suite/url.js
1..14
ok 1 - running in colony
ok 2 - url parses
not ok 3 - hash should matched expected
not ok 4 - path should matched expected
ok 5 - protocol should matched expected
ok 6 - href should matched expected
not ok 7 - host should matched expected
not ok 8 - port should matched expected
not ok 9 - slashes should matched expected
not ok 10 - hostname should matched expected
ok 11 - query should matched expected
ok 12 - pathname should matched expected
ok 13 - search should matched expected
not ok 14 - auth should matched expected

On Node.js v0.10.26

λ: node test/suite/url.js
1..14
not ok 1 - running in colony
ok 2 - url parses
ok 3 - protocol should matched expected
ok 4 - slashes should matched expected
ok 5 - auth should matched expected
ok 6 - host should matched expected
ok 7 - port should matched expected
ok 8 - hostname should matched expected
ok 9 - hash should matched expected
ok 10 - search should matched expected
ok 11 - query should matched expected
ok 12 - pathname should matched expected
ok 13 - path should matched expected
ok 14 - href should matched expected
~/Software/tessel/runtime [master*]
λ: node --version
v0.10.26

Error: not implemented

var Readable = require('stream').Readable;
var rs = new Readable;
Readable.prototype._read = function () {
console.log('lolwhat');
console.log((new Error).stack)
}
rs._read = function () {
rs.push('boop\n');
rs.push(null); 
}
process.stdout._read = function () {
process.stdout.push('test case');
process.stdout.push(null);
}
rs.push('beep ');
rs.pipe(new (require('stream').Writable));

http.createServer is extremely inconsistent

Running the following code:

var http = require('http');
http.createServer(function (req, res) {
  res.writeHead(200, {'Content-Type': 'text/plain'});
  res.end('Hello World\n');
}).listen(1337, "localhost");

console.log('Server running at localhost:1337/');

It works really well when I connect through my phone's hotspot but I can rarely connect on our corporate wifi network.

Requiring up the dependency chain

Express can't be run right now because of a new issue.

What happens is the express module had a dependency on buffer-crc32 and installs it in its node_modules folder. Then, a dependency of express, send, also requires the same version of the module. By default npm install will only install one instance of a specific module version. So the send module doesn't actually have a buffer-crc32 module in its node_modules folder.

-app
--node_modules
---express
----node_modules
-----buffer-crc32
-----send
------node_modules
-------WE EXPECT buffer-crc32

Our CLI (?) doesn't have this check so we get:

➜  server  tessel run app.js
TESSEL! Connected to TM-00-04-f000da30-00664340-4a602586.

Error: ENOENT, no such file or directory '/Users/Jon/Code/server/node_modules/express/node_modules/send/node_modules/buffer-crc32'
    at Object.fs.lstatSync (fs.js:679:18)
    at submodules.filter.filter.ret (/usr/local/lib/node_modules/tessel/node_modules/hardware-resolve/index.js:123:15)
    at Array.filter (native)
    at list (/usr/local/lib/node_modules/tessel/node_modules/hardware-resolve/index.js:122:14)
    at /usr/local/lib/node_modules/tessel/node_modules/hardware-resolve/index.js:148:26
    at Array.forEach (native)
    at list (/usr/local/lib/node_modules/tessel/node_modules/hardware-resolve/index.js:142:27)
    at /usr/local/lib/node_modules/tessel/node_modules/hardware-resolve/index.js:148:26
    at Array.forEach (native)

String.prototype.indexOf's fromIndex parameter ignored

String.prototype.indexOf does not support fromIndex. MDN's example shows this sample code:

"Blue Whale".indexOf("Blue");     // returns  0
"Blue Whale".indexOf("Blute");    // returns -1
"Blue Whale".indexOf("Whale", 0); // returns  5
"Blue Whale".indexOf("Whale", 5); // returns  5
"Blue Whale".indexOf("", 9);      // returns  9
"Blue Whale".indexOf("", 10);     // returns 10
"Blue Whale".indexOf("", 11);     // returns 10

whereas when I test it on the Tessel, this is the output I get:

 0
-1
 5
 5
 0
 0
 0

This is related to #185.

Cannot register for pin events in GPIO; throws error

Registering a GPIO pin.on event listener triggers the error "attempt to call method 'on' (a nil value)."

Here's my code:

var tessel = require('tessel');
var motion = tessel.port.GPIO.pin.A6;  // PIR sensor

// sanity check - this works
console.log('pin A6:', motion.read());

// this next line throws an error
motion.on('change', function(time, type) {
      console.log('motion:', time, type, motion.read());
});

I've put the first console.log in there to prove that the attached device is indeed changing the value of the pin. FWIW, the device is a PIR motion sensor.

When I point the PIR sensor at myself and run the script, the pin value is 1 (good, PIR sees me); when I point it away, the value is 0 (good, PIR doesn't see me). So the pin value is being set correctly, and pin.read works. Yet attempts to attach listeners to the pin fail.

tessel version 0.3.6
Firmware Version: 2d997e2
Runtime Version: ced4026

Domain module: unsupported?

Howdy.

I make use of the domain module. I see on the compatibility page that there are no plans to support it.

I can conditionally require it deep in my dependent libraries, but I'd rather not if I can help it. Luckily, the only domain-using dependency in the code I'd like to run on the Tessel happens to be pipeworks, which is a library I created. I imagine I won't always be so fortunate.

May I ask...

  1. What are the reasons the domain module will not be supported?
  2. At the very least, would it be possible to create an API-compatible domain module that doesn't deliver on the promise of domains but still allows code to run?

I ask the first question because I'm not familiar with Lua bytecode or any limitations that would come from using a tool like colony.

The second bullet point probably requires more explanation. Basically, I guess this would mean the error event never fires; uncaught exceptions would still propagate to the process level.

Thanks!

Require causing script to not run

Forum post: https://forums.tessel.io/t/require-causing-script-to-not-run/176

barrettbreshears17h
for some reason if I use require the script does not run. for example:

console.log('hello world');
var twitterAPI = require('node-twitter-api');
console.log('hello again');

output from the console:
tessel-tweet barrettbreshears$ tessel run tweet2.js
TESSEL! Connected to TM-00-04-f0009a30-00694743-523465c2.
INFO Bundling directory /Users/barrettbreshears/Development/My Tessel (~4.19 MB)
INFO Deploying bundle (6.41 MB)...
INFO Running script...
hello world
Barretts-MacBook-Pro:tessel-tweet barrettbreshears$

it never makes it to the second console.log

I am new to node, so any help would be awesome! Thanks.

The quest to functional socket.io

Test Code:

var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);

app.get('/', function(req, res){
  res.sendfile('index.html');
});

io.on('connection', function(socket){
  console.log('a user connected');
});

http.listen(3000, function(){
  console.log('listening on *:3000');
});

Current Blocker:

➜  sandbox  tessel run socket-test.js
TESSEL! Connected to TM-00-04-f000da30-0056473b-343c2586.
INFO Bundling directory /Users/Jon/Work/technical/sandbox (~3.97 MB)
INFO Deploying bundle (6.24 MB)...
INFO Running script...
/app/node_modules/socket.io/lib/index.js:28: attempt to call method 'resolve' (a nil value)

Undefined reference to HTTP Parser

I'm trying to run an un-minified version of the Firebase module (see code below). The error I get is:

>> colony lib/firebase-node.js
...websocket-driver/lib/websocket/driver/http_parser.js:80: attempt to index local 'HTTPParser' (a nil value)

Code:

var COMPILED = !0, goog = goog || {};
goog.global = this;
goog.isDef = function(a) {
  return void 0 !== a;
};
goog.exportPath_ = function(a, b, c) {
  a = a.split(".");
  c = c || goog.global;
  a[0] in c || !c.execScript || c.execScript("var " + a[0]);
  for (var d;a.length && (d = a.shift());) {
    !a.length && goog.isDef(b) ? c[d] = b : c = c[d] ? c[d] : c[d] = {};
  }
};
goog.define = function(a, b) {
  var c = b;
  COMPILED || (goog.global.CLOSURE_UNCOMPILED_DEFINES && Object.prototype.hasOwnProperty.call(goog.global.CLOSURE_UNCOMPILED_DEFINES, a) ? c = goog.global.CLOSURE_UNCOMPILED_DEFINES[a] : goog.global.CLOSURE_DEFINES && Object.prototype.hasOwnProperty.call(goog.global.CLOSURE_DEFINES, a) && (c = goog.global.CLOSURE_DEFINES[a]));
  goog.exportPath_(a, c);
};
goog.DEBUG = !0;
goog.LOCALE = "en";
goog.TRUSTED_SITE = !0;
goog.STRICT_MODE_COMPATIBLE = !1;
goog.provide = function(a) {
  if (!COMPILED) {
    if (goog.isProvided_(a)) {
      throw Error('Namespace "' + a + '" already declared.');
    }
    delete goog.implicitNamespaces_[a];
    for (var b = a;(b = b.substring(0, b.lastIndexOf("."))) && !goog.getObjectByName(b);) {
      goog.implicitNamespaces_[b] = !0;
    }
  }
  goog.exportPath_(a);
};
goog.setTestOnly = function(a) {
  if (COMPILED && !goog.DEBUG) {
    throw a = a || "", Error("Importing test-only code into non-debug environment" + a ? ": " + a : ".");
  }
};
goog.forwardDeclare = function(a) {
};
COMPILED || (goog.isProvided_ = function(a) {
  return!goog.implicitNamespaces_[a] && goog.isDefAndNotNull(goog.getObjectByName(a));
}, goog.implicitNamespaces_ = {});
goog.getObjectByName = function(a, b) {
  for (var c = a.split("."), d = b || goog.global, e;e = c.shift();) {
    if (goog.isDefAndNotNull(d[e])) {
      d = d[e];
    } else {
      return null;
    }
  }
  return d;
};
goog.globalize = function(a, b) {
  var c = b || goog.global, d;
  for (d in a) {
    c[d] = a[d];
  }
};
goog.addDependency = function(a, b, c) {
  if (goog.DEPENDENCIES_ENABLED) {
    var d;
    a = a.replace(/\\/g, "/");
    for (var e = goog.dependencies_, f = 0;d = b[f];f++) {
      e.nameToPath[d] = a, a in e.pathToNames || (e.pathToNames[a] = {}), e.pathToNames[a][d] = !0;
    }
    for (d = 0;b = c[d];d++) {
      a in e.requires || (e.requires[a] = {}), e.requires[a][b] = !0;
    }
  }
};
goog.ENABLE_DEBUG_LOADER = !0;
goog.require = function(a) {
  if (!COMPILED && !goog.isProvided_(a)) {
    if (goog.ENABLE_DEBUG_LOADER) {
      var b = goog.getPathFromDeps_(a);
      if (b) {
        goog.included_[b] = !0;
        goog.writeScripts_();
        return;
      }
    }
    a = "goog.require could not find: " + a;
    goog.global.console && goog.global.console.error(a);
    throw Error(a);
  }
};
goog.basePath = "";
goog.nullFunction = function() {
};
goog.identityFunction = function(a, b) {
  return a;
};
goog.abstractMethod = function() {
  throw Error("unimplemented abstract method");
};
goog.addSingletonGetter = function(a) {
  a.getInstance = function() {
    if (a.instance_) {
      return a.instance_;
    }
    goog.DEBUG && (goog.instantiatedSingletons_[goog.instantiatedSingletons_.length] = a);
    return a.instance_ = new a;
  };
};
goog.instantiatedSingletons_ = [];
goog.DEPENDENCIES_ENABLED = !COMPILED && goog.ENABLE_DEBUG_LOADER;
goog.DEPENDENCIES_ENABLED && (goog.included_ = {}, goog.dependencies_ = {pathToNames:{}, nameToPath:{}, requires:{}, visited:{}, written:{}}, goog.inHtmlDocument_ = function() {
  var a = goog.global.document;
  return "undefined" != typeof a && "write" in a;
}, goog.findBasePath_ = function() {
  if (goog.global.CLOSURE_BASE_PATH) {
    goog.basePath = goog.global.CLOSURE_BASE_PATH;
  } else {
    if (goog.inHtmlDocument_()) {
      for (var a = goog.global.document.getElementsByTagName("script"), b = a.length - 1;0 <= b;--b) {
        var c = a[b].src, d = c.lastIndexOf("?"), d = -1 == d ? c.length : d;
        if ("base.js" == c.substr(d - 7, 7)) {
          goog.basePath = c.substr(0, d - 7);
          break;
        }
      }
    }
  }
}, goog.importScript_ = function(a) {
  var b = goog.global.CLOSURE_IMPORT_SCRIPT || goog.writeScriptTag_;
  !goog.dependencies_.written[a] && b(a) && (goog.dependencies_.written[a] = !0);
}, goog.writeScriptTag_ = function(a) {
  if (goog.inHtmlDocument_()) {
    var b = goog.global.document;
    if ("complete" == b.readyState) {
      if (/\bdeps.js$/.test(a)) {
        return!1;
      }
      throw Error('Cannot write "' + a + '" after document load');
    }
    b.write('<script type="text/javascript" src="' + a + '">\x3c/script>');
    return!0;
  }
  return!1;
}, goog.writeScripts_ = function() {
  function a(e) {
    if (!(e in d.written)) {
      if (!(e in d.visited) && (d.visited[e] = !0, e in d.requires)) {
        for (var g in d.requires[e]) {
          if (!goog.isProvided_(g)) {
            if (g in d.nameToPath) {
              a(d.nameToPath[g]);
            } else {
              throw Error("Undefined nameToPath for " + g);
            }
          }
        }
      }
      e in c || (c[e] = !0, b.push(e));
    }
  }
  var b = [], c = {}, d = goog.dependencies_, e;
  for (e in goog.included_) {
    d.written[e] || a(e);
  }
  for (e = 0;e < b.length;e++) {
    if (b[e]) {
      goog.importScript_(goog.basePath + b[e]);
    } else {
      throw Error("Undefined script input");
    }
  }
}, goog.getPathFromDeps_ = function(a) {
  return a in goog.dependencies_.nameToPath ? goog.dependencies_.nameToPath[a] : null;
}, goog.findBasePath_(), goog.global.CLOSURE_NO_DEPS || goog.importScript_(goog.basePath + "deps.js"));
goog.typeOf = function(a) {
  var b = typeof a;
  if ("object" == b) {
    if (a) {
      if (a instanceof Array) {
        return "array";
      }
      if (a instanceof Object) {
        return b;
      }
      var c = Object.prototype.toString.call(a);
      if ("[object Window]" == c) {
        return "object";
      }
      if ("[object Array]" == c || "number" == typeof a.length && "undefined" != typeof a.splice && "undefined" != typeof a.propertyIsEnumerable && !a.propertyIsEnumerable("splice")) {
        return "array";
      }
      if ("[object Function]" == c || "undefined" != typeof a.call && "undefined" != typeof a.propertyIsEnumerable && !a.propertyIsEnumerable("call")) {
        return "function";
      }
    } else {
      return "null";
    }
  } else {
    if ("function" == b && "undefined" == typeof a.call) {
      return "object";
    }
  }
  return b;
};
goog.isNull = function(a) {
  return null === a;
};
goog.isDefAndNotNull = function(a) {
  return null != a;
};
goog.isArray = function(a) {
  return "array" == goog.typeOf(a);
};
goog.isArrayLike = function(a) {
  var b = goog.typeOf(a);
  return "array" == b || "object" == b && "number" == typeof a.length;
};
goog.isDateLike = function(a) {
  return goog.isObject(a) && "function" == typeof a.getFullYear;
};
goog.isString = function(a) {
  return "string" == typeof a;
};
goog.isBoolean = function(a) {
  return "boolean" == typeof a;
};
goog.isNumber = function(a) {
  return "number" == typeof a;
};
goog.isFunction = function(a) {
  return "function" == goog.typeOf(a);
};
goog.isObject = function(a) {
  var b = typeof a;
  return "object" == b && null != a || "function" == b;
};
goog.getUid = function(a) {
  return a[goog.UID_PROPERTY_] || (a[goog.UID_PROPERTY_] = ++goog.uidCounter_);
};
goog.hasUid = function(a) {
  return!!a[goog.UID_PROPERTY_];
};
goog.removeUid = function(a) {
  "removeAttribute" in a && a.removeAttribute(goog.UID_PROPERTY_);
  try {
    delete a[goog.UID_PROPERTY_];
  } catch (b) {
  }
};
goog.UID_PROPERTY_ = "closure_uid_" + (1E9 * Math.random() >>> 0);
goog.uidCounter_ = 0;
goog.getHashCode = goog.getUid;
goog.removeHashCode = goog.removeUid;
goog.cloneObject = function(a) {
  var b = goog.typeOf(a);
  if ("object" == b || "array" == b) {
    if (a.clone) {
      return a.clone();
    }
    var b = "array" == b ? [] : {}, c;
    for (c in a) {
      b[c] = goog.cloneObject(a[c]);
    }
    return b;
  }
  return a;
};
goog.bindNative_ = function(a, b, c) {
  return a.call.apply(a.bind, arguments);
};
goog.bindJs_ = function(a, b, c) {
  if (!a) {
    throw Error();
  }
  if (2 < arguments.length) {
    var d = Array.prototype.slice.call(arguments, 2);
    return function() {
      var c = Array.prototype.slice.call(arguments);
      Array.prototype.unshift.apply(c, d);
      return a.apply(b, c);
    };
  }
  return function() {
    return a.apply(b, arguments);
  };
};
goog.bind = function(a, b, c) {
  Function.prototype.bind && -1 != Function.prototype.bind.toString().indexOf("native code") ? goog.bind = goog.bindNative_ : goog.bind = goog.bindJs_;
  return goog.bind.apply(null, arguments);
};
goog.partial = function(a, b) {
  var c = Array.prototype.slice.call(arguments, 1);
  return function() {
    var b = c.slice();
    b.push.apply(b, arguments);
    return a.apply(this, b);
  };
};
goog.mixin = function(a, b) {
  for (var c in b) {
    a[c] = b[c];
  }
};
goog.now = goog.TRUSTED_SITE && Date.now || function() {
  return+new Date;
};
goog.globalEval = function(a) {
  if (goog.global.execScript) {
    goog.global.execScript(a, "JavaScript");
  } else {
    if (goog.global.eval) {
      if (null == goog.evalWorksForGlobals_ && (goog.global.eval("var _et_ = 1;"), "undefined" != typeof goog.global._et_ ? (delete goog.global._et_, goog.evalWorksForGlobals_ = !0) : goog.evalWorksForGlobals_ = !1), goog.evalWorksForGlobals_) {
        goog.global.eval(a);
      } else {
        var b = goog.global.document, c = b.createElement("script");
        c.type = "text/javascript";
        c.defer = !1;
        c.appendChild(b.createTextNode(a));
        b.body.appendChild(c);
        b.body.removeChild(c);
      }
    } else {
      throw Error("goog.globalEval not available");
    }
  }
};
goog.evalWorksForGlobals_ = null;
goog.getCssName = function(a, b) {
  var c = function(a) {
    return goog.cssNameMapping_[a] || a;
  }, d = function(a) {
    a = a.split("-");
    for (var b = [], d = 0;d < a.length;d++) {
      b.push(c(a[d]));
    }
    return b.join("-");
  }, d = goog.cssNameMapping_ ? "BY_WHOLE" == goog.cssNameMappingStyle_ ? c : d : function(a) {
    return a;
  };
  return b ? a + "-" + d(b) : d(a);
};
goog.setCssNameMapping = function(a, b) {
  goog.cssNameMapping_ = a;
  goog.cssNameMappingStyle_ = b;
};
!COMPILED && goog.global.CLOSURE_CSS_NAME_MAPPING && (goog.cssNameMapping_ = goog.global.CLOSURE_CSS_NAME_MAPPING);
goog.getMsg = function(a, b) {
  var c = b || {}, d;
  for (d in c) {
    var e = ("" + c[d]).replace(/\$/g, "$$$$");
    a = a.replace(new RegExp("\\{\\$" + d + "\\}", "gi"), e);
  }
  return a;
};
goog.getMsgWithFallback = function(a, b) {
  return a;
};
goog.exportSymbol = function(a, b, c) {
  goog.exportPath_(a, b, c);
};
goog.exportProperty = function(a, b, c) {
  a[b] = c;
};
goog.inherits = function(a, b) {
  function c() {
  }
  c.prototype = b.prototype;
  a.superClass_ = b.prototype;
  a.prototype = new c;
  a.prototype.constructor = a;
  a.base = function(a, c, f) {
    var g = Array.prototype.slice.call(arguments, 2);
    return b.prototype[c].apply(a, g);
  };
};
goog.base = function(a, b, c) {
  var d = arguments.callee.caller;
  if (goog.STRICT_MODE_COMPATIBLE || goog.DEBUG && !d) {
    throw Error("arguments.caller not defined.  goog.base() cannot be used with strict mode code. See http://www.ecma-international.org/ecma-262/5.1/#sec-C");
  }
  if (d.superClass_) {
    return d.superClass_.constructor.apply(a, Array.prototype.slice.call(arguments, 1));
  }
  for (var e = Array.prototype.slice.call(arguments, 2), f = !1, g = a.constructor;g;g = g.superClass_ && g.superClass_.constructor) {
    if (g.prototype[b] === d) {
      f = !0;
    } else {
      if (f) {
        return g.prototype[b].apply(a, e);
      }
    }
  }
  if (a[b] === d) {
    return a.constructor.prototype[b].apply(a, e);
  }
  throw Error("goog.base called from a method of one name to a method of a different name");
};
goog.scope = function(a) {
  a.call(goog.global);
};
COMPILED || (goog.global.COMPILED = COMPILED);
goog.json = {};
goog.json.USE_NATIVE_JSON = !1;
goog.json.isValid_ = function(a) {
  return/^\s*$/.test(a) ? !1 : /^[\],:{}\s\u2028\u2029]*$/.test(a.replace(/\\["\\\/bfnrtu]/g, "@").replace(/"[^"\\\n\r\u2028\u2029\x00-\x08\x0a-\x1f]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g, "]").replace(/(?:^|:|,)(?:[\s\u2028\u2029]*\[)+/g, ""));
};
goog.json.parse = goog.json.USE_NATIVE_JSON ? goog.global.JSON.parse : function(a) {
  a = String(a);
  if (goog.json.isValid_(a)) {
    try {
      return eval("(" + a + ")");
    } catch (b) {
    }
  }
  throw Error("Invalid JSON string: " + a);
};
goog.json.unsafeParse = goog.json.USE_NATIVE_JSON ? goog.global.JSON.parse : function(a) {
  return eval("(" + a + ")");
};
goog.json.serialize = goog.json.USE_NATIVE_JSON ? goog.global.JSON.stringify : function(a, b) {
  return(new goog.json.Serializer(b)).serialize(a);
};
goog.json.Serializer = function(a) {
  this.replacer_ = a;
};
goog.json.Serializer.prototype.serialize = function(a) {
  var b = [];
  this.serializeInternal(a, b);
  return b.join("");
};
goog.json.Serializer.prototype.serializeInternal = function(a, b) {
  switch(typeof a) {
    case "string":
      this.serializeString_(a, b);
      break;
    case "number":
      this.serializeNumber_(a, b);
      break;
    case "boolean":
      b.push(a);
      break;
    case "undefined":
      b.push("null");
      break;
    case "object":
      if (null == a) {
        b.push("null");
        break;
      }
      if (goog.isArray(a)) {
        this.serializeArray(a, b);
        break;
      }
      this.serializeObject_(a, b);
      break;
    case "function":
      break;
    default:
      throw Error("Unknown type: " + typeof a);;
  }
};
goog.json.Serializer.charToJsonCharCache_ = {'"':'\\"', "\\":"\\\\", "/":"\\/", "\b":"\\b", "\f":"\\f", "\n":"\\n", "\r":"\\r", "\t":"\\t", "\x0B":"\\u000b"};
goog.json.Serializer.charsToReplace_ = /\uffff/.test("\uffff") ? /[\\\"\x00-\x1f\x7f-\uffff]/g : /[\\\"\x00-\x1f\x7f-\xff]/g;
goog.json.Serializer.prototype.serializeString_ = function(a, b) {
  b.push('"', a.replace(goog.json.Serializer.charsToReplace_, function(a) {
    if (a in goog.json.Serializer.charToJsonCharCache_) {
      return goog.json.Serializer.charToJsonCharCache_[a];
    }
    var b = a.charCodeAt(0), e = "\\u";
    16 > b ? e += "000" : 256 > b ? e += "00" : 4096 > b && (e += "0");
    return goog.json.Serializer.charToJsonCharCache_[a] = e + b.toString(16);
  }), '"');
};
goog.json.Serializer.prototype.serializeNumber_ = function(a, b) {
  b.push(isFinite(a) && !isNaN(a) ? a : "null");
};
goog.json.Serializer.prototype.serializeArray = function(a, b) {
  var c = a.length;
  b.push("[");
  for (var d = "", e = 0;e < c;e++) {
    b.push(d), d = a[e], this.serializeInternal(this.replacer_ ? this.replacer_.call(a, String(e), d) : d, b), d = ",";
  }
  b.push("]");
};
goog.json.Serializer.prototype.serializeObject_ = function(a, b) {
  b.push("{");
  var c = "", d;
  for (d in a) {
    if (Object.prototype.hasOwnProperty.call(a, d)) {
      var e = a[d];
      "function" != typeof e && (b.push(c), this.serializeString_(d, b), b.push(":"), this.serializeInternal(this.replacer_ ? this.replacer_.call(a, d, e) : e, b), c = ",");
    }
  }
  b.push("}");
};
var fb = {util:{}};
fb.util.json = {};
fb.util.json.eval = function(a) {
  return "undefined" !== typeof JSON && goog.isDef(JSON.parse) ? JSON.parse(a) : goog.json.parse(a);
};
fb.util.json.stringify = function(a) {
  return "undefined" !== typeof JSON && goog.isDef(JSON.stringify) ? JSON.stringify(a) : goog.json.serialize(a);
};
fb.util.utf8 = {};
fb.util.utf8.stringToByteArray = function(a) {
  for (var b = [], c = 0, d = 0;d < a.length;d++) {
    var e = a.charCodeAt(d);
    if (55296 <= e && 56319 >= e) {
      e -= 55296;
      d++;
      fb.core.util.assert(d < a.length, "Surrogate pair missing trail surrogate.");
      var f = a.charCodeAt(d) - 56320, e = 65536 + (e << 10) + f;
    }
    128 > e ? b[c++] = e : (2048 > e ? b[c++] = e >> 6 | 192 : (65536 > e ? b[c++] = e >> 12 | 224 : (b[c++] = e >> 18 | 240, b[c++] = e >> 12 & 63 | 128), b[c++] = e >> 6 & 63 | 128), b[c++] = e & 63 | 128);
  }
  return b;
};
fb.util.utf8.stringLength = function(a) {
  for (var b = 0, c = 0;c < a.length;c++) {
    var d = a.charCodeAt(c);
    128 > d ? b++ : 2048 > d ? b += 2 : 55296 <= d && 56319 >= d ? (b += 4, c++) : b += 3;
  }
  return b;
};
fb.util.validation = {};
fb.util.validation.validateArgCount = function(a, b, c, d) {
  var e;
  d < b ? e = "at least " + b : d > c && (e = 0 === c ? "none" : "no more than " + c);
  if (e) {
    throw Error(a + " failed: Was called with " + d + (1 === d ? " argument." : " arguments.") + " Expects " + e + ".");
  }
};
fb.util.validation.errorPrefix = function(a, b, c) {
  var d = "";
  switch(b) {
    case 1:
      d = c ? "first" : "First";
      break;
    case 2:
      d = c ? "second" : "Second";
      break;
    case 3:
      d = c ? "third" : "Third";
      break;
    case 4:
      d = c ? "fourth" : "Fourth";
      break;
    default:
      fb.core.util.validation.assert(!1, "errorPrefix_ called with argumentNumber > 4.  Need to update it?");
  }
  return a = a + " failed: " + (d + " argument ");
};
fb.util.validation.validateNamespace = function(a, b, c, d) {
  if ((!d || goog.isDef(c)) && !goog.isString(c)) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + "must be a valid firebase namespace.");
  }
};
fb.util.validation.validateCallback = function(a, b, c, d) {
  if ((!d || goog.isDef(c)) && !goog.isFunction(c)) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + "must be a valid function.");
  }
};
fb.util.validation.validateString = function(a, b, c, d) {
  if ((!d || goog.isDef(c)) && !goog.isString(c)) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + "must be a valid string.");
  }
};
fb.util.validation.validateContextObject = function(a, b, c, d) {
  if (!d || goog.isDef(c)) {
    if (!goog.isObject(c) || null === c) {
      throw Error(fb.util.validation.errorPrefix(a, b, d) + "must be a valid context object.");
    }
  }
};
fb.util.obj = {};
fb.util.obj.contains = function(a, b) {
  return Object.prototype.hasOwnProperty.call(a, b);
};
fb.util.obj.get = function(a, b) {
  if (Object.prototype.hasOwnProperty.call(a, b)) {
    return a[b];
  }
};
fb.core = {};
fb.core.util = {};
fb.core.util.validation = {};
fb.core.util.validation.INVALID_KEY_REGEX_ = /[\[\].#$\/\u0000-\u001F\u007F]/;
fb.core.util.validation.INVALID_PATH_REGEX_ = /[\[\].#$\u0000-\u001F\u007F]/;
fb.core.util.validation.MAX_LEAF_SIZE_ = 10485760;
fb.core.util.validation.MAX_DEPTH_SIZE_ = 1E3;
fb.core.util.validation.isValidKey = function(a) {
  return goog.isString(a) && 0 !== a.length && !fb.core.util.validation.INVALID_KEY_REGEX_.test(a);
};
fb.core.util.validation.isValidPathString = function(a) {
  return goog.isString(a) && 0 !== a.length && !fb.core.util.validation.INVALID_PATH_REGEX_.test(a);
};
fb.core.util.validation.isValidRootPathString = function(a) {
  a && (a = a.replace(/^\/*\.info(\/|$)/, "/"));
  return fb.core.util.validation.isValidPathString(a);
};
fb.core.util.validation.validateFirebaseDataArg = function(a, b, c, d) {
  d && !goog.isDef(c) || fb.core.util.validation.validateFirebaseData(fb.util.validation.errorPrefix(a, b, d), c);
};
fb.core.util.validation.validateFirebaseData = function(a, b, c, d) {
  c || (c = 0);
  d = d || [];
  if (!goog.isDef(b)) {
    throw Error(a + "contains undefined" + fb.core.util.validation.pathLocation_(d));
  }
  if (goog.isFunction(b)) {
    throw Error(a + "contains a function" + fb.core.util.validation.pathLocation_(d) + " with contents: " + b.toString());
  }
  if (fb.core.util.isInvalidJSONNumber(b)) {
    throw Error(a + "contains " + b.toString() + fb.core.util.validation.pathLocation_(d));
  }
  if (c > fb.core.util.validation.MAX_DEPTH_SIZE_) {
    throw new TypeError(a + "contains a cyclic object value (" + d.slice(0, 100).join(".") + "...)");
  }
  if (goog.isString(b) && b.length > fb.core.util.validation.MAX_LEAF_SIZE_ / 3 && fb.util.utf8.stringToByteArray(b).length > fb.core.util.validation.MAX_LEAF_SIZE_) {
    throw Error(a + "contains a string greater than " + fb.core.util.validation.MAX_LEAF_SIZE_ + " utf8 bytes" + fb.core.util.validation.pathLocation_(d) + " ('" + b.substring(0, 50) + "...')");
  }
  if (goog.isObject(b)) {
    for (var e in b) {
      if (fb.util.obj.contains(b, e)) {
        var f = b[e];
        if (".priority" !== e && ".value" !== e && ".sv" !== e && !fb.core.util.validation.isValidKey(e)) {
          throw Error(a + " contains an invalid key (" + e + ")" + fb.core.util.validation.pathLocation_(d) + '.  Keys must be non-empty strings and can\'t contain ".", "#", "$", "/", "[", or "]"');
        }
        d.push(e);
        fb.core.util.validation.validateFirebaseData(a, f, c + 1, d);
        d.pop();
      }
    }
  }
};
fb.core.util.validation.pathLocation_ = function(a) {
  return 0 == a.length ? "" : " in property '" + a.join(".") + "'";
};
fb.core.util.validation.validateFirebaseObjectDataArg = function(a, b, c, d) {
  if (!d || goog.isDef(c)) {
    if (!goog.isObject(c)) {
      throw Error(fb.util.validation.errorPrefix(a, b, d) + " must be an object containing the children to replace.");
    }
    fb.core.util.validation.validateFirebaseDataArg(a, b, c, d);
  }
};
fb.core.util.validation.validatePriority = function(a, b, c, d) {
  if (!(d && !goog.isDef(c) || null === c || goog.isNumber(c) || goog.isString(c) || goog.isObject(c) && fb.util.obj.contains(c, ".sv"))) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + "must be a valid firebase priority (a string, number, or null).");
  }
};
fb.core.util.validation.validateEventType = function(a, b, c, d) {
  if (!d || goog.isDef(c)) {
    switch(c) {
      case "value":
      ;
      case "child_added":
      ;
      case "child_removed":
      ;
      case "child_changed":
      ;
      case "child_moved":
        break;
      default:
        throw Error(fb.util.validation.errorPrefix(a, b, d) + 'must be a valid event type: "value", "child_added", "child_removed", "child_changed", or "child_moved".');;
    }
  }
};
fb.core.util.validation.validateKey = function(a, b, c, d) {
  if ((!d || goog.isDef(c)) && !fb.core.util.validation.isValidKey(c)) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + 'was an invalid key: "' + c + '".  Firebase keys must be non-empty strings and can\'t contain ".", "#", "$", "/", "[", or "]").');
  }
};
fb.core.util.validation.validatePathString = function(a, b, c, d) {
  if ((!d || goog.isDef(c)) && !fb.core.util.validation.isValidPathString(c)) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + 'was an invalid path: "' + c + '". Paths must be non-empty strings and can\'t contain ".", "#", "$", "[", or "]"');
  }
};
fb.core.util.validation.validateRootPathString = function(a, b, c, d) {
  c && (c = c.replace(/^\/*\.info(\/|$)/, "/"));
  fb.core.util.validation.validatePathString(a, b, c, d);
};
fb.core.util.validation.validateWritablePath = function(a, b) {
  if (".info" === b.getFront()) {
    throw Error(a + " failed: Can't modify data under /.info/");
  }
};
fb.core.util.validation.validateUrl = function(a, b, c) {
  var d = c.path.toString();
  if (!goog.isString(c.repoInfo.host) || 0 === c.repoInfo.host.length || !fb.core.util.validation.isValidKey(c.repoInfo.namespace) || 0 !== d.length && !fb.core.util.validation.isValidRootPathString(d)) {
    throw Error(fb.util.validation.errorPrefix(a, b, !1) + 'must be a valid firebase URL and the path can\'t contain ".", "#", "$", "[", or "]".');
  }
};
fb.core.util.validation.validateCredential = function(a, b, c, d) {
  if ((!d || goog.isDef(c)) && !goog.isString(c)) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + "must be a valid credential (a string).");
  }
};
fb.core.util.validation.validateBoolean = function(a, b, c, d) {
  if ((!d || goog.isDef(c)) && !goog.isBoolean(c)) {
    throw Error(fb.util.validation.errorPrefix(a, b, d) + "must be a boolean.");
  }
};
fb.api = {};
fb.api.Query = function(a, b, c, d, e, f, g) {
  this.repo = a;
  this.path = b;
  this.itemLimit = c;
  this.startPriority = d;
  this.startName = e;
  this.endPriority = f;
  this.endName = g;
  if (goog.isDef(this.startPriority) && goog.isDef(this.endPriority) && goog.isDef(this.itemLimit)) {
    throw "Query: Can't combine startAt(), endAt(), and limit().";
  }
};
fb.api.Query.prototype.ref = function() {
  fb.util.validation.validateArgCount("Query.ref", 0, 0, arguments.length);
  return new Firebase(this.repo, this.path);
};
goog.exportProperty(fb.api.Query.prototype, "ref", fb.api.Query.prototype.ref);
fb.api.Query.prototype.on = function(a, b) {
  fb.util.validation.validateArgCount("Query.on", 2, 4, arguments.length);
  fb.core.util.validation.validateEventType("Query.on", 1, a, !1);
  fb.util.validation.validateCallback("Query.on", 2, b, !1);
  var c = this.getCancelAndContextArgs_("Query.on", arguments[2], arguments[3]);
  this.repo.addEventCallbackForQuery(this, a, b, c.cancel, c.context);
  return b;
};
goog.exportProperty(fb.api.Query.prototype, "on", fb.api.Query.prototype.on);
fb.api.Query.prototype.off = function(a, b, c) {
  fb.util.validation.validateArgCount("Query.off", 0, 3, arguments.length);
  fb.core.util.validation.validateEventType("Query.off", 1, a, !0);
  fb.util.validation.validateCallback("Query.off", 2, b, !0);
  fb.util.validation.validateContextObject("Query.off", 3, c, !0);
  this.repo.removeEventCallbackForQuery(this, a, b, c);
};
goog.exportProperty(fb.api.Query.prototype, "off", fb.api.Query.prototype.off);
fb.api.Query.prototype.once = function(a, b) {
  fb.util.validation.validateArgCount("Query.once", 2, 4, arguments.length);
  fb.core.util.validation.validateEventType("Query.once", 1, a, !1);
  fb.util.validation.validateCallback("Query.once", 2, b, !1);
  var c = this.getCancelAndContextArgs_("Query.once", arguments[2], arguments[3]), d = this, e = !0, f = function(g) {
    e && (e = !1, d.off(a, f), b.call(c.context, g));
  };
  this.on(a, f, function(b) {
    d.off(a, f);
    c.cancel && c.cancel.call(c.context, b);
  });
};
goog.exportProperty(fb.api.Query.prototype, "once", fb.api.Query.prototype.once);
fb.api.Query.prototype.limit = function(a) {
  fb.util.validation.validateArgCount("Query.limit", 1, 1, arguments.length);
  if (!goog.isNumber(a) || Math.floor(a) !== a || 0 >= a) {
    throw "Query.limit: First argument must be a positive integer.";
  }
  return new fb.api.Query(this.repo, this.path, a, this.startPriority, this.startName, this.endPriority, this.endName);
};
goog.exportProperty(fb.api.Query.prototype, "limit", fb.api.Query.prototype.limit);
fb.api.Query.prototype.startAt = function(a, b) {
  fb.util.validation.validateArgCount("Query.startAt", 0, 2, arguments.length);
  fb.core.util.validation.validatePriority("Query.startAt", 1, a, !0);
  fb.core.util.validation.validateKey("Query.startAt", 2, b, !0);
  goog.isDef(a) || (b = a = null);
  return new fb.api.Query(this.repo, this.path, this.itemLimit, a, b, this.endPriority, this.endName);
};
goog.exportProperty(fb.api.Query.prototype, "startAt", fb.api.Query.prototype.startAt);
fb.api.Query.prototype.endAt = function(a, b) {
  fb.util.validation.validateArgCount("Query.endAt", 0, 2, arguments.length);
  fb.core.util.validation.validatePriority("Query.endAt", 1, a, !0);
  fb.core.util.validation.validateKey("Query.endAt", 2, b, !0);
  return new fb.api.Query(this.repo, this.path, this.itemLimit, this.startPriority, this.startName, a, b);
};
goog.exportProperty(fb.api.Query.prototype, "endAt", fb.api.Query.prototype.endAt);
fb.api.Query.prototype.queryObject = function() {
  var a = {};
  goog.isDef(this.startPriority) && (a.sp = this.startPriority);
  goog.isDef(this.startName) && (a.sn = this.startName);
  goog.isDef(this.endPriority) && (a.ep = this.endPriority);
  goog.isDef(this.endName) && (a.en = this.endName);
  goog.isDef(this.itemLimit) && (a.l = this.itemLimit);
  goog.isDef(this.startPriority) && goog.isDef(this.startName) && null === this.startPriority && null === this.startName && (a.vf = "l");
  return a;
};
fb.api.Query.prototype.queryIdentifier = function() {
  var a = this.queryObject(), a = fb.core.util.ObjectToUniqueKey(a);
  return "{}" === a ? "default" : a;
};
fb.api.Query.prototype.getCancelAndContextArgs_ = function(a, b, c) {
  var d = {};
  if (b && c) {
    d.cancel = b, fb.util.validation.validateCallback(a, 3, d.cancel, !0), d.context = c, fb.util.validation.validateContextObject(a, 4, d.context, !0);
  } else {
    if (b) {
      if ("object" === typeof b && null !== b) {
        d.context = b;
      } else {
        if ("function" === typeof b) {
          d.cancel = b;
        } else {
          throw Error(fb.util.validation.errorPrefix_(a, 3, !0) + "must either be a cancel callback or a context object.");
        }
      }
    }
  }
  return d;
};
fb.core.util.Path = function(a, b) {
  if (1 == arguments.length) {
    this.pieces_ = a.split("/");
    for (var c = 0, d = 0;d < this.pieces_.length;d++) {
      0 < this.pieces_[d].length && (this.pieces_[c] = this.pieces_[d], c++);
    }
    this.pieces_.length = c;
    this.pieceNum_ = 0;
  } else {
    this.pieces_ = a, this.pieceNum_ = b;
  }
};
fb.core.util.Path.prototype.getFront = function() {
  return this.pieceNum_ >= this.pieces_.length ? null : this.pieces_[this.pieceNum_];
};
fb.core.util.Path.prototype.popFront = function() {
  var a = this.pieceNum_;
  a < this.pieces_.length && a++;
  return new fb.core.util.Path(this.pieces_, a);
};
fb.core.util.Path.prototype.getBack = function() {
  return this.pieceNum_ < this.pieces_.length ? this.pieces_[this.pieces_.length - 1] : null;
};
fb.core.util.Path.prototype.toString = function() {
  for (var a = "", b = this.pieceNum_;b < this.pieces_.length;b++) {
    "" !== this.pieces_[b] && (a += "/" + this.pieces_[b]);
  }
  return a || "/";
};
fb.core.util.Path.prototype.parent = function() {
  if (this.pieceNum_ >= this.pieces_.length) {
    return null;
  }
  for (var a = [], b = this.pieceNum_;b < this.pieces_.length - 1;b++) {
    a.push(this.pieces_[b]);
  }
  return new fb.core.util.Path(a, 0);
};
fb.core.util.Path.prototype.child = function(a) {
  for (var b = [], c = this.pieceNum_;c < this.pieces_.length;c++) {
    b.push(this.pieces_[c]);
  }
  if (a instanceof fb.core.util.Path) {
    for (c = a.pieceNum_;c < a.pieces_.length;c++) {
      b.push(a.pieces_[c]);
    }
  } else {
    for (a = a.split("/"), c = 0;c < a.length;c++) {
      0 < a[c].length && b.push(a[c]);
    }
  }
  return new fb.core.util.Path(b, 0);
};
fb.core.util.Path.prototype.isEmpty = function() {
  return this.pieceNum_ >= this.pieces_.length;
};
fb.core.util.Path.RelativePath = function(a, b) {
  var c = a.getFront(), d = b.getFront();
  if (null === c) {
    return b;
  }
  if (c === d) {
    return fb.core.util.Path.RelativePath(a.popFront(), b.popFront());
  }
  throw "INTERNAL ERROR: innerPath (" + b + ") is not within outerPath (" + a + ")";
};
fb.core.util.Path.prototype.contains = function(a) {
  var b = 0;
  if (this.pieces_.length > a.pieces_.length) {
    return!1;
  }
  for (;b < this.pieces_.length;) {
    if (this.pieces_[b] !== a.pieces_[b]) {
      return!1;
    }
    ++b;
  }
  return!0;
};
fb.core.util.TreeNode = function() {
  this.children = {};
  this.childCount = 0;
  this.value = null;
};
fb.core.util.Tree = function(a, b, c) {
  this.name_ = a ? a : "";
  this.parent_ = b ? b : null;
  this.node_ = c ? c : new fb.core.util.TreeNode;
};
fb.core.util.Tree.prototype.subTree = function(a) {
  a = a instanceof fb.core.util.Path ? a : new fb.core.util.Path(a);
  for (var b = this, c;null !== (c = a.getFront());) {
    var d = fb.util.obj.get(b.node_.children, c) || new fb.core.util.TreeNode, b = new fb.core.util.Tree(c, b, d);
    a = a.popFront();
  }
  return b;
};
fb.core.util.Tree.prototype.getValue = function() {
  return this.node_.value;
};
fb.core.util.Tree.prototype.setValue = function(a) {
  fb.core.util.assert("undefined" !== typeof a, "Cannot set value to undefined");
  this.node_.value = a;
  this.updateParents_();
};
fb.core.util.Tree.prototype.clear = function() {
  this.node_.value = null;
  this.node_.children = {};
  this.node_.childCount = 0;
  this.updateParents_();
};
fb.core.util.Tree.prototype.hasChildren = function() {
  return 0 < this.node_.childCount;
};
fb.core.util.Tree.prototype.isEmpty = function() {
  return null === this.getValue() && !this.hasChildren();
};
fb.core.util.Tree.prototype.forEachChild = function(a) {
  for (var b in this.node_.children) {
    a(new fb.core.util.Tree(b, this, this.node_.children[b]));
  }
};
fb.core.util.Tree.prototype.forEachDescendant = function(a, b, c) {
  b && !c && a(this);
  this.forEachChild(function(b) {
    b.forEachDescendant(a, !0, c);
  });
  b && c && a(this);
};
fb.core.util.Tree.prototype.forEachAncestor = function(a, b) {
  for (var c = b ? this : this.parent();null !== c;) {
    if (a(c)) {
      return!0;
    }
    c = c.parent();
  }
  return!1;
};
fb.core.util.Tree.prototype.forEachImmediateDescendantWithValue = function(a) {
  this.forEachChild(function(b) {
    null !== b.getValue() ? a(b) : b.forEachImmediateDescendantWithValue(a);
  });
};
fb.core.util.Tree.prototype.path = function() {
  return new fb.core.util.Path(null === this.parent_ ? this.name_ : this.parent_.path() + "/" + this.name_);
};
fb.core.util.Tree.prototype.name = function() {
  return this.name_;
};
fb.core.util.Tree.prototype.parent = function() {
  return this.parent_;
};
fb.core.util.Tree.prototype.updateParents_ = function() {
  null !== this.parent_ && this.parent_.updateChild_(this.name_, this);
};
fb.core.util.Tree.prototype.updateChild_ = function(a, b) {
  var c = b.isEmpty(), d = fb.util.obj.contains(this.node_.children, a);
  c && d ? (delete this.node_.children[a], this.node_.childCount--, this.updateParents_()) : c || d || (this.node_.children[a] = b.node_, this.node_.childCount++, this.updateParents_());
};
fb.core.util.SortedMap = function(a, b) {
  this.comparator_ = a ? a : fb.core.util.SortedMap.STANDARD_COMPARATOR_;
  this.root_ = b ? b : fb.core.util.SortedMap.EMPTY_NODE_;
};
fb.core.util.SortedMap.STANDARD_COMPARATOR_ = function(a, b) {
  return a < b ? -1 : a > b ? 1 : 0;
};
fb.core.util.SortedMap.prototype.insert = function(a, b) {
  return new fb.core.util.SortedMap(this.comparator_, this.root_.insert(a, b, this.comparator_).copy(null, null, fb.LLRBNode.BLACK, null, null));
};
fb.core.util.SortedMap.prototype.remove = function(a) {
  return new fb.core.util.SortedMap(this.comparator_, this.root_.remove(a, this.comparator_).copy(null, null, fb.LLRBNode.BLACK, null, null));
};
fb.core.util.SortedMap.prototype.get = function(a) {
  for (var b, c = this.root_;!c.isEmpty();) {
    b = this.comparator_(a, c.key);
    if (0 === b) {
      return c.value;
    }
    0 > b ? c = c.left : 0 < b && (c = c.right);
  }
  return null;
};
fb.core.util.SortedMap.prototype.getPredecessorKey = function(a) {
  for (var b, c = this.root_, d = null;!c.isEmpty();) {
    b = this.comparator_(a, c.key);
    if (0 === b) {
      if (c.left.isEmpty()) {
        return d ? d.key : null;
      }
      for (c = c.left;!c.right.isEmpty();) {
        c = c.right;
      }
      return c.key;
    }
    0 > b ? c = c.left : 0 < b && (d = c, c = c.right);
  }
  throw Error("Attempted to find predecessor key for a nonexistent key.  What gives?");
};
fb.core.util.SortedMap.prototype.isEmpty = function() {
  return this.root_.isEmpty();
};
fb.core.util.SortedMap.prototype.count = function() {
  return this.root_.count();
};
fb.core.util.SortedMap.prototype.minKey = function() {
  return this.root_.minKey();
};
fb.core.util.SortedMap.prototype.maxKey = function() {
  return this.root_.maxKey();
};
fb.core.util.SortedMap.prototype.inorderTraversal = function(a) {
  return this.root_.inorderTraversal(a);
};
fb.core.util.SortedMap.prototype.reverseTraversal = function(a) {
  return this.root_.reverseTraversal(a);
};
fb.core.util.SortedMap.prototype.getIterator = function(a) {
  return new fb.core.util.SortedMapIterator(this.root_, a);
};
fb.core.util.SortedMapIterator = function(a, b) {
  this.resultGenerator_ = b;
  for (this.nodeStack_ = [];!a.isEmpty();) {
    this.nodeStack_.push(a), a = a.left;
  }
};
fb.core.util.SortedMapIterator.prototype.getNext = function() {
  if (0 === this.nodeStack_.length) {
    return null;
  }
  var a = this.nodeStack_.pop(), b;
  b = this.resultGenerator_ ? this.resultGenerator_(a.key, a.value) : {key:a.key, value:a.value};
  for (a = a.right;!a.isEmpty();) {
    this.nodeStack_.push(a), a = a.left;
  }
  return b;
};
fb.LLRBNode = function(a, b, c, d, e) {
  this.key = a;
  this.value = b;
  this.color = null != c ? c : fb.LLRBNode.RED;
  this.left = null != d ? d : fb.core.util.SortedMap.EMPTY_NODE_;
  this.right = null != e ? e : fb.core.util.SortedMap.EMPTY_NODE_;
};
fb.LLRBNode.RED = !0;
fb.LLRBNode.BLACK = !1;
fb.LLRBNode.prototype.copy = function(a, b, c, d, e) {
  return new fb.LLRBNode(null != a ? a : this.key, null != b ? b : this.value, null != c ? c : this.color, null != d ? d : this.left, null != e ? e : this.right);
};
fb.LLRBNode.prototype.count = function() {
  return this.left.count() + 1 + this.right.count();
};
fb.LLRBNode.prototype.isEmpty = function() {
  return!1;
};
fb.LLRBNode.prototype.inorderTraversal = function(a) {
  return this.left.inorderTraversal(a) || a(this.key, this.value) || this.right.inorderTraversal(a);
};
fb.LLRBNode.prototype.reverseTraversal = function(a) {
  return this.right.reverseTraversal(a) || a(this.key, this.value) || this.left.reverseTraversal(a);
};
fb.LLRBNode.prototype.min_ = function() {
  return this.left.isEmpty() ? this : this.left.min_();
};
fb.LLRBNode.prototype.minKey = function() {
  return this.min_().key;
};
fb.LLRBNode.prototype.maxKey = function() {
  return this.right.isEmpty() ? this.key : this.right.maxKey();
};
fb.LLRBNode.prototype.insert = function(a, b, c) {
  var d, e;
  e = this;
  d = c(a, e.key);
  e = 0 > d ? e.copy(null, null, null, e.left.insert(a, b, c), null) : 0 === d ? e.copy(null, b, null, null, null) : e.copy(null, null, null, null, e.right.insert(a, b, c));
  return e.fixUp_();
};
fb.LLRBNode.prototype.removeMin_ = function() {
  var a;
  if (this.left.isEmpty()) {
    return fb.core.util.SortedMap.EMPTY_NODE_;
  }
  a = this;
  a.left.isRed_() || a.left.left.isRed_() || (a = a.moveRedLeft_());
  a = a.copy(null, null, null, a.left.removeMin_(), null);
  return a.fixUp_();
};
fb.LLRBNode.prototype.remove = function(a, b) {
  var c, d;
  c = this;
  if (0 > b(a, c.key)) {
    c.left.isEmpty() || c.left.isRed_() || c.left.left.isRed_() || (c = c.moveRedLeft_()), c = c.copy(null, null, null, c.left.remove(a, b), null);
  } else {
    c.left.isRed_() && (c = c.rotateRight_());
    c.right.isEmpty() || c.right.isRed_() || c.right.left.isRed_() || (c = c.moveRedRight_());
    if (0 === b(a, c.key)) {
      if (c.right.isEmpty()) {
        return fb.core.util.SortedMap.EMPTY_NODE_;
      }
      d = c.right.min_();
      c = c.copy(d.key, d.value, null, null, c.right.removeMin_());
    }
    c = c.copy(null, null, null, null, c.right.remove(a, b));
  }
  return c.fixUp_();
};
fb.LLRBNode.prototype.isRed_ = function() {
  return this.color;
};
fb.LLRBNode.prototype.fixUp_ = function() {
  var a = this;
  a.right.isRed_() && !a.left.isRed_() && (a = a.rotateLeft_());
  a.left.isRed_() && a.left.left.isRed_() && (a = a.rotateRight_());
  a.left.isRed_() && a.right.isRed_() && (a = a.colorFlip_());
  return a;
};
fb.LLRBNode.prototype.moveRedLeft_ = function() {
  var a = this.colorFlip_();
  a.right.left.isRed_() && (a = a.copy(null, null, null, null, a.right.rotateRight_()), a = a.rotateLeft_(), a = a.colorFlip_());
  return a;
};
fb.LLRBNode.prototype.moveRedRight_ = function() {
  var a = this.colorFlip_();
  a.left.left.isRed_() && (a = a.rotateRight_(), a = a.colorFlip_());
  return a;
};
fb.LLRBNode.prototype.rotateLeft_ = function() {
  var a;
  a = this.copy(null, null, fb.LLRBNode.RED, null, this.right.left);
  return this.right.copy(null, null, this.color, a, null);
};
fb.LLRBNode.prototype.rotateRight_ = function() {
  var a;
  a = this.copy(null, null, fb.LLRBNode.RED, this.left.right, null);
  return this.left.copy(null, null, this.color, null, a);
};
fb.LLRBNode.prototype.colorFlip_ = function() {
  var a, b;
  a = this.left.copy(null, null, !this.left.color, null, null);
  b = this.right.copy(null, null, !this.right.color, null, null);
  return this.copy(null, null, !this.color, a, b);
};
fb.LLRBNode.prototype.checkMaxDepth_ = function() {
  var a;
  a = this.check_();
  return Math.pow(2, a) <= this.count() + 1 ? !0 : !1;
};
fb.LLRBNode.prototype.check_ = function() {
  var a;
  if (this.isRed_() && this.left.isRed_()) {
    throw Error("Red node has red child(" + this.key + "," + this.value + ")");
  }
  if (this.right.isRed_()) {
    throw Error("Right child of (" + this.key + "," + this.value + ") is red");
  }
  a = this.left.check_();
  if (a !== this.right.check_()) {
    throw Error("Black depths differ");
  }
  return a + (this.isRed_() ? 0 : 1);
};
fb.LLRBEmptyNode = function() {
};
fb.LLRBEmptyNode.prototype.copy = function() {
  return this;
};
fb.LLRBEmptyNode.prototype.insert = function(a, b, c) {
  return new fb.LLRBNode(a, b, null);
};
fb.LLRBEmptyNode.prototype.remove = function(a, b) {
  return this;
};
fb.LLRBEmptyNode.prototype.count = function() {
  return 0;
};
fb.LLRBEmptyNode.prototype.isEmpty = function() {
  return!0;
};
fb.LLRBEmptyNode.prototype.inorderTraversal = function(a) {
  return!1;
};
fb.LLRBEmptyNode.prototype.reverseTraversal = function(a) {
  return!1;
};
fb.LLRBEmptyNode.prototype.minKey = function() {
  return null;
};
fb.LLRBEmptyNode.prototype.maxKey = function() {
  return null;
};
fb.LLRBEmptyNode.prototype.check_ = function() {
  return 0;
};
fb.LLRBEmptyNode.prototype.isRed_ = function() {
  return!1;
};
fb.core.util.SortedMap.EMPTY_NODE_ = new fb.LLRBEmptyNode;
fb.core.storage = {};
fb.core.storage.DOMStorageWrapper = function(a) {
  this.domStorage_ = a;
  this.prefix_ = "firebase:";
};
fb.core.storage.DOMStorageWrapper.prototype.set = function(a, b) {
  null == b ? this.domStorage_.removeItem(this.prefixedName_(a)) : this.domStorage_.setItem(this.prefixedName_(a), fb.util.json.stringify(b));
};
fb.core.storage.DOMStorageWrapper.prototype.get = function(a) {
  a = this.domStorage_.getItem(this.prefixedName_(a));
  return null == a ? null : fb.util.json.eval(a);
};
fb.core.storage.DOMStorageWrapper.prototype.remove = function(a) {
  this.domStorage_.removeItem(this.prefixedName_(a));
};
fb.core.storage.DOMStorageWrapper.prototype.isInMemoryStorage = !1;
fb.core.storage.DOMStorageWrapper.prototype.prefixedName_ = function(a) {
  return this.prefix_ + a;
};
fb.core.storage.MemoryStorage = function() {
  this.cache_ = {};
};
fb.core.storage.MemoryStorage.prototype.set = function(a, b) {
  null == b ? delete this.cache_[a] : this.cache_[a] = b;
};
fb.core.storage.MemoryStorage.prototype.get = function(a) {
  return fb.util.obj.contains(this.cache_, a) ? this.cache_[a] : null;
};
fb.core.storage.MemoryStorage.prototype.remove = function(a) {
  delete this.cache_[a];
};
fb.core.storage.MemoryStorage.prototype.isInMemoryStorage = !0;
fb.core.storage.createStoragefor = function(a) {
  try {
    if ("undefined" !== typeof window && "undefined" !== typeof window[a]) {
      var b = window[a];
      b.setItem("firebase:sentinel", "cache");
      b.removeItem("firebase:sentinel");
      return new fb.core.storage.DOMStorageWrapper(b);
    }
  } catch (c) {
  }
  return new fb.core.storage.MemoryStorage;
};
fb.core.storage.PersistentStorage = fb.core.storage.createStoragefor("localStorage");
fb.core.storage.SessionStorage = fb.core.storage.createStoragefor("sessionStorage");
fb.core.RepoInfo = function(a, b, c, d) {
  this.host = a.toLowerCase();
  this.domain = this.host.substr(this.host.indexOf(".") + 1);
  this.secure = b;
  this.namespace = c;
  this.webSocketOnly = d;
  this.internalHost = fb.core.storage.PersistentStorage.get("host:" + a) || this.host;
};
fb.core.RepoInfo.prototype.needsQueryParam = function() {
  return this.host !== this.internalHost;
};
fb.core.RepoInfo.prototype.isCacheableHost = function() {
  return "s-" === this.internalHost.substr(0, 2);
};
fb.core.RepoInfo.prototype.isDemoHost = function() {
  return "firebaseio-demo.com" === this.domain;
};
fb.core.RepoInfo.prototype.updateHost = function(a) {
  a !== this.internalHost && (this.internalHost = a, this.isCacheableHost() && fb.core.storage.PersistentStorage.set("host:" + this.host, this.internalHost));
};
fb.core.RepoInfo.prototype.toString = function() {
  return(this.secure ? "https://" : "http://") + this.host;
};
fb.constants = {};
var NODE_CLIENT = !0;
goog.crypt = {};
goog.crypt.Hash = function() {
  this.blockSize = -1;
};
goog.crypt.Sha1 = function() {
  goog.crypt.Hash.call(this);
  this.blockSize = 64;
  this.chain_ = [];
  this.buf_ = [];
  this.W_ = [];
  this.pad_ = [];
  this.pad_[0] = 128;
  for (var a = 1;a < this.blockSize;++a) {
    this.pad_[a] = 0;
  }
  this.total_ = this.inbuf_ = 0;
  this.reset();
};
goog.inherits(goog.crypt.Sha1, goog.crypt.Hash);
goog.crypt.Sha1.prototype.reset = function() {
  this.chain_[0] = 1732584193;
  this.chain_[1] = 4023233417;
  this.chain_[2] = 2562383102;
  this.chain_[3] = 271733878;
  this.chain_[4] = 3285377520;
  this.total_ = this.inbuf_ = 0;
};
goog.crypt.Sha1.prototype.compress_ = function(a, b) {
  b || (b = 0);
  var c = this.W_;
  if (goog.isString(a)) {
    for (var d = 0;16 > d;d++) {
      c[d] = a.charCodeAt(b) << 24 | a.charCodeAt(b + 1) << 16 | a.charCodeAt(b + 2) << 8 | a.charCodeAt(b + 3), b += 4;
    }
  } else {
    for (d = 0;16 > d;d++) {
      c[d] = a[b] << 24 | a[b + 1] << 16 | a[b + 2] << 8 | a[b + 3], b += 4;
    }
  }
  for (d = 16;80 > d;d++) {
    var e = c[d - 3] ^ c[d - 8] ^ c[d - 14] ^ c[d - 16];
    c[d] = (e << 1 | e >>> 31) & 4294967295;
  }
  for (var f = this.chain_[0], g = this.chain_[1], h = this.chain_[2], k = this.chain_[3], l = this.chain_[4], m, d = 0;80 > d;d++) {
    40 > d ? 20 > d ? (e = k ^ g & (h ^ k), m = 1518500249) : (e = g ^ h ^ k, m = 1859775393) : 60 > d ? (e = g & h | k & (g | h), m = 2400959708) : (e = g ^ h ^ k, m = 3395469782), e = (f << 5 | f >>> 27) + e + l + m + c[d] & 4294967295, l = k, k = h, h = (g << 30 | g >>> 2) & 4294967295, g = f, f = e;
  }
  this.chain_[0] = this.chain_[0] + f & 4294967295;
  this.chain_[1] = this.chain_[1] + g & 4294967295;
  this.chain_[2] = this.chain_[2] + h & 4294967295;
  this.chain_[3] = this.chain_[3] + k & 4294967295;
  this.chain_[4] = this.chain_[4] + l & 4294967295;
};
goog.crypt.Sha1.prototype.update = function(a, b) {
  goog.isDef(b) || (b = a.length);
  for (var c = b - this.blockSize, d = 0, e = this.buf_, f = this.inbuf_;d < b;) {
    if (0 == f) {
      for (;d <= c;) {
        this.compress_(a, d), d += this.blockSize;
      }
    }
    if (goog.isString(a)) {
      for (;d < b;) {
        if (e[f] = a.charCodeAt(d), ++f, ++d, f == this.blockSize) {
          this.compress_(e);
          f = 0;
          break;
        }
      }
    } else {
      for (;d < b;) {
        if (e[f] = a[d], ++f, ++d, f == this.blockSize) {
          this.compress_(e);
          f = 0;
          break;
        }
      }
    }
  }
  this.inbuf_ = f;
  this.total_ += b;
};
goog.crypt.Sha1.prototype.digest = function() {
  var a = [], b = 8 * this.total_;
  56 > this.inbuf_ ? this.update(this.pad_, 56 - this.inbuf_) : this.update(this.pad_, this.blockSize - (this.inbuf_ - 56));
  for (var c = this.blockSize - 1;56 <= c;c--) {
    this.buf_[c] = b & 255, b /= 256;
  }
  this.compress_(this.buf_);
  for (c = b = 0;5 > c;c++) {
    for (var d = 24;0 <= d;d -= 8) {
      a[b] = this.chain_[c] >> d & 255, ++b;
    }
  }
  return a;
};
goog.dom = {};
goog.dom.NodeType = {ELEMENT:1, ATTRIBUTE:2, TEXT:3, CDATA_SECTION:4, ENTITY_REFERENCE:5, ENTITY:6, PROCESSING_INSTRUCTION:7, COMMENT:8, DOCUMENT:9, DOCUMENT_TYPE:10, DOCUMENT_FRAGMENT:11, NOTATION:12};
goog.debug = {};
goog.debug.Error = function(a) {
  if (Error.captureStackTrace) {
    Error.captureStackTrace(this, goog.debug.Error);
  } else {
    var b = Error().stack;
    b && (this.stack = b);
  }
  a && (this.message = String(a));
};
goog.inherits(goog.debug.Error, Error);
goog.debug.Error.prototype.name = "CustomError";
goog.string = {};
goog.string.DETECT_DOUBLE_ESCAPING = !1;
goog.string.Unicode = {NBSP:"\u00a0"};
goog.string.startsWith = function(a, b) {
  return 0 == a.lastIndexOf(b, 0);
};
goog.string.endsWith = function(a, b) {
  var c = a.length - b.length;
  return 0 <= c && a.indexOf(b, c) == c;
};
goog.string.caseInsensitiveStartsWith = function(a, b) {
  return 0 == goog.string.caseInsensitiveCompare(b, a.substr(0, b.length));
};
goog.string.caseInsensitiveEndsWith = function(a, b) {
  return 0 == goog.string.caseInsensitiveCompare(b, a.substr(a.length - b.length, b.length));
};
goog.string.caseInsensitiveEquals = function(a, b) {
  return a.toLowerCase() == b.toLowerCase();
};
goog.string.subs = function(a, b) {
  for (var c = a.split("%s"), d = "", e = Array.prototype.slice.call(arguments, 1);e.length && 1 < c.length;) {
    d += c.shift() + e.shift();
  }
  return d + c.join("%s");
};
goog.string.collapseWhitespace = function(a) {
  return a.replace(/[\s\xa0]+/g, " ").replace(/^\s+|\s+$/g, "");
};
goog.string.isEmpty = function(a) {
  return/^[\s\xa0]*$/.test(a);
};
goog.string.isEmptySafe = function(a) {
  return goog.string.isEmpty(goog.string.makeSafe(a));
};
goog.string.isBreakingWhitespace = function(a) {
  return!/[^\t\n\r ]/.test(a);
};
goog.string.isAlpha = function(a) {
  return!/[^a-zA-Z]/.test(a);
};
goog.string.isNumeric = function(a) {
  return!/[^0-9]/.test(a);
};
goog.string.isAlphaNumeric = function(a) {
  return!/[^a-zA-Z0-9]/.test(a);
};
goog.string.isSpace = function(a) {
  return " " == a;
};
goog.string.isUnicodeChar = function(a) {
  return 1 == a.length && " " <= a && "~" >= a || "\u0080" <= a && "\ufffd" >= a;
};
goog.string.stripNewlines = function(a) {
  return a.replace(/(\r\n|\r|\n)+/g, " ");
};
goog.string.canonicalizeNewlines = function(a) {
  return a.replace(/(\r\n|\r|\n)/g, "\n");
};
goog.string.normalizeWhitespace = function(a) {
  return a.replace(/\xa0|\s/g, " ");
};
goog.string.normalizeSpaces = function(a) {
  return a.replace(/\xa0|[ \t]+/g, " ");
};
goog.string.collapseBreakingSpaces = function(a) {
  return a.replace(/[\t\r\n ]+/g, " ").replace(/^[\t\r\n ]+|[\t\r\n ]+$/g, "");
};
goog.string.trim = function(a) {
  return a.replace(/^[\s\xa0]+|[\s\xa0]+$/g, "");
};
goog.string.trimLeft = function(a) {
  return a.replace(/^[\s\xa0]+/, "");
};
goog.string.trimRight = function(a) {
  return a.replace(/[\s\xa0]+$/, "");
};
goog.string.caseInsensitiveCompare = function(a, b) {
  var c = String(a).toLowerCase(), d = String(b).toLowerCase();
  return c < d ? -1 : c == d ? 0 : 1;
};
goog.string.numerateCompareRegExp_ = /(\.\d+)|(\d+)|(\D+)/g;
goog.string.numerateCompare = function(a, b) {
  if (a == b) {
    return 0;
  }
  if (!a) {
    return-1;
  }
  if (!b) {
    return 1;
  }
  for (var c = a.toLowerCase().match(goog.string.numerateCompareRegExp_), d = b.toLowerCase().match(goog.string.numerateCompareRegExp_), e = Math.min(c.length, d.length), f = 0;f < e;f++) {
    var g = c[f], h = d[f];
    if (g != h) {
      return c = parseInt(g, 10), !isNaN(c) && (d = parseInt(h, 10), !isNaN(d) && c - d) ? c - d : g < h ? -1 : 1;
    }
  }
  return c.length != d.length ? c.length - d.length : a < b ? -1 : 1;
};
goog.string.urlEncode = function(a) {
  return encodeURIComponent(String(a));
};
goog.string.urlDecode = function(a) {
  return decodeURIComponent(a.replace(/\+/g, " "));
};
goog.string.newLineToBr = function(a, b) {
  return a.replace(/(\r\n|\r|\n)/g, b ? "<br />" : "<br>");
};
goog.string.htmlEscape = function(a, b) {
  if (b) {
    a = a.replace(goog.string.AMP_RE_, "&amp;").replace(goog.string.LT_RE_, "&lt;").replace(goog.string.GT_RE_, "&gt;").replace(goog.string.QUOT_RE_, "&quot;").replace(goog.string.SINGLE_QUOTE_RE_, "&#39;").replace(goog.string.NULL_RE_, "&#0;"), goog.string.DETECT_DOUBLE_ESCAPING && (a = a.replace(goog.string.E_RE_, "&#101;"));
  } else {
    if (!goog.string.ALL_RE_.test(a)) {
      return a;
    }
    -1 != a.indexOf("&") && (a = a.replace(goog.string.AMP_RE_, "&amp;"));
    -1 != a.indexOf("<") && (a = a.replace(goog.string.LT_RE_, "&lt;"));
    -1 != a.indexOf(">") && (a = a.replace(goog.string.GT_RE_, "&gt;"));
    -1 != a.indexOf('"') && (a = a.replace(goog.string.QUOT_RE_, "&quot;"));
    -1 != a.indexOf("'") && (a = a.replace(goog.string.SINGLE_QUOTE_RE_, "&#39;"));
    -1 != a.indexOf("\x00") && (a = a.replace(goog.string.NULL_RE_, "&#0;"));
    goog.string.DETECT_DOUBLE_ESCAPING && -1 != a.indexOf("e") && (a = a.replace(goog.string.E_RE_, "&#101;"));
  }
  return a;
};
goog.string.AMP_RE_ = /&/g;
goog.string.LT_RE_ = /</g;
goog.string.GT_RE_ = />/g;
goog.string.QUOT_RE_ = /"/g;
goog.string.SINGLE_QUOTE_RE_ = /'/g;
goog.string.NULL_RE_ = /\x00/g;
goog.string.E_RE_ = /e/g;
goog.string.ALL_RE_ = goog.string.DETECT_DOUBLE_ESCAPING ? /[\x00&<>"'e]/ : /[\x00&<>"']/;
goog.string.unescapeEntities = function(a) {
  return goog.string.contains(a, "&") ? "document" in goog.global ? goog.string.unescapeEntitiesUsingDom_(a) : goog.string.unescapePureXmlEntities_(a) : a;
};
goog.string.unescapeEntitiesWithDocument = function(a, b) {
  return goog.string.contains(a, "&") ? goog.string.unescapeEntitiesUsingDom_(a, b) : a;
};
goog.string.unescapeEntitiesUsingDom_ = function(a, b) {
  var c = {"&amp;":"&", "&lt;":"<", "&gt;":">", "&quot;":'"'}, d;
  d = b ? b.createElement("div") : goog.global.document.createElement("div");
  return a.replace(goog.string.HTML_ENTITY_PATTERN_, function(a, b) {
    var g = c[a];
    if (g) {
      return g;
    }
    if ("#" == b.charAt(0)) {
      var h = Number("0" + b.substr(1));
      isNaN(h) || (g = String.fromCharCode(h));
    }
    g || (d.innerHTML = a + " ", g = d.firstChild.nodeValue.slice(0, -1));
    return c[a] = g;
  });
};
goog.string.unescapePureXmlEntities_ = function(a) {
  return a.replace(/&([^;]+);/g, function(a, c) {
    switch(c) {
      case "amp":
        return "&";
      case "lt":
        return "<";
      case "gt":
        return ">";
      case "quot":
        return'"';
      default:
        if ("#" == c.charAt(0)) {
          var d = Number("0" + c.substr(1));
          if (!isNaN(d)) {
            return String.fromCharCode(d);
          }
        }
        return a;
    }
  });
};
goog.string.HTML_ENTITY_PATTERN_ = /&([^;\s<&]+);?/g;
goog.string.whitespaceEscape = function(a, b) {
  return goog.string.newLineToBr(a.replace(/  /g, " &#160;"), b);
};
goog.string.preserveSpaces = function(a) {
  return a.replace(/(^|[\n ]) /g, "$1" + goog.string.Unicode.NBSP);
};
goog.string.stripQuotes = function(a, b) {
  for (var c = b.length, d = 0;d < c;d++) {
    var e = 1 == c ? b : b.charAt(d);
    if (a.charAt(0) == e && a.charAt(a.length - 1) == e) {
      return a.substring(1, a.length - 1);
    }
  }
  return a;
};
goog.string.truncate = function(a, b, c) {
  c && (a = goog.string.unescapeEntities(a));
  a.length > b && (a = a.substring(0, b - 3) + "...");
  c && (a = goog.string.htmlEscape(a));
  return a;
};
goog.string.truncateMiddle = function(a, b, c, d) {
  c && (a = goog.string.unescapeEntities(a));
  if (d && a.length > b) {
    d > b && (d = b);
    var e = a.length - d;
    a = a.substring(0, b - d) + "..." + a.substring(e);
  } else {
    a.length > b && (d = Math.floor(b / 2), e = a.length - d, a = a.substring(0, d + b % 2) + "..." + a.substring(e));
  }
  c && (a = goog.string.htmlEscape(a));
  return a;
};
goog.string.specialEscapeChars_ = {"\x00":"\\0", "\b":"\\b", "\f":"\\f", "\n":"\\n", "\r":"\\r", "\t":"\\t", "\x0B":"\\x0B", '"':'\\"', "\\":"\\\\"};
goog.string.jsEscapeCache_ = {"'":"\\'"};
goog.string.quote = function(a) {
  a = String(a);
  if (a.quote) {
    return a.quote();
  }
  for (var b = ['"'], c = 0;c < a.length;c++) {
    var d = a.charAt(c), e = d.charCodeAt(0);
    b[c + 1] = goog.string.specialEscapeChars_[d] || (31 < e && 127 > e ? d : goog.string.escapeChar(d));
  }
  b.push('"');
  return b.join("");
};
goog.string.escapeString = function(a) {
  for (var b = [], c = 0;c < a.length;c++) {
    b[c] = goog.string.escapeChar(a.charAt(c));
  }
  return b.join("");
};
goog.string.escapeChar = function(a) {
  if (a in goog.string.jsEscapeCache_) {
    return goog.string.jsEscapeCache_[a];
  }
  if (a in goog.string.specialEscapeChars_) {
    return goog.string.jsEscapeCache_[a] = goog.string.specialEscapeChars_[a];
  }
  var b = a, c = a.charCodeAt(0);
  if (31 < c && 127 > c) {
    b = a;
  } else {
    if (256 > c) {
      if (b = "\\x", 16 > c || 256 < c) {
        b += "0";
      }
    } else {
      b = "\\u", 4096 > c && (b += "0");
    }
    b += c.toString(16).toUpperCase();
  }
  return goog.string.jsEscapeCache_[a] = b;
};
goog.string.toMap = function(a) {
  for (var b = {}, c = 0;c < a.length;c++) {
    b[a.charAt(c)] = !0;
  }
  return b;
};
goog.string.contains = function(a, b) {
  return-1 != a.indexOf(b);
};
goog.string.caseInsensitiveContains = function(a, b) {
  return goog.string.contains(a.toLowerCase(), b.toLowerCase());
};
goog.string.countOf = function(a, b) {
  return a && b ? a.split(b).length - 1 : 0;
};
goog.string.removeAt = function(a, b, c) {
  var d = a;
  0 <= b && b < a.length && 0 < c && (d = a.substr(0, b) + a.substr(b + c, a.length - b - c));
  return d;
};
goog.string.remove = function(a, b) {
  var c = new RegExp(goog.string.regExpEscape(b), "");
  return a.replace(c, "");
};
goog.string.removeAll = function(a, b) {
  var c = new RegExp(goog.string.regExpEscape(b), "g");
  return a.replace(c, "");
};
goog.string.regExpEscape = function(a) {
  return String(a).replace(/([-()\[\]{}+?*.$\^|,:#<!\\])/g, "\\$1").replace(/\x08/g, "\\x08");
};
goog.string.repeat = function(a, b) {
  return Array(b + 1).join(a);
};
goog.string.padNumber = function(a, b, c) {
  a = goog.isDef(c) ? a.toFixed(c) : String(a);
  c = a.indexOf(".");
  -1 == c && (c = a.length);
  return goog.string.repeat("0", Math.max(0, b - c)) + a;
};
goog.string.makeSafe = function(a) {
  return null == a ? "" : String(a);
};
goog.string.buildString = function(a) {
  return Array.prototype.join.call(arguments, "");
};
goog.string.getRandomString = function() {
  return Math.floor(2147483648 * Math.random()).toString(36) + Math.abs(Math.floor(2147483648 * Math.random()) ^ goog.now()).toString(36);
};
goog.string.compareVersions = function(a, b) {
  for (var c = 0, d = goog.string.trim(String(a)).split("."), e = goog.string.trim(String(b)).split("."), f = Math.max(d.length, e.length), g = 0;0 == c && g < f;g++) {
    var h = d[g] || "", k = e[g] || "", l = RegExp("(\\d*)(\\D*)", "g"), m = RegExp("(\\d*)(\\D*)", "g");
    do {
      var p = l.exec(h) || ["", "", ""], n = m.exec(k) || ["", "", ""];
      if (0 == p[0].length && 0 == n[0].length) {
        break;
      }
      var c = 0 == p[1].length ? 0 : parseInt(p[1], 10), q = 0 == n[1].length ? 0 : parseInt(n[1], 10), c = goog.string.compareElements_(c, q) || goog.string.compareElements_(0 == p[2].length, 0 == n[2].length) || goog.string.compareElements_(p[2], n[2]);
    } while (0 == c);
  }
  return c;
};
goog.string.compareElements_ = function(a, b) {
  return a < b ? -1 : a > b ? 1 : 0;
};
goog.string.HASHCODE_MAX_ = 4294967296;
goog.string.hashCode = function(a) {
  for (var b = 0, c = 0;c < a.length;++c) {
    b = 31 * b + a.charCodeAt(c), b %= goog.string.HASHCODE_MAX_;
  }
  return b;
};
goog.string.uniqueStringCounter_ = 2147483648 * Math.random() | 0;
goog.string.createUniqueString = function() {
  return "goog_" + goog.string.uniqueStringCounter_++;
};
goog.string.toNumber = function(a) {
  var b = Number(a);
  return 0 == b && goog.string.isEmpty(a) ? NaN : b;
};
goog.string.isLowerCamelCase = function(a) {
  return/^[a-z]+([A-Z][a-z]*)*$/.test(a);
};
goog.string.isUpperCamelCase = function(a) {
  return/^([A-Z][a-z]*)+$/.test(a);
};
goog.string.toCamelCase = function(a) {
  return String(a).replace(/\-([a-z])/g, function(a, c) {
    return c.toUpperCase();
  });
};
goog.string.toSelectorCase = function(a) {
  return String(a).replace(/([A-Z])/g, "-$1").toLowerCase();
};
goog.string.toTitleCase = function(a, b) {
  var c = goog.isString(b) ? goog.string.regExpEscape(b) : "\\s";
  return a.replace(new RegExp("(^" + (c ? "|[" + c + "]+" : "") + ")([a-z])", "g"), function(a, b, c) {
    return b + c.toUpperCase();
  });
};
goog.string.parseInt = function(a) {
  isFinite(a) && (a = String(a));
  return goog.isString(a) ? /^\s*-?0x/i.test(a) ? parseInt(a, 16) : parseInt(a, 10) : NaN;
};
goog.string.splitLimit = function(a, b, c) {
  a = a.split(b);
  for (var d = [];0 < c && a.length;) {
    d.push(a.shift()), c--;
  }
  a.length && d.push(a.join(b));
  return d;
};
goog.asserts = {};
goog.asserts.ENABLE_ASSERTS = goog.DEBUG;
goog.asserts.AssertionError = function(a, b) {
  b.unshift(a);
  goog.debug.Error.call(this, goog.string.subs.apply(null, b));
  b.shift();
  this.messagePattern = a;
};
goog.inherits(goog.asserts.AssertionError, goog.debug.Error);
goog.asserts.AssertionError.prototype.name = "AssertionError";
goog.asserts.doAssertFailure_ = function(a, b, c, d) {
  var e = "Assertion failed";
  if (c) {
    var e = e + (": " + c), f = d
  } else {
    a && (e += ": " + a, f = b);
  }
  throw new goog.asserts.AssertionError("" + e, f || []);
};
goog.asserts.assert = function(a, b, c) {
  goog.asserts.ENABLE_ASSERTS && !a && goog.asserts.doAssertFailure_("", null, b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.fail = function(a, b) {
  if (goog.asserts.ENABLE_ASSERTS) {
    throw new goog.asserts.AssertionError("Failure" + (a ? ": " + a : ""), Array.prototype.slice.call(arguments, 1));
  }
};
goog.asserts.assertNumber = function(a, b, c) {
  goog.asserts.ENABLE_ASSERTS && !goog.isNumber(a) && goog.asserts.doAssertFailure_("Expected number but got %s: %s.", [goog.typeOf(a), a], b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.assertString = function(a, b, c) {
  goog.asserts.ENABLE_ASSERTS && !goog.isString(a) && goog.asserts.doAssertFailure_("Expected string but got %s: %s.", [goog.typeOf(a), a], b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.assertFunction = function(a, b, c) {
  goog.asserts.ENABLE_ASSERTS && !goog.isFunction(a) && goog.asserts.doAssertFailure_("Expected function but got %s: %s.", [goog.typeOf(a), a], b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.assertObject = function(a, b, c) {
  goog.asserts.ENABLE_ASSERTS && !goog.isObject(a) && goog.asserts.doAssertFailure_("Expected object but got %s: %s.", [goog.typeOf(a), a], b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.assertArray = function(a, b, c) {
  goog.asserts.ENABLE_ASSERTS && !goog.isArray(a) && goog.asserts.doAssertFailure_("Expected array but got %s: %s.", [goog.typeOf(a), a], b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.assertBoolean = function(a, b, c) {
  goog.asserts.ENABLE_ASSERTS && !goog.isBoolean(a) && goog.asserts.doAssertFailure_("Expected boolean but got %s: %s.", [goog.typeOf(a), a], b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.assertElement = function(a, b, c) {
  !goog.asserts.ENABLE_ASSERTS || goog.isObject(a) && a.nodeType == goog.dom.NodeType.ELEMENT || goog.asserts.doAssertFailure_("Expected Element but got %s: %s.", [goog.typeOf(a), a], b, Array.prototype.slice.call(arguments, 2));
  return a;
};
goog.asserts.assertInstanceof = function(a, b, c, d) {
  !goog.asserts.ENABLE_ASSERTS || a instanceof b || goog.asserts.doAssertFailure_("instanceof check failed.", null, c, Array.prototype.slice.call(arguments, 3));
  return a;
};
goog.asserts.assertObjectPrototypeIsIntact = function() {
  for (var a in Object.prototype) {
    goog.asserts.fail(a + " should not be enumerable in Object.prototype.");
  }
};
goog.array = {};
goog.NATIVE_ARRAY_PROTOTYPES = goog.TRUSTED_SITE;
goog.array.ASSUME_NATIVE_FUNCTIONS = !1;
goog.array.peek = function(a) {
  return a[a.length - 1];
};
goog.array.last = goog.array.peek;
goog.array.ARRAY_PROTOTYPE_ = Array.prototype;
goog.array.indexOf = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.indexOf) ? function(a, b, c) {
  goog.asserts.assert(null != a.length);
  return goog.array.ARRAY_PROTOTYPE_.indexOf.call(a, b, c);
} : function(a, b, c) {
  c = null == c ? 0 : 0 > c ? Math.max(0, a.length + c) : c;
  if (goog.isString(a)) {
    return goog.isString(b) && 1 == b.length ? a.indexOf(b, c) : -1;
  }
  for (;c < a.length;c++) {
    if (c in a && a[c] === b) {
      return c;
    }
  }
  return-1;
};
goog.array.lastIndexOf = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.lastIndexOf) ? function(a, b, c) {
  goog.asserts.assert(null != a.length);
  return goog.array.ARRAY_PROTOTYPE_.lastIndexOf.call(a, b, null == c ? a.length - 1 : c);
} : function(a, b, c) {
  c = null == c ? a.length - 1 : c;
  0 > c && (c = Math.max(0, a.length + c));
  if (goog.isString(a)) {
    return goog.isString(b) && 1 == b.length ? a.lastIndexOf(b, c) : -1;
  }
  for (;0 <= c;c--) {
    if (c in a && a[c] === b) {
      return c;
    }
  }
  return-1;
};
goog.array.forEach = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.forEach) ? function(a, b, c) {
  goog.asserts.assert(null != a.length);
  goog.array.ARRAY_PROTOTYPE_.forEach.call(a, b, c);
} : function(a, b, c) {
  for (var d = a.length, e = goog.isString(a) ? a.split("") : a, f = 0;f < d;f++) {
    f in e && b.call(c, e[f], f, a);
  }
};
goog.array.forEachRight = function(a, b, c) {
  for (var d = a.length, e = goog.isString(a) ? a.split("") : a, d = d - 1;0 <= d;--d) {
    d in e && b.call(c, e[d], d, a);
  }
};
goog.array.filter = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.filter) ? function(a, b, c) {
  goog.asserts.assert(null != a.length);
  return goog.array.ARRAY_PROTOTYPE_.filter.call(a, b, c);
} : function(a, b, c) {
  for (var d = a.length, e = [], f = 0, g = goog.isString(a) ? a.split("") : a, h = 0;h < d;h++) {
    if (h in g) {
      var k = g[h];
      b.call(c, k, h, a) && (e[f++] = k);
    }
  }
  return e;
};
goog.array.map = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.map) ? function(a, b, c) {
  goog.asserts.assert(null != a.length);
  return goog.array.ARRAY_PROTOTYPE_.map.call(a, b, c);
} : function(a, b, c) {
  for (var d = a.length, e = Array(d), f = goog.isString(a) ? a.split("") : a, g = 0;g < d;g++) {
    g in f && (e[g] = b.call(c, f[g], g, a));
  }
  return e;
};
goog.array.reduce = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.reduce) ? function(a, b, c, d) {
  goog.asserts.assert(null != a.length);
  d && (b = goog.bind(b, d));
  return goog.array.ARRAY_PROTOTYPE_.reduce.call(a, b, c);
} : function(a, b, c, d) {
  var e = c;
  goog.array.forEach(a, function(c, g) {
    e = b.call(d, e, c, g, a);
  });
  return e;
};
goog.array.reduceRight = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.reduceRight) ? function(a, b, c, d) {
  goog.asserts.assert(null != a.length);
  d && (b = goog.bind(b, d));
  return goog.array.ARRAY_PROTOTYPE_.reduceRight.call(a, b, c);
} : function(a, b, c, d) {
  var e = c;
  goog.array.forEachRight(a, function(c, g) {
    e = b.call(d, e, c, g, a);
  });
  return e;
};
goog.array.some = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.some) ? function(a, b, c) {
  goog.asserts.assert(null != a.length);
  return goog.array.ARRAY_PROTOTYPE_.some.call(a, b, c);
} : function(a, b, c) {
  for (var d = a.length, e = goog.isString(a) ? a.split("") : a, f = 0;f < d;f++) {
    if (f in e && b.call(c, e[f], f, a)) {
      return!0;
    }
  }
  return!1;
};
goog.array.every = goog.NATIVE_ARRAY_PROTOTYPES && (goog.array.ASSUME_NATIVE_FUNCTIONS || goog.array.ARRAY_PROTOTYPE_.every) ? function(a, b, c) {
  goog.asserts.assert(null != a.length);
  return goog.array.ARRAY_PROTOTYPE_.every.call(a, b, c);
} : function(a, b, c) {
  for (var d = a.length, e = goog.isString(a) ? a.split("") : a, f = 0;f < d;f++) {
    if (f in e && !b.call(c, e[f], f, a)) {
      return!1;
    }
  }
  return!0;
};
goog.array.count = function(a, b, c) {
  var d = 0;
  goog.array.forEach(a, function(a, f, g) {
    b.call(c, a, f, g) && ++d;
  }, c);
  return d;
};
goog.array.find = function(a, b, c) {
  b = goog.array.findIndex(a, b, c);
  return 0 > b ? null : goog.isString(a) ? a.charAt(b) : a[b];
};
goog.array.findIndex = function(a, b, c) {
  for (var d = a.length, e = goog.isString(a) ? a.split("") : a, f = 0;f < d;f++) {
    if (f in e && b.call(c, e[f], f, a)) {
      return f;
    }
  }
  return-1;
};
goog.array.findRight = function(a, b, c) {
  b = goog.array.findIndexRight(a, b, c);
  return 0 > b ? null : goog.isString(a) ? a.charAt(b) : a[b];
};
goog.array.findIndexRight = function(a, b, c) {
  for (var d = a.length, e = goog.isString(a) ? a.split("") : a, d = d - 1;0 <= d;d--) {
    if (d in e && b.call(c, e[d], d, a)) {
      return d;
    }
  }
  return-1;
};
goog.array.contains = function(a, b) {
  return 0 <= goog.array.indexOf(a, b);
};
goog.array.isEmpty = function(a) {
  return 0 == a.length;
};
goog.array.clear = function(a) {
  if (!goog.isArray(a)) {
    for (var b = a.length - 1;0 <= b;b--) {
      delete a[b];
    }
  }
  a.length = 0;
};
goog.array.insert = function(a, b) {
  goog.array.contains(a, b) || a.push(b);
};
goog.array.insertAt = function(a, b, c) {
  goog.array.splice(a, c, 0, b);
};
goog.array.insertArrayAt = function(a, b, c) {
  goog.partial(goog.array.splice, a, c, 0).apply(null, b);
};
goog.array.insertBefore = function(a, b, c) {
  var d;
  2 == arguments.length || 0 > (d = goog.array.indexOf(a, c)) ? a.push(b) : goog.array.insertAt(a, b, d);
};
goog.array.remove = function(a, b) {
  var c = goog.array.indexOf(a, b), d;
  (d = 0 <= c) && goog.array.removeAt(a, c);
  return d;
};
goog.array.removeAt = function(a, b) {
  goog.asserts.assert(null != a.length);
  return 1 == goog.array.ARRAY_PROTOTYPE_.splice.call(a, b, 1).length;
};
goog.array.removeIf = function(a, b, c) {
  b = goog.array.findIndex(a, b, c);
  return 0 <= b ? (goog.array.removeAt(a, b), !0) : !1;
};
goog.array.concat = function(a) {
  return goog.array.ARRAY_PROTOTYPE_.concat.apply(goog.array.ARRAY_PROTOTYPE_, arguments);
};
goog.array.join = function(a) {
  return goog.array.ARRAY_PROTOTYPE_.concat.apply(goog.array.ARRAY_PROTOTYPE_, arguments);
};
goog.array.toArray = function(a) {
  var b = a.length;
  if (0 < b) {
    for (var c = Array(b), d = 0;d < b;d++) {
      c[d] = a[d];
    }
    return c;
  }
  return[];
};
goog.array.clone = goog.array.toArray;
goog.array.extend = function(a, b) {
  for (var c = 1;c < arguments.length;c++) {
    var d = arguments[c], e;
    if (goog.isArray(d) || (e = goog.isArrayLike(d)) && Object.prototype.hasOwnProperty.call(d, "callee")) {
      a.push.apply(a, d);
    } else {
      if (e) {
        for (var f = a.length, g = d.length, h = 0;h < g;h++) {
          a[f + h] = d[h];
        }
      } else {
        a.push(d);
      }
    }
  }
};
goog.array.splice = function(a, b, c, d) {
  goog.asserts.assert(null != a.length);
  return goog.array.ARRAY_PROTOTYPE_.splice.apply(a, goog.array.slice(arguments, 1));
};
goog.array.slice = function(a, b, c) {
  goog.asserts.assert(null != a.length);
  return 2 >= arguments.length ? goog.array.ARRAY_PROTOTYPE_.slice.call(a, b) : goog.array.ARRAY_PROTOTYPE_.slice.call(a, b, c);
};
goog.array.removeDuplicates = function(a, b, c) {
  b = b || a;
  var d = function(a) {
    return goog.isObject(g) ? "o" + goog.getUid(g) : (typeof g).charAt(0) + g;
  };
  c = c || d;
  for (var d = {}, e = 0, f = 0;f < a.length;) {
    var g = a[f++], h = c(g);
    Object.prototype.hasOwnProperty.call(d, h) || (d[h] = !0, b[e++] = g);
  }
  b.length = e;
};
goog.array.binarySearch = function(a, b, c) {
  return goog.array.binarySearch_(a, c || goog.array.defaultCompare, !1, b);
};
goog.array.binarySelect = function(a, b, c) {
  return goog.array.binarySearch_(a, b, !0, void 0, c);
};
goog.array.binarySearch_ = function(a, b, c, d, e) {
  for (var f = 0, g = a.length, h;f < g;) {
    var k = f + g >> 1, l;
    l = c ? b.call(e, a[k], k, a) : b(d, a[k]);
    0 < l ? f = k + 1 : (g = k, h = !l);
  }
  return h ? f : ~f;
};
goog.array.sort = function(a, b) {
  a.sort(b || goog.array.defaultCompare);
};
goog.array.stableSort = function(a, b) {
  for (var c = 0;c < a.length;c++) {
    a[c] = {index:c, value:a[c]};
  }
  var d = b || goog.array.defaultCompare;
  goog.array.sort(a, function(a, b) {
    return d(a.value, b.value) || a.index - b.index;
  });
  for (c = 0;c < a.length;c++) {
    a[c] = a[c].value;
  }
};
goog.array.sortObjectsByKey = function(a, b, c) {
  var d = c || goog.array.defaultCompare;
  goog.array.sort(a, function(a, c) {
    return d(a[b], c[b]);
  });
};
goog.array.isSorted = function(a, b, c) {
  b = b || goog.array.defaultCompare;
  for (var d = 1;d < a.length;d++) {
    var e = b(a[d - 1], a[d]);
    if (0 < e || 0 == e && c) {
      return!1;
    }
  }
  return!0;
};
goog.array.equals = function(a, b, c) {
  if (!goog.isArrayLike(a) || !goog.isArrayLike(b) || a.length != b.length) {
    return!1;
  }
  var d = a.length;
  c = c || goog.array.defaultCompareEquality;
  for (var e = 0;e < d;e++) {
    if (!c(a[e], b[e])) {
      return!1;
    }
  }
  return!0;
};
goog.array.compare3 = function(a, b, c) {
  c = c || goog.array.defaultCompare;
  for (var d = Math.min(a.length, b.length), e = 0;e < d;e++) {
    var f = c(a[e], b[e]);
    if (0 != f) {
      return f;
    }
  }
  return goog.array.defaultCompare(a.length, b.length);
};
goog.array.defaultCompare = function(a, b) {
  return a > b ? 1 : a < b ? -1 : 0;
};
goog.array.defaultCompareEquality = function(a, b) {
  return a === b;
};
goog.array.binaryInsert = function(a, b, c) {
  c = goog.array.binarySearch(a, b, c);
  return 0 > c ? (goog.array.insertAt(a, b, -(c + 1)), !0) : !1;
};
goog.array.binaryRemove = function(a, b, c) {
  b = goog.array.binarySearch(a, b, c);
  return 0 <= b ? goog.array.removeAt(a, b) : !1;
};
goog.array.bucket = function(a, b, c) {
  for (var d = {}, e = 0;e < a.length;e++) {
    var f = a[e], g = b.call(c, f, e, a);
    goog.isDef(g) && (d[g] || (d[g] = [])).push(f);
  }
  return d;
};
goog.array.toObject = function(a, b, c) {
  var d = {};
  goog.array.forEach(a, function(e, f) {
    d[b.call(c, e, f, a)] = e;
  });
  return d;
};
goog.array.range = function(a, b, c) {
  var d = [], e = 0, f = a;
  c = c || 1;
  void 0 !== b && (e = a, f = b);
  if (0 > c * (f - e)) {
    return[];
  }
  if (0 < c) {
    for (a = e;a < f;a += c) {
      d.push(a);
    }
  } else {
    for (a = e;a > f;a += c) {
      d.push(a);
    }
  }
  return d;
};
goog.array.repeat = function(a, b) {
  for (var c = [], d = 0;d < b;d++) {
    c[d] = a;
  }
  return c;
};
goog.array.flatten = function(a) {
  for (var b = [], c = 0;c < arguments.length;c++) {
    var d = arguments[c];
    goog.isArray(d) ? b.push.apply(b, goog.array.flatten.apply(null, d)) : b.push(d);
  }
  return b;
};
goog.array.rotate = function(a, b) {
  goog.asserts.assert(null != a.length);
  a.length && (b %= a.length, 0 < b ? goog.array.ARRAY_PROTOTYPE_.unshift.apply(a, a.splice(-b, b)) : 0 > b && goog.array.ARRAY_PROTOTYPE_.push.apply(a, a.splice(0, -b)));
  return a;
};
goog.array.moveItem = function(a, b, c) {
  goog.asserts.assert(0 <= b && b < a.length);
  goog.asserts.assert(0 <= c && c < a.length);
  b = goog.array.ARRAY_PROTOTYPE_.splice.call(a, b, 1);
  goog.array.ARRAY_PROTOTYPE_.splice.call(a, c, 0, b[0]);
};
goog.array.zip = function(a) {
  if (!arguments.length) {
    return[];
  }
  for (var b = [], c = 0;;c++) {
    for (var d = [], e = 0;e < arguments.length;e++) {
      var f = arguments[e];
      if (c >= f.length) {
        return b;
      }
      d.push(f[c]);
    }
    b.push(d);
  }
};
goog.array.shuffle = function(a, b) {
  for (var c = b || Math.random, d = a.length - 1;0 < d;d--) {
    var e = Math.floor(c() * (d + 1)), f = a[d];
    a[d] = a[e];
    a[e] = f;
  }
};
goog.crypt.stringToByteArray = function(a) {
  for (var b = [], c = 0, d = 0;d < a.length;d++) {
    for (var e = a.charCodeAt(d);255 < e;) {
      b[c++] = e & 255, e >>= 8;
    }
    b[c++] = e;
  }
  return b;
};
goog.crypt.byteArrayToString = function(a) {
  if (8192 > a.length) {
    return String.fromCharCode.apply(null, a);
  }
  for (var b = "", c = 0;c < a.length;c += 8192) {
    var d = goog.array.slice(a, c, c + 8192), b = b + String.fromCharCode.apply(null, d)
  }
  return b;
};
goog.crypt.byteArrayToHex = function(a) {
  return goog.array.map(a, function(a) {
    a = a.toString(16);
    return 1 < a.length ? a : "0" + a;
  }).join("");
};
goog.crypt.hexToByteArray = function(a) {
  goog.asserts.assert(0 == a.length % 2, "Key string length must be multiple of 2");
  for (var b = [], c = 0;c < a.length;c += 2) {
    b.push(parseInt(a.substring(c, c + 2), 16));
  }
  return b;
};
goog.crypt.stringToUtf8ByteArray = function(a) {
  a = a.replace(/\r\n/g, "\n");
  for (var b = [], c = 0, d = 0;d < a.length;d++) {
    var e = a.charCodeAt(d);
    128 > e ? b[c++] = e : (2048 > e ? b[c++] = e >> 6 | 192 : (b[c++] = e >> 12 | 224, b[c++] = e >> 6 & 63 | 128), b[c++] = e & 63 | 128);
  }
  return b;
};
goog.crypt.utf8ByteArrayToString = function(a) {
  for (var b = [], c = 0, d = 0;c < a.length;) {
    var e = a[c++];
    if (128 > e) {
      b[d++] = String.fromCharCode(e);
    } else {
      if (191 < e && 224 > e) {
        var f = a[c++];
        b[d++] = String.fromCharCode((e & 31) << 6 | f & 63);
      } else {
        var f = a[c++], g = a[c++];
        b[d++] = String.fromCharCode((e & 15) << 12 | (f & 63) << 6 | g & 63);
      }
    }
  }
  return b.join("");
};
goog.crypt.xorByteArray = function(a, b) {
  goog.asserts.assert(a.length == b.length, "XOR array lengths must match");
  for (var c = [], d = 0;d < a.length;d++) {
    c.push(a[d] ^ b[d]);
  }
  return c;
};
goog.labs = {};
goog.labs.userAgent = {};
goog.labs.userAgent.util = {};
goog.labs.userAgent.util.getNativeUserAgentString_ = function() {
  var a = goog.labs.userAgent.util.getNavigator_();
  return a && (a = a.userAgent) ? a : "";
};
goog.labs.userAgent.util.getNavigator_ = function() {
  return goog.global.navigator;
};
goog.labs.userAgent.util.userAgent_ = goog.labs.userAgent.util.getNativeUserAgentString_();
goog.labs.userAgent.util.setUserAgent = function(a) {
  goog.labs.userAgent.util.userAgent_ = a || goog.labs.userAgent.util.getNativeUserAgentString_();
};
goog.labs.userAgent.util.getUserAgent = function() {
  return goog.labs.userAgent.util.userAgent_;
};
goog.labs.userAgent.util.matchUserAgent = function(a) {
  var b = goog.labs.userAgent.util.getUserAgent();
  return goog.string.contains(b, a);
};
goog.labs.userAgent.util.matchUserAgentIgnoreCase = function(a) {
  var b = goog.labs.userAgent.util.getUserAgent();
  return goog.string.caseInsensitiveContains(b, a);
};
goog.labs.userAgent.util.extractVersionTuples = function(a) {
  for (var b = RegExp("(\\w[\\w ]+)/([^\\s]+)\\s*(?:\\((.*?)\\))?", "g"), c = [], d;d = b.exec(a);) {
    c.push([d[1], d[2], d[3] || void 0]);
  }
  return c;
};
goog.labs.userAgent.browser = {};
goog.labs.userAgent.browser.matchOpera_ = function() {
  return goog.labs.userAgent.util.matchUserAgent("Opera") || goog.labs.userAgent.util.matchUserAgent("OPR");
};
goog.labs.userAgent.browser.matchIE_ = function() {
  return goog.labs.userAgent.util.matchUserAgent("Trident") || goog.labs.userAgent.util.matchUserAgent("MSIE");
};
goog.labs.userAgent.browser.matchFirefox_ = function() {
  return goog.labs.userAgent.util.matchUserAgent("Firefox");
};
goog.labs.userAgent.browser.matchSafari_ = function() {
  return goog.labs.userAgent.util.matchUserAgent("Safari") && !goog.labs.userAgent.util.matchUserAgent("Chrome") && !goog.labs.userAgent.util.matchUserAgent("CriOS") && !goog.labs.userAgent.util.matchUserAgent("Android");
};
goog.labs.userAgent.browser.matchChrome_ = function() {
  return goog.labs.userAgent.util.matchUserAgent("Chrome") || goog.labs.userAgent.util.matchUserAgent("CriOS");
};
goog.labs.userAgent.browser.matchAndroidBrowser_ = function() {
  return goog.labs.userAgent.util.matchUserAgent("Android") && !goog.labs.userAgent.util.matchUserAgent("Chrome") && !goog.labs.userAgent.util.matchUserAgent("CriOS");
};
goog.labs.userAgent.browser.isOpera = goog.labs.userAgent.browser.matchOpera_;
goog.labs.userAgent.browser.isIE = goog.labs.userAgent.browser.matchIE_;
goog.labs.userAgent.browser.isFirefox = goog.labs.userAgent.browser.matchFirefox_;
goog.labs.userAgent.browser.isSafari = goog.labs.userAgent.browser.matchSafari_;
goog.labs.userAgent.browser.isChrome = goog.labs.userAgent.browser.matchChrome_;
goog.labs.userAgent.browser.isAndroidBrowser = goog.labs.userAgent.browser.matchAndroidBrowser_;
goog.labs.userAgent.browser.isSilk = function() {
  return goog.labs.userAgent.util.matchUserAgent("Silk");
};
goog.labs.userAgent.browser.getVersion = function() {
  var a = goog.labs.userAgent.util.getUserAgent();
  if (goog.labs.userAgent.browser.isIE()) {
    return goog.labs.userAgent.browser.getIEVersion_(a);
  }
  if (goog.labs.userAgent.browser.isOpera()) {
    return goog.labs.userAgent.browser.getOperaVersion_(a);
  }
  a = goog.labs.userAgent.util.extractVersionTuples(a);
  return goog.labs.userAgent.browser.getVersionFromTuples_(a);
};
goog.labs.userAgent.browser.isVersionOrHigher = function(a) {
  return 0 <= goog.string.compareVersions(goog.labs.userAgent.browser.getVersion(), a);
};
goog.labs.userAgent.browser.getIEVersion_ = function(a) {
  var b = /rv: *([\d\.]*)/.exec(a);
  if (b && b[1]) {
    return b[1];
  }
  var b = "", c = /MSIE +([\d\.]+)/.exec(a);
  if (c && c[1]) {
    if (a = /Trident\/(\d.\d)/.exec(a), "7.0" == c[1]) {
      if (a && a[1]) {
        switch(a[1]) {
          case "4.0":
            b = "8.0";
            break;
          case "5.0":
            b = "9.0";
            break;
          case "6.0":
            b = "10.0";
            break;
          case "7.0":
            b = "11.0";
        }
      } else {
        b = "7.0";
      }
    } else {
      b = c[1];
    }
  }
  return b;
};
goog.labs.userAgent.browser.getOperaVersion_ = function(a) {
  a = goog.labs.userAgent.util.extractVersionTuples(a);
  var b = goog.array.peek(a);
  return "OPR" == b[0] && b[1] ? b[1] : goog.labs.userAgent.browser.getVersionFromTuples_(a);
};
goog.labs.userAgent.browser.getVersionFromTuples_ = function(a) {
  goog.asserts.assert(2 < a.length, "Couldn't extract version tuple from user agent string");
  return a[2] && a[2][1] ? a[2][1] : "";
};
goog.labs.userAgent.engine = {};
goog.labs.userAgent.engine.isPresto = function() {
  return goog.labs.userAgent.util.matchUserAgent("Presto");
};
goog.labs.userAgent.engine.isTrident = function() {
  return goog.labs.userAgent.util.matchUserAgent("Trident") || goog.labs.userAgent.util.matchUserAgent("MSIE");
};
goog.labs.userAgent.engine.isWebKit = function() {
  return goog.labs.userAgent.util.matchUserAgentIgnoreCase("WebKit");
};
goog.labs.userAgent.engine.isGecko = function() {
  return goog.labs.userAgent.util.matchUserAgent("Gecko") && !goog.labs.userAgent.engine.isWebKit() && !goog.labs.userAgent.engine.isTrident();
};
goog.labs.userAgent.engine.getVersion = function() {
  var a = goog.labs.userAgent.util.getUserAgent();
  if (a) {
    var a = goog.labs.userAgent.util.extractVersionTuples(a), b = a[1];
    if (b) {
      return "Gecko" == b[0] ? goog.labs.userAgent.engine.getVersionForKey_(a, "Firefox") : b[1];
    }
    var a = a[0], c;
    if (a && (c = a[2]) && (c = /Trident\/([^\s;]+)/.exec(c))) {
      return c[1];
    }
  }
  return "";
};
goog.labs.userAgent.engine.isVersionOrHigher = function(a) {
  return 0 <= goog.string.compareVersions(goog.labs.userAgent.engine.getVersion(), a);
};
goog.labs.userAgent.engine.getVersionForKey_ = function(a, b) {
  var c = goog.array.find(a, function(a) {
    return b == a[0];
  });
  return c && c[1] || "";
};
goog.userAgent = {};
goog.userAgent.ASSUME_IE = !1;
goog.userAgent.ASSUME_GECKO = !1;
goog.userAgent.ASSUME_WEBKIT = !1;
goog.userAgent.ASSUME_MOBILE_WEBKIT = !1;
goog.userAgent.ASSUME_OPERA = !1;
goog.userAgent.ASSUME_ANY_VERSION = !1;
goog.userAgent.BROWSER_KNOWN_ = goog.userAgent.ASSUME_IE || goog.userAgent.ASSUME_GECKO || goog.userAgent.ASSUME_MOBILE_WEBKIT || goog.userAgent.ASSUME_WEBKIT || goog.userAgent.ASSUME_OPERA;
goog.userAgent.getUserAgentString = function() {
  return goog.labs.userAgent.util.getUserAgent();
};
goog.userAgent.getNavigator = function() {
  return goog.global.navigator || null;
};
goog.userAgent.OPERA = goog.userAgent.BROWSER_KNOWN_ ? goog.userAgent.ASSUME_OPERA : goog.labs.userAgent.browser.isOpera();
goog.userAgent.IE = goog.userAgent.BROWSER_KNOWN_ ? goog.userAgent.ASSUME_IE : goog.labs.userAgent.browser.isIE();
goog.userAgent.GECKO = goog.userAgent.BROWSER_KNOWN_ ? goog.userAgent.ASSUME_GECKO : goog.labs.userAgent.engine.isGecko();
goog.userAgent.WEBKIT = goog.userAgent.BROWSER_KNOWN_ ? goog.userAgent.ASSUME_WEBKIT || goog.userAgent.ASSUME_MOBILE_WEBKIT : goog.labs.userAgent.engine.isWebKit();
goog.userAgent.isMobile_ = function() {
  return goog.userAgent.WEBKIT && goog.labs.userAgent.util.matchUserAgent("Mobile");
};
goog.userAgent.MOBILE = goog.userAgent.ASSUME_MOBILE_WEBKIT || goog.userAgent.isMobile_();
goog.userAgent.SAFARI = goog.userAgent.WEBKIT;
goog.userAgent.determinePlatform_ = function() {
  var a = goog.userAgent.getNavigator();
  return a && a.platform || "";
};
goog.userAgent.PLATFORM = goog.userAgent.determinePlatform_();
goog.userAgent.ASSUME_MAC = !1;
goog.userAgent.ASSUME_WINDOWS = !1;
goog.userAgent.ASSUME_LINUX = !1;
goog.userAgent.ASSUME_X11 = !1;
goog.userAgent.ASSUME_ANDROID = !1;
goog.userAgent.ASSUME_IPHONE = !1;
goog.userAgent.ASSUME_IPAD = !1;
goog.userAgent.PLATFORM_KNOWN_ = goog.userAgent.ASSUME_MAC || goog.userAgent.ASSUME_WINDOWS || goog.userAgent.ASSUME_LINUX || goog.userAgent.ASSUME_X11 || goog.userAgent.ASSUME_ANDROID || goog.userAgent.ASSUME_IPHONE || goog.userAgent.ASSUME_IPAD;
goog.userAgent.initPlatform_ = function() {
  goog.userAgent.detectedMac_ = goog.string.contains(goog.userAgent.PLATFORM, "Mac");
  goog.userAgent.detectedWindows_ = goog.string.contains(goog.userAgent.PLATFORM, "Win");
  goog.userAgent.detectedLinux_ = goog.string.contains(goog.userAgent.PLATFORM, "Linux");
  goog.userAgent.detectedX11_ = !!goog.userAgent.getNavigator() && goog.string.contains(goog.userAgent.getNavigator().appVersion || "", "X11");
  var a = goog.userAgent.getUserAgentString();
  goog.userAgent.detectedAndroid_ = !!a && goog.string.contains(a, "Android");
  goog.userAgent.detectedIPhone_ = !!a && goog.string.contains(a, "iPhone");
  goog.userAgent.detectedIPad_ = !!a && goog.string.contains(a, "iPad");
};
goog.userAgent.PLATFORM_KNOWN_ || goog.userAgent.initPlatform_();
goog.userAgent.MAC = goog.userAgent.PLATFORM_KNOWN_ ? goog.userAgent.ASSUME_MAC : goog.userAgent.detectedMac_;
goog.userAgent.WINDOWS = goog.userAgent.PLATFORM_KNOWN_ ? goog.userAgent.ASSUME_WINDOWS : goog.userAgent.detectedWindows_;
goog.userAgent.LINUX = goog.userAgent.PLATFORM_KNOWN_ ? goog.userAgent.ASSUME_LINUX : goog.userAgent.detectedLinux_;
goog.userAgent.X11 = goog.userAgent.PLATFORM_KNOWN_ ? goog.userAgent.ASSUME_X11 : goog.userAgent.detectedX11_;
goog.userAgent.ANDROID = goog.userAgent.PLATFORM_KNOWN_ ? goog.userAgent.ASSUME_ANDROID : goog.userAgent.detectedAndroid_;
goog.userAgent.IPHONE = goog.userAgent.PLATFORM_KNOWN_ ? goog.userAgent.ASSUME_IPHONE : goog.userAgent.detectedIPhone_;
goog.userAgent.IPAD = goog.userAgent.PLATFORM_KNOWN_ ? goog.userAgent.ASSUME_IPAD : goog.userAgent.detectedIPad_;
goog.userAgent.determineVersion_ = function() {
  var a = "", b;
  if (goog.userAgent.OPERA && goog.global.opera) {
    return a = goog.global.opera.version, goog.isFunction(a) ? a() : a;
  }
  goog.userAgent.GECKO ? b = /rv\:([^\);]+)(\)|;)/ : goog.userAgent.IE ? b = /\b(?:MSIE|rv)[: ]([^\);]+)(\)|;)/ : goog.userAgent.WEBKIT && (b = /WebKit\/(\S+)/);
  b && (a = (a = b.exec(goog.userAgent.getUserAgentString())) ? a[1] : "");
  return goog.userAgent.IE && (b = goog.userAgent.getDocumentMode_(), b > parseFloat(a)) ? String(b) : a;
};
goog.userAgent.getDocumentMode_ = function() {
  var a = goog.global.document;
  return a ? a.documentMode : void 0;
};
goog.userAgent.VERSION = goog.userAgent.determineVersion_();
goog.userAgent.compare = function(a, b) {
  return goog.string.compareVersions(a, b);
};
goog.userAgent.isVersionOrHigherCache_ = {};
goog.userAgent.isVersionOrHigher = function(a) {
  return goog.userAgent.ASSUME_ANY_VERSION || goog.userAgent.isVersionOrHigherCache_[a] || (goog.userAgent.isVersionOrHigherCache_[a] = 0 <= goog.string.compareVersions(goog.userAgent.VERSION, a));
};
goog.userAgent.isVersion = goog.userAgent.isVersionOrHigher;
goog.userAgent.isDocumentModeOrHigher = function(a) {
  return goog.userAgent.IE && goog.userAgent.DOCUMENT_MODE >= a;
};
goog.userAgent.isDocumentMode = goog.userAgent.isDocumentModeOrHigher;
goog.userAgent.DOCUMENT_MODE = function() {
  var a = goog.global.document;
  return a && goog.userAgent.IE ? goog.userAgent.getDocumentMode_() || ("CSS1Compat" == a.compatMode ? parseInt(goog.userAgent.VERSION, 10) : 5) : void 0;
}();
goog.crypt.base64 = {};
goog.crypt.base64.byteToCharMap_ = null;
goog.crypt.base64.charToByteMap_ = null;
goog.crypt.base64.byteToCharMapWebSafe_ = null;
goog.crypt.base64.charToByteMapWebSafe_ = null;
goog.crypt.base64.ENCODED_VALS_BASE = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
goog.crypt.base64.ENCODED_VALS = goog.crypt.base64.ENCODED_VALS_BASE + "+/=";
goog.crypt.base64.ENCODED_VALS_WEBSAFE = goog.crypt.base64.ENCODED_VALS_BASE + "-_.";
goog.crypt.base64.HAS_NATIVE_SUPPORT = goog.userAgent.GECKO || goog.userAgent.WEBKIT || goog.userAgent.OPERA || "function" == typeof goog.global.atob;
goog.crypt.base64.encodeByteArray = function(a, b) {
  if (!goog.isArrayLike(a)) {
    throw Error("encodeByteArray takes an array as a parameter");
  }
  goog.crypt.base64.init_();
  for (var c = b ? goog.crypt.base64.byteToCharMapWebSafe_ : goog.crypt.base64.byteToCharMap_, d = [], e = 0;e < a.length;e += 3) {
    var f = a[e], g = e + 1 < a.length, h = g ? a[e + 1] : 0, k = e + 2 < a.length, l = k ? a[e + 2] : 0, m = f >> 2, f = (f & 3) << 4 | h >> 4, h = (h & 15) << 2 | l >> 6, l = l & 63;
    k || (l = 64, g || (h = 64));
    d.push(c[m], c[f], c[h], c[l]);
  }
  return d.join("");
};
goog.crypt.base64.encodeString = function(a, b) {
  return goog.crypt.base64.HAS_NATIVE_SUPPORT && !b ? goog.global.btoa(a) : goog.crypt.base64.encodeByteArray(goog.crypt.stringToByteArray(a), b);
};
goog.crypt.base64.decodeString = function(a, b) {
  return goog.crypt.base64.HAS_NATIVE_SUPPORT && !b ? goog.global.atob(a) : goog.crypt.byteArrayToString(goog.crypt.base64.decodeStringToByteArray(a, b));
};
goog.crypt.base64.decodeStringToByteArray = function(a, b) {
  goog.crypt.base64.init_();
  for (var c = b ? goog.crypt.base64.charToByteMapWebSafe_ : goog.crypt.base64.charToByteMap_, d = [], e = 0;e < a.length;) {
    var f = c[a.charAt(e++)], g = e < a.length ? c[a.charAt(e)] : 0;
    ++e;
    var h = e < a.length ? c[a.charAt(e)] : 64;
    ++e;
    var k = e < a.length ? c[a.charAt(e)] : 64;
    ++e;
    if (null == f || null == g || null == h || null == k) {
      throw Error();
    }
    d.push(f << 2 | g >> 4);
    64 != h && (d.push(g << 4 & 240 | h >> 2), 64 != k && d.push(h << 6 & 192 | k));
  }
  return d;
};
goog.crypt.base64.init_ = function() {
  if (!goog.crypt.base64.byteToCharMap_) {
    goog.crypt.base64.byteToCharMap_ = {};
    goog.crypt.base64.charToByteMap_ = {};
    goog.crypt.base64.byteToCharMapWebSafe_ = {};
    goog.crypt.base64.charToByteMapWebSafe_ = {};
    for (var a = 0;a < goog.crypt.base64.ENCODED_VALS.length;a++) {
      goog.crypt.base64.byteToCharMap_[a] = goog.crypt.base64.ENCODED_VALS.charAt(a), goog.crypt.base64.charToByteMap_[goog.crypt.base64.byteToCharMap_[a]] = a, goog.crypt.base64.byteToCharMapWebSafe_[a] = goog.crypt.base64.ENCODED_VALS_WEBSAFE.charAt(a), goog.crypt.base64.charToByteMapWebSafe_[goog.crypt.base64.byteToCharMapWebSafe_[a]] = a;
    }
  }
};
fb.core.util.LUIDGenerator = function() {
  var a = 1;
  return function() {
    return a++;
  };
}();
fb.core.util.assert = function(a, b) {
  if (!a) {
    throw Error("Firebase INTERNAL ASSERT FAILED:" + b);
  }
};
fb.core.util.assertWeak = function(a, b) {
  a || fb.core.util.error(b);
};
fb.core.util.base64Encode = function(a) {
  a = fb.util.utf8.stringToByteArray(a);
  return goog.crypt.base64.encodeByteArray(a, !0);
};
fb.core.util.base64DecodeIfNativeSupport = function(a) {
  try {
    if (NODE_CLIENT) {
      return(new Buffer(a, "base64")).toString("utf8");
    }
    if ("undefined" !== typeof atob) {
      return atob(a);
    }
  } catch (b) {
    fb.core.util.log("base64DecodeIfNativeSupport failed: ", b);
  }
  return null;
};
fb.core.util.sha1 = function(a) {
  a = fb.util.utf8.stringToByteArray(a);
  var b = new goog.crypt.Sha1;
  b.update(a);
  a = b.digest();
  return goog.crypt.base64.encodeByteArray(a);
};
fb.core.util.buildLogMessage_ = function(a) {
  for (var b = "", c = 0;c < arguments.length;c++) {
    b = goog.isArrayLike(arguments[c]) ? b + fb.core.util.buildLogMessage_.apply(null, arguments[c]) : "object" === typeof arguments[c] ? b + fb.util.json.stringify(arguments[c]) : b + arguments[c], b += " ";
  }
  return b;
};
fb.core.util.logger = null;
fb.core.util.firstLog_ = !0;
fb.core.util.log = function(a) {
  !0 === fb.core.util.firstLog_ && (fb.core.util.firstLog_ = !1, null === fb.core.util.logger && !0 === fb.core.storage.SessionStorage.get("logging_enabled") && Firebase.enableLogging(!0));
  if (fb.core.util.logger) {
    var b = fb.core.util.buildLogMessage_.apply(null, arguments);
    fb.core.util.logger(b);
  }
};
fb.core.util.logWrapper = function(a) {
  return function() {
    fb.core.util.log(a, arguments);
  };
};
fb.core.util.error = function(a) {
  if ("undefined" !== typeof console) {
    var b = "FIREBASE INTERNAL ERROR: " + fb.core.util.buildLogMessage_.apply(null, arguments);
    "undefined" !== typeof console.error ? console.error(b) : console.log(b);
  }
};
fb.core.util.fatal = function(a) {
  var b = fb.core.util.buildLogMessage_.apply(null, arguments);
  throw Error("FIREBASE FATAL ERROR: " + b);
};
fb.core.util.warn = function(a) {
  if ("undefined" !== typeof console) {
    var b = "FIREBASE WARNING: " + fb.core.util.buildLogMessage_.apply(null, arguments);
    "undefined" !== typeof console.warn ? console.warn(b) : console.log(b);
  }
};
fb.core.util.warnIfPageIsSecure = function() {
  "undefined" !== typeof window && window.location && window.location.protocol && -1 !== window.location.protocol.indexOf("https:") && fb.core.util.warn("Insecure Firebase access from a secure page. Please use https in calls to new Firebase().");
};
fb.core.util.parseURL = function(a) {
  var b = "", c = "", d = !0, e = "";
  if (goog.isString(a)) {
    var f = a.indexOf("//");
    if (0 <= f) {
      var g = a.substring(0, f - 1);
      a = a.substring(f + 2);
    }
    f = a.indexOf("/");
    -1 === f && (f = a.length);
    b = a.substring(0, f);
    a = a.substring(f + 1);
    var h = b.split(".");
    3 == h.length ? (f = h[2].indexOf(":"), d = 0 <= f ? "https" === g || "wss" === g : !0, "firebase" === h[1] ? fb.core.util.fatal(b + " is no longer supported. Please use <YOUR FIREBASE>.firebaseio.com instead") : (c = h[0], e = fb.core.util.decodePath("/" + a)), c = c.toLowerCase()) : fb.core.util.fatal("Cannot parse Firebase url. Please use https:<YOUR FIREBASE>.firebaseio.com");
  }
  d || fb.core.util.warnIfPageIsSecure();
  return{repoInfo:new fb.core.RepoInfo(b, d, c, "ws" === g || "wss" === g), path:new fb.core.util.Path(e)};
};
fb.core.util.decodePath = function(a) {
  var b = "";
  a = a.split("/");
  for (var c = 0;c < a.length;c++) {
    if (0 < a[c].length) {
      var d = a[c];
      try {
        d = goog.string.urlDecode(d);
      } catch (e) {
      }
      b += "/" + d;
    }
  }
  return b;
};
fb.core.util.isInvalidJSONNumber = function(a) {
  return goog.isNumber(a) && (a != a || a == Number.POSITIVE_INFINITY || a == Number.NEGATIVE_INFINITY);
};
fb.core.util.executeWhenDOMReady = function(a) {
  if (NODE_CLIENT || "complete" === document.readyState) {
    a();
  } else {
    var b = !1, c = function() {
      document.body ? b || (b = !0, a()) : setTimeout(c, 10);
    };
    document.addEventListener ? (document.addEventListener("DOMContentLoaded", c, !1), window.addEventListener("load", c, !1)) : document.attachEvent && (document.attachEvent("onreadystatechange", function() {
      "complete" === document.readyState && c();
    }), window.attachEvent("onload", c));
  }
};
fb.core.util.priorityCompare = function(a, b) {
  return a !== b ? null === a ? -1 : null === b ? 1 : typeof a !== typeof b ? "number" === typeof a ? -1 : 1 : a > b ? 1 : -1 : 0;
};
fb.core.util.nameCompare = function(a, b) {
  if (a === b) {
    return 0;
  }
  var c = fb.core.util.tryParseInt(a), d = fb.core.util.tryParseInt(b);
  return null !== c ? null !== d ? 0 == c - d ? a.length - b.length : c - d : -1 : null !== d ? 1 : a < b ? -1 : 1;
};
fb.core.util.requireKey = function(a, b) {
  if (b && a in b) {
    return b[a];
  }
  throw Error("Missing required key (" + a + ") in object: " + fb.util.json.stringify(b));
};
fb.core.util.ObjectToUniqueKey = function(a) {
  if ("object" !== typeof a || null === a) {
    return fb.util.json.stringify(a);
  }
  var b = [], c;
  for (c in a) {
    b.push(c);
  }
  b.sort();
  c = "{";
  for (var d = 0;d < b.length;d++) {
    0 !== d && (c += ","), c += fb.util.json.stringify(b[d]), c += ":", c += fb.core.util.ObjectToUniqueKey(a[b[d]]);
  }
  return c + "}";
};
fb.core.util.splitStringBySize = function(a, b) {
  if (a.length <= b) {
    return[a];
  }
  for (var c = [], d = 0;d < a.length;d += b) {
    d + b > a ? c.push(a.substring(d, a.length)) : c.push(a.substring(d, d + b));
  }
  return c;
};
fb.core.util.each = function(a, b) {
  if (goog.isArray(a)) {
    for (var c = 0;c < a.length;++c) {
      b(c, a[c]);
    }
  } else {
    goog.object.forEach(a, b);
  }
};
fb.core.util.bindCallback = function(a, b) {
  return b ? goog.bind(a, b) : a;
};
fb.core.util.doubleToIEEE754String = function(a) {
  fb.core.util.assert(!fb.core.util.isInvalidJSONNumber(a), "Invalid JSON number");
  var b, c, d, e;
  0 === a ? (d = c = 0, b = -Infinity === 1 / a ? 1 : 0) : (b = 0 > a, a = Math.abs(a), a >= Math.pow(2, -1022) ? (d = Math.min(Math.floor(Math.log(a) / Math.LN2), 1023), c = d + 1023, d = Math.round(a * Math.pow(2, 52 - d) - Math.pow(2, 52))) : (c = 0, d = Math.round(a / Math.pow(2, -1074))));
  e = [];
  for (a = 52;a;a -= 1) {
    e.push(d % 2 ? 1 : 0), d = Math.floor(d / 2);
  }
  for (a = 11;a;a -= 1) {
    e.push(c % 2 ? 1 : 0), c = Math.floor(c / 2);
  }
  e.push(b ? 1 : 0);
  e.reverse();
  b = e.join("");
  c = "";
  for (a = 0;64 > a;a += 8) {
    d = parseInt(b.substr(a, 8), 2).toString(16), 1 === d.length && (d = "0" + d), c += d;
  }
  return c.toLowerCase();
};
fb.core.util.isChromeExtensionContentScript = function() {
  return!("object" !== typeof window || !window.chrome || !window.chrome.extension || /^chrome/.test(window.location.href));
};
fb.core.util.isWindowsStoreApp = function() {
  return "object" === typeof Windows && "object" === typeof Windows.UI;
};
fb.core.util.errorForServerCode = function(a) {
  var b = "Unknown Error";
  "too_big" === a ? b = "The data requested exceeds the maximum size that can be accessed with a single request." : "permission_denied" == a ? b = "Client doesn't have permission to access the desired data." : "unavailable" == a && (b = "The service is unavailable");
  b = Error(a + ": " + b);
  b.code = a.toUpperCase();
  return b;
};
fb.core.util.INTEGER_REGEXP_ = /^-?\d{1,10}$/;
fb.core.util.tryParseInt = function(a) {
  return fb.core.util.INTEGER_REGEXP_.test(a) && (a = Number(a), -2147483648 <= a && 2147483647 >= a) ? a : null;
};
fb.core.util.exceptionGuard = function(a) {
  try {
    a();
  } catch (b) {
    setTimeout(function() {
      throw b;
    }, 0);
  }
};
fb.core.snap = {};
fb.core.snap.LeafNode = function(a, b) {
  this.value_ = a;
  fb.core.util.assert(null !== this.value_, "LeafNode shouldn't be created with null value.");
  this.priority_ = "undefined" !== typeof b ? b : null;
};
fb.core.snap.LeafNode.prototype.isLeafNode = function() {
  return!0;
};
fb.core.snap.LeafNode.prototype.getPriority = function() {
  return this.priority_;
};
fb.core.snap.LeafNode.prototype.updatePriority = function(a) {
  return new fb.core.snap.LeafNode(this.value_, a);
};
fb.core.snap.LeafNode.prototype.updateValue = function(a) {
  return new fb.core.snap.LeafNode(a, this.priority_);
};
fb.core.snap.LeafNode.prototype.getImmediateChild = function(a) {
  return fb.core.snap.EMPTY_NODE;
};
fb.core.snap.LeafNode.prototype.getChild = function(a) {
  return null === a.getFront() ? this : fb.core.snap.EMPTY_NODE;
};
fb.core.snap.LeafNode.prototype.getPredecessorChildName = function(a, b) {
  return null;
};
fb.core.snap.LeafNode.prototype.updateImmediateChild = function(a, b) {
  return(new fb.core.snap.ChildrenNode).updateImmediateChild(a, b).updatePriority(this.priority_);
};
fb.core.snap.LeafNode.prototype.updateChild = function(a, b) {
  var c = a.getFront();
  return null === c ? b : this.updateImmediateChild(c, fb.core.snap.EMPTY_NODE.updateChild(a.popFront(), b));
};
fb.core.snap.LeafNode.prototype.isEmpty = function() {
  return!1;
};
fb.core.snap.LeafNode.prototype.numChildren = function() {
  return 0;
};
fb.core.snap.LeafNode.prototype.val = function(a) {
  return a && null !== this.getPriority() ? {".value":this.getValue(), ".priority":this.getPriority()} : this.getValue();
};
fb.core.snap.LeafNode.prototype.hash = function() {
  var a = "";
  null !== this.getPriority() && (a += "priority:" + fb.core.snap.priorityHashText(this.getPriority()) + ":");
  var b = typeof this.value_, a = a + (b + ":"), a = "number" === b ? a + fb.core.util.doubleToIEEE754String(this.value_) : a + this.value_;
  return fb.core.util.sha1(a);
};
fb.core.snap.LeafNode.prototype.getValue = function() {
  return this.value_;
};
goog.DEBUG && (fb.core.snap.LeafNode.prototype.toString = function() {
  return "string" === typeof this.value_ ? this.value_ : '"' + this.value_ + '"';
});
fb.core.snap.comparators = {};
fb.core.snap.NAME_AND_PRIORITY_COMPARATOR = function(a, b) {
  return fb.core.util.priorityCompare(a.priority, b.priority) || fb.core.util.nameCompare(a.name, b.name);
};
fb.core.snap.NAME_ONLY_COMPARATOR = function(a, b) {
  return fb.core.util.nameCompare(a.name, b.name);
};
fb.core.snap.NAME_COMPARATOR = function(a, b) {
  return fb.core.util.nameCompare(a, b);
};
fb.core.snap.ChildrenNode = function(a, b) {
  this.children_ = a || new fb.core.util.SortedMap(fb.core.snap.NAME_COMPARATOR);
  this.priority_ = "undefined" !== typeof b ? b : null;
};
fb.core.snap.ChildrenNode.prototype.isLeafNode = function() {
  return!1;
};
fb.core.snap.ChildrenNode.prototype.getPriority = function() {
  return this.priority_;
};
fb.core.snap.ChildrenNode.prototype.updatePriority = function(a) {
  return new fb.core.snap.ChildrenNode(this.children_, a);
};
fb.core.snap.ChildrenNode.prototype.updateValue = function(a) {
  return new fb.core.snap.LeafNode(a, this.priority_);
};
fb.core.snap.ChildrenNode.prototype.updateImmediateChild = function(a, b) {
  var c = this.children_.remove(a);
  b && b.isEmpty() && (b = null);
  null !== b && (c = c.insert(a, b));
  return b && null !== b.getPriority() ? new fb.core.snap.SortedChildrenNode(c, null, this.priority_) : new fb.core.snap.ChildrenNode(c, this.priority_);
};
fb.core.snap.ChildrenNode.prototype.updateChild = function(a, b) {
  var c = a.getFront();
  if (null === c) {
    return b;
  }
  var d = this.getImmediateChild(c).updateChild(a.popFront(), b);
  return this.updateImmediateChild(c, d);
};
fb.core.snap.ChildrenNode.prototype.isEmpty = function() {
  return this.children_.isEmpty();
};
fb.core.snap.ChildrenNode.prototype.numChildren = function() {
  return this.children_.count();
};
fb.core.snap.ChildrenNode.INTEGER_REGEXP_ = /^\d+$/;
fb.core.snap.ChildrenNode.prototype.val = function(a) {
  if (this.isEmpty()) {
    return null;
  }
  var b = {}, c = 0, d = 0, e = !0;
  this.forEachChild(function(f, g) {
    b[f] = g.val(a);
    c++;
    e && fb.core.snap.ChildrenNode.INTEGER_REGEXP_.test(f) ? d = Math.max(d, Number(f)) : e = !1;
  });
  if (!a && e && d < 2 * c) {
    var f = [], g;
    for (g in b) {
      f[g] = b[g];
    }
    return f;
  }
  a && null !== this.getPriority() && (b[".priority"] = this.getPriority());
  return b;
};
fb.core.snap.ChildrenNode.prototype.hash = function() {
  var a = "";
  null !== this.getPriority() && (a += "priority:" + fb.core.snap.priorityHashText(this.getPriority()) + ":");
  this.forEachChild(function(b, c) {
    var d = c.hash();
    "" !== d && (a += ":" + b + ":" + d);
  });
  return "" === a ? "" : fb.core.util.sha1(a);
};
fb.core.snap.ChildrenNode.prototype.getImmediateChild = function(a) {
  a = this.children_.get(a);
  return null === a ? fb.core.snap.EMPTY_NODE : a;
};
fb.core.snap.ChildrenNode.prototype.getChild = function(a) {
  var b = a.getFront();
  return null === b ? this : this.getImmediateChild(b).getChild(a.popFront());
};
fb.core.snap.ChildrenNode.prototype.getPredecessorChildName = function(a, b) {
  return this.children_.getPredecessorKey(a);
};
fb.core.snap.ChildrenNode.prototype.getFirstChildName = function() {
  return this.children_.minKey();
};
fb.core.snap.ChildrenNode.prototype.getLastChildName = function() {
  return this.children_.maxKey();
};
fb.core.snap.ChildrenNode.prototype.forEachChild = function(a) {
  return this.children_.inorderTraversal(a);
};
fb.core.snap.ChildrenNode.prototype.forEachChildReverse = function(a) {
  return this.children_.reverseTraversal(a);
};
fb.core.snap.ChildrenNode.prototype.getIterator = function() {
  return this.children_.getIterator();
};
goog.DEBUG && (fb.core.snap.ChildrenNode.prototype.toString = function() {
  var a = "{", b = !0;
  this.forEachChild(function(c, d) {
    b ? b = !1 : a += ", ";
    a += '"' + c + '" : ' + d.toString();
  });
  return a += "}";
});
fb.core.snap.EMPTY_NODE = new fb.core.snap.ChildrenNode;
fb.core.snap.SortedChildrenNode = function(a, b, c) {
  fb.core.snap.ChildrenNode.call(this, a, c);
  null === b && (b = new fb.core.util.SortedMap(fb.core.snap.NAME_AND_PRIORITY_COMPARATOR), a.inorderTraversal(function(a, c) {
    b = b.insert({name:a, priority:c.getPriority()}, c);
  }));
  this.sortedChildren_ = b;
};
goog.inherits(fb.core.snap.SortedChildrenNode, fb.core.snap.ChildrenNode);
fb.core.snap.SortedChildrenNode.prototype.updateImmediateChild = function(a, b) {
  var c = this.getImmediateChild(a), d = this.children_, e = this.sortedChildren_;
  null !== c && (d = d.remove(a), e = e.remove({name:a, priority:c.getPriority()}));
  b && b.isEmpty() && (b = null);
  null !== b && (d = d.insert(a, b), e = e.insert({name:a, priority:b.getPriority()}, b));
  return new fb.core.snap.SortedChildrenNode(d, e, this.getPriority());
};
fb.core.snap.SortedChildrenNode.prototype.getPredecessorChildName = function(a, b) {
  var c = this.sortedChildren_.getPredecessorKey({name:a, priority:b.getPriority()});
  return c ? c.name : null;
};
fb.core.snap.SortedChildrenNode.prototype.forEachChild = function(a) {
  return this.sortedChildren_.inorderTraversal(function(b, c) {
    return a(b.name, c);
  });
};
fb.core.snap.SortedChildrenNode.prototype.forEachChildReverse = function(a) {
  return this.sortedChildren_.reverseTraversal(function(b, c) {
    return a(b.name, c);
  });
};
fb.core.snap.SortedChildrenNode.prototype.getIterator = function() {
  return this.sortedChildren_.getIterator(function(a, b) {
    return{key:a.name, value:b};
  });
};
fb.core.snap.SortedChildrenNode.prototype.getFirstChildName = function() {
  return this.sortedChildren_.isEmpty() ? null : this.sortedChildren_.minKey().name;
};
fb.core.snap.SortedChildrenNode.prototype.getLastChildName = function() {
  return this.sortedChildren_.isEmpty() ? null : this.sortedChildren_.maxKey().name;
};
var USE_HINZE = !0;
fb.core.snap.NodeFromJSON = function(a, b) {
  if (null === a) {
    return fb.core.snap.EMPTY_NODE;
  }
  var c = null;
  "object" === typeof a && ".priority" in a ? c = a[".priority"] : "undefined" !== typeof b && (c = b);
  fb.core.util.assert(null === c || "string" === typeof c || "number" === typeof c || "object" === typeof c && ".sv" in c, "Invalid priority type found: " + typeof c);
  "object" === typeof a && ".value" in a && null !== a[".value"] && (a = a[".value"]);
  if ("object" !== typeof a || ".sv" in a) {
    return new fb.core.snap.LeafNode(a, c);
  }
  if (a instanceof Array || !USE_HINZE) {
    var d = fb.core.snap.EMPTY_NODE, e = a;
    goog.object.forEach(e, function(a, b) {
      if (fb.util.obj.contains(e, b) && "." !== b.substring(0, 1)) {
        var c = fb.core.snap.NodeFromJSON(a);
        if (c.isLeafNode() || !c.isEmpty()) {
          d = d.updateImmediateChild(b, c);
        }
      }
    });
    return d.updatePriority(c);
  }
  var f = [], g = {}, h = !1, k = a;
  fb.core.util.each(k, function(a, b) {
    if ("string" !== typeof b || "." !== b.substring(0, 1)) {
      var c = fb.core.snap.NodeFromJSON(k[b]);
      c.isEmpty() || (h = h || null !== c.getPriority(), f.push({name:b, priority:c.getPriority()}), g[b] = c);
    }
  });
  var l = fb.core.snap.buildChildSet(f, g, !1);
  if (h) {
    var m = fb.core.snap.buildChildSet(f, g, !0);
    return new fb.core.snap.SortedChildrenNode(l, m, c);
  }
  return new fb.core.snap.ChildrenNode(l, c);
};
var LOG_2 = Math.log(2);
fb.core.snap.Base12Num = function(a) {
  this.count = parseInt(Math.log(a + 1) / LOG_2, 10);
  this.current_ = this.count - 1;
  var b = parseInt(Array(this.count + 1).join("1"), 2);
  this.bits_ = a + 1 & b;
};
fb.core.snap.Base12Num.prototype.nextBitIsOne = function() {
  var a = !(this.bits_ & 1 << this.current_);
  this.current_--;
  return a;
};
fb.core.snap.buildChildSet = function(a, b, c) {
  var d = c ? fb.core.snap.NAME_AND_PRIORITY_COMPARATOR : fb.core.snap.NAME_ONLY_COMPARATOR;
  a.sort(d);
  var e = function(d, f) {
    var k = f - d;
    if (0 == k) {
      return null;
    }
    if (1 == k) {
      var k = a[d].name, l = c ? a[d] : k;
      return new fb.LLRBNode(l, b[k], fb.LLRBNode.BLACK, null, null);
    }
    var l = parseInt(k / 2, 10) + d, m = e(d, l), p = e(l + 1, f), k = a[l].name, l = c ? a[l] : k;
    return new fb.LLRBNode(l, b[k], fb.LLRBNode.BLACK, m, p);
  }, f = function(d) {
    for (var f = null, k = null, l = a.length, m = function(d, g) {
      var m = l - d, n = l;
      l -= d;
      var n = e(m + 1, n), p = a[m].name, m = new fb.LLRBNode(c ? a[m] : p, b[p], g, null, n);
      f ? f.left = m : k = m;
      f = m;
    }, p = 0;p < d.count;++p) {
      var n = d.nextBitIsOne(), q = Math.pow(2, d.count - (p + 1));
      n ? m(q, fb.LLRBNode.BLACK) : (m(q, fb.LLRBNode.BLACK), m(q, fb.LLRBNode.RED));
    }
    return k;
  }(new fb.core.snap.Base12Num(a.length)), d = c ? fb.core.snap.NAME_AND_PRIORITY_COMPARATOR : fb.core.snap.NAME_COMPARATOR;
  return null !== f ? new fb.core.util.SortedMap(d, f) : new fb.core.util.SortedMap(d);
};
fb.core.snap.priorityHashText = function(a) {
  return "number" === typeof a ? "number:" + fb.core.util.doubleToIEEE754String(a) : "string:" + a;
};
fb.api.DataSnapshot = function(a, b) {
  this.node_ = a;
  this.ref_ = b;
};
fb.api.DataSnapshot.prototype.val = function() {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.val", 0, 0, arguments.length);
  return this.node_.val();
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "val", fb.api.DataSnapshot.prototype.val);
fb.api.DataSnapshot.prototype.exportVal = function() {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.exportVal", 0, 0, arguments.length);
  return this.node_.val(!0);
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "exportVal", fb.api.DataSnapshot.prototype.exportVal);
fb.api.DataSnapshot.prototype.child = function(a) {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.child", 0, 1, arguments.length);
  goog.isNumber(a) && (a = String(a));
  fb.core.util.validation.validatePathString("Firebase.DataSnapshot.child", 1, a, !1);
  var b = new fb.core.util.Path(a), c = this.ref_.child(b);
  return new fb.api.DataSnapshot(this.node_.getChild(b), c);
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "child", fb.api.DataSnapshot.prototype.child);
fb.api.DataSnapshot.prototype.hasChild = function(a) {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.hasChild", 1, 1, arguments.length);
  fb.core.util.validation.validatePathString("Firebase.DataSnapshot.hasChild", 1, a, !1);
  var b = new fb.core.util.Path(a);
  return!this.node_.getChild(b).isEmpty();
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "hasChild", fb.api.DataSnapshot.prototype.hasChild);
fb.api.DataSnapshot.prototype.getPriority = function() {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.getPriority", 0, 0, arguments.length);
  return this.node_.getPriority();
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "getPriority", fb.api.DataSnapshot.prototype.getPriority);
fb.api.DataSnapshot.prototype.forEach = function(a) {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.forEach", 1, 1, arguments.length);
  fb.util.validation.validateCallback("Firebase.DataSnapshot.forEach", 1, a, !1);
  if (this.node_.isLeafNode()) {
    return!1;
  }
  var b = this;
  return this.node_.forEachChild(function(c, d) {
    return a(new fb.api.DataSnapshot(d, b.ref_.child(c)));
  });
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "forEach", fb.api.DataSnapshot.prototype.forEach);
fb.api.DataSnapshot.prototype.hasChildren = function() {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.hasChildren", 0, 0, arguments.length);
  return this.node_.isLeafNode() ? !1 : !this.node_.isEmpty();
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "hasChildren", fb.api.DataSnapshot.prototype.hasChildren);
fb.api.DataSnapshot.prototype.name = function() {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.name", 0, 0, arguments.length);
  return this.ref_.name();
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "name", fb.api.DataSnapshot.prototype.name);
fb.api.DataSnapshot.prototype.numChildren = function() {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.numChildren", 0, 0, arguments.length);
  return this.node_.numChildren();
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "numChildren", fb.api.DataSnapshot.prototype.numChildren);
fb.api.DataSnapshot.prototype.ref = function() {
  fb.util.validation.validateArgCount("Firebase.DataSnapshot.ref", 0, 0, arguments.length);
  return this.ref_;
};
goog.exportProperty(fb.api.DataSnapshot.prototype, "ref", fb.api.DataSnapshot.prototype.ref);
fb.core.util.EventEmitter = function(a) {
  fb.core.util.assert(goog.isArray(a) && 0 < a.length, "Requires a non-empty array");
  this.allowedEvents_ = a;
  this.listeners_ = {};
};
fb.core.util.EventEmitter.prototype.trigger = function(a, b) {
  for (var c = this.listeners_[a] || [], d = 0;d < c.length;d++) {
    c[d].callback.apply(c[d].context, Array.prototype.slice.call(arguments, 1));
  }
};
fb.core.util.EventEmitter.prototype.on = function(a, b, c) {
  this.validateEventType_(a);
  this.listeners_[a] = this.listeners_[a] || [];
  this.listeners_[a].push({callback:b, context:c});
  (a = this.getInitialEvent(a)) && b.apply(c, a);
};
fb.core.util.EventEmitter.prototype.off = function(a, b, c) {
  this.validateEventType_(a);
  a = this.listeners_[a] || [];
  for (var d = 0;d < a.length;d++) {
    if (a[d].callback === b && (!c || c === a[d].context)) {
      a.splice(d, 1);
      break;
    }
  }
};
fb.core.util.EventEmitter.prototype.validateEventType_ = function(a) {
  fb.core.util.assert(goog.array.find(this.allowedEvents_, function(b) {
    return b === a;
  }), "Unknown event: " + a);
};
fb.core.util.VisibilityMonitor = function() {
  fb.core.util.EventEmitter.call(this, ["visible"]);
  var a, b;
  "undefined" !== typeof document && "undefined" !== typeof document.addEventListener && ("undefined" !== typeof document.hidden ? (b = "visibilitychange", a = "hidden") : "undefined" !== typeof document.mozHidden ? (b = "mozvisibilitychange", a = "mozHidden") : "undefined" !== typeof document.msHidden ? (b = "msvisibilitychange", a = "msHidden") : "undefined" !== typeof document.webkitHidden && (b = "webkitvisibilitychange", a = "webkitHidden"));
  this.visible_ = !0;
  if (b) {
    var c = this;
    document.addEventListener(b, function() {
      var b = !document[a];
      b !== c.visible_ && (c.visible_ = b, c.trigger("visible", b));
    }, !1);
  }
};
goog.inherits(fb.core.util.VisibilityMonitor, fb.core.util.EventEmitter);
goog.addSingletonGetter(fb.core.util.VisibilityMonitor);
fb.core.util.VisibilityMonitor.prototype.getInitialEvent = function(a) {
  fb.core.util.assert("visible" === a, "Unknown event type: " + a);
  return[this.visible_];
};
fb.core.util.OnlineMonitor = function() {
  fb.core.util.EventEmitter.call(this, ["online"]);
  this.online_ = !0;
  if ("undefined" !== typeof window && "undefined" !== typeof window.addEventListener) {
    var a = this;
    window.addEventListener("online", function() {
      a.online_ || a.trigger("online", !0);
      a.online_ = !0;
    }, !1);
    window.addEventListener("offline", function() {
      a.online_ && a.trigger("online", !1);
      a.online_ = !1;
    }, !1);
  }
};
goog.inherits(fb.core.util.OnlineMonitor, fb.core.util.EventEmitter);
goog.addSingletonGetter(fb.core.util.OnlineMonitor);
fb.core.util.OnlineMonitor.prototype.getInitialEvent = function(a) {
  fb.core.util.assert("online" === a, "Unknown event type: " + a);
  return[this.online_];
};
fb.realtime = {};
fb.realtime.Constants = {PROTOCOL_VERSION:"5", VERSION_PARAM:"v", SESSION_PARAM:"s"};
fb.realtime.Transport = function(a, b, c) {
};
fb.realtime.Transport.prototype.open = function(a, b) {
};
fb.realtime.Transport.prototype.start = function() {
};
fb.realtime.Transport.prototype.close = function() {
};
fb.realtime.Transport.prototype.send = function(a) {
};
fb.core.util.NodePatches = {};
(function() {
  if (NODE_CLIENT) {
    var a = process.version;
    if ("v0.10.22" === a || "v0.10.23" === a || "v0.10.24" === a) {
      a = require("_stream_writable");
      a.prototype.write = function(a, e, h) {
        var k = this._writableState, l = !1;
        "function" === typeof e && (h = e, e = null);
        Buffer.isBuffer(a) ? e = "buffer" : e || (e = k.defaultEncoding);
        "function" !== typeof h && (h = function() {
        });
        k.ended ? b(this, k, h) : c(this, k, a, h) && (l = d(this, k, a, e, h));
        return l;
      };
      var b = function(a, b, c) {
        var d = Error("write after end");
        a.emit("error", d);
        process.nextTick(function() {
          c(d);
        });
      }, c = function(a, b, c, d) {
        var e = !0;
        if (!Buffer.isBuffer(c) && "string" !== typeof c && null !== c && void 0 !== c && !b.objectMode) {
          var m = new TypeError("Invalid non-string/buffer chunk");
          a.emit("error", m);
          process.nextTick(function() {
            d(m);
          });
          e = !1;
        }
        return e;
      }, d = function(a, b, c, d, l) {
        b.objectMode || !1 === b.decodeStrings || "string" !== typeof c || (c = new Buffer(c, d));
        Buffer.isBuffer(c) && (d = "buffer");
        var m = b.objectMode ? 1 : c.length;
        b.length += m;
        var p = b.length < b.highWaterMark;
        p || (b.needDrain = !0);
        b.writing ? b.buffer.push(new e(c, d, l)) : (b.writelen = m, b.writecb = l, b.writing = !0, b.sync = !0, a._write(c, d, b.onwrite), b.sync = !1);
        return p;
      }, e = function(a, b, c) {
        this.chunk = a;
        this.encoding = b;
        this.callback = c;
      };
      require("_stream_duplex").prototype.write = a.prototype.write;
    }
  }
})();
goog.object = {};
goog.object.forEach = function(a, b, c) {
  for (var d in a) {
    b.call(c, a[d], d, a);
  }
};
goog.object.filter = function(a, b, c) {
  var d = {}, e;
  for (e in a) {
    b.call(c, a[e], e, a) && (d[e] = a[e]);
  }
  return d;
};
goog.object.map = function(a, b, c) {
  var d = {}, e;
  for (e in a) {
    d[e] = b.call(c, a[e], e, a);
  }
  return d;
};
goog.object.some = function(a, b, c) {
  for (var d in a) {
    if (b.call(c, a[d], d, a)) {
      return!0;
    }
  }
  return!1;
};
goog.object.every = function(a, b, c) {
  for (var d in a) {
    if (!b.call(c, a[d], d, a)) {
      return!1;
    }
  }
  return!0;
};
goog.object.getCount = function(a) {
  var b = 0, c;
  for (c in a) {
    b++;
  }
  return b;
};
goog.object.getAnyKey = function(a) {
  for (var b in a) {
    return b;
  }
};
goog.object.getAnyValue = function(a) {
  for (var b in a) {
    return a[b];
  }
};
goog.object.contains = function(a, b) {
  return goog.object.containsValue(a, b);
};
goog.object.getValues = function(a) {
  var b = [], c = 0, d;
  for (d in a) {
    b[c++] = a[d];
  }
  return b;
};
goog.object.getKeys = function(a) {
  var b = [], c = 0, d;
  for (d in a) {
    b[c++] = d;
  }
  return b;
};
goog.object.getValueByKeys = function(a, b) {
  for (var c = goog.isArrayLike(b), d = c ? b : arguments, c = c ? 0 : 1;c < d.length && (a = a[d[c]], goog.isDef(a));c++) {
  }
  return a;
};
goog.object.containsKey = function(a, b) {
  return b in a;
};
goog.object.containsValue = function(a, b) {
  for (var c in a) {
    if (a[c] == b) {
      return!0;
    }
  }
  return!1;
};
goog.object.findKey = function(a, b, c) {
  for (var d in a) {
    if (b.call(c, a[d], d, a)) {
      return d;
    }
  }
};
goog.object.findValue = function(a, b, c) {
  return(b = goog.object.findKey(a, b, c)) && a[b];
};
goog.object.isEmpty = function(a) {
  for (var b in a) {
    return!1;
  }
  return!0;
};
goog.object.clear = function(a) {
  for (var b in a) {
    delete a[b];
  }
};
goog.object.remove = function(a, b) {
  var c;
  (c = b in a) && delete a[b];
  return c;
};
goog.object.add = function(a, b, c) {
  if (b in a) {
    throw Error('The object already contains the key "' + b + '"');
  }
  goog.object.set(a, b, c);
};
goog.object.get = function(a, b, c) {
  return b in a ? a[b] : c;
};
goog.object.set = function(a, b, c) {
  a[b] = c;
};
goog.object.setIfUndefined = function(a, b, c) {
  return b in a ? a[b] : a[b] = c;
};
goog.object.clone = function(a) {
  var b = {}, c;
  for (c in a) {
    b[c] = a[c];
  }
  return b;
};
goog.object.unsafeClone = function(a) {
  var b = goog.typeOf(a);
  if ("object" == b || "array" == b) {
    if (a.clone) {
      return a.clone();
    }
    var b = "array" == b ? [] : {}, c;
    for (c in a) {
      b[c] = goog.object.unsafeClone(a[c]);
    }
    return b;
  }
  return a;
};
goog.object.transpose = function(a) {
  var b = {}, c;
  for (c in a) {
    b[a[c]] = c;
  }
  return b;
};
goog.object.PROTOTYPE_FIELDS_ = "constructor hasOwnProperty isPrototypeOf propertyIsEnumerable toLocaleString toString valueOf".split(" ");
goog.object.extend = function(a, b) {
  for (var c, d, e = 1;e < arguments.length;e++) {
    d = arguments[e];
    for (c in d) {
      a[c] = d[c];
    }
    for (var f = 0;f < goog.object.PROTOTYPE_FIELDS_.length;f++) {
      c = goog.object.PROTOTYPE_FIELDS_[f], Object.prototype.hasOwnProperty.call(d, c) && (a[c] = d[c]);
    }
  }
};
goog.object.create = function(a) {
  var b = arguments.length;
  if (1 == b && goog.isArray(arguments[0])) {
    return goog.object.create.apply(null, arguments[0]);
  }
  if (b % 2) {
    throw Error("Uneven number of arguments");
  }
  for (var c = {}, d = 0;d < b;d += 2) {
    c[arguments[d]] = arguments[d + 1];
  }
  return c;
};
goog.object.createSet = function(a) {
  var b = arguments.length;
  if (1 == b && goog.isArray(arguments[0])) {
    return goog.object.createSet.apply(null, arguments[0]);
  }
  for (var c = {}, d = 0;d < b;d++) {
    c[arguments[d]] = !0;
  }
  return c;
};
goog.object.createImmutableView = function(a) {
  var b = a;
  Object.isFrozen && !Object.isFrozen(a) && (b = Object.create(a), Object.freeze(b));
  return b;
};
goog.object.isImmutableView = function(a) {
  return!!Object.isFrozen && Object.isFrozen(a);
};
fb.core.stats = {};
fb.core.stats.StatsCollection = function() {
  this.counters_ = {};
};
fb.core.stats.StatsCollection.prototype.incrementCounter = function(a, b) {
  goog.isDef(b) || (b = 1);
  fb.util.obj.contains(this.counters_, a) || (this.counters_[a] = 0);
  this.counters_[a] += b;
};
fb.core.stats.StatsCollection.prototype.get = function() {
  return goog.object.clone(this.counters_);
};
fb.core.stats.StatsListener = function(a) {
  this.collection_ = a;
  this.last_ = null;
};
fb.core.stats.StatsListener.prototype.get = function() {
  var a = this.collection_.get(), b = goog.object.clone(a);
  if (this.last_) {
    for (var c in this.last_) {
      b[c] -= this.last_[c];
    }
  }
  this.last_ = a;
  return b;
};
var FIRST_STATS_TIME = 3E4, REPORT_STATS_INTERVAL = 3E5;
fb.core.stats.StatsReporter = function(a, b) {
  this.statsToReport_ = {};
  this.statsListener_ = new fb.core.stats.StatsListener(a);
  this.connection_ = b;
  setTimeout(goog.bind(this.reportStats_, this), 10 + 2 * Math.random() * FIRST_STATS_TIME);
};
fb.core.stats.StatsReporter.prototype.includeStat = function(a) {
  this.statsToReport_[a] = !0;
};
fb.core.stats.StatsReporter.prototype.reportStats_ = function() {
  var a = this.statsListener_.get(), b = {}, c = !1, d;
  for (d in a) {
    0 < a[d] && fb.util.obj.contains(this.statsToReport_, d) && (b[d] = a[d], c = !0);
  }
  c && this.connection_.reportStats(b);
  setTimeout(goog.bind(this.reportStats_, this), 2 * Math.random() * REPORT_STATS_INTERVAL);
};
fb.core.stats.StatsManager = {};
fb.core.stats.StatsManager.collections_ = {};
fb.core.stats.StatsManager.reporters_ = {};
fb.core.stats.StatsManager.getCollection = function(a) {
  a = a.toString();
  fb.core.stats.StatsManager.collections_[a] || (fb.core.stats.StatsManager.collections_[a] = new fb.core.stats.StatsCollection);
  return fb.core.stats.StatsManager.collections_[a];
};
fb.core.stats.StatsManager.getOrCreateReporter = function(a, b) {
  var c = a.toString();
  fb.core.stats.StatsManager.reporters_[c] || (fb.core.stats.StatsManager.reporters_[c] = b());
  return fb.core.stats.StatsManager.reporters_[c];
};
var WEBSOCKET_MAX_FRAME_SIZE = 16384, WEBSOCKET_KEEPALIVE_INTERVAL = 45E3;
fb.WebSocket = null;
NODE_CLIENT ? fb.WebSocket = require("faye-websocket").Client : "undefined" !== typeof MozWebSocket ? fb.WebSocket = MozWebSocket : "undefined" !== typeof WebSocket && (fb.WebSocket = WebSocket);
fb.realtime.WebSocketConnection = function(a, b, c) {
  this.connId = a;
  this.log_ = fb.core.util.logWrapper(this.connId);
  this.frames = this.keepaliveTimer = null;
  this.bytesReceived = this.bytesSent = this.totalFrames = 0;
  this.stats_ = fb.core.stats.StatsManager.getCollection(b);
  this.connURL = (b.secure ? "wss://" : "ws://") + b.internalHost + "/.ws?" + fb.realtime.Constants.VERSION_PARAM + "=" + fb.realtime.Constants.PROTOCOL_VERSION;
  b.needsQueryParam() && (this.connURL = this.connURL + "&ns=" + b.namespace);
  c && (this.connURL = this.connURL + "&" + fb.realtime.Constants.SESSION_PARAM + "=" + c);
};
fb.realtime.WebSocketConnection.prototype.open = function(a, b) {
  this.onDisconnect = b;
  this.onMessage = a;
  this.log_("Websocket connecting to " + this.connURL);
  this.mySock = new fb.WebSocket(this.connURL);
  this.everConnected_ = !1;
  fb.core.storage.PersistentStorage.set("previous_websocket_failure", !0);
  var c = this;
  this.mySock.onopen = function() {
    c.log_("Websocket connected.");
    c.everConnected_ = !0;
  };
  this.mySock.onclose = function() {
    c.log_("Websocket connection was disconnected.");
    c.mySock = null;
    c.onClosed_();
  };
  this.mySock.onmessage = function(a) {
    c.handleIncomingFrame(a);
  };
  this.mySock.onerror = function(a) {
    c.log_("WebSocket error.  Closing connection.");
    (a = a.message || a.data) && c.log_(a);
    c.onClosed_();
  };
};
fb.realtime.WebSocketConnection.prototype.start = function() {
};
fb.realtime.WebSocketConnection.forceDisallow = function() {
  fb.realtime.WebSocketConnection.forceDisallow_ = !0;
};
fb.realtime.WebSocketConnection.isAvailable = function() {
  var a = !1;
  if ("undefined" !== typeof navigator && navigator.userAgent) {
    var b = navigator.userAgent.match(/Android ([0-9]{0,}\.[0-9]{0,})/);
    b && 1 < b.length && 4.4 > parseFloat(b[1]) && (a = !0);
  }
  return!a && null !== fb.WebSocket && !fb.realtime.WebSocketConnection.forceDisallow_;
};
fb.realtime.WebSocketConnection.responsesRequiredToBeHealthy = 2;
fb.realtime.WebSocketConnection.healthyTimeout = 3E4;
fb.realtime.WebSocketConnection.previouslyFailed = function() {
  return fb.core.storage.PersistentStorage.isInMemoryStorage || !0 === fb.core.storage.PersistentStorage.get("previous_websocket_failure");
};
fb.realtime.WebSocketConnection.prototype.markConnectionHealthy = function() {
  fb.core.storage.PersistentStorage.remove("previous_websocket_failure");
};
fb.realtime.WebSocketConnection.prototype.appendFrame_ = function(a) {
  this.frames.push(a);
  this.frames.length == this.totalFrames && (a = this.frames.join(""), this.frames = null, a = fb.util.json.eval(a), this.onMessage(a));
};
fb.realtime.WebSocketConnection.prototype.handleNewFrameCount_ = function(a) {
  this.totalFrames = a;
  this.frames = [];
};
fb.realtime.WebSocketConnection.prototype.extractFrameCount_ = function(a) {
  fb.core.util.assert(null === this.frames, "We already have a frame buffer");
  if (6 >= a.length) {
    var b = Number(a);
    if (!isNaN(b)) {
      return this.handleNewFrameCount_(b), null;
    }
  }
  this.handleNewFrameCount_(1);
  return a;
};
fb.realtime.WebSocketConnection.prototype.handleIncomingFrame = function(a) {
  null !== this.mySock && (a = a.data, this.bytesReceived += a.length, this.stats_.incrementCounter("bytes_received", a.length), this.resetKeepAlive(), null !== this.frames ? this.appendFrame_(a) : (a = this.extractFrameCount_(a), null !== a && this.appendFrame_(a)));
};
fb.realtime.WebSocketConnection.prototype.send = function(a) {
  this.resetKeepAlive();
  a = fb.util.json.stringify(a);
  this.bytesSent += a.length;
  this.stats_.incrementCounter("bytes_sent", a.length);
  a = fb.core.util.splitStringBySize(a, WEBSOCKET_MAX_FRAME_SIZE);
  1 < a.length && this.mySock.send(String(a.length));
  for (var b = 0;b < a.length;b++) {
    this.mySock.send(a[b]);
  }
};
fb.realtime.WebSocketConnection.prototype.shutdown_ = function() {
  this.isClosed_ = !0;
  this.keepaliveTimer && (clearInterval(this.keepaliveTimer), this.keepaliveTimer = null);
  this.mySock && (this.mySock.close(), this.mySock = null);
};
fb.realtime.WebSocketConnection.prototype.onClosed_ = function() {
  this.isClosed_ || (this.log_("WebSocket is closing itself"), this.shutdown_(), this.onDisconnect && (this.onDisconnect(this.everConnected_), this.onDisconnect = null));
};
fb.realtime.WebSocketConnection.prototype.close = function() {
  this.isClosed_ || (this.log_("WebSocket is being closed"), this.shutdown_());
};
fb.realtime.WebSocketConnection.prototype.resetKeepAlive = function() {
  var a = this;
  clearInterval(this.keepaliveTimer);
  this.keepaliveTimer = setInterval(function() {
    a.mySock && a.mySock.send("0");
    a.resetKeepAlive();
  }, WEBSOCKET_KEEPALIVE_INTERVAL);
};
fb.realtime.polling = {};
fb.realtime.polling.PacketReceiver = function(a) {
  this.onMessage_ = a;
  this.pendingResponses = [];
  this.currentResponseNum = 0;
  this.closeAfterResponse = -1;
  this.onClose = null;
};
fb.realtime.polling.PacketReceiver.prototype.closeAfter = function(a, b) {
  this.closeAfterResponse = a;
  this.onClose = b;
  this.closeAfterResponse < this.currentResponseNum && (this.onClose(), this.onClose = null);
};
fb.realtime.polling.PacketReceiver.prototype.handleResponse = function(a, b) {
  for (this.pendingResponses[a] = b;this.pendingResponses[this.currentResponseNum];) {
    var c = this.pendingResponses[this.currentResponseNum];
    delete this.pendingResponses[this.currentResponseNum];
    for (var d = 0;d < c.length;++d) {
      if (c[d]) {
        var e = this;
        fb.core.util.exceptionGuard(function() {
          e.onMessage_(c[d]);
        });
      }
    }
    if (this.currentResponseNum === this.closeAfterResponse) {
      this.onClose && (clearTimeout(this.onClose), this.onClose(), this.onClose = null);
      break;
    }
    this.currentResponseNum++;
  }
};
fb.core.util.CountedSet = function() {
  this.set = {};
};
fb.core.util.CountedSet.prototype.add = function(a, b) {
  this.set[a] = null !== b ? b : !0;
};
fb.core.util.CountedSet.prototype.contains = function(a) {
  return fb.util.obj.contains(this.set, a);
};
fb.core.util.CountedSet.prototype.get = function(a) {
  return this.contains(a) ? this.set[a] : void 0;
};
fb.core.util.CountedSet.prototype.remove = function(a) {
  delete this.set[a];
};
fb.core.util.CountedSet.prototype.clear = function() {
  this.set = {};
};
fb.core.util.CountedSet.prototype.isEmpty = function() {
  return goog.object.isEmpty(this.set);
};
fb.core.util.CountedSet.prototype.count = function() {
  return goog.object.getCount(this.set);
};
fb.core.util.CountedSet.prototype.each = function(a) {
  goog.object.forEach(this.set, function(b, c) {
    a(c, b);
  });
};
fb.core.util.CountedSet.prototype.keys = function() {
  var a = [];
  goog.object.forEach(this.set, function(b, c) {
    a.push(c);
  });
  return a;
};
var FIREBASE_LONGPOLL_START_PARAM = "start", FIREBASE_LONGPOLL_CLOSE_COMMAND = "close", FIREBASE_LONGPOLL_COMMAND_CB_NAME = "pLPCommand", FIREBASE_LONGPOLL_DATA_CB_NAME = "pRTLPCB", FIREBASE_LONGPOLL_ID_PARAM = "id", FIREBASE_LONGPOLL_PW_PARAM = "pw", FIREBASE_LONGPOLL_SERIAL_PARAM = "ser", FIREBASE_LONGPOLL_CALLBACK_ID_PARAM = "cb", FIREBASE_LONGPOLL_SEGMENT_NUM_PARAM = "seg", FIREBASE_LONGPOLL_SEGMENTS_IN_PACKET = "ts", FIREBASE_LONGPOLL_DATA_PARAM = "d", FIREBASE_LONGPOLL_DISCONN_FRAME_PARAM = 
"disconn", FIREBASE_LONGPOLL_DISCONN_FRAME_REQUEST_PARAM = "dframe", MAX_URL_DATA_SIZE = 1870, SEG_HEADER_SIZE = 30, MAX_PAYLOAD_SIZE = MAX_URL_DATA_SIZE - SEG_HEADER_SIZE, KEEPALIVE_REQUEST_INTERVAL = 25E3, LP_CONNECT_TIMEOUT = 3E4;
fb.realtime.BrowserPollConnection = function(a, b, c) {
  this.connId = a;
  this.log_ = fb.core.util.logWrapper(a);
  this.repoInfo = b;
  this.bytesReceived = this.bytesSent = 0;
  this.stats_ = fb.core.stats.StatsManager.getCollection(b);
  this.sessionId = c;
  this.everConnected_ = !1;
  this.urlFn = function(a) {
    b.needsQueryParam() && (a.ns = b.namespace);
    var c = [], f;
    for (f in a) {
      a.hasOwnProperty(f) && c.push(f + "=" + a[f]);
    }
    return(b.secure ? "https://" : "http://") + b.internalHost + "/.lp?" + c.join("&");
  };
};
fb.realtime.BrowserPollConnection.prototype.open = function(a, b) {
  this.curSegmentNum = 0;
  this.onDisconnect_ = b;
  this.myPacketOrderer = new fb.realtime.polling.PacketReceiver(a);
  this.isClosed_ = !1;
  var c = this;
  this.connectTimeoutTimer_ = setTimeout(function() {
    c.log_("Timed out trying to connect.");
    c.onClosed_();
    c.connectTimeoutTimer_ = null;
  }, LP_CONNECT_TIMEOUT);
  fb.core.util.executeWhenDOMReady(function() {
    if (!c.isClosed_) {
      c.scriptTagHolder = new FirebaseIFrameScriptHolder(function(a, b, d, h, k) {
        c.incrementIncomingBytes_(arguments);
        if (c.scriptTagHolder) {
          if (c.connectTimeoutTimer_ && (clearTimeout(c.connectTimeoutTimer_), c.connectTimeoutTimer_ = null), c.everConnected_ = !0, a == FIREBASE_LONGPOLL_START_PARAM) {
            c.id = b, c.password = d;
          } else {
            if (a === FIREBASE_LONGPOLL_CLOSE_COMMAND) {
              if (b) {
                c.scriptTagHolder.sendNewPolls = !1, c.myPacketOrderer.closeAfter(b, function() {
                  c.onClosed_();
                });
              } else {
                c.onClosed_();
              }
            } else {
              throw Error("Unrecognized command received: " + a);
            }
          }
        }
      }, function(a, b) {
        c.incrementIncomingBytes_(arguments);
        c.myPacketOrderer.handleResponse(a, b);
      }, function() {
        c.onClosed_();
      }, c.urlFn);
      var a = {};
      a[FIREBASE_LONGPOLL_START_PARAM] = "t";
      a[FIREBASE_LONGPOLL_SERIAL_PARAM] = Math.floor(1E8 * Math.random());
      c.scriptTagHolder.uniqueCallbackIdentifier && (a[FIREBASE_LONGPOLL_CALLBACK_ID_PARAM] = c.scriptTagHolder.uniqueCallbackIdentifier);
      a[fb.realtime.Constants.VERSION_PARAM] = fb.realtime.Constants.PROTOCOL_VERSION;
      c.sessionId && (a[fb.realtime.Constants.SESSION_PARAM] = c.sessionId);
      a = c.urlFn(a);
      c.log_("Connecting via long-poll to " + a);
      c.scriptTagHolder.addTag(a, function() {
      });
    }
  });
};
fb.realtime.BrowserPollConnection.prototype.start = function() {
  this.scriptTagHolder.startLongPoll(this.id, this.password);
  this.addDisconnectPingFrame(this.id, this.password);
};
fb.realtime.BrowserPollConnection.forceAllow = function() {
  fb.realtime.BrowserPollConnection.forceAllow_ = !0;
};
fb.realtime.BrowserPollConnection.forceDisallow = function() {
  fb.realtime.BrowserPollConnection.forceDisallow_ = !0;
};
fb.realtime.BrowserPollConnection.isAvailable = function() {
  return!fb.realtime.BrowserPollConnection.forceDisallow_ && !fb.core.util.isChromeExtensionContentScript() && !fb.core.util.isWindowsStoreApp() && (fb.realtime.BrowserPollConnection.forceAllow_ || !NODE_CLIENT);
};
fb.realtime.BrowserPollConnection.prototype.markConnectionHealthy = function() {
};
fb.realtime.BrowserPollConnection.prototype.shutdown_ = function() {
  this.isClosed_ = !0;
  this.scriptTagHolder && (this.scriptTagHolder.close(), this.scriptTagHolder = null);
  this.myDisconnFrame && (document.body.removeChild(this.myDisconnFrame), this.myDisconnFrame = null);
  this.connectTimeoutTimer_ && (clearTimeout(this.connectTimeoutTimer_), this.connectTimeoutTimer_ = null);
};
fb.realtime.BrowserPollConnection.prototype.onClosed_ = function() {
  this.isClosed_ || (this.log_("Longpoll is closing itself"), this.shutdown_(), this.onDisconnect_ && (this.onDisconnect_(this.everConnected_), this.onDisconnect_ = null));
};
fb.realtime.BrowserPollConnection.prototype.close = function() {
  this.isClosed_ || (this.log_("Longpoll is being closed."), this.shutdown_());
};
fb.realtime.BrowserPollConnection.prototype.send = function(a) {
  a = fb.util.json.stringify(a);
  this.bytesSent += a.length;
  this.stats_.incrementCounter("bytes_sent", a.length);
  a = fb.core.util.base64Encode(a);
  a = fb.core.util.splitStringBySize(a, MAX_PAYLOAD_SIZE);
  for (var b = 0;b < a.length;b++) {
    this.scriptTagHolder.enqueueSegment(this.curSegmentNum, a.length, a[b]), this.curSegmentNum++;
  }
};
fb.realtime.BrowserPollConnection.prototype.addDisconnectPingFrame = function(a, b) {
  if (!NODE_CLIENT) {
    this.myDisconnFrame = document.createElement("iframe");
    var c = {};
    c[FIREBASE_LONGPOLL_DISCONN_FRAME_REQUEST_PARAM] = "t";
    c[FIREBASE_LONGPOLL_ID_PARAM] = a;
    c[FIREBASE_LONGPOLL_PW_PARAM] = b;
    this.myDisconnFrame.src = this.urlFn(c);
    this.myDisconnFrame.style.display = "none";
    document.body.appendChild(this.myDisconnFrame);
  }
};
fb.realtime.BrowserPollConnection.prototype.incrementIncomingBytes_ = function(a) {
  a = fb.util.json.stringify(a).length;
  this.bytesReceived += a;
  this.stats_.incrementCounter("bytes_received", a);
};
function FirebaseIFrameScriptHolder(a, b, c, d) {
  this.urlFn = d;
  this.onDisconnect = c;
  this.outstandingRequests = new fb.core.util.CountedSet;
  this.pendingSegs = [];
  this.currentSerial = Math.floor(1E8 * Math.random());
  this.sendNewPolls = !0;
  if (NODE_CLIENT) {
    this.commandCB = a, this.onMessageCB = b;
  } else {
    this.uniqueCallbackIdentifier = fb.core.util.LUIDGenerator();
    window[FIREBASE_LONGPOLL_COMMAND_CB_NAME + this.uniqueCallbackIdentifier] = a;
    window[FIREBASE_LONGPOLL_DATA_CB_NAME + this.uniqueCallbackIdentifier] = b;
    this.myIFrame = this.createIFrame_();
    a = "";
    this.myIFrame.src && "javascript:" === this.myIFrame.src.substr(0, 11) && (a = '<script>document.domain="' + document.domain + '";\x3c/script>');
    a = "<html><body>" + a + "</body></html>";
    try {
      this.myIFrame.doc.open(), this.myIFrame.doc.write(a), this.myIFrame.doc.close();
    } catch (e) {
      fb.core.util.log("frame writing exception"), e.stack && fb.core.util.log(e.stack), fb.core.util.log(e);
    }
  }
}
FirebaseIFrameScriptHolder.prototype.createIFrame_ = function() {
  var a = document.createElement("iframe");
  a.style.display = "none";
  if (document.body) {
    document.body.appendChild(a);
    try {
      a.contentWindow.document || fb.core.util.log("No IE domain setting required");
    } catch (b) {
      a.src = "javascript:void((function(){document.open();document.domain='" + document.domain + "';document.close();})())";
    }
  } else {
    throw "Document body has not initialized. Wait to initialize Firebase until after the document is ready.";
  }
  a.contentDocument ? a.doc = a.contentDocument : a.contentWindow ? a.doc = a.contentWindow.document : a.document && (a.doc = a.document);
  return a;
};
FirebaseIFrameScriptHolder.prototype.close = function() {
  this.alive = !1;
  if (this.myIFrame) {
    this.myIFrame.doc.body.innerHTML = "";
    var a = this;
    setTimeout(function() {
      null !== a.myIFrame && (document.body.removeChild(a.myIFrame), a.myIFrame = null);
    }, 0);
  }
  if (NODE_CLIENT && this.myID) {
    var b = {};
    b[FIREBASE_LONGPOLL_DISCONN_FRAME_PARAM] = "t";
    b[FIREBASE_LONGPOLL_ID_PARAM] = this.myID;
    b[FIREBASE_LONGPOLL_PW_PARAM] = this.myPW;
    b = this.urlFn(b);
    FirebaseIFrameScriptHolder.nodeRestRequest(b);
  }
  if (b = this.onDisconnect) {
    this.onDisconnect = null, b();
  }
};
FirebaseIFrameScriptHolder.prototype.startLongPoll = function(a, b) {
  this.myID = a;
  this.myPW = b;
  for (this.alive = !0;this.newRequest_();) {
  }
};
FirebaseIFrameScriptHolder.prototype.newRequest_ = function() {
  if (this.alive && this.sendNewPolls && this.outstandingRequests.count() < (0 < this.pendingSegs.length ? 2 : 1)) {
    this.currentSerial++;
    var a = {};
    a[FIREBASE_LONGPOLL_ID_PARAM] = this.myID;
    a[FIREBASE_LONGPOLL_PW_PARAM] = this.myPW;
    a[FIREBASE_LONGPOLL_SERIAL_PARAM] = this.currentSerial;
    for (var a = this.urlFn(a), b = "", c = 0;0 < this.pendingSegs.length;) {
      if (this.pendingSegs[0].d.length + SEG_HEADER_SIZE + b.length <= MAX_URL_DATA_SIZE) {
        var d = this.pendingSegs.shift(), b = b + "&" + FIREBASE_LONGPOLL_SEGMENT_NUM_PARAM + c + "=" + d.seg + "&" + FIREBASE_LONGPOLL_SEGMENTS_IN_PACKET + c + "=" + d.ts + "&" + FIREBASE_LONGPOLL_DATA_PARAM + c + "=" + d.d;
        c++;
      } else {
        break;
      }
    }
    this.addLongPollTag_(a + b, this.currentSerial);
    return!0;
  }
  return!1;
};
FirebaseIFrameScriptHolder.prototype.enqueueSegment = function(a, b, c) {
  this.pendingSegs.push({seg:a, ts:b, d:c});
  this.alive && this.newRequest_();
};
FirebaseIFrameScriptHolder.prototype.addLongPollTag_ = function(a, b) {
  var c = this;
  c.outstandingRequests.add(b);
  var d = function() {
    c.outstandingRequests.remove(b);
    c.newRequest_();
  }, e = setTimeout(d, KEEPALIVE_REQUEST_INTERVAL);
  this.addTag(a, function() {
    clearTimeout(e);
    d();
  });
};
FirebaseIFrameScriptHolder.prototype.addTag = function(a, b) {
  if (NODE_CLIENT) {
    this.doNodeLongPoll(a, b);
  } else {
    var c = this;
    setTimeout(function() {
      try {
        if (c.sendNewPolls) {
          var d = c.myIFrame.doc.createElement("script");
          d.type = "text/javascript";
          d.async = !0;
          d.src = a;
          d.onload = d.onreadystatechange = function() {
            var a = d.readyState;
            a && "loaded" !== a && "complete" !== a || (d.onload = d.onreadystatechange = null, d.parentNode && d.parentNode.removeChild(d), b());
          };
          d.onerror = function() {
            fb.core.util.log("Long-poll script failed to load: " + a);
            c.sendNewPolls = !1;
            c.close();
          };
          c.myIFrame.doc.body.appendChild(d);
        }
      } catch (e) {
      }
    }, 1);
  }
};
"undefined" !== typeof NODE_CLIENT && NODE_CLIENT && (FirebaseIFrameScriptHolder.request = null, FirebaseIFrameScriptHolder.nodeRestRequest = function(a, b) {
  FirebaseIFrameScriptHolder.request || (FirebaseIFrameScriptHolder.request = require("request"));
  FirebaseIFrameScriptHolder.request(a, function(c, d, e) {
    if (c) {
      throw "Rest request for " + a.url + " failed.";
    }
    b && b(e);
  });
}, FirebaseIFrameScriptHolder.prototype.doNodeLongPoll = function(a, b) {
  var c = this;
  FirebaseIFrameScriptHolder.nodeRestRequest({url:a, forever:!0}, function(a) {
    c.evalBody(a);
    b();
  });
}, FirebaseIFrameScriptHolder.prototype.evalBody = function(a) {
  eval("var jsonpCB = function(" + FIREBASE_LONGPOLL_COMMAND_CB_NAME + ", " + FIREBASE_LONGPOLL_DATA_CB_NAME + ") {" + a + "}");
  jsonpCB(this.commandCB, this.onMessageCB);
});
fb.realtime.TransportManager = function(a) {
  this.initTransports_(a);
};
fb.realtime.TransportManager.ALL_TRANSPORTS = [fb.realtime.BrowserPollConnection, fb.realtime.WebSocketConnection];
fb.realtime.TransportManager.prototype.initTransports_ = function(a) {
  var b = fb.realtime.WebSocketConnection && fb.realtime.WebSocketConnection.isAvailable(), c = b && !fb.realtime.WebSocketConnection.previouslyFailed();
  a.webSocketOnly && (b || fb.core.util.warn("wss:// URL used, but browser isn't known to support websockets.  Trying anyway."), c = !0);
  if (c) {
    this.transports_ = [fb.realtime.WebSocketConnection];
  } else {
    var d = this.transports_ = [];
    fb.core.util.each(fb.realtime.TransportManager.ALL_TRANSPORTS, function(a, b) {
      b && b.isAvailable() && d.push(b);
    });
  }
};
fb.realtime.TransportManager.prototype.initialTransport = function() {
  if (0 < this.transports_.length) {
    return this.transports_[0];
  }
  throw Error("No transports available");
};
fb.realtime.TransportManager.prototype.upgradeTransport = function() {
  return 1 < this.transports_.length ? this.transports_[1] : null;
};
var UPGRADE_TIMEOUT = 6E4, DELAY_BEFORE_SENDING_EXTRA_REQUESTS = 5E3, BYTES_SENT_HEALTHY_OVERRIDE = 10240, BYTES_RECEIVED_HEALTHY_OVERRIDE = 102400, REALTIME_STATE_CONNECTING = 0, REALTIME_STATE_CONNECTED = 1, REALTIME_STATE_DISCONNECTED = 2, MESSAGE_TYPE = "t", MESSAGE_DATA = "d", CONTROL_SHUTDOWN = "s", CONTROL_RESET = "r", CONTROL_ERROR = "e", CONTROL_PONG = "o", SWITCH_ACK = "a", END_TRANSMISSION = "n", PING = "p", SERVER_HELLO = "h";
fb.realtime.Connection = function(a, b, c, d, e, f) {
  this.id = a;
  this.log_ = fb.core.util.logWrapper("c:" + this.id + ":");
  this.onMessage_ = c;
  this.onReady_ = d;
  this.onDisconnect_ = e;
  this.onKill_ = f;
  this.repoInfo_ = b;
  this.pendingDataMessages = [];
  this.connectionCount = 0;
  this.transportManager_ = new fb.realtime.TransportManager(b);
  this.state_ = REALTIME_STATE_CONNECTING;
  this.log_("Connection created");
  this.start_();
};
fb.realtime.Connection.prototype.start_ = function() {
  var a = this.transportManager_.initialTransport();
  this.conn_ = new a(this.nextTransportId_(), this.repoInfo_);
  this.primaryResponsesRequired_ = a.responsesRequiredToBeHealthy || 0;
  var b = this.connReceiver_(this.conn_), c = this.disconnReceiver_(this.conn_);
  this.rx_ = this.tx_ = this.conn_;
  this.secondaryConn_ = null;
  this.isHealthy_ = !1;
  var d = this;
  setTimeout(function() {
    d.conn_ && d.conn_.open(b, c);
  }, 0);
  a = a.healthyTimeout || 0;
  0 < a && (this.healthyTimeout_ = setTimeout(function() {
    d.healthyTimeout_ = null;
    d.isHealthy_ || (d.conn_ && d.conn_.bytesReceived > BYTES_RECEIVED_HEALTHY_OVERRIDE ? (d.log_("Connection exceeded healthy timeout but has received " + d.conn_.bytesReceived + " bytes.  Marking connection healthy."), d.isHealthy_ = !0, d.conn_.markConnectionHealthy()) : d.conn_ && d.conn_.bytesSent > BYTES_SENT_HEALTHY_OVERRIDE ? d.log_("Connection exceeded healthy timeout but has sent " + d.conn_.bytesSent + " bytes.  Leaving connection alive.") : (d.log_("Closing unhealthy connection after timeout."), 
    d.close()));
  }, a));
};
fb.realtime.Connection.prototype.nextTransportId_ = function() {
  return "c:" + this.id + ":" + this.connectionCount++;
};
fb.realtime.Connection.prototype.disconnReceiver_ = function(a) {
  var b = this;
  return function(c) {
    if (a === b.conn_) {
      b.onConnectionLost_(c);
    } else {
      a === b.secondaryConn_ ? (b.log_("Secondary connection lost."), b.onSecondaryConnectionLost_()) : b.log_("closing an old connection");
    }
  };
};
fb.realtime.Connection.prototype.connReceiver_ = function(a) {
  var b = this;
  return function(c) {
    if (b.state_ != REALTIME_STATE_DISCONNECTED) {
      if (a === b.rx_) {
        b.onPrimaryMessageReceived_(c);
      } else {
        if (a === b.secondaryConn_) {
          b.onSecondaryMessageReceived_(c);
        } else {
          b.log_("message on old connection");
        }
      }
    }
  };
};
fb.realtime.Connection.prototype.sendRequest = function(a) {
  this.sendData_({t:"d", d:a});
};
fb.realtime.Connection.prototype.tryCleanupConnection = function() {
  this.tx_ === this.secondaryConn_ && this.rx_ === this.secondaryConn_ && (this.log_("cleaning up and promoting a connection: " + this.secondaryConn_.connId), this.conn_ = this.secondaryConn_, this.secondaryConn_ = null);
};
fb.realtime.Connection.prototype.onSecondaryControl_ = function(a) {
  MESSAGE_TYPE in a && (a = a[MESSAGE_TYPE], a === SWITCH_ACK ? this.upgradeIfSecondaryHealthy_() : a === CONTROL_RESET ? (this.log_("Got a reset on secondary, closing it"), this.secondaryConn_.close(), this.tx_ !== this.secondaryConn_ && this.rx_ !== this.secondaryConn_ || this.close()) : a === CONTROL_PONG && (this.log_("got pong on secondary."), this.secondaryResponsesRequired_--, this.upgradeIfSecondaryHealthy_()));
};
fb.realtime.Connection.prototype.onSecondaryMessageReceived_ = function(a) {
  var b = fb.core.util.requireKey("t", a);
  a = fb.core.util.requireKey("d", a);
  if ("c" == b) {
    this.onSecondaryControl_(a);
  } else {
    if ("d" == b) {
      this.pendingDataMessages.push(a);
    } else {
      throw Error("Unknown protocol layer: " + b);
    }
  }
};
fb.realtime.Connection.prototype.upgradeIfSecondaryHealthy_ = function() {
  0 >= this.secondaryResponsesRequired_ ? (this.log_("Secondary connection is healthy."), this.isHealthy_ = !0, this.secondaryConn_.markConnectionHealthy(), this.proceedWithUpgrade_()) : (this.log_("sending ping on secondary."), this.secondaryConn_.send({t:"c", d:{t:PING, d:{}}}));
};
fb.realtime.Connection.prototype.proceedWithUpgrade_ = function() {
  this.secondaryConn_.start();
  this.log_("sending client ack on secondary");
  this.secondaryConn_.send({t:"c", d:{t:SWITCH_ACK, d:{}}});
  this.log_("Ending transmission on primary");
  this.conn_.send({t:"c", d:{t:END_TRANSMISSION, d:{}}});
  this.tx_ = this.secondaryConn_;
  this.tryCleanupConnection();
};
fb.realtime.Connection.prototype.onPrimaryMessageReceived_ = function(a) {
  var b = fb.core.util.requireKey("t", a);
  a = fb.core.util.requireKey("d", a);
  if ("c" == b) {
    this.onControl_(a);
  } else {
    if ("d" == b) {
      this.onDataMessage_(a);
    }
  }
};
fb.realtime.Connection.prototype.onDataMessage_ = function(a) {
  this.onPrimaryResponse_();
  this.onMessage_(a);
};
fb.realtime.Connection.prototype.onPrimaryResponse_ = function() {
  this.isHealthy_ || (this.primaryResponsesRequired_--, 0 >= this.primaryResponsesRequired_ && (this.log_("Primary connection is healthy."), this.isHealthy_ = !0, this.conn_.markConnectionHealthy()));
};
fb.realtime.Connection.prototype.onControl_ = function(a) {
  var b = fb.core.util.requireKey(MESSAGE_TYPE, a);
  if (MESSAGE_DATA in a) {
    if (a = a[MESSAGE_DATA], b === SERVER_HELLO) {
      this.onHandshake_(a);
    } else {
      if (b === END_TRANSMISSION) {
        this.log_("recvd end transmission on primary");
        this.rx_ = this.secondaryConn_;
        for (b = 0;b < this.pendingDataMessages.length;++b) {
          this.onDataMessage_(this.pendingDataMessages[b]);
        }
        this.pendingDataMessages = [];
        this.tryCleanupConnection();
      } else {
        if (b === CONTROL_SHUTDOWN) {
          this.onConnectionShutdown_(a);
        } else {
          if (b === CONTROL_RESET) {
            this.onReset_(a);
          } else {
            b === CONTROL_ERROR ? fb.core.util.error("Server Error: " + a) : b === CONTROL_PONG ? (this.log_("got pong on primary."), this.onPrimaryResponse_(), this.sendPingOnPrimaryIfNecessary_()) : fb.core.util.error("Unknown control packet command: " + b);
          }
        }
      }
    }
  }
};
fb.realtime.Connection.prototype.onHandshake_ = function(a) {
  var b = a.ts, c = a.v, d = a.h;
  this.sessionId = a.s;
  this.repoInfo_.updateHost(d);
  this.state_ == REALTIME_STATE_CONNECTING && (this.conn_.start(), this.onConnectionEstablished_(this.conn_, b), fb.realtime.Constants.PROTOCOL_VERSION !== c && fb.core.util.warn("Protocol version mismatch detected"), this.tryStartUpgrade_());
};
fb.realtime.Connection.prototype.tryStartUpgrade_ = function() {
  var a = this.transportManager_.upgradeTransport();
  a && this.startUpgrade_(a);
};
fb.realtime.Connection.prototype.startUpgrade_ = function(a) {
  this.secondaryConn_ = new a(this.nextTransportId_(), this.repoInfo_, this.sessionId);
  this.secondaryResponsesRequired_ = a.responsesRequiredToBeHealthy || 0;
  a = this.connReceiver_(this.secondaryConn_);
  var b = this.disconnReceiver_(this.secondaryConn_);
  this.secondaryConn_.open(a, b);
  var c = this;
  setTimeout(function() {
    c.secondaryConn_ && (c.log_("Timed out trying to upgrade."), c.secondaryConn_.close());
  }, UPGRADE_TIMEOUT);
};
fb.realtime.Connection.prototype.onReset_ = function(a) {
  this.log_("Reset packet received.  New host: " + a);
  this.repoInfo_.updateHost(a);
  this.state_ === REALTIME_STATE_CONNECTED ? this.close() : (this.closeConnections_(), this.start_());
};
fb.realtime.Connection.prototype.onConnectionEstablished_ = function(a, b) {
  this.log_("Realtime connection established.");
  this.conn_ = a;
  this.state_ = REALTIME_STATE_CONNECTED;
  this.onReady_ && (this.onReady_(b), this.onReady_ = null);
  var c = this;
  0 === this.primaryResponsesRequired_ ? (this.log_("Primary connection is healthy."), this.isHealthy_ = !0) : setTimeout(function() {
    c.sendPingOnPrimaryIfNecessary_();
  }, DELAY_BEFORE_SENDING_EXTRA_REQUESTS);
};
fb.realtime.Connection.prototype.sendPingOnPrimaryIfNecessary_ = function() {
  this.isHealthy_ || this.state_ !== REALTIME_STATE_CONNECTED || (this.log_("sending ping on primary."), this.sendData_({t:"c", d:{t:PING, d:{}}}));
};
fb.realtime.Connection.prototype.onSecondaryConnectionLost_ = function() {
  var a = this.secondaryConn_;
  this.secondaryConn_ = null;
  this.tx_ !== a && this.rx_ !== a || this.close();
};
fb.realtime.Connection.prototype.onConnectionLost_ = function(a) {
  this.conn_ = null;
  a || this.state_ !== REALTIME_STATE_CONNECTING ? this.state_ === REALTIME_STATE_CONNECTED && this.log_("Realtime connection lost.") : (this.log_("Realtime connection failed."), this.repoInfo_.isCacheableHost() && (fb.core.storage.PersistentStorage.remove("host:" + this.repoInfo_.host), this.repoInfo_.internalHost = this.repoInfo_.host));
  this.close();
};
fb.realtime.Connection.prototype.onConnectionShutdown_ = function(a) {
  this.log_("Connection shutdown command received. Shutting down...");
  this.onKill_ && (this.onKill_(a), this.onKill_ = null);
  this.onDisconnect_ = null;
  this.close();
};
fb.realtime.Connection.prototype.sendData_ = function(a) {
  if (this.state_ !== REALTIME_STATE_CONNECTED) {
    throw "Connection is not connected";
  }
  this.tx_.send(a);
};
fb.realtime.Connection.prototype.close = function() {
  this.state_ !== REALTIME_STATE_DISCONNECTED && (this.log_("Closing realtime connection."), this.state_ = REALTIME_STATE_DISCONNECTED, this.closeConnections_(), this.onDisconnect_ && (this.onDisconnect_(), this.onDisconnect_ = null));
};
fb.realtime.Connection.prototype.closeConnections_ = function() {
  this.log_("Shutting down all connections");
  this.conn_ && (this.conn_.close(), this.conn_ = null);
  this.secondaryConn_ && (this.secondaryConn_.close(), this.secondaryConn_ = null);
  this.healthyTimeout_ && (clearTimeout(this.healthyTimeout_), this.healthyTimeout_ = null);
};
var RECONNECT_MIN_DELAY = 1E3, RECONNECT_MAX_DELAY_DEFAULT = 3E5, RECONNECT_MAX_DELAY_FOR_ADMINS = 3E4, RECONNECT_DELAY_MULTIPLIER = 1.3, RECONNECT_DELAY_RESET_TIMEOUT = 3E4;
fb.core.PersistentConnection = function(a, b, c, d, e, f) {
  this.id = fb.core.PersistentConnection.nextPersistentConnectionId_++;
  this.log_ = fb.core.util.logWrapper("p:" + this.id + ":");
  this.shouldReconnect_ = !0;
  this.listens_ = {};
  this.outstandingPuts_ = [];
  this.outstandingPutCount_ = 0;
  this.onDisconnectRequestQueue_ = [];
  this.connected_ = !1;
  this.reconnectDelay_ = RECONNECT_MIN_DELAY;
  this.maxReconnectDelay_ = RECONNECT_MAX_DELAY_DEFAULT;
  this.onDataUpdate_ = b || goog.nullFunction;
  this.onConnectStatus_ = c || goog.nullFunction;
  this.onAuthStatus_ = d || goog.nullFunction;
  this.onServerInfoUpdate_ = e || goog.nullFunction;
  this.getServerDataHashForPath_ = f || goog.nullFunction;
  this.repoInfo_ = a;
  this.securityDebugCallback_ = null;
  this.requestCBHash_ = {};
  this.requestNumber_ = 0;
  this.lastConnectionEstablishedTime_ = this.lastConnectionAttemptTime_ = null;
  this.scheduleConnect_(0);
  fb.core.util.VisibilityMonitor.getInstance().on("visible", this.onVisible_, this);
  if (-1 === a.host.indexOf("fblocal")) {
    fb.core.util.OnlineMonitor.getInstance().on("online", this.onOnline_, this);
  }
};
fb.core.PersistentConnection.nextPersistentConnectionId_ = 0;
fb.core.PersistentConnection.nextConnectionId_ = 0;
fb.core.PersistentConnection.prototype.sendRequest_ = function(a, b, c) {
  var d = ++this.requestNumber_;
  a = {r:d, a:a, b:b};
  this.log_(fb.util.json.stringify(a));
  fb.core.util.assert(this.connected_, "sendRequest_ call when we're not connected not allowed.");
  this.realtime_.sendRequest(a);
  c && (this.requestCBHash_[d] = c);
};
fb.core.PersistentConnection.prototype.listen = function(a, b) {
  var c = a.toString(), d = a.path().toString();
  this.listens_[d] = this.listens_[d] || {};
  fb.core.util.assert(!this.listens_[d][c], "listen() called twice for same path/queryId.");
  this.listens_[d][c] = {queries:a.queries(), onComplete:b};
  this.connected_ && this.sendListen_(d, c, a.queries(), b);
};
fb.core.PersistentConnection.prototype.sendListen_ = function(a, b, c, d) {
  var e = this;
  this.log_("Listen on " + a + " for " + b);
  var f = {p:a};
  c = goog.array.map(c, function(a) {
    return a.queryObject();
  });
  "{}" !== b && (f.q = c);
  f.h = this.getServerDataHashForPath_(a);
  this.sendRequest_("l", f, function(c) {
    e.log_("listen response", c);
    c = c.s;
    "ok" !== c && e.removeListen_(a, b);
    d && d(c);
  });
};
fb.core.PersistentConnection.prototype.auth = function(a, b, c) {
  this.credential_ = {cred:a, firstRequestSent:!1, callback:b, cancelCallback:c};
  this.log_("Authenticating using credential: " + this.credential_);
  this.tryAuth();
  this.reduceReconnectDelayIfAdminCredential_(a);
};
fb.core.PersistentConnection.prototype.reduceReconnectDelayIfAdminCredential_ = function(a) {
  if (40 == a.length || this.isAdminAuthToken_(a)) {
    this.log_("Admin auth credential detected.  Reducing max reconnect time."), this.maxReconnectDelay_ = RECONNECT_MAX_DELAY_FOR_ADMINS;
  }
};
fb.core.PersistentConnection.prototype.isAdminAuthToken_ = function(a) {
  var b;
  try {
    var c = a.split(".");
    if (3 !== c.length) {
      return!1;
    }
    var d = fb.core.util.base64DecodeIfNativeSupport(c[1]);
    null !== d && (b = fb.util.json.eval(d));
  } catch (e) {
    fb.core.util.log("isAdminAuthToken_ failed", e);
  }
  return "object" === typeof b && !0 === fb.util.obj.get(b, "admin");
};
fb.core.PersistentConnection.prototype.unauth = function(a) {
  delete this.credential_;
  this.onAuthStatus_(!1);
  this.connected_ && this.sendRequest_("unauth", {}, function(b) {
    a(b.s, b.d);
  });
};
fb.core.PersistentConnection.prototype.tryAuth = function() {
  var a = this.credential_, b = this;
  this.connected_ && a && this.sendRequest_("auth", {cred:a.cred}, function(c) {
    var d = c.s;
    c = c.d || "error";
    "ok" !== d && b.credential_ === a && delete b.credential_;
    b.onAuthStatus_("ok" === d);
    a.firstRequestSent ? "ok" !== d && a.cancelCallback && a.cancelCallback(d, c) : (a.firstRequestSent = !0, a.callback && a.callback(d, c));
  });
};
fb.core.PersistentConnection.prototype.unlisten = function(a, b, c) {
  a = a.toString();
  this.removeListen_(a, b) && this.connected_ && this.sendUnlisten_(a, b, c);
};
fb.core.PersistentConnection.prototype.sendUnlisten_ = function(a, b, c) {
  this.log_("Unlisten on " + a + " for " + b);
  a = {p:a};
  c = goog.array.map(c, function(a) {
    return a.queryObject();
  });
  "{}" !== b && (a.q = c);
  this.sendRequest_("u", a);
};
fb.core.PersistentConnection.prototype.onDisconnectPut = function(a, b, c) {
  this.connected_ ? this.sendOnDisconnect_("o", a, b, c) : this.onDisconnectRequestQueue_.push({pathString:a, action:"o", data:b, onComplete:c});
};
fb.core.PersistentConnection.prototype.onDisconnectMerge = function(a, b, c) {
  this.connected_ ? this.sendOnDisconnect_("om", a, b, c) : this.onDisconnectRequestQueue_.push({pathString:a, action:"om", data:b, onComplete:c});
};
fb.core.PersistentConnection.prototype.onDisconnectCancel = function(a, b) {
  this.connected_ ? this.sendOnDisconnect_("oc", a, null, b) : this.onDisconnectRequestQueue_.push({pathString:a, action:"oc", data:null, onComplete:b});
};
fb.core.PersistentConnection.prototype.sendOnDisconnect_ = function(a, b, c, d) {
  b = {p:b, d:c};
  this.log_("onDisconnect " + a, b);
  this.sendRequest_(a, b, function(a) {
    d && setTimeout(function() {
      d(a.s, a.d);
    }, 0);
  });
};
fb.core.PersistentConnection.prototype.put = function(a, b, c, d) {
  this.putInternal("p", a, b, c, d);
};
fb.core.PersistentConnection.prototype.merge = function(a, b, c, d) {
  this.putInternal("m", a, b, c, d);
};
fb.core.PersistentConnection.prototype.putInternal = function(a, b, c, d, e) {
  b = {p:b, d:c};
  goog.isDef(e) && (b.h = e);
  this.outstandingPuts_.push({action:a, request:b, onComplete:d});
  this.outstandingPutCount_++;
  a = this.outstandingPuts_.length - 1;
  this.connected_ && this.sendPut_(a);
};
fb.core.PersistentConnection.prototype.sendPut_ = function(a) {
  var b = this, c = this.outstandingPuts_[a].action, d = this.outstandingPuts_[a].request, e = this.outstandingPuts_[a].onComplete;
  this.outstandingPuts_[a].queued = this.connected_;
  this.sendRequest_(c, d, function(d) {
    b.log_(c + " response", d);
    delete b.outstandingPuts_[a];
    b.outstandingPutCount_--;
    0 === b.outstandingPutCount_ && (b.outstandingPuts_ = []);
    e && e(d.s, d.d);
  });
};
fb.core.PersistentConnection.prototype.reportStats = function(a) {
  this.connected_ && (a = {c:a}, this.log_("reportStats", a), this.sendRequest_("s", a));
};
fb.core.PersistentConnection.prototype.onDataMessage_ = function(a) {
  if ("r" in a) {
    this.log_("from server: " + fb.util.json.stringify(a));
    var b = a.r, c = this.requestCBHash_[b];
    c && (delete this.requestCBHash_[b], c(a.b));
  } else {
    if ("error" in a) {
      throw "A server-side error has occurred: " + a.error;
    }
    if ("a" in a) {
      this.onDataPush_(a.a, a.b);
    }
  }
};
fb.core.PersistentConnection.prototype.onDataPush_ = function(a, b) {
  this.log_("handleServerMessage", a, b);
  if ("d" === a) {
    this.onDataUpdate_(b.p, b.d, !1);
  } else {
    if ("m" === a) {
      this.onDataUpdate_(b.p, b.d, !0);
    } else {
      if ("c" === a) {
        this.onListenRevoked_(b.p, b.q);
      } else {
        if ("ac" === a) {
          this.onAuthRevoked_(b.s, b.d);
        } else {
          if ("sd" === a) {
            this.onSecurityDebugPacket_(b);
          } else {
            fb.core.util.error("Unrecognized action received from server: " + fb.util.json.stringify(a) + "\nAre you using the latest client?");
          }
        }
      }
    }
  }
};
fb.core.PersistentConnection.prototype.onReady_ = function(a) {
  this.log_("connection ready");
  this.connected_ = !0;
  this.lastConnectionEstablishedTime_ = (new Date).getTime();
  this.handleTimestamp_(a);
  this.restoreState_();
  this.onConnectStatus_(!0);
};
fb.core.PersistentConnection.prototype.scheduleConnect_ = function(a) {
  fb.core.util.assert(!this.realtime_, "Scheduling a connect when we're already connected/ing?");
  this.establishConnectionTimer_ && clearTimeout(this.establishConnectionTimer_);
  var b = this;
  this.establishConnectionTimer_ = setTimeout(function() {
    b.establishConnectionTimer_ = null;
    b.establishConnection_();
  }, a);
};
fb.core.PersistentConnection.prototype.onVisible_ = function(a) {
  a && !this.visible_ && this.reconnectDelay_ === this.maxReconnectDelay_ && (this.log_("Window became visible.  Reducing delay."), this.reconnectDelay_ = RECONNECT_MIN_DELAY, this.realtime_ || this.scheduleConnect_(0));
  this.visible_ = a;
};
fb.core.PersistentConnection.prototype.onOnline_ = function(a) {
  a ? (this.log_("Browser went online.  Reconnecting."), this.reconnectDelay_ = RECONNECT_MIN_DELAY, this.shouldReconnect_ = !0, this.realtime_ || this.scheduleConnect_(0)) : (this.log_("Browser went offline.  Killing connection; don't reconnect."), this.shouldReconnect_ = !1, this.realtime_ && this.realtime_.close());
};
fb.core.PersistentConnection.prototype.onRealtimeDisconnect_ = function() {
  this.log_("data client disconnected");
  this.connected_ = !1;
  this.realtime_ = null;
  this.cancelSentTransactions_();
  if (this.shouldReconnect_) {
    this.visible_ ? this.lastConnectionEstablishedTime_ && ((new Date).getTime() - this.lastConnectionEstablishedTime_ > RECONNECT_DELAY_RESET_TIMEOUT && (this.reconnectDelay_ = RECONNECT_MIN_DELAY), this.lastConnectionEstablishedTime_ = null) : (this.log_("Window isn't visible.  Delaying reconnect."), this.reconnectDelay_ = this.maxReconnectDelay_, this.lastConnectionAttemptTime_ = (new Date).getTime());
    var a = (new Date).getTime() - this.lastConnectionAttemptTime_, a = Math.max(0, this.reconnectDelay_ - a), a = Math.random() * a;
    this.log_("Trying to reconnect in " + a + "ms");
    this.scheduleConnect_(a);
    this.reconnectDelay_ = Math.min(this.maxReconnectDelay_, this.reconnectDelay_ * RECONNECT_DELAY_MULTIPLIER);
  } else {
    for (a in this.requestCBHash_) {
      delete this.requestCBHash_[a];
    }
  }
  this.onConnectStatus_(!1);
};
fb.core.PersistentConnection.prototype.establishConnection_ = function() {
  if (this.shouldReconnect_) {
    this.log_("Making a connection attempt");
    this.lastConnectionAttemptTime_ = (new Date).getTime();
    this.lastConnectionEstablishedTime_ = null;
    var a = goog.bind(this.onDataMessage_, this), b = goog.bind(this.onReady_, this), c = goog.bind(this.onRealtimeDisconnect_, this), d = this.id + ":" + fb.core.PersistentConnection.nextConnectionId_++, e = this;
    this.realtime_ = new fb.realtime.Connection(d, this.repoInfo_, a, b, c, function(a) {
      fb.core.util.warn(a + " (" + e.repoInfo_.toString() + ")");
      e.shouldReconnect_ = !1;
    });
  }
};
fb.core.PersistentConnection.prototype.interrupt = function() {
  this.shouldReconnect_ = !1;
  if (this.realtime_) {
    this.realtime_.close();
  } else {
    if (this.establishConnectionTimer_ && (clearTimeout(this.establishConnectionTimer_), this.establishConnectionTimer_ = null), this.connected_) {
      this.onRealtimeDisconnect_();
    }
  }
};
fb.core.PersistentConnection.prototype.resume = function() {
  this.shouldReconnect_ = !0;
  this.reconnectDelay_ = RECONNECT_MIN_DELAY;
  this.connected_ || this.scheduleConnect_(0);
};
fb.core.PersistentConnection.prototype.handleTimestamp_ = function(a) {
  a -= (new Date).getTime();
  this.onServerInfoUpdate_({serverTimeOffset:a});
};
fb.core.PersistentConnection.prototype.cancelSentTransactions_ = function() {
  for (var a = 0;a < this.outstandingPuts_.length;a++) {
    var b = this.outstandingPuts_[a];
    if (b && "h" in b.request && b.queued) {
      if (b.onComplete) {
        b.onComplete("disconnect");
      }
      delete this.outstandingPuts_[a];
      this.outstandingPutCount_--;
    }
  }
  0 === this.outstandingPutCount_ && (this.outstandingPuts_ = []);
};
fb.core.PersistentConnection.prototype.onListenRevoked_ = function(a, b) {
  var c;
  c = b ? goog.array.map(b, function(a) {
    return fb.core.util.ObjectToUniqueKey(a);
  }).join("$") : "{}";
  if ((c = this.removeListen_(a, c)) && c.onComplete) {
    c.onComplete("permission_denied");
  }
};
fb.core.PersistentConnection.prototype.removeListen_ = function(a, b) {
  var c = (new fb.core.util.Path(a)).toString();
  b || (b = "{}");
  var d = this.listens_[c][b];
  delete this.listens_[c][b];
  return d;
};
fb.core.PersistentConnection.prototype.onAuthRevoked_ = function(a, b) {
  var c = this.credential_;
  delete this.credential_;
  c && c.cancelCallback && c.cancelCallback(a, b);
  this.onAuthStatus_(!1);
};
fb.core.PersistentConnection.prototype.onSecurityDebugPacket_ = function(a) {
  this.securityDebugCallback_ ? this.securityDebugCallback_(a) : "msg" in a && "undefined" !== typeof console && console.log("FIREBASE: " + a.msg.replace("\n", "\nFIREBASE: "));
};
fb.core.PersistentConnection.prototype.restoreState_ = function() {
  this.tryAuth();
  for (var a in this.listens_) {
    for (var b in this.listens_[a]) {
      var c = this.listens_[a][b];
      this.sendListen_(a, b, c.queries, c.onComplete);
    }
  }
  for (a = 0;a < this.outstandingPuts_.length;a++) {
    this.outstandingPuts_[a] && this.sendPut_(a);
  }
  for (;this.onDisconnectRequestQueue_.length;) {
    a = this.onDisconnectRequestQueue_.shift(), this.sendOnDisconnect_(a.action, a.pathString, a.data, a.onComplete);
  }
};
fb.core.snap.Node = function() {
};
fb.core.SparseSnapshotTree = function() {
  this.children_ = this.value_ = null;
};
fb.core.SparseSnapshotTree.prototype.find = function(a) {
  if (null != this.value_) {
    return this.value_.getChild(a);
  }
  if (a.isEmpty() || null == this.children_) {
    return null;
  }
  var b = a.getFront();
  a = a.popFront();
  return this.children_.contains(b) ? this.children_.get(b).find(a) : null;
};
fb.core.SparseSnapshotTree.prototype.remember = function(a, b) {
  if (a.isEmpty()) {
    this.value_ = b, this.children_ = null;
  } else {
    if (null !== this.value_) {
      this.value_ = this.value_.updateChild(a, b);
    } else {
      null == this.children_ && (this.children_ = new fb.core.util.CountedSet);
      var c = a.getFront();
      this.children_.contains(c) || this.children_.add(c, new fb.core.SparseSnapshotTree);
      c = this.children_.get(c);
      a = a.popFront();
      c.remember(a, b);
    }
  }
};
fb.core.SparseSnapshotTree.prototype.forget = function(a) {
  if (a.isEmpty()) {
    return this.children_ = this.value_ = null, !0;
  }
  if (null !== this.value_) {
    if (this.value_.isLeafNode()) {
      return!1;
    }
    var b = this.value_;
    this.value_ = null;
    var c = this;
    b.forEachChild(function(a, b) {
      c.remember(new fb.core.util.Path(a), b);
    });
    return this.forget(a);
  }
  return null !== this.children_ ? (b = a.getFront(), a = a.popFront(), this.children_.contains(b) && this.children_.get(b).forget(a) && this.children_.remove(b), this.children_.isEmpty() ? (this.children_ = null, !0) : !1) : !0;
};
fb.core.SparseSnapshotTree.prototype.forEachTree = function(a, b) {
  null !== this.value_ ? b(a, this.value_) : this.forEachChild(function(c, d) {
    var e = new fb.core.util.Path(a.toString() + "/" + c);
    d.forEachTree(e, b);
  });
};
fb.core.SparseSnapshotTree.prototype.forEachChild = function(a) {
  null !== this.children_ && this.children_.each(function(b, c) {
    a(b, c);
  });
};
fb.core.SnapshotHolder = function() {
  this.rootNode_ = fb.core.snap.EMPTY_NODE;
};
fb.core.SnapshotHolder.prototype.getNode = function(a) {
  return this.rootNode_.getChild(a);
};
fb.core.SnapshotHolder.prototype.updateSnapshot = function(a, b) {
  this.rootNode_ = this.rootNode_.updateChild(a, b);
};
goog.DEBUG && (fb.core.SnapshotHolder.prototype.toString = function() {
  return this.rootNode_.toString();
});
fb.core.FirebaseData = function() {
  this.serverData = new fb.core.SnapshotHolder;
  this.mergedData = new fb.core.SnapshotHolder;
  this.visibleData = new fb.core.SnapshotHolder;
  this.pendingPuts = new fb.core.util.Tree;
};
fb.core.FirebaseData.prototype.updateServerData = function(a, b) {
  this.serverData.updateSnapshot(a, b);
  return this.mergeServerAndPendingData(a);
};
fb.core.FirebaseData.prototype.mergeServerAndPendingData = function(a) {
  for (var b = this.serverData.getNode(a), c = this.mergedData.getNode(a), d = this.pendingPuts.subTree(a), e = !1, f = d;null !== f;) {
    if (null !== f.getValue()) {
      e = !0;
      break;
    }
    f = f.parent();
  }
  if (e) {
    return!1;
  }
  b = fb.core.FirebaseData.mergeSnapshotNodes_(b, c, d);
  return b !== c ? (this.mergedData.updateSnapshot(a, b), !0) : !1;
};
fb.core.FirebaseData.mergeSnapshotNodes_ = function(a, b, c) {
  if (c.isEmpty()) {
    return a;
  }
  if (null !== c.getValue()) {
    return b;
  }
  a = a || fb.core.snap.EMPTY_NODE;
  c.forEachChild(function(d) {
    d = d.name();
    var e = a.getImmediateChild(d), f = b.getImmediateChild(d), g = c.subTree(d), e = fb.core.FirebaseData.mergeSnapshotNodes_(e, f, g);
    a = a.updateImmediateChild(d, e);
  });
  return a;
};
fb.core.FirebaseData.prototype.set = function(a, b) {
  var c = this, d = [];
  goog.array.forEach(b, function(a) {
    var b = a.path;
    a = a.node;
    var g = fb.core.util.LUIDGenerator();
    c.pendingPuts.subTree(b).setValue(g);
    c.mergedData.updateSnapshot(b, a);
    d.push({path:b, setId:g});
  });
  return d;
};
fb.core.FirebaseData.prototype.setCompleted = function(a) {
  var b = this;
  goog.array.forEach(a, function(a) {
    var d = a.setId;
    a = b.pendingPuts.subTree(a.path);
    var e = a.getValue();
    fb.core.util.assert(null !== e, "pendingPut should not be null.");
    e === d && a.setValue(null);
  });
};
fb.core.FirebaseData.prototype.forgetPath = function(a, b) {
  for (var c = [], d = 0;d < b.length;++d) {
    c[d] = this.serverData.getNode(b[d]);
  }
  this.serverData.updateSnapshot(a, fb.core.snap.EMPTY_NODE);
  for (d = 0;d < b.length;++d) {
    this.serverData.updateSnapshot(b[d], c[d]);
  }
  return this.mergeServerAndPendingData(a);
};
fb.core.util.ServerValues = {};
fb.core.util.ServerValues.generateWithValues = function(a) {
  a = a || {};
  a.timestamp = a.timestamp || (new Date).getTime();
  return a;
};
fb.core.util.ServerValues.resolveDeferredValue = function(a, b) {
  return a && "object" === typeof a ? (fb.core.util.assert(".sv" in a, "Unexpected leaf node or priority contents"), b[a[".sv"]]) : a;
};
fb.core.util.ServerValues.resolveDeferredValueTree = function(a, b) {
  var c = new fb.core.SparseSnapshotTree;
  a.forEachTree(new fb.core.util.Path(""), function(a, e) {
    c.remember(a, fb.core.util.ServerValues.resolveDeferredValueSnapshot(e, b));
  });
  return c;
};
fb.core.util.ServerValues.resolveDeferredValueSnapshot = function(a, b) {
  var c = fb.core.util.ServerValues.resolveDeferredValue(a.getPriority(), b), d;
  if (a.isLeafNode()) {
    var e = fb.core.util.ServerValues.resolveDeferredValue(a.getValue(), b);
    return e !== a.getValue() || c !== a.getPriority() ? new fb.core.snap.LeafNode(e, c) : a;
  }
  d = a;
  c !== a.getPriority() && (d = d.updatePriority(c));
  a.forEachChild(function(a, c) {
    var e = fb.core.util.ServerValues.resolveDeferredValueSnapshot(c, b);
    e !== c && (d = d.updateImmediateChild(a, e));
  });
  return d;
};
fb.core.view = {};
fb.core.view.EventQueue = function() {
  this.events = [];
};
fb.core.view.EventQueue.prototype.queueEvents = function(a) {
  if (0 !== a.length) {
    for (var b = 0;b < a.length;b++) {
      this.events.push(a[b]);
    }
  }
};
fb.core.view.EventQueue.prototype.raiseQueuedEvents = function() {
  for (var a = 0;a < this.events.length;a++) {
    if (this.events[a]) {
      var b = this.events[a];
      this.events[a] = null;
      this.raiseEvent_(b);
    }
  }
  this.events = [];
};
fb.core.view.EventQueue.prototype.raiseEvent_ = function(a) {
  var b = a.callback, c = a.snapshot, d = a.prevName;
  fb.core.util.exceptionGuard(function() {
    b(c, d);
  });
};
fb.core.view.Change = function(a, b, c, d) {
  this.type = a;
  this.snapshotNode = b;
  this.childName = c;
  this.prevName = d;
};
fb.core.view.Change.CHILD_ADDED = "child_added";
fb.core.view.Change.CHILD_REMOVED = "child_removed";
fb.core.view.Change.CHILD_CHANGED = "child_changed";
fb.core.view.Change.CHILD_MOVED = "child_moved";
fb.core.view.Change.VALUE = "value";
fb.core.view.ViewBase = function(a) {
  this.query_ = a;
  this.callbacks_ = [];
  this.eventQueue_ = new fb.core.view.EventQueue;
};
fb.core.view.ViewBase.prototype.getQuery = function() {
  return this.query_;
};
fb.core.view.ViewBase.prototype.addEventCallback = function(a, b, c, d) {
  this.callbacks_.push({type:a, callback:b, cancel:c, context:d});
  c = [];
  var e = this.generateChangesForSnapshot(this.snapshotNode_);
  this.isComplete_ && e.push(new fb.core.view.Change("value", this.snapshotNode_));
  for (var f = 0;f < e.length;f++) {
    if (e[f].type === a) {
      var g = new Firebase(this.query_.repo, this.query_.path);
      e[f].childName && (g = g.child(e[f].childName));
      c.push({callback:fb.core.util.bindCallback(b, d), snapshot:new fb.api.DataSnapshot(e[f].snapshotNode, g), prevName:e[f].prevName});
    }
  }
  this.eventQueue_.queueEvents(c);
};
fb.core.view.ViewBase.prototype.removeEventCallback = function(a, b, c) {
  for (var d = !1, e = this.callbacks_.length - 1;0 <= e;e--) {
    var f = this.callbacks_[e];
    if (!(a && f.type !== a || b && f.callback !== b || c && f.context !== c) && (this.callbacks_.splice(e, 1), d = !0, a && b)) {
      break;
    }
  }
  return d;
};
fb.core.view.ViewBase.prototype.hasCallbacks = function() {
  return 0 < this.callbacks_.length;
};
fb.core.view.ViewBase.prototype.processChanges = function(a, b) {
  b = this.processChanges_(a, b);
  null != b && this.queueEventsForChanges_(b);
};
fb.core.view.ViewBase.prototype.raiseCancelEvents = function(a) {
  for (var b = 0;b < this.callbacks_.length;b++) {
    var c = this.callbacks_[b];
    c.cancel && fb.core.util.bindCallback(c.cancel, c.context)(a);
  }
};
fb.core.view.ViewBase.prototype.queueEventsForChanges_ = function(a) {
  for (var b = [], c = 0;c < a.length;c++) {
    var d = a[c], e = d.type, f = new Firebase(this.query_.repo, this.query_.path);
    a[c].childName && (f = f.child(a[c].childName));
    f = new fb.api.DataSnapshot(a[c].snapshotNode, f);
    "value" !== d.type || f.hasChildren() ? "value" !== d.type && (e += " " + f.name()) : e += "(" + f.val() + ")";
    fb.core.util.log(this.query_.repo.connection_.id + ": event:" + this.query_.path + ":" + this.query_.queryIdentifier() + ":" + e);
    for (e = 0;e < this.callbacks_.length;e++) {
      var g = this.callbacks_[e];
      a[c].type === g.type && b.push({callback:fb.core.util.bindCallback(g.callback, g.context), snapshot:f, prevName:d.prevName});
    }
  }
  this.eventQueue_.queueEvents(b);
};
fb.core.view.ViewBase.prototype.raiseQueuedEvents = function() {
  this.eventQueue_.raiseQueuedEvents();
};
fb.core.view.ViewBase.prototype.generateChangesForSnapshot = function(a) {
  var b = [];
  if (!a.isLeafNode()) {
    var c = null;
    a.forEachChild(function(a, e) {
      b.push(new fb.core.view.Change(fb.core.view.Change.CHILD_ADDED, e, a, c));
      c = a;
    });
  }
  return b;
};
fb.core.view.ViewBase.prototype.isComplete = function() {
  return this.isComplete_;
};
fb.core.view.ViewBase.prototype.markComplete = function() {
  this.isComplete_ || (this.isComplete_ = !0, this.queueEventsForChanges_([new fb.core.view.Change("value", this.snapshotNode_)]));
};
fb.core.view.DefaultView = function(a, b) {
  fb.core.view.ViewBase.call(this, a);
  this.snapshotNode_ = b;
};
goog.inherits(fb.core.view.DefaultView, fb.core.view.ViewBase);
fb.core.view.DefaultView.prototype.processChanges_ = function(a, b) {
  this.snapshotNode_ = a;
  this.isComplete_ && null != b && b.push(new fb.core.view.Change("value", this.snapshotNode_));
  return b;
};
fb.core.view.DefaultView.prototype.getChildRelevance = function(a, b, c) {
  return{};
};
fb.core.view.SnapshotDiffer = function(a, b) {
  this.diffMaskTree_ = a;
  this.onDiffCallback_ = b;
};
fb.core.view.SnapshotDiffer.Diff = function(a, b, c, d, e) {
  var f = a.getChild(c), g = b.getChild(c);
  d = new fb.core.view.SnapshotDiffer(d, e);
  e = d.diffRecursive_(c, f, g);
  f = !f.isEmpty() && !g.isEmpty() && f.getPriority() !== g.getPriority();
  (e || f) && d.propagateDiffUpward_(c, a, b, e, f);
};
fb.core.view.SnapshotDiffer.prototype.propagateDiffUpward_ = function(a, b, c, d, e) {
  for (;null !== a.parent();) {
    var f = b.getChild(a), g = c.getChild(a), h = a.parent();
    if (!this.diffMaskTree_ || this.diffMaskTree_.subTree(h).getValue()) {
      var k = c.getChild(h), l = [];
      a = a.getBack();
      f.isEmpty() ? (f = k.getPredecessorChildName(a, g), l.push(new fb.core.view.Change("child_added", g, a, f))) : g.isEmpty() ? l.push(new fb.core.view.Change("child_removed", f, a)) : (f = k.getPredecessorChildName(a, g), e && l.push(new fb.core.view.Change("child_moved", g, a, f)), d && l.push(new fb.core.view.Change("child_changed", g, a, f)));
      this.onDiffCallback_(h, k, l);
    }
    e && (e = !1, d = !0);
    a = h;
  }
};
fb.core.view.SnapshotDiffer.prototype.diffRecursive_ = function(a, b, c) {
  var d, e = [];
  b === c ? d = !1 : b.isLeafNode() && c.isLeafNode() ? d = b.getValue() !== c.getValue() : b.isLeafNode() ? (this.diffChildrenRecursive_(a, fb.core.snap.EMPTY_NODE, c, e), d = !0) : c.isLeafNode() ? (this.diffChildrenRecursive_(a, b, fb.core.snap.EMPTY_NODE, e), d = !0) : d = this.diffChildrenRecursive_(a, b, c, e);
  if (d) {
    this.onDiffCallback_(a, c, e);
  } else {
    if (b.getPriority() !== c.getPriority()) {
      this.onDiffCallback_(a, c, null);
    }
  }
  return d;
};
fb.core.view.SnapshotDiffer.prototype.diffChildrenRecursive_ = function(a, b, c, d) {
  var e = !1, f = !this.diffMaskTree_ || !this.diffMaskTree_.subTree(a).isEmpty(), g = [], h = [], k = [], l = [], m = {}, p = {}, n, q, r, s;
  n = b.getIterator();
  r = n.getNext();
  q = c.getIterator();
  for (s = q.getNext();null !== r || null !== s;) {
    b = this.compareChildren_(r, s);
    if (0 > b) {
      e = fb.util.obj.get(m, r.key), goog.isDef(e) ? (k.push({from:r, to:g[e]}), g[e] = null) : (p[r.key] = h.length, h.push(r)), e = !0, r = n.getNext();
    } else {
      if (0 < b) {
        e = fb.util.obj.get(p, s.key), goog.isDef(e) ? (k.push({from:h[e], to:s}), h[e] = null) : (m[s.key] = g.length, g.push(s)), e = !0;
      } else {
        b = a.child(s.key);
        if (b = this.diffRecursive_(b, r.value, s.value)) {
          l.push(s), e = !0;
        }
        r.value.getPriority() !== s.value.getPriority() && (k.push({from:r, to:s}), e = !0);
        r = n.getNext();
      }
      s = q.getNext();
    }
    if (!f && e) {
      return!0;
    }
  }
  for (f = 0;f < h.length;f++) {
    if (m = h[f]) {
      b = a.child(m.key), this.diffRecursive_(b, m.value, fb.core.snap.EMPTY_NODE), d.push(new fb.core.view.Change("child_removed", m.value, m.key));
    }
  }
  for (f = 0;f < g.length;f++) {
    if (m = g[f]) {
      b = a.child(m.key), h = c.getPredecessorChildName(m.key, m.value), this.diffRecursive_(b, fb.core.snap.EMPTY_NODE, m.value), d.push(new fb.core.view.Change("child_added", m.value, m.key, h));
    }
  }
  for (f = 0;f < k.length;f++) {
    m = k[f].from, g = k[f].to, b = a.child(g.key), h = c.getPredecessorChildName(g.key, g.value), d.push(new fb.core.view.Change("child_moved", g.value, g.key, h)), (b = this.diffRecursive_(b, m.value, g.value)) && l.push(g);
  }
  for (f = 0;f < l.length;f++) {
    a = l[f], h = c.getPredecessorChildName(a.key, a.value), d.push(new fb.core.view.Change("child_changed", a.value, a.key, h));
  }
  return e;
};
fb.core.view.SnapshotDiffer.prototype.compareChildren_ = function(a, b) {
  return null === a ? 1 : null === b ? -1 : a.key === b.key ? 0 : fb.core.snap.NAME_AND_PRIORITY_COMPARATOR({name:a.key, priority:a.value.getPriority()}, {name:b.key, priority:b.value.getPriority()});
};
fb.core.view.QueryMap = function() {
  this.path_ = this.stopListener_ = null;
  fb.core.util.CountedSet.call(this);
};
goog.inherits(fb.core.view.QueryMap, fb.core.util.CountedSet);
fb.core.view.QueryMap.prototype.setActive = function(a) {
  this.stopListener_ = a;
};
fb.core.view.QueryMap.prototype.isActive = function() {
  return null != this.stopListener_;
};
fb.core.view.QueryMap.prototype.setView = function(a, b) {
  this.add(a, b);
  this.path_ || (this.path_ = b.getQuery().path);
};
fb.core.view.QueryMap.prototype.deactivate = function() {
  this.stopListener_ && this.stopListener_();
  this.stopListener_ = null;
};
fb.core.view.QueryMap.prototype.removeStopListener = function() {
  var a = this.stopListener_;
  this.stopListener_ = null;
  return a;
};
fb.core.view.QueryMap.prototype.hasDefaultQuery = function() {
  return this.contains("default");
};
fb.core.view.QueryMap.prototype.hasActiveDefaultQuery = function() {
  return null != this.stopListener_ && this.hasDefaultQuery();
};
fb.core.view.QueryMap.prototype.defaultView = function() {
  return this.hasDefaultQuery() ? this.get("default") : null;
};
fb.core.view.QueryMap.prototype.path = function() {
  return this.path_;
};
fb.core.view.QueryMap.prototype.toString = function() {
  return goog.array.map(this.keys(), function(a) {
    return "default" === a ? "{}" : a;
  }).join("$");
};
fb.core.view.QueryMap.prototype.queries = function() {
  var a = [];
  this.each(function(b, c) {
    a.push(c.getQuery());
  });
  return a;
};
fb.core.view.QueryView = function(a, b) {
  fb.core.view.ViewBase.call(this, a);
  this.snapshotNode_ = fb.core.snap.EMPTY_NODE;
  this.processChanges_(b, this.generateChangesForSnapshot(b));
};
goog.inherits(fb.core.view.QueryView, fb.core.view.ViewBase);
fb.core.view.QueryView.prototype.processChanges_ = function(a, b) {
  if (null === b) {
    return b;
  }
  var c = [], d = this.query_;
  goog.isDef(d.startPriority) && (goog.isDef(d.startName) && null != d.startName ? c.push(function(a, b) {
    var c = fb.core.util.priorityCompare(b, d.startPriority);
    return 0 < c || 0 === c && 0 <= fb.core.util.nameCompare(a, d.startName);
  }) : c.push(function(a, b) {
    return 0 <= fb.core.util.priorityCompare(b, d.startPriority);
  }));
  goog.isDef(d.endPriority) && (goog.isDef(d.endName) ? c.push(function(a, b) {
    var c = fb.core.util.priorityCompare(b, d.endPriority);
    return 0 > c || 0 === c && 0 >= fb.core.util.nameCompare(a, d.endName);
  }) : c.push(function(a, b) {
    return 0 >= fb.core.util.priorityCompare(b, d.endPriority);
  }));
  var e = null, f = null;
  if (goog.isDef(this.query_.itemLimit)) {
    if (goog.isDef(this.query_.startPriority)) {
      if (e = this.getLimitName_(a, c, this.query_.itemLimit, !1)) {
        var g = a.getImmediateChild(e).getPriority();
        c.push(function(a, b) {
          var c = fb.core.util.priorityCompare(b, g);
          return 0 > c || 0 === c && 0 >= fb.core.util.nameCompare(a, e);
        });
      }
    } else {
      if (f = this.getLimitName_(a, c, this.query_.itemLimit, !0)) {
        var h = a.getImmediateChild(f).getPriority();
        c.push(function(a, b) {
          var c = fb.core.util.priorityCompare(b, h);
          return 0 < c || 0 === c && 0 <= fb.core.util.nameCompare(a, f);
        });
      }
    }
  }
  for (var k = [], l = [], m = [], p = [], n = 0;n < b.length;n++) {
    var q = b[n].childName, r = b[n].snapshotNode;
    switch(b[n].type) {
      case fb.core.view.Change.CHILD_ADDED:
        this.meetsConstraints_(c, q, r) && (this.snapshotNode_ = this.snapshotNode_.updateImmediateChild(q, r), l.push(b[n]));
        break;
      case fb.core.view.Change.CHILD_REMOVED:
        this.snapshotNode_.getImmediateChild(q).isEmpty() || (this.snapshotNode_ = this.snapshotNode_.updateImmediateChild(q, null), k.push(b[n]));
        break;
      case fb.core.view.Change.CHILD_CHANGED:
        !this.snapshotNode_.getImmediateChild(q).isEmpty() && this.meetsConstraints_(c, q, r) && (this.snapshotNode_ = this.snapshotNode_.updateImmediateChild(q, r), p.push(b[n]));
        break;
      case fb.core.view.Change.CHILD_MOVED:
        var s = !this.snapshotNode_.getImmediateChild(q).isEmpty(), w = this.meetsConstraints_(c, q, r);
        s ? w ? (this.snapshotNode_ = this.snapshotNode_.updateImmediateChild(q, r), m.push(b[n])) : (k.push(new fb.core.view.Change("child_removed", this.snapshotNode_.getImmediateChild(q), q)), this.snapshotNode_ = this.snapshotNode_.updateImmediateChild(q, null)) : w && (this.snapshotNode_ = this.snapshotNode_.updateImmediateChild(q, r), l.push(b[n]));
    }
  }
  var x = e || f;
  if (x) {
    var y = (n = null !== f) ? this.snapshotNode_.getFirstChildName() : this.snapshotNode_.getLastChildName(), v = !1, t = !1, u = this;
    (n ? a.forEachChildReverse : a.forEachChild).call(a, function(a, b) {
      t || null !== y || (t = !0);
      if (t && v) {
        return!0;
      }
      v ? (k.push(new fb.core.view.Change("child_removed", u.snapshotNode_.getImmediateChild(a), a)), u.snapshotNode_ = u.snapshotNode_.updateImmediateChild(a, null)) : t && (l.push(new fb.core.view.Change("child_added", b, a)), u.snapshotNode_ = u.snapshotNode_.updateImmediateChild(a, b));
      y === a && (t = !0);
      a === x && (v = !0);
    });
  }
  for (n = 0;n < l.length;n++) {
    c = l[n], q = this.snapshotNode_.getPredecessorChildName(c.childName, c.snapshotNode), k.push(new fb.core.view.Change("child_added", c.snapshotNode, c.childName, q));
  }
  for (n = 0;n < m.length;n++) {
    c = m[n], q = this.snapshotNode_.getPredecessorChildName(c.childName, c.snapshotNode), k.push(new fb.core.view.Change("child_moved", c.snapshotNode, c.childName, q));
  }
  for (n = 0;n < p.length;n++) {
    c = p[n], q = this.snapshotNode_.getPredecessorChildName(c.childName, c.snapshotNode), k.push(new fb.core.view.Change("child_changed", c.snapshotNode, c.childName, q));
  }
  this.isComplete_ && 0 < k.length && k.push(new fb.core.view.Change("value", this.snapshotNode_));
  return k;
};
fb.core.view.QueryView.prototype.getLimitName_ = function(a, b, c, d) {
  if (a.isLeafNode()) {
    return null;
  }
  var e = this, f = null;
  (d ? a.forEachChildReverse : a.forEachChild).call(a, function(a, d) {
    if (e.meetsConstraints_(b, a, d) && (f = a, c--, 0 === c)) {
      return!0;
    }
  });
  return f;
};
fb.core.view.QueryView.prototype.meetsConstraints_ = function(a, b, c) {
  for (var d = 0;d < a.length;d++) {
    if (!a[d](b, c.getPriority())) {
      return!1;
    }
  }
  return!0;
};
fb.core.view.QueryView.prototype.hasChild = function(a) {
  return this.snapshotNode_.getImmediateChild(a) !== fb.core.snap.EMPTY_NODE;
};
fb.core.view.QueryView.ENTERING_VIEW = 1;
fb.core.view.QueryView.LEAVING_VIEW = 2;
fb.core.view.QueryView.IN_VIEW = 3;
fb.core.view.QueryView.OUT_OF_VIEW = 4;
fb.core.view.QueryView.prototype.getChildRelevance = function(a, b, c) {
  var d = {};
  this.snapshotNode_.isLeafNode() || this.snapshotNode_.forEachChild(function(a) {
    d[a] = fb.core.view.QueryView.IN_VIEW;
  });
  var e = this.snapshotNode_;
  c = c.getNode(new fb.core.util.Path(""));
  var f = new fb.core.util.Tree;
  f.subTree(this.query_.path).setValue(!0);
  b = fb.core.snap.EMPTY_NODE.updateChild(a, b);
  var g = this;
  fb.core.view.SnapshotDiffer.Diff(c, b, a, f, function(a, b, c) {
    null !== c && a.toString() === g.query_.path.toString() && g.processChanges_(b, c);
  });
  this.snapshotNode_.isLeafNode() ? goog.object.forEach(d, function(a, b) {
    d[b] = fb.core.view.QueryView.LEAVING_VIEW;
  }) : (this.snapshotNode_.forEachChild(function(a) {
    fb.util.obj.contains(d, a) || (d[a] = fb.core.view.QueryView.ENTERING_VIEW);
  }), goog.object.forEach(d, function(a, b) {
    g.snapshotNode_.getImmediateChild(b).isEmpty() && (d[b] = fb.core.view.QueryView.LEAVING_VIEW);
  }));
  this.snapshotNode_ = e;
  return d;
};
fb.core.ViewManager = function(a, b) {
  this.connection_ = a;
  this.data_ = b;
  this.oldDataNode_ = b.rootNode_;
  this.viewsTree_ = new fb.core.util.Tree;
};
fb.core.ViewManager.prototype.addEventCallbackForQuery = function(a, b, c, d, e) {
  var f = a.path, g = this.viewsTree_.subTree(f), h = g.getValue();
  null === h ? (h = new fb.core.view.QueryMap, g.setValue(h)) : fb.core.util.assert(!h.isEmpty(), "We shouldn't be storing empty QueryMaps");
  var k = a.queryIdentifier();
  if (h.contains(k)) {
    a = h.get(k), a.addEventCallback(b, c, d, e);
  } else {
    var l = this.data_.rootNode_.getChild(f);
    a = this.createView_(a, l);
    this.ensureListening_(g, h, k, a);
    a.addEventCallback(b, c, d, e);
    (b = (b = this.viewsTree_.subTree(f).forEachAncestor(function(a) {
      if (a.getValue() && a.getValue().defaultView() && a.getValue().defaultView().isComplete()) {
        return!0;
      }
    }, !0)) || null === this.connection_ && !this.data_.getNode(f).isEmpty()) && a.markComplete();
  }
  a.raiseQueuedEvents();
};
fb.core.ViewManager.prototype.removeCallbackForQuery_ = function(a, b, c, d, e) {
  var f = a.get(b);
  (c = f && f.removeEventCallback(c, d, e) && !f.hasCallbacks()) && a.remove(b);
  return c;
};
fb.core.ViewManager.prototype.doRemoveQueries_ = function(a, b, c, d, e) {
  b = b ? b.queryIdentifier() : null;
  var f = [];
  if (b && "default" !== b) {
    this.removeCallbackForQuery_(a, b, c, d, e) && f.push(b);
  } else {
    var g = this;
    goog.array.forEach(a.keys(), function(b) {
      g.removeCallbackForQuery_(a, b, c, d, e) && f.push(b);
    });
  }
  return f;
};
fb.core.ViewManager.prototype.removeEventCallbackForQuery = function(a, b, c, d) {
  var e = this.viewsTree_.subTree(a.path).getValue();
  return null === e ? null : this.removeQueries_(e, a, b, c, d);
};
fb.core.ViewManager.prototype.removeQueries_ = function(a, b, c, d, e) {
  var f = a.path(), f = this.viewsTree_.subTree(f);
  b = this.doRemoveQueries_(a, b, c, d, e);
  a.isEmpty() && f.setValue(null);
  c = this.hasActiveAncestor(f);
  if (0 < b.length && !c) {
    c = f;
    d = f.parent();
    for (b = !1;!b && d;) {
      if (e = d.getValue()) {
        fb.core.util.assert(!e.hasActiveDefaultQuery());
        var g = c.name(), h = !1;
        e.each(function(a, b) {
          h = b.hasChild(g) || h;
        });
        h && (b = !0);
      }
      c = d;
      d = d.parent();
    }
    c = null;
    a.hasActiveDefaultQuery() || (a = a.removeStopListener(), c = this.collectListeners_(f, !0), a && a());
    return b ? null : c;
  }
  return null;
};
fb.core.ViewManager.prototype.markQueriesComplete = function(a, b) {
  this.viewsTree_.subTree(a).forEachDescendant(function(a) {
    (a = a.getValue()) && a.each(function(a, b) {
      b.markComplete();
    });
  }, b, !0);
};
fb.core.ViewManager.prototype.raiseEventsForChange = function(a, b) {
  var c = this, d = this.oldDataNode_, e = this.data_.rootNode_;
  this.oldDataNode_ = e;
  for (var f = {}, g = 0;g < b.length;g++) {
    f[b[g].toString()] = !0;
  }
  var h = function(a) {
    do {
      if (f[a.toString()]) {
        return!0;
      }
      a = a.parent();
    } while (null !== a);
    return!1;
  };
  fb.core.view.SnapshotDiffer.Diff(d, e, a, this.viewsTree_, function(b, d, e) {
    if (a.contains(b)) {
      var f = h(b);
      f && c.markQueriesComplete(b, !1);
      c.processChanges(b, d, e);
      f && c.markQueriesComplete(b, !0);
    } else {
      c.processChanges(b, d, e);
    }
  });
  h(a) && this.markQueriesComplete(a, !0);
  this.raiseQueuedEvents_(a);
};
fb.core.ViewManager.prototype.raiseQueuedEvents_ = function(a) {
  a = this.viewsTree_.subTree(a);
  a.forEachDescendant(function(a) {
    (a = a.getValue()) && a.each(function(a, b) {
      b.raiseQueuedEvents();
    });
  }, !0, !0);
  a.forEachAncestor(function(a) {
    (a = a.getValue()) && a.each(function(a, b) {
      b.raiseQueuedEvents();
    });
  }, !1);
};
fb.core.ViewManager.prototype.processChanges = function(a, b, c) {
  a = this.viewsTree_.subTree(a).getValue();
  null !== a && a.each(function(a, e) {
    e.processChanges(b, c);
  });
};
fb.core.ViewManager.prototype.hasActiveAncestor = function(a) {
  return a.forEachAncestor(function(a) {
    return a.getValue() && a.getValue().hasActiveDefaultQuery();
  });
};
fb.core.ViewManager.prototype.ensureListening_ = function(a, b, c, d) {
  if (b.hasActiveDefaultQuery() || this.hasActiveAncestor(a)) {
    b.setView(c, d);
  } else {
    var e, f;
    b.isEmpty() || (e = b.toString(), f = b.queries());
    b.setView(c, d);
    b.setActive(this.startListening(b));
    e && f && this.connection_.unlisten(b.path(), e, f);
  }
  b.hasActiveDefaultQuery() && a.forEachDescendant(function(a) {
    (a = a.getValue()) && a.deactivate();
  });
};
fb.core.ViewManager.prototype.collectListeners_ = function(a, b) {
  var c = [], d = this, e = function(a) {
    var g = a.getValue();
    if (g && g.hasDefaultQuery()) {
      c.push(g.path()), b && !g.isActive() && g.setActive(d.startListening(g));
    } else {
      if (b && g) {
        g.isActive() || g.setActive(d.startListening(g));
        var h = {};
        g.each(function(a, b) {
          b.snapshotNode_.forEachChild(function(a, b) {
            if (!fb.util.obj.contains(h, a)) {
              h[a] = !0;
              var d = g.path().child(a);
              c.push(d);
            }
          });
        });
      }
      a.forEachChild(e);
    }
  };
  e(a);
  return c;
};
fb.core.ViewManager.prototype.startListening = function(a) {
  if (this.connection_) {
    var b = this, c = this.connection_, d = a.path(), e = a.toString(), f = a.queries(), g, h = a.keys(), k = a.hasDefaultQuery();
    this.connection_.listen(a, function(c) {
      "ok" !== c ? (c = fb.core.util.errorForServerCode(c), fb.core.util.warn("on() or once() for " + a.path().toString() + " failed: " + c.toString()), b.raiseCancelEventsForQuery_(a, c)) : g || (k ? b.markQueriesComplete(a.path(), !0) : goog.array.forEach(h, function(b) {
        (b = a.get(b)) && b.markComplete();
      }), b.raiseQueuedEvents_(a.path()));
    });
    return function() {
      g = !0;
      c.unlisten(d, e, f);
    };
  }
  return goog.nullFunction;
};
fb.core.ViewManager.prototype.raiseCancelEventsForQuery_ = function(a, b) {
  a && (a.each(function(a, d) {
    d.raiseCancelEvents(b);
  }), this.removeQueries_(a));
};
fb.core.ViewManager.prototype.createView_ = function(a, b) {
  return "default" === a.queryIdentifier() ? new fb.core.view.DefaultView(a, b) : new fb.core.view.QueryView(a, b);
};
fb.core.ViewManager.prototype.getChildRelevance = function(a, b, c, d) {
  var e = {}, f = function(a) {
    goog.object.forEach(a, function(a, b) {
      a === fb.core.view.QueryView.IN_VIEW ? e[b] = fb.core.view.QueryView.IN_VIEW : (fb.util.obj.get(e, b) || a) === a ? e[b] = a : e[b] = fb.core.view.QueryView.IN_VIEW;
    });
  };
  b.each(function(b, e) {
    f(e.getChildRelevance(a, c, d));
  });
  c.isLeafNode() || c.forEachChild(function(a) {
    fb.util.obj.contains(e, a) || (e[a] = fb.core.view.QueryView.OUT_OF_VIEW);
  });
  return e;
};
fb.core.ViewManager.prototype.getAncestorUpdate = function(a, b, c) {
  for (var d = this.viewsTree_.subTree(a), e = d.parent(), f = [];null !== e;) {
    var g = e.getValue();
    if (null !== g) {
      if (g.hasDefaultQuery()) {
        return[{path:a, node:b}];
      }
      g = this.getChildRelevance(a, g, b, c);
      d = fb.util.obj.get(g, d.name());
      if (d === fb.core.view.QueryView.IN_VIEW || d === fb.core.view.QueryView.ENTERING_VIEW) {
        return[{path:a, node:b}];
      }
      d === fb.core.view.QueryView.LEAVING_VIEW && f.push({path:a, node:fb.core.snap.EMPTY_NODE});
    }
    d = e;
    e = e.parent();
  }
  return f;
};
fb.core.ViewManager.prototype.pruneNonDefaultQuery = function(a, b, c, d) {
  var e = a.path();
  a = this.getChildRelevance(e, a, c, d);
  var f = fb.core.snap.EMPTY_NODE, g = [], h = this;
  goog.object.forEach(a, function(a, l) {
    var m = new fb.core.util.Path(l);
    a === fb.core.view.QueryView.IN_VIEW || a === fb.core.view.QueryView.ENTERING_VIEW ? f = f.updateImmediateChild(l, c.getChild(m)) : (a === fb.core.view.QueryView.LEAVING_VIEW && g.push({path:e.child(l), node:fb.core.snap.EMPTY_NODE}), g = g.concat(h.pruneObjectToListeners_(c.getChild(m), b.subTree(m), d)));
  });
  return[{path:e, node:f}].concat(g);
};
fb.core.ViewManager.prototype.pruneUpdateNode = function(a, b, c) {
  var d = this.getAncestorUpdate(a, b, c);
  if (1 == d.length && (!d[0].node.isEmpty() || b.isEmpty())) {
    return d;
  }
  var e = this.viewsTree_.subTree(a), f = e.getValue();
  null !== f ? f.hasDefaultQuery() ? d.push({path:a, node:b}) : d = d.concat(this.pruneNonDefaultQuery(f, e, b, c)) : d = d.concat(this.pruneObjectToListeners_(b, e, c));
  return d;
};
fb.core.ViewManager.prototype.pruneObjectToListeners_ = function(a, b, c) {
  var d = b.getValue();
  if (null !== d) {
    return d.hasDefaultQuery() ? [{path:b.path(), node:a}] : this.pruneNonDefaultQuery(d, b, a, c);
  }
  var e = [], f = this;
  b.forEachChild(function(b) {
    var d = a.isLeafNode() ? fb.core.snap.EMPTY_NODE : a.getImmediateChild(b.name());
    b = f.pruneObjectToListeners_(d, b, c);
    e = e.concat(b);
  });
  return e;
};
fb.core.Repo = function(a) {
  this.repoInfo_ = a;
  this.stats_ = fb.core.stats.StatsManager.getCollection(a);
  this.connection_ = new fb.core.PersistentConnection(this.repoInfo_, goog.bind(this.onDataUpdate_, this), goog.bind(this.onConnectStatus_, this), goog.bind(this.onAuthStatus_, this), goog.bind(this.onServerInfoUpdate_, this), goog.bind(this.getServerDataHashForPath_, this));
  this.statsReporter_ = fb.core.stats.StatsManager.getOrCreateReporter(a, goog.bind(function() {
    return new fb.core.stats.StatsReporter(this.stats_, this.connection_);
  }, this));
  this.transactions_init_();
  this.data_ = new fb.core.FirebaseData;
  this.viewManager_ = new fb.core.ViewManager(this.connection_, this.data_.visibleData);
  this.infoData_ = new fb.core.SnapshotHolder;
  this.infoViewManager_ = new fb.core.ViewManager(null, this.infoData_);
  this.updateInfo_("connected", !1);
  this.updateInfo_("authenticated", !1);
  this.onDisconnect_ = new fb.core.SparseSnapshotTree;
  this.dataUpdateCount = 0;
};
fb.core.Repo.prototype.toString = function() {
  return(this.repoInfo_.secure ? "https://" : "http://") + this.repoInfo_.host;
};
fb.core.Repo.prototype.name = function() {
  return this.repoInfo_.namespace;
};
fb.core.Repo.prototype.serverTime = function() {
  var a = this.infoData_.getNode(new fb.core.util.Path(".info/serverTimeOffset")).val() || 0;
  return(new Date).getTime() + a;
};
fb.core.Repo.prototype.generateServerValues = function() {
  return fb.core.util.ServerValues.generateWithValues({timestamp:this.serverTime()});
};
fb.core.Repo.prototype.onDataUpdate_ = function(a, b, c) {
  this.dataUpdateCount++;
  this.interceptServerDataCallback_ && (b = this.interceptServerDataCallback_(a, b));
  var d, e, f = [];
  9 <= a.length && a.lastIndexOf(".priority") === a.length - 9 ? (d = new fb.core.util.Path(a.substring(0, a.length - 9)), e = this.data_.serverData.getNode(d).updatePriority(b), f.push(d)) : c ? (d = new fb.core.util.Path(a), e = this.data_.serverData.getNode(d), goog.object.forEach(b, function(a, b) {
    var c = new fb.core.util.Path(b);
    ".priority" === b ? e = e.updatePriority(a) : (e = e.updateChild(c, fb.core.snap.NodeFromJSON(a)), f.push(d.child(b)));
  })) : (d = new fb.core.util.Path(a), e = fb.core.snap.NodeFromJSON(b), f.push(d));
  a = this.viewManager_.pruneUpdateNode(d, e, this.data_.mergedData, c ? b : null);
  b = !1;
  for (c = 0;c < a.length;++c) {
    var g = a[c];
    b = this.data_.updateServerData(g.path, g.node) || b;
  }
  b && (d = this.rerunTransactionsAndUpdateVisibleData_(d));
  this.viewManager_.raiseEventsForChange(d, f);
};
fb.core.Repo.prototype.interceptServerData_ = function(a) {
  this.interceptServerDataCallback_ = a;
};
fb.core.Repo.prototype.onConnectStatus_ = function(a) {
  this.updateInfo_("connected", a);
  !1 === a && this.runOnDisconnectEvents_();
};
fb.core.Repo.prototype.onServerInfoUpdate_ = function(a) {
  var b = this;
  fb.core.util.each(a, function(a, d) {
    b.updateInfo_(d, a);
  });
};
fb.core.Repo.prototype.getServerDataHashForPath_ = function(a) {
  a = new fb.core.util.Path(a);
  return this.data_.serverData.getNode(a).hash();
};
fb.core.Repo.prototype.onAuthStatus_ = function(a) {
  this.updateInfo_("authenticated", a);
};
fb.core.Repo.prototype.updateInfo_ = function(a, b) {
  var c = new fb.core.util.Path("/.info/" + a);
  this.infoData_.updateSnapshot(c, fb.core.snap.NodeFromJSON(b));
  this.infoViewManager_.raiseEventsForChange(c, [c]);
};
fb.core.Repo.prototype.auth = function(a, b, c) {
  this.repoInfo_.isDemoHost() && fb.core.util.warn("FirebaseRef.auth() not supported on demo (*.firebaseio-demo.com) Firebases. Please use on production (*.firebaseio.com) Firebases only.");
  var d = this;
  this.connection_.auth(a, function(a, c) {
    d.callOnCompleteCallback(b, a, c);
  }, function(a, b) {
    fb.core.util.warn("auth() was canceled: " + b);
    if (c) {
      var d = Error(b);
      d.code = a.toUpperCase();
      c(d);
    }
  });
};
fb.core.Repo.prototype.unauth = function(a) {
  var b = this;
  this.connection_.unauth(function(c, d) {
    b.callOnCompleteCallback(a, c, d);
  });
};
fb.core.Repo.prototype.setWithPriority = function(a, b, c, d) {
  this.log_("set", {path:a.toString(), value:b, priority:c});
  var e = this.generateServerValues();
  b = fb.core.snap.NodeFromJSON(b, c);
  var e = fb.core.util.ServerValues.resolveDeferredValueSnapshot(b, e), e = this.viewManager_.pruneUpdateNode(a, e, this.data_.mergedData, null), f = this.data_.set(a, e), g = this;
  this.connection_.put(a.toString(), b.val(!0), function(b, c) {
    "ok" !== b && fb.core.util.warn("set at " + a + " failed: " + b);
    g.data_.setCompleted(f);
    g.data_.mergeServerAndPendingData(a);
    var e = g.rerunTransactionsAndUpdateVisibleData_(a);
    g.viewManager_.raiseEventsForChange(e, []);
    g.callOnCompleteCallback(d, b, c);
  });
  e = this.abortTransactions_(a);
  this.rerunTransactionsAndUpdateVisibleData_(e);
  this.viewManager_.raiseEventsForChange(e, [a]);
};
fb.core.Repo.prototype.update = function(a, b, c) {
  this.log_("update", {path:a.toString(), value:b});
  var d = this.data_.visibleData.getNode(a), e = !0, f = [], g = this.generateServerValues(), h = [], k;
  for (k in b) {
    var e = !1, l = fb.core.snap.NodeFromJSON(b[k]), l = fb.core.util.ServerValues.resolveDeferredValueSnapshot(l, g), d = d.updateImmediateChild(k, l), m = a.child(k);
    f.push(m);
    l = this.viewManager_.pruneUpdateNode(m, l, this.data_.mergedData, null);
    h = h.concat(this.data_.set(a, l));
  }
  if (e) {
    fb.core.util.log("update() called with empty data.  Don't do anything."), this.callOnCompleteCallback(c, "ok");
  } else {
    var p = this;
    this.connection_.merge(a.toString(), b, function(b, d) {
      fb.core.util.assert("ok" === b || "permission_denied" === b, "merge at " + a + " failed.");
      "ok" !== b && fb.core.util.warn("update at " + a + " failed: " + b);
      p.data_.setCompleted(h);
      p.data_.mergeServerAndPendingData(a);
      var e = p.rerunTransactionsAndUpdateVisibleData_(a);
      p.viewManager_.raiseEventsForChange(e, []);
      p.callOnCompleteCallback(c, b, d);
    });
    b = this.abortTransactions_(a);
    this.rerunTransactionsAndUpdateVisibleData_(b);
    p.viewManager_.raiseEventsForChange(b, f);
  }
};
fb.core.Repo.prototype.setPriority = function(a, b, c) {
  this.log_("setPriority", {path:a.toString(), priority:b});
  var d = this.generateServerValues(), d = fb.core.util.ServerValues.resolveDeferredValue(b, d), d = this.data_.mergedData.getNode(a).updatePriority(d), d = this.viewManager_.pruneUpdateNode(a, d, this.data_.mergedData, null), e = this.data_.set(a, d), f = this;
  this.connection_.put(a.toString() + "/.priority", b, function(b, d) {
    "permission_denied" === b && fb.core.util.warn("setPriority at " + a + " failed: " + b);
    f.data_.setCompleted(e);
    f.data_.mergeServerAndPendingData(a);
    var k = f.rerunTransactionsAndUpdateVisibleData_(a);
    f.viewManager_.raiseEventsForChange(k, []);
    f.callOnCompleteCallback(c, b, d);
  });
  b = this.rerunTransactionsAndUpdateVisibleData_(a);
  f.viewManager_.raiseEventsForChange(b, []);
};
fb.core.Repo.prototype.runOnDisconnectEvents_ = function() {
  this.log_("onDisconnectEvents");
  var a = this, b = [], c = this.generateServerValues();
  fb.core.util.ServerValues.resolveDeferredValueTree(this.onDisconnect_, c).forEachTree(new fb.core.util.Path(""), function(c, e) {
    var f = a.viewManager_.pruneUpdateNode(c, e, a.data_.mergedData, null);
    b.push.apply(b, a.data_.set(c, f));
    f = a.abortTransactions_(c);
    a.rerunTransactionsAndUpdateVisibleData_(f);
    a.viewManager_.raiseEventsForChange(f, [c]);
  });
  this.data_.setCompleted(b);
  this.onDisconnect_ = new fb.core.SparseSnapshotTree;
};
fb.core.Repo.prototype.onDisconnectCancel = function(a, b) {
  var c = this;
  this.connection_.onDisconnectCancel(a.toString(), function(d, e) {
    "ok" === d && c.onDisconnect_.forget(a);
    c.callOnCompleteCallback(b, d, e);
  });
};
fb.core.Repo.prototype.onDisconnectSet = function(a, b, c) {
  var d = this, e = fb.core.snap.NodeFromJSON(b);
  this.connection_.onDisconnectPut(a.toString(), e.val(!0), function(b, g) {
    "ok" === b && d.onDisconnect_.remember(a, e);
    d.callOnCompleteCallback(c, b, g);
  });
};
fb.core.Repo.prototype.onDisconnectSetWithPriority = function(a, b, c, d) {
  var e = this, f = fb.core.snap.NodeFromJSON(b, c);
  this.connection_.onDisconnectPut(a.toString(), f.val(!0), function(b, c) {
    "ok" === b && e.onDisconnect_.remember(a, f);
    e.callOnCompleteCallback(d, b, c);
  });
};
fb.core.Repo.prototype.onDisconnectUpdate = function(a, b, c) {
  var d = !0, e;
  for (e in b) {
    d = !1;
  }
  if (d) {
    fb.core.util.log("onDisconnect().update() called with empty data.  Don't do anything."), this.callOnCompleteCallback(c, "ok");
  } else {
    var f = this;
    this.connection_.onDisconnectMerge(a.toString(), b, function(d, e) {
      if ("ok" === d) {
        for (var k in b) {
          var l = fb.core.snap.NodeFromJSON(b[k]);
          f.onDisconnect_.remember(a.child(k), l);
        }
      }
      f.callOnCompleteCallback(c, d, e);
    });
  }
};
fb.core.Repo.prototype.logOnDisconnectDeprecatedSignature = function() {
  this.stats_.incrementCounter("deprecated_on_disconnect");
  this.statsReporter_.includeStat("deprecated_on_disconnect");
};
fb.core.Repo.prototype.addEventCallbackForQuery = function(a, b, c, d, e) {
  ".info" === a.path.getFront() ? this.infoViewManager_.addEventCallbackForQuery(a, b, c, d, e) : this.viewManager_.addEventCallbackForQuery(a, b, c, d, e);
};
fb.core.Repo.prototype.removeEventCallbackForQuery = function(a, b, c, d) {
  ".info" === a.path.getFront() ? this.infoViewManager_.removeEventCallbackForQuery(a, b, c, d) : (b = this.viewManager_.removeEventCallbackForQuery(a, b, c, d), null !== b && this.data_.forgetPath(a.path, b) && (fb.core.util.assert(this.data_.visibleData.rootNode_ === this.viewManager_.oldDataNode_, "We should have raised any outstanding events by now.  Else, we'll blow them away."), this.data_.visibleData.updateSnapshot(a.path, this.data_.mergedData.getNode(a.path)), this.viewManager_.oldDataNode_ = 
  this.data_.visibleData.rootNode_));
};
fb.core.Repo.prototype.interrupt = function() {
  this.connection_.interrupt();
};
fb.core.Repo.prototype.resume = function() {
  this.connection_.resume();
};
fb.core.Repo.prototype.stats = function(a) {
  if ("undefined" !== typeof console) {
    a ? (this.statsListener_ || (this.statsListener_ = new fb.core.stats.StatsListener(this.stats_)), a = this.statsListener_.get()) : a = this.stats_.get();
    var b = goog.array.reduce(goog.object.getKeys(a), function(a, b, c, d) {
      return Math.max(b.length, a);
    }, 0), c;
    for (c in a) {
      for (var d = a[c], e = c.length;e < b + 2;e++) {
        c += " ";
      }
      console.log(c + d);
    }
  }
};
fb.core.Repo.prototype.statsIncrementCounter = function(a) {
  this.stats_.incrementCounter(a);
  this.statsReporter_.includeStat(a);
};
fb.core.Repo.prototype.log_ = function() {
  fb.core.util.log("r:" + this.connection_.id + ":", arguments);
};
fb.core.Repo.prototype.callOnCompleteCallback = function(a, b, c) {
  a && fb.core.util.exceptionGuard(function() {
    if ("ok" == b) {
      a(null, c);
    } else {
      var d = (b || "error").toUpperCase(), e = d;
      c && (e += ": " + c);
      e = Error(e);
      e.code = d;
      a(e);
    }
  });
};
fb.core.Repo_transaction = {};
fb.core.TransactionStatus = {RUN:1, SENT:2, COMPLETED:3, SENT_NEEDS_ABORT:4, NEEDS_ABORT:5};
fb.core.MAX_TRANSACTION_RETRIES_ = 25;
fb.core.Repo.prototype.transactions_init_ = function() {
  this.transactionQueueTree_ = new fb.core.util.Tree;
  this.transactionResultData_ = new fb.core.SnapshotHolder;
};
fb.core.Repo.prototype.startTransaction = function(a, b, c, d) {
  this.log_("transaction on " + a);
  var e = function() {
  }, f = new Firebase(this, a);
  f.on("value", e);
  b = {path:a, update:b, onComplete:c, status:null, order:fb.core.util.LUIDGenerator(), applyLocally:d, retryCount:0, unwatcher:function() {
    f.off("value", e);
  }, abortReason:null};
  this.pruneResultData_();
  c = b.update(this.transactionResultData_.getNode(a).val());
  if (goog.isDef(c)) {
    fb.core.util.validation.validateFirebaseData("transaction failed: Data returned ", c);
    b.status = fb.core.TransactionStatus.RUN;
    d = this.transactionQueueTree_.subTree(a);
    var g = d.getValue() || [];
    g.push(b);
    d.setValue(g);
    g = "object" === typeof c && null !== c && fb.util.obj.contains(c, ".priority") ? c[".priority"] : this.data_.mergedData.getNode(a).getPriority();
    d = this.generateServerValues();
    c = fb.core.snap.NodeFromJSON(c, g);
    c = fb.core.util.ServerValues.resolveDeferredValueSnapshot(c, d);
    this.transactionResultData_.updateSnapshot(a, c);
    b.applyLocally && (this.data_.visibleData.updateSnapshot(a, c), this.viewManager_.raiseEventsForChange(a, [a]));
    this.sendReadyTransactions_();
  } else {
    b.unwatcher(), b.onComplete && (a = this.getSnapshot_(a), b.onComplete(null, !1, a));
  }
};
fb.core.Repo.prototype.sendReadyTransactions_ = function(a) {
  var b = a || this.transactionQueueTree_;
  a || this.pruneCompletedTransactionsBelowNode_(b);
  if (null !== b.getValue()) {
    a = this.buildTransactionQueue_(b), fb.core.util.assert(0 < a.length), goog.array.every(a, function(a) {
      return a.status === fb.core.TransactionStatus.RUN;
    }) && this.sendTransactionQueue_(b.path(), a);
  } else {
    if (b.hasChildren()) {
      var c = this;
      b.forEachChild(function(a) {
        c.sendReadyTransactions_(a);
      });
    }
  }
};
fb.core.Repo.prototype.sendTransactionQueue_ = function(a, b) {
  for (var c = 0;c < b.length;c++) {
    fb.core.util.assert(b[c].status === fb.core.TransactionStatus.RUN, "tryToSendTransactionQueue_: items in queue should all be run."), b[c].status = fb.core.TransactionStatus.SENT, b[c].retryCount++;
  }
  var d = this.data_.mergedData.getNode(a).hash();
  this.data_.mergedData.updateSnapshot(a, this.data_.visibleData.getNode(a));
  for (var e = this.transactionResultData_.getNode(a).val(!0), f = fb.core.util.LUIDGenerator(), g = this.pathsWithLocallyAppliedChanges(b), c = 0;c < g.length;c++) {
    this.data_.pendingPuts.subTree(g[c]).setValue(f);
  }
  var h = this;
  this.connection_.put(a.toString(), e, function(d) {
    h.log_("transaction put response", {path:a.toString(), status:d});
    for (c = 0;c < g.length;c++) {
      var e = h.data_.pendingPuts.subTree(g[c]), m = e.getValue();
      fb.core.util.assert(null !== m, "sendTransactionQueue_: pendingPut should not be null.");
      m === f && (e.setValue(null), h.data_.mergedData.updateSnapshot(g[c], h.data_.serverData.getNode(g[c])));
    }
    if ("ok" === d) {
      d = [];
      for (c = 0;c < b.length;c++) {
        b[c].status = fb.core.TransactionStatus.COMPLETED, b[c].onComplete && (e = h.getSnapshot_(b[c].path), d.push(goog.bind(b[c].onComplete, null, null, !0, e))), b[c].unwatcher();
      }
      h.pruneCompletedTransactionsBelowNode_(h.transactionQueueTree_.subTree(a));
      h.sendReadyTransactions_();
      for (c = 0;c < d.length;c++) {
        fb.core.util.exceptionGuard(d[c]);
      }
    } else {
      if ("datastale" === d) {
        for (c = 0;c < b.length;c++) {
          b[c].status = b[c].status === fb.core.TransactionStatus.SENT_NEEDS_ABORT ? fb.core.TransactionStatus.NEEDS_ABORT : fb.core.TransactionStatus.RUN;
        }
      } else {
        for (fb.core.util.warn("transaction at " + a + " failed: " + d), c = 0;c < b.length;c++) {
          b[c].status = fb.core.TransactionStatus.NEEDS_ABORT, b[c].abortReason = d;
        }
      }
      d = h.rerunTransactionsAndUpdateVisibleData_(a);
      h.viewManager_.raiseEventsForChange(d, [a]);
    }
  }, d);
};
fb.core.Repo.prototype.pathsWithLocallyAppliedChanges = function(a) {
  for (var b = {}, c = 0;c < a.length;c++) {
    a[c].applyLocally && (b[a[c].path.toString()] = a[c].path);
  }
  a = [];
  for (var d in b) {
    a.push(b[d]);
  }
  return a;
};
fb.core.Repo.prototype.rerunTransactionsAndUpdateVisibleData_ = function(a) {
  var b = this.getAncestorTransactionNode_(a);
  a = b.path();
  b = this.buildTransactionQueue_(b);
  this.rerunTransactionQueue_(b, a);
  return a;
};
fb.core.Repo.prototype.rerunTransactionQueue_ = function(a, b) {
  this.data_.visibleData.updateSnapshot(b, this.data_.mergedData.getNode(b));
  this.transactionResultData_.updateSnapshot(b, this.data_.mergedData.getNode(b));
  if (0 !== a.length) {
    for (var c = this.data_.visibleData.getNode(b), d = c, e = [], f = 0;f < a.length;f++) {
      var g = fb.core.util.Path.RelativePath(b, a[f].path), h = !1, k;
      fb.core.util.assert(null !== g, "rerunTransactionsUnderNode_: relativePath should not be null.");
      if (a[f].status === fb.core.TransactionStatus.NEEDS_ABORT) {
        h = !0, k = a[f].abortReason;
      } else {
        if (a[f].status === fb.core.TransactionStatus.RUN) {
          if (a[f].retryCount >= fb.core.MAX_TRANSACTION_RETRIES_) {
            h = !0, k = "maxretry";
          } else {
            var l = c.getChild(g), m = a[f].update(l.val());
            if (goog.isDef(m)) {
              fb.core.util.validation.validateFirebaseData("transaction failed: Data returned ", m);
              var p = fb.core.snap.NodeFromJSON(m);
              "object" === typeof m && null != m && fb.util.obj.contains(m, ".priority") || (p = p.updatePriority(l.getPriority()));
              c = c.updateChild(g, p);
              a[f].applyLocally && (d = d.updateChild(g, p));
            } else {
              h = !0, k = "nodata";
            }
          }
        }
      }
      h && (a[f].status = fb.core.TransactionStatus.COMPLETED, setTimeout(a[f].unwatcher, 0), a[f].onComplete && (h = new Firebase(this, a[f].path), g = new fb.api.DataSnapshot(c.getChild(g), h), "nodata" === k ? e.push(goog.bind(a[f].onComplete, null, null, !1, g)) : e.push(goog.bind(a[f].onComplete, null, Error(k), !1, g))));
    }
    this.transactionResultData_.updateSnapshot(b, c);
    this.data_.visibleData.updateSnapshot(b, d);
    this.pruneCompletedTransactionsBelowNode_(this.transactionQueueTree_);
    for (f = 0;f < e.length;f++) {
      fb.core.util.exceptionGuard(e[f]);
    }
    this.sendReadyTransactions_();
  }
};
fb.core.Repo.prototype.getAncestorTransactionNode_ = function(a) {
  for (var b, c = this.transactionQueueTree_;null !== (b = a.getFront()) && null === c.getValue();) {
    c = c.subTree(b), a = a.popFront();
  }
  return c;
};
fb.core.Repo.prototype.buildTransactionQueue_ = function(a) {
  var b = [];
  this.aggregateTransactionQueuesForNode_(a, b);
  b.sort(function(a, b) {
    return a.order - b.order;
  });
  return b;
};
fb.core.Repo.prototype.aggregateTransactionQueuesForNode_ = function(a, b) {
  var c = a.getValue();
  if (null !== c) {
    for (var d = 0;d < c.length;d++) {
      b.push(c[d]);
    }
  }
  var e = this;
  a.forEachChild(function(a) {
    e.aggregateTransactionQueuesForNode_(a, b);
  });
};
fb.core.Repo.prototype.pruneCompletedTransactionsBelowNode_ = function(a) {
  var b = a.getValue();
  if (b) {
    for (var c = 0, d = 0;d < b.length;d++) {
      b[d].status !== fb.core.TransactionStatus.COMPLETED && (b[c] = b[d], c++);
    }
    b.length = c;
    a.setValue(0 < b.length ? b : null);
  }
  var e = this;
  a.forEachChild(function(a) {
    e.pruneCompletedTransactionsBelowNode_(a);
  });
};
fb.core.Repo.prototype.abortTransactions_ = function(a) {
  var b = this.getAncestorTransactionNode_(a).path();
  a = this.transactionQueueTree_.subTree(a);
  var c = this;
  a.forEachAncestor(function(a) {
    c.abortTransactionsOnNode_(a);
  });
  this.abortTransactionsOnNode_(a);
  a.forEachDescendant(function(a) {
    c.abortTransactionsOnNode_(a);
  });
  return b;
};
fb.core.Repo.prototype.abortTransactionsOnNode_ = function(a) {
  var b = a.getValue();
  if (null !== b) {
    for (var c = [], d = -1, e = 0;e < b.length;e++) {
      b[e].status !== fb.core.TransactionStatus.SENT_NEEDS_ABORT && (b[e].status === fb.core.TransactionStatus.SENT ? (fb.core.util.assert(d === e - 1, "All SENT items should be at beginning of queue."), d = e, b[e].status = fb.core.TransactionStatus.SENT_NEEDS_ABORT, b[e].abortReason = "set") : (fb.core.util.assert(b[e].status === fb.core.TransactionStatus.RUN), b[e].unwatcher(), b[e].onComplete && c.push(goog.bind(b[e].onComplete, null, Error("set"), !1, null))));
    }
    -1 === d ? a.setValue(null) : b.length = d + 1;
    for (e = 0;e < c.length;e++) {
      fb.core.util.exceptionGuard(c[e]);
    }
  }
};
fb.core.Repo.prototype.getSnapshot_ = function(a) {
  var b = new Firebase(this, a);
  return new fb.api.DataSnapshot(this.transactionResultData_.getNode(a), b);
};
fb.core.Repo.prototype.pruneResultData_ = function() {
  this.transactionResultData_.rootNode_ = this.pruneResultDataHelper_(this.transactionResultData_.rootNode_, this.data_.mergedData.rootNode_, this.transactionQueueTree_);
};
fb.core.Repo.prototype.pruneResultDataHelper_ = function(a, b, c) {
  var d = this;
  if (c.isEmpty()) {
    return b;
  }
  if (null != c.getValue()) {
    return a;
  }
  var e = b;
  c.forEachChild(function(c) {
    var g = c.name(), h = new fb.core.util.Path(g);
    c = d.pruneResultDataHelper_(a.getChild(h), b.getChild(h), c);
    e = e.updateImmediateChild(g, c);
  });
  return e;
};
fb.core.RepoManager = function() {
  this.repos_ = {};
};
goog.addSingletonGetter(fb.core.RepoManager);
fb.core.RepoManager.prototype.interrupt = function() {
  for (var a in this.repos_) {
    this.repos_[a].interrupt();
  }
};
goog.exportProperty(fb.core.RepoManager.prototype, "interrupt", fb.core.RepoManager.prototype.interrupt);
fb.core.RepoManager.prototype.resume = function() {
  for (var a in this.repos_) {
    this.repos_[a].resume();
  }
};
goog.exportProperty(fb.core.RepoManager.prototype, "resume", fb.core.RepoManager.prototype.resume);
fb.core.RepoManager.prototype.getRepo = function(a) {
  var b = a.toString(), c = fb.util.obj.get(this.repos_, b);
  c || (c = new fb.core.Repo(a), this.repos_[b] = c);
  return c;
};
fb.api.INTERNAL = {};
fb.api.INTERNAL.hijackHash = function(a) {
  var b = fb.core.snap.ChildrenNode.prototype.hash;
  fb.core.snap.ChildrenNode.prototype.hash = a;
  var c = fb.core.snap.LeafNode.prototype.hash;
  fb.core.snap.LeafNode.prototype.hash = a;
  return function() {
    fb.core.snap.ChildrenNode.prototype.hash = b;
    fb.core.snap.LeafNode.prototype.hash = c;
  };
};
goog.exportProperty(fb.api.INTERNAL, "hijackHash", fb.api.INTERNAL.hijackHash);
fb.api.INTERNAL.queryIdentifier = function(a) {
  return a.queryIdentifier();
};
goog.exportProperty(fb.api.INTERNAL, "queryIdentifier", fb.api.INTERNAL.queryIdentifier);
fb.api.INTERNAL.listens = function(a) {
  return a.repo.connection_.listens_;
};
goog.exportProperty(fb.api.INTERNAL, "listens", fb.api.INTERNAL.listens);
fb.api.INTERNAL.refConnection = function(a) {
  return a.repo.connection_.realtime_;
};
goog.exportProperty(fb.api.INTERNAL, "refConnection", fb.api.INTERNAL.refConnection);
fb.api.INTERNAL.DataConnection = fb.core.PersistentConnection;
goog.exportProperty(fb.api.INTERNAL, "DataConnection", fb.api.INTERNAL.DataConnection);
goog.exportProperty(fb.core.PersistentConnection.prototype, "sendRequest", fb.core.PersistentConnection.prototype.sendRequest_);
goog.exportProperty(fb.core.PersistentConnection.prototype, "interrupt", fb.core.PersistentConnection.prototype.interrupt);
fb.api.INTERNAL.RealTimeConnection = fb.realtime.Connection;
goog.exportProperty(fb.api.INTERNAL, "RealTimeConnection", fb.api.INTERNAL.RealTimeConnection);
goog.exportProperty(fb.realtime.Connection.prototype, "sendRequest", fb.realtime.Connection.prototype.sendRequest);
goog.exportProperty(fb.realtime.Connection.prototype, "close", fb.realtime.Connection.prototype.close);
fb.api.INTERNAL.ConnectionTarget = fb.core.RepoInfo;
goog.exportProperty(fb.api.INTERNAL, "ConnectionTarget", fb.api.INTERNAL.ConnectionTarget);
fb.api.INTERNAL.forceLongPolling = function() {
  fb.realtime.WebSocketConnection.forceDisallow();
  fb.realtime.BrowserPollConnection.forceAllow();
};
goog.exportProperty(fb.api.INTERNAL, "forceLongPolling", fb.api.INTERNAL.forceLongPolling);
fb.api.INTERNAL.forceWebSockets = function() {
  fb.realtime.BrowserPollConnection.forceDisallow();
};
goog.exportProperty(fb.api.INTERNAL, "forceWebSockets", fb.api.INTERNAL.forceWebSockets);
fb.api.INTERNAL.setSecurityDebugCallback = function(a, b) {
  a.repo.connection_.securityDebugCallback_ = b;
};
goog.exportProperty(fb.api.INTERNAL, "setSecurityDebugCallback", fb.api.INTERNAL.setSecurityDebugCallback);
fb.api.INTERNAL.stats = function(a, b) {
  a.repo.stats(b);
};
goog.exportProperty(fb.api.INTERNAL, "stats", fb.api.INTERNAL.stats);
fb.api.INTERNAL.statsIncrementCounter = function(a, b) {
  a.repo.statsIncrementCounter(b);
};
goog.exportProperty(fb.api.INTERNAL, "statsIncrementCounter", fb.api.INTERNAL.statsIncrementCounter);
fb.api.INTERNAL.dataUpdateCount = function(a) {
  return a.repo.dataUpdateCount;
};
fb.api.INTERNAL.interceptServerData = function(a, b) {
  return a.repo.interceptServerData_(b);
};
goog.exportProperty(fb.api.INTERNAL, "interceptServerData", fb.api.INTERNAL.interceptServerData);
fb.api.OnDisconnect = function(a, b, c) {
  this.repo_ = a;
  this.path_ = b;
  this.name_ = c;
};
fb.api.OnDisconnect.prototype.cancel = function(a) {
  fb.util.validation.validateArgCount("Firebase.onDisconnect().cancel", 0, 1, arguments.length);
  fb.util.validation.validateCallback("Firebase.onDisconnect().cancel", 1, a, !0);
  this.repo_.onDisconnectCancel(this.path_, a);
};
goog.exportProperty(fb.api.OnDisconnect.prototype, "cancel", fb.api.OnDisconnect.prototype.cancel);
fb.api.OnDisconnect.prototype.remove = function(a) {
  fb.util.validation.validateArgCount("Firebase.onDisconnect().remove", 0, 1, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.onDisconnect().remove", this.path_);
  fb.util.validation.validateCallback("Firebase.onDisconnect().remove", 1, a, !0);
  this.repo_.onDisconnectSet(this.path_, null, a);
};
goog.exportProperty(fb.api.OnDisconnect.prototype, "remove", fb.api.OnDisconnect.prototype.remove);
fb.api.OnDisconnect.prototype.set = function(a, b) {
  fb.util.validation.validateArgCount("Firebase.onDisconnect().set", 1, 2, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.onDisconnect().set", this.path_);
  fb.core.util.validation.validateFirebaseDataArg("Firebase.onDisconnect().set", 1, a, !1);
  fb.util.validation.validateCallback("Firebase.onDisconnect().set", 2, b, !0);
  this.repo_.onDisconnectSet(this.path_, a, b);
};
goog.exportProperty(fb.api.OnDisconnect.prototype, "set", fb.api.OnDisconnect.prototype.set);
fb.api.OnDisconnect.prototype.setWithPriority = function(a, b, c) {
  fb.util.validation.validateArgCount("Firebase.onDisconnect().setWithPriority", 2, 3, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.onDisconnect().setWithPriority", this.path_);
  fb.core.util.validation.validateFirebaseDataArg("Firebase.onDisconnect().setWithPriority", 1, a, !1);
  fb.core.util.validation.validatePriority("Firebase.onDisconnect().setWithPriority", 2, b, !1);
  fb.util.validation.validateCallback("Firebase.onDisconnect().setWithPriority", 3, c, !0);
  if (".length" === this.name_ || ".keys" === this.name_) {
    throw "Firebase.onDisconnect().setWithPriority failed: " + this.name_ + " is a read-only object.";
  }
  this.repo_.onDisconnectSetWithPriority(this.path_, a, b, c);
};
goog.exportProperty(fb.api.OnDisconnect.prototype, "setWithPriority", fb.api.OnDisconnect.prototype.setWithPriority);
fb.api.OnDisconnect.prototype.update = function(a, b) {
  fb.util.validation.validateArgCount("Firebase.onDisconnect().update", 1, 2, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.onDisconnect().update", this.path_);
  fb.core.util.validation.validateFirebaseObjectDataArg("Firebase.onDisconnect().update", 1, a, !1);
  fb.util.validation.validateCallback("Firebase.onDisconnect().update", 2, b, !0);
  this.repo_.onDisconnectUpdate(this.path_, a, b);
};
goog.exportProperty(fb.api.OnDisconnect.prototype, "update", fb.api.OnDisconnect.prototype.update);
fb.core.util.NextPushId = function() {
  var a = 0, b = [];
  return function(c) {
    var d = c === a;
    a = c;
    for (var e = Array(8), f = 7;0 <= f;f--) {
      e[f] = "-0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz".charAt(c % 64), c = Math.floor(c / 64);
    }
    fb.core.util.assert(0 === c, "Cannot push at time == 0");
    c = e.join("");
    if (d) {
      for (f = 11;0 <= f && 63 === b[f];f--) {
        b[f] = 0;
      }
      b[f]++;
    } else {
      for (f = 0;12 > f;f++) {
        b[f] = Math.floor(64 * Math.random());
      }
    }
    for (f = 0;12 > f;f++) {
      c += "-0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz".charAt(b[f]);
    }
    fb.core.util.assert(20 === c.length, "NextPushId: Length should be 20.");
    return c;
  };
}();
var Firebase = function(a, b) {
  var c, d;
  if (a instanceof fb.core.Repo) {
    c = a, d = b;
  } else {
    fb.util.validation.validateArgCount("new Firebase", 1, 2, arguments.length);
    d = fb.core.util.parseURL(arguments[0]);
    fb.core.util.validation.validateUrl("new Firebase", 1, d);
    if (b) {
      if (b instanceof fb.core.RepoManager) {
        c = b;
      } else {
        throw Error("Expected a valid Firebase.Context for second argument to new Firebase()");
      }
    } else {
      c = fb.core.RepoManager.getInstance();
    }
    c = c.getRepo(d.repoInfo);
    d = d.path;
  }
  fb.api.Query.call(this, c, d);
};
goog.inherits(Firebase, fb.api.Query);
goog.exportSymbol("Firebase", Firebase);
NODE_CLIENT && (module.exports = Firebase);
Firebase.prototype.name = function() {
  fb.util.validation.validateArgCount("Firebase.name", 0, 0, arguments.length);
  return this.path.isEmpty() ? null : this.path.getBack();
};
goog.exportProperty(Firebase.prototype, "name", Firebase.prototype.name);
Firebase.prototype.child = function(a) {
  fb.util.validation.validateArgCount("Firebase.child", 1, 1, arguments.length);
  goog.isNumber(a) ? a = String(a) : a instanceof fb.core.util.Path || (null === this.path.getFront() ? fb.core.util.validation.validateRootPathString("Firebase.child", 1, a, !1) : fb.core.util.validation.validatePathString("Firebase.child", 1, a, !1));
  return new Firebase(this.repo, this.path.child(a));
};
goog.exportProperty(Firebase.prototype, "child", Firebase.prototype.child);
Firebase.prototype.parent = function() {
  fb.util.validation.validateArgCount("Firebase.parent", 0, 0, arguments.length);
  var a = this.path.parent();
  return null === a ? null : new Firebase(this.repo, a);
};
goog.exportProperty(Firebase.prototype, "parent", Firebase.prototype.parent);
Firebase.prototype.root = function() {
  fb.util.validation.validateArgCount("Firebase.ref", 0, 0, arguments.length);
  for (var a = this;null !== a.parent();) {
    a = a.parent();
  }
  return a;
};
goog.exportProperty(Firebase.prototype, "root", Firebase.prototype.root);
Firebase.prototype.toString = function() {
  fb.util.validation.validateArgCount("Firebase.toString", 0, 0, arguments.length);
  return null === this.parent() ? this.repo.toString() : this.parent().toString() + "/" + goog.string.urlEncode(this.name());
};
goog.exportProperty(Firebase.prototype, "toString", Firebase.prototype.toString);
Firebase.prototype.set = function(a, b) {
  fb.util.validation.validateArgCount("Firebase.set", 1, 2, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.set", this.path);
  fb.core.util.validation.validateFirebaseDataArg("Firebase.set", 1, a, !1);
  fb.util.validation.validateCallback("Firebase.set", 2, b, !0);
  this.repo.setWithPriority(this.path, a, null, b);
};
goog.exportProperty(Firebase.prototype, "set", Firebase.prototype.set);
Firebase.prototype.update = function(a, b) {
  fb.util.validation.validateArgCount("Firebase.update", 1, 2, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.update", this.path);
  fb.core.util.validation.validateFirebaseObjectDataArg("Firebase.update", 1, a, !1);
  fb.util.validation.validateCallback("Firebase.update", 2, b, !0);
  if (fb.util.obj.contains(a, ".priority")) {
    throw Error("update() does not currently support updating .priority.");
  }
  this.repo.update(this.path, a, b);
};
goog.exportProperty(Firebase.prototype, "update", Firebase.prototype.update);
Firebase.prototype.setWithPriority = function(a, b, c) {
  fb.util.validation.validateArgCount("Firebase.setWithPriority", 2, 3, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.setWithPriority", this.path);
  fb.core.util.validation.validateFirebaseDataArg("Firebase.setWithPriority", 1, a, !1);
  fb.core.util.validation.validatePriority("Firebase.setWithPriority", 2, b, !1);
  fb.util.validation.validateCallback("Firebase.setWithPriority", 3, c, !0);
  if (".length" === this.name() || ".keys" === this.name()) {
    throw "Firebase.setWithPriority failed: " + this.name() + " is a read-only object.";
  }
  this.repo.setWithPriority(this.path, a, b, c);
};
goog.exportProperty(Firebase.prototype, "setWithPriority", Firebase.prototype.setWithPriority);
Firebase.prototype.remove = function(a) {
  fb.util.validation.validateArgCount("Firebase.remove", 0, 1, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.remove", this.path);
  fb.util.validation.validateCallback("Firebase.remove", 1, a, !0);
  this.set(null, a);
};
goog.exportProperty(Firebase.prototype, "remove", Firebase.prototype.remove);
Firebase.prototype.transaction = function(a, b, c) {
  fb.util.validation.validateArgCount("Firebase.transaction", 1, 3, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.transaction", this.path);
  fb.util.validation.validateCallback("Firebase.transaction", 1, a, !1);
  fb.util.validation.validateCallback("Firebase.transaction", 2, b, !0);
  fb.core.util.validation.validateBoolean("Firebase.transaction", 3, c, !0);
  if (".length" === this.name() || ".keys" === this.name()) {
    throw "Firebase.transaction failed: " + this.name() + " is a read-only object.";
  }
  "undefined" === typeof c && (c = !0);
  this.repo.startTransaction(this.path, a, b, c);
};
goog.exportProperty(Firebase.prototype, "transaction", Firebase.prototype.transaction);
Firebase.prototype.setPriority = function(a, b) {
  fb.util.validation.validateArgCount("Firebase.setPriority", 1, 2, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.setPriority", this.path);
  fb.core.util.validation.validatePriority("Firebase.setPriority", 1, a, !1);
  fb.util.validation.validateCallback("Firebase.setPriority", 2, b, !0);
  this.repo.setPriority(this.path, a, b);
};
goog.exportProperty(Firebase.prototype, "setPriority", Firebase.prototype.setPriority);
Firebase.prototype.push = function(a, b) {
  fb.util.validation.validateArgCount("Firebase.push", 0, 2, arguments.length);
  fb.core.util.validation.validateWritablePath("Firebase.push", this.path);
  fb.core.util.validation.validateFirebaseDataArg("Firebase.push", 1, a, !0);
  fb.util.validation.validateCallback("Firebase.push", 2, b, !0);
  var c = this.repo.serverTime(), c = fb.core.util.NextPushId(c), c = this.child(c);
  "undefined" !== typeof a && null !== a && c.set(a, b);
  return c;
};
goog.exportProperty(Firebase.prototype, "push", Firebase.prototype.push);
Firebase.prototype.onDisconnect = function() {
  return new fb.api.OnDisconnect(this.repo, this.path, this.name());
};
goog.exportProperty(Firebase.prototype, "onDisconnect", Firebase.prototype.onDisconnect);
Firebase.prototype.removeOnDisconnect = function() {
  fb.core.util.warn("FirebaseRef.removeOnDisconnect() being deprecated. Please use FirebaseRef.onDisconnect().remove() instead.");
  this.onDisconnect().remove();
  this.repo.logOnDisconnectDeprecatedSignature();
};
goog.exportProperty(Firebase.prototype, "removeOnDisconnect", Firebase.prototype.removeOnDisconnect);
Firebase.prototype.setOnDisconnect = function(a) {
  fb.core.util.warn("FirebaseRef.setOnDisconnect(value) being deprecated. Please use FirebaseRef.onDisconnect().set(value) instead.");
  this.onDisconnect().set(a);
  this.repo.logOnDisconnectDeprecatedSignature();
};
goog.exportProperty(Firebase.prototype, "setOnDisconnect", Firebase.prototype.setOnDisconnect);
Firebase.prototype.auth = function(a, b, c) {
  fb.util.validation.validateArgCount("Firebase.auth", 1, 3, arguments.length);
  fb.core.util.validation.validateCredential("Firebase.auth", 1, a, !1);
  fb.util.validation.validateCallback("Firebase.auth", 2, b, !0);
  fb.util.validation.validateCallback("Firebase.auth", 3, b, !0);
  this.repo.auth(a, b, c);
};
goog.exportProperty(Firebase.prototype, "auth", Firebase.prototype.auth);
Firebase.prototype.unauth = function(a) {
  fb.util.validation.validateArgCount("Firebase.unauth", 0, 1, arguments.length);
  fb.util.validation.validateCallback("Firebase.unauth", 1, a, !0);
  this.repo.unauth(a);
};
goog.exportProperty(Firebase.prototype, "unauth", Firebase.prototype.unauth);
Firebase.goOffline = function() {
  fb.util.validation.validateArgCount("Firebase.goOffline", 0, 0, arguments.length);
  fb.core.RepoManager.getInstance().interrupt();
};
goog.exportProperty(Firebase, "goOffline", Firebase.goOffline);
Firebase.goOnline = function() {
  fb.util.validation.validateArgCount("Firebase.goOnline", 0, 0, arguments.length);
  fb.core.RepoManager.getInstance().resume();
};
goog.exportProperty(Firebase, "goOnline", Firebase.goOnline);
Firebase.enableLogging = function(a, b) {
  fb.core.util.assert(!b || !0 === a || !1 === a, "Can't turn on custom loggers persistently.");
  !0 === a ? ("undefined" !== typeof console && ("function" === typeof console.log ? fb.core.util.logger = goog.bind(console.log, console) : "object" === typeof console.log && (fb.core.util.logger = function(a) {
    console.log(a);
  })), b && fb.core.storage.SessionStorage.set("logging_enabled", !0)) : a ? fb.core.util.logger = a : (fb.core.util.logger = null, fb.core.storage.SessionStorage.remove("logging_enabled"));
};
goog.exportProperty(Firebase, "enableLogging", Firebase.enableLogging);
Firebase.ServerValue = {TIMESTAMP:{".sv":"timestamp"}};
goog.exportProperty(Firebase, "ServerValue", Firebase.ServerValue);
Firebase.INTERNAL = fb.api.INTERNAL;
goog.exportProperty(Firebase, "INTERNAL", Firebase.INTERNAL);
Firebase.Context = fb.core.RepoManager;
goog.exportProperty(Firebase, "Context", Firebase.Context);

http_parser, TCP sockets manipulate strings, not buffers.

This is okay from a Lua perspective but is causing incompatibilities elsewhere in our Node code.

  1. We need to update the http_parser bindings in lua to deal with buffers (using colony_toconstdata or colony_tobuffer)
  2. Check that the net and http modules are handling buffers appropriately. Remove casts to buffers where they occur.
  3. Increase test coverage.

Express breaking on util.inspect

Trying to run this code sample:

var express = require('express');
var app = express();

app.get('/', function(req, res){
  res.send('Hello World');
});

app.listen(3000);

Error Message:

➜  sandbox  tessel run server.js
TESSEL! Connected to TM-00-04-f000da30-00664340-4a602586.
WARN There is a newer version of firmware available. You should run "tessel update".
INFO Bundling directory /Users/Jon/Work/technical/sandbox (~629.83 KB)
INFO Deploying bundle (999.50 KB)...
INFO Running script...
/app/node_modules/express/node_modules/debug/node.js:48: attempt to index field 'inspect' (a nil value)

Because we haven't implemented util.inspect yet.

Dictionary keys not set if values are null

var dict = {
    host: '0.0.0.0',
    port: 'null',
    server: null,
    verifyClient: null,
    handleProtocols: null,
    path: null,
    noServer: false,
    disableHixie: false,
    clientTracking: true
  };

console.log("dict", dict);

On a Tessel

dict { disableHixie: false, host: '0.0.0.0', port: 'null', clientTracking: true, noServer: false }

How do I run the tests?

I think I found a bug in your JS implementation. I'd like to add a test for it, but I'm not sure how to run them in the first place... any help would be appreciated! :)

BTW -- awesome job, Tessel is pretty incredible.

NaN is not defined

Not undefined, just not defined. At all.

type(NaN) currently returns 'nil' when it should return 'NaN'

Can't compile minified version of Firebase module

See the code to compile below. The error I'm seeing is:

>> colony app.js
fs.js:1740
  fs.writeSync(this.fd, data, 0, data.length);
                                     ^
TypeError: Cannot read property 'length' of undefined
    at SyncWriteStream.write (fs.js:1740:38)
    at /Users/Jon/Work/technical/colony-compiler/bin/colony-compiler.js:47:22
    at Object.exports.compile (/Users/Jon/Work/technical/colony-compiler/src/bytecode/index.js:21:7)
    at Object.exports.toBytecode (/Users/Jon/Work/technical/colony-compiler/src/index.js:29:12)
    at cli (/Users/Jon/Work/technical/colony-compiler/bin/colony-compiler.js:46:12)
    at Object.<anonymous> (/Users/Jon/Work/technical/colony-compiler/bin/colony-compiler.js:55:3)
    at Module._compile (module.js:456:26)
    at Object.Module._extensions..js (module.js:474:10)
    at Module.load (module.js:356:32)
    at Function.Module._load (module.js:312:12)

You can get the code with npm install firebase and app.js just contains:

var fb = require('firebase');

Keen.io not required correctly

See related Forum post.

Test Code (after npm install keen.io)

require('keen.io');

Output:

INFO Running script...
Error: Could not find module "/app/node_modules/keen.io/node_modules/superagent/lib/node.js"
stack traceback:
    /app/node_modules/keen.io/lib/requests.js:62: in function 'res'
    /app/node_modules/keen.io/index.js:4: in function 'res'
    /app/tempbug/tempbug.js:9: in function 'res'
    /_start.js:4: in function 'res'
    [T]: runtime:1: in main chunk

Hangs when doing subtraction with `undefined` values

Here's a simplified version of the bug I ran into:

var mAccelLast;
var delta = 20 - mAccelLast; // Tessel would hang here!

That same code run on V8 (node):

> var mAccelLast;
> var delta = 20 - mAccelLast;
> delta
NaN

This could affect other undefined operations, I don't have a tessel on me to verify.
This was witnessed by @johnnyman727 last night.

Invalid regex when running Express

Test Code:

var express = require('express');
console.log('instantiating');
var app = express();

console.log('setting route');
app.get('/', function(req, res){
    res.send('Hello World');
});

console.log('listening');
var server = app.listen(3000, function() {
    console.log('Listening on port %d', server.address().port);
});

Output:

SyntaxError: Invalid regex "\x2E|\u3002|\uFF0E|\uFF61" (error 8)
stack traceback:
    ...
    /app/app.js:14: in function 'res'
    /_start.js:14: in function 'res'
    [T]: runtime:1: in main chunk
➜  server  tessel run app.js

I should note that sometimes I don't get the above output, but instead the console output terminates with no logs.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.