/*\ title: $:/plugins/dropbox/dropbox.js type: application/javascript module-type: startup Startup the Dropbox integration plugin \*/ (function(){ /*jslint node: true, browser: true */ /*global $tw: false */ "use strict"; // Obfuscated API key var apiKey = "m+qwjj8wFRA=|1TSoitGS9Nz2RTwv+jrUJnsAj0yy57NhQJ4TkZ/+Hw=="; // Query string marker for forcing authentication var queryLoginMarker = "login=true"; $tw.plugins.dropbox = { client: null, // Dropbox.js client object fileInfo: {}, // Hashmap of each file as retrieved from Dropbox: {versionTag:,title:} titleIsLoggedIn: "$:/plugins/dropbox/IsLoggedIn", titleUserName: "$:/plugins/dropbox/UserName", titlePublicAppUrl: "$:/plugins/dropbox/PublicAppUrl", titleAppTemplateHtml: "$:/plugins/dropbox/apptemplate.html", titleTiddlerIndex: "$:/plugins/dropbox/Index", titleAppIndexTemplate: "$:/plugins/dropbox/index.template.html", titleWikiName: "$:/plugins/dropbox/WikiName", titleLoadedWikis: "$:/plugins/dropbox/LoadedWikis" }; // Error handling $tw.plugins.dropbox.showError = function(error) { alert("Dropbox error: " + error); console.log("Dropbox error: " + error); }; // Authenticate $tw.plugins.dropbox.login = function() { $tw.plugins.dropbox.client.authenticate(function(error, client) { if(error) { return $tw.plugins.dropbox.showError(error); } // Mark us as logged in $tw.wiki.addTiddler({title: $tw.plugins.dropbox.titleIsLoggedIn, text: "yes"},true); // Get user information $tw.plugins.dropbox.getUserInfo(function() { // Invoke any dropbox-startup modules var mods = $tw.modules.types["dropbox-startup"]; for(var m=0; m> 18; // 16515072 = (2^6 - 1) << 18 b = (chunk & 258048) >> 12; // 258048 = (2^6 - 1) << 12 c = (chunk & 4032) >> 6; // 4032 = (2^6 - 1) << 6 d = chunk & 63; // 63 = 2^6 - 1 // Convert the raw binary segments to the appropriate ASCII encoding base64.push(charmap[a],charmap[b],charmap[c],charmap[d]); } // Deal with the remaining bytes and padding if(byteRemainder === 1) { chunk = data[mainLength]; a = (chunk & 252) >> 2; // 252 = (2^6 - 1) << 2 // Set the 4 least significant bits to zero b = (chunk & 3) << 4; // 3 = 2^2 - 1 base64.push(charmap[a],charmap[b],"=="); } else if(byteRemainder === 2) { chunk = (data[mainLength] << 8) | data[mainLength + 1]; a = (chunk & 64512) >> 10; // 64512 = (2^6 - 1) << 10 b = (chunk & 1008) >> 4; // 1008 = (2^6 - 1) << 4 // Set the 2 least significant bits to zero c = (chunk & 15) << 2; // 15 = 2^4 - 1 base64.push(charmap[a],charmap[b],charmap[c],"="); } return base64.join(""); }; // Rewrite the document location to include a force login marker $tw.plugins.dropbox.forceLogin = function() { if(document.location.search.indexOf(queryLoginMarker) === -1) { document.location.search = queryLoginMarker; } }; // Create a new empty TiddlyWiki $tw.plugins.dropbox.createWiki = function(wikiName) { // Remove any dodgy characters from the wiki name wikiName = wikiName.replace(/[\!\@\€\£\%\^\*\+\$\:\?\#\/\\\<\>\|\"\'\`\~\=]/g,""); // Check that the name isn't now empty if(wikiName.length === 0) { return alert("Bad wiki name"); } // Create the wiki async.series([ function(callback) { // First create the wiki folder $tw.plugins.dropbox.client.mkdir(wikiName,function(error,stat) { callback(error); }); }, function(callback) { // Second create the tiddlers folder $tw.plugins.dropbox.client.mkdir(wikiName + "/tiddlers",function(error,stat) { callback(error); }); }, function(callback) { // Third save the template app HTML file var tiddler = $tw.wiki.getTiddler($tw.plugins.dropbox.titleAppTemplateHtml); if(!tiddler) { callback("Cannot find app template tiddler"); } else { $tw.plugins.dropbox.client.writeFile(wikiName + "/index.html",tiddler.fields.text,function(error,stat) { callback(error); }); } } ], // optional callback function(error,results) { if(error) { $tw.plugins.dropbox.showError(error); } else { alert("Created wiki " + wikiName); } }); }; // Save the index file $tw.plugins.dropbox.saveTiddlerIndex = function(path,callback) { // Get the tiddler index information var index = {tiddlers: [],shadows: [], fileInfo: $tw.plugins.dropbox.fileInfo}; // First all the tiddlers $tw.wiki.forEachTiddler(function(title,tiddler) { if(tiddler.isShadow) { index.shadows.push(tiddler.fields); } else { index.tiddlers.push(tiddler.fields); } }); // Save everything to a tiddler $tw.wiki.addTiddler({title: $tw.plugins.dropbox.titleTiddlerIndex, type: "application/json", text: JSON.stringify(index)},true); // Generate the index file var file = $tw.wiki.renderTiddler("text/plain",$tw.plugins.dropbox.titleAppIndexTemplate); // Save the index to Dropbox $tw.plugins.dropbox.client.writeFile(path,file,function(error,stat) { callback(error); }); }; exports.startup = function() { if(!$tw.browser) { return; } // Mark us as not logged in $tw.wiki.addTiddler({title: $tw.plugins.dropbox.titleIsLoggedIn, text: "no"},true); // Initialise Dropbox for sandbox access $tw.plugins.dropbox.client = new Dropbox.Client({key: apiKey, sandbox: true}); // Use the basic redirection authentication driver $tw.plugins.dropbox.client.authDriver(new Dropbox.Drivers.Redirect({rememberUser: true})); // Authenticate ourselves if the marker is in the document query string if(document.location.search.indexOf(queryLoginMarker) !== -1) { $tw.plugins.dropbox.login(); } }; })();