| <!DOCTYPE html> |
| <!-- much of this is stolen from omahaproxy.appspot.com/viewer --> |
| <html> |
| <head> |
| <meta content="text/html; charset=iso-8859-1" http-equiv="Content-Type"> |
| <title>NaCl SDK Manifest Viewer</title> |
| </head> |
| <style type="text/css" media="screen"> |
| body { |
| font-family: monospace; |
| font-size: 10pt; |
| } |
| |
| table { |
| border-collapse: collapse; |
| border-color: rgb(100, 100, 100); |
| border-style: solid; |
| border-width: 1px 0px 1px 0px; |
| } |
| |
| table td { |
| padding: 3px; |
| border-color: rgb(100, 100, 100); |
| border-style: solid; |
| border-width: 0px 1px 0px 1px; |
| } |
| |
| thead { |
| background-color: lightblue; |
| font-weight: bold; |
| border-style: solid; |
| border-color: rgb(100, 100, 100); |
| border-width: 0px 0px 2px 0px; |
| text-align: center; |
| } |
| |
| tbody tr:nth-child(odd) { |
| background-color: rgb(230, 230, 230); |
| } |
| |
| tbody tr:hover { |
| background-color: orange; |
| } |
| |
| td a { |
| padding: 3px; |
| } |
| |
| #log > span { |
| display: block; |
| } |
| |
| #log > span.highlight { |
| font-weight: bold; |
| } |
| |
| #log > span.missing { |
| color: #f00; |
| } |
| </style> |
| <body> |
| <h1>NaCl SDK Manifest Viewer</h1> |
| <table> |
| <thead id="columns"> |
| </thead> |
| <tbody id="rows"> |
| </tbody> |
| </table> |
| <h2>Most recent upload log:</h2> |
| <div id="log"> |
| </div> |
| <script type="application/javascript"> |
| function loadText(url, callback) { |
| var xhr = new XMLHttpRequest(); |
| xhr.open('GET', url, true); |
| xhr.onreadystatechange = function (e) { |
| if (xhr.readyState == 4) { |
| if (xhr.status == 200) { |
| callback(xhr.responseText); |
| } else { |
| console.log("Failed to load "+url+": error " + xhr.status); |
| } |
| } |
| } |
| xhr.send(null); |
| } |
| |
| function loadJson(url, callback) { |
| loadText(url, function (text) { |
| callback(JSON.parse(text)); |
| }); |
| } |
| |
| function removeAllChildren(elm) { |
| while (elm.childNodes.length) { |
| elm.removeChild(elm.firstChild); |
| } |
| } |
| |
| function display(data) { |
| data = data.bundles; |
| |
| var columnsElm = document.getElementById('columns'); |
| var rowsElm = document.getElementById('rows'); |
| removeAllChildren(columnsElm); |
| removeAllChildren(rowsElm); |
| |
| // Create the column headers. |
| var tr = document.createElement('tr'); |
| var columns = [ |
| 'name', 'version', 'revision', 'trunk_revision', 'chrome_version', 'win', 'mac', 'linux', 'all' |
| ]; |
| columns.forEach(function(column) { |
| var td = document.createElement('td'); |
| var text = document.createTextNode(column); |
| td.appendChild(text); |
| tr.appendChild(td); |
| }); |
| columnsElm.appendChild(tr); |
| |
| data.forEach(function(row) { |
| var tr = document.createElement('tr'); |
| columns.forEach(function(column) { |
| var td = document.createElement('td'); |
| var node = makeCell(row, column); |
| if (node) { |
| td.appendChild(node); |
| } |
| tr.appendChild(td); |
| }); |
| rowsElm.appendChild(tr); |
| }); |
| } |
| |
| function makeCell(row, column) { |
| var platforms = ['win', 'mac', 'linux', 'all']; |
| |
| if (platforms.indexOf(column) !== -1) { |
| return makePlatformCell(row, column); |
| } else if (column === 'trunk_revision') { |
| return makeTrunkRevisionCell(row); |
| } else if (column === 'chrome_version') { |
| return makeChromeVersionCell(row); |
| } else { |
| return document.createTextNode(row[column]); |
| } |
| } |
| |
| function makePlatformCell(row, column) { |
| var archives = row.archives; |
| for (var k = 0; k < archives.length; ++k) { |
| if (column !== archives[k].host_os) { |
| continue; |
| } |
| |
| // Convert the URL to a short name: |
| // https://.../36.0.1974.2/naclsdk_linux.tar.bz2 -> naclsdk_linux |
| var url = archives[k].url; |
| var lastSlash = url.lastIndexOf('/'); |
| var nextDot = url.indexOf('.', lastSlash); |
| var name = url.substr(lastSlash + 1, nextDot - lastSlash - 1); |
| |
| var node = document.createElement('a'); |
| node.setAttribute('href', url); |
| node.appendChild(document.createTextNode(name)); |
| return node; |
| } |
| return null; |
| } |
| |
| function makeTrunkRevisionCell(row) { |
| var url = row.archives[0].url; |
| var version = versionFromUrl(url); |
| if (version) { |
| var node = document.createTextNode(''); |
| baseTrunkRevisionFromVersion(version, function(node) { |
| return function(revision) { |
| node.textContent = revision; |
| }; |
| }(node)); |
| return node; |
| } |
| return null; |
| } |
| |
| function makeChromeVersionCell(row) { |
| var url = row.archives[0].url; |
| var version = versionFromUrl(url); |
| if (version) { |
| return document.createTextNode(version); |
| } |
| return null; |
| } |
| |
| function versionFromUrl(url) { |
| // Extract the Chrome version from an archive URL. |
| // It should look something like: |
| // https://storage.googleapis.com/nativeclient-mirror/nacl/nacl_sdk/36.0.1974.2/naclsdk_win.tar.bz2 |
| var lastSlash = url.lastIndexOf('/'); |
| var penultimateSlash = url.lastIndexOf('/', lastSlash - 1); |
| // The version is between these two slashes. |
| var version = url.substr(penultimateSlash + 1, |
| lastSlash - penultimateSlash - 1); |
| // It is a chrome version if it matches one of these regexes: |
| if (/trunk\.\d+/.test(version)) { |
| // Trunk version. |
| return version; |
| } else if (/\d+\.\d+\.\d+\.\d+/.test(version)) { |
| // Branch version. |
| return version; |
| } else { |
| // Not a version. |
| return null; |
| } |
| } |
| |
| function baseTrunkRevisionFromVersion(version, callback) { |
| if (version.indexOf('trunk', 0) === 0) { |
| callback(version.substr(6)); // Skip "trunk." |
| } else { |
| revisionFromVersion(baseTrunkVersionFromVersion(version), callback); |
| } |
| } |
| |
| function baseTrunkVersionFromVersion(version) { |
| var lastDot = version.lastIndexOf('.'); |
| return version.substr(0, lastDot) + '.0'; |
| } |
| |
| function revisionFromVersion(version, callback) { |
| var url = 'http://omahaproxy.appspot.com/revision.json?version='+version; |
| loadJson(url, function(data) { |
| callback(data.chromium_revision); |
| }); |
| } |
| |
| function displayLog(text) { |
| var lines = text.split('\n'); |
| var logEl = document.getElementById('log'); |
| lines.forEach(function (line) { |
| var spanEl = document.createElement('span'); |
| spanEl.textContent = line; |
| if (line.indexOf('>>>', 0) === 0) { |
| spanEl.classList.add('highlight'); |
| } else if (line.indexOf('Missing archives') !== -1) { |
| spanEl.classList.add('missing'); |
| } |
| logEl.appendChild(spanEl); |
| }); |
| } |
| |
| loadJson('naclsdk_manifest2.json', display); |
| loadText('naclsdk_manifest2.json.log', displayLog); |
| </script> |
| </body> |
| </html> |