Projects: initialize project and add folder dependency actions.
diff --git a/bundles/org.eclipse.orion.client.core/web/orion/fileClient.js b/bundles/org.eclipse.orion.client.core/web/orion/fileClient.js
index 6d911b4..bf7c61d 100644
--- a/bundles/org.eclipse.orion.client.core/web/orion/fileClient.js
+++ b/bundles/org.eclipse.orion.client.core/web/orion/fileClient.js
@@ -445,8 +445,21 @@
 		
 		readProject: function(location){
 			return _doServiceCall(this._getService(location), "readProject", arguments); //$NON-NLS-0$
-		}
+		},
 		
+		initProject: function(location){
+			return _doServiceCall(this._getService(location), "initProject", arguments); //$NON-NLS-0$
+		},
+		/**
+		* @param {String} location Project location
+		* @param {Object} dependency The JSON representation of the depenency
+		* @param {String} dependency.Type Type of the depenency (i.e. "file")
+		* @param {String} dependency.Name String description of the dependency (i.e. folder name)
+		* @param {String} dependency.Location Location of the depenency understood by the plugin of given type
+		*/
+		addProjectDepenency: function(location, depenency){
+			return _doServiceCall(this._getService(location), "addProjectDepenency", arguments); //$NON-NLS-0$
+		}
 	};//end FileClient prototype
 	FileClient.prototype.constructor = FileClient;
 
diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/projectCommands.js b/bundles/org.eclipse.orion.client.ui/web/orion/projectCommands.js
index c82410b..7d96ba3 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/projectCommands.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/projectCommands.js
@@ -11,8 +11,8 @@
  *******************************************************************************/
 /*global window define orion XMLHttpRequest confirm*/
 /*jslint sub:true*/
-define(['i18n!orion/navigate/nls/messages', 'orion/webui/littlelib', 'orion/commands', 'orion/Deferred'],
-	function(messages, lib, mCommands, Deferred){
+define(['i18n!orion/navigate/nls/messages', 'orion/webui/littlelib', 'orion/commands', 'orion/Deferred', 'orion/webui/dialogs/DirectoryPrompterDialog'],
+	function(messages, lib, mCommands, Deferred, DirectoryPrompterDialog){
 		var projectCommandUtils = {};
 		
 		var selectionListenerAdded = false;
@@ -117,14 +117,44 @@
 	 */
 	projectCommandUtils.createProjectCommands = function(serviceRegistry, commandService, explorer, fileClient) {
 		progressService = serviceRegistry.getService("orion.page.progress"); //$NON-NLS-0$
+		var that = this;
+		function errorHandler(error) {
+			if (progressService) {
+				progressService.setProgressResult(error);
+			} else {
+				window.console.log(error);
+			}
+		}
 		
 		var addFolderCommand = new mCommands.Command({
-			name: "Add folder",
-			tooltip: "Add an external folder",
+			name: "Add External Folder",
+			tooltip: "Add an external folder from workspace",
 			id: "orion.project.addFolder", //$NON-NLS-0$
 			callback: function(data) {
 				var item = forceSingleItem(data.items);
 				
+				var dialog = new DirectoryPrompterDialog.DirectoryPrompterDialog({ title : messages["Choose a Folder"],
+					serviceRegistry : serviceRegistry,
+					fileClient : fileClient,
+					func : function(targetFolder) {
+						fileClient.read(targetFolder.Location, true).then(function(fileMetadata){
+							var fileLocation = "";
+							if(fileMetadata.Parents){
+								for(var i=fileMetadata.Parents.length-1; i>=0; i--){
+									fileLocation+=fileMetadata.Parents[i].Name;
+									fileLocation+= "/";
+								}
+								fileLocation+=fileMetadata.Name;
+							}
+							fileClient.addProjectDepenency(item.Location, {Name: fileMetadata.Name, Type: "file", Location: fileLocation}).then(function(){
+								explorer.changedItem();
+							}, errorHandler);
+						}, errorHandler);
+					}
+				});
+				
+				dialog.show();
+				
 			},
 			visibleWhen: function(item) {
 				return item.type==="Project";
@@ -138,6 +168,19 @@
 			id: "orion.project.initProject", //$NON-NLS-0$
 			callback: function(data) {
 				var item = forceSingleItem(data.items);
+				var parentProject;
+				if (item.Parents && item.Parents.length===0){
+					parentProject = item;
+				} else if(item.Parents){
+					parentProject = item.Parents[item.Parents.length-1];
+				}
+				if(parentProject){
+					fileClient.initProject(parentProject.Location).then(function(){
+						fileClient.read(item.Location, true).then(function(fileMetadata){
+							explorer.changedItem(fileMetadata);
+						}, errorHandler);
+					}, errorHandler);
+				}
 				
 			},
 			visibleWhen: function(item) {
diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/nav/project-nav.js b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/nav/project-nav.js
index c1a94c0..f32f250 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/nav/project-nav.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/nav/project-nav.js
@@ -106,11 +106,11 @@
 		 * Loads the given children location as the root.
 		 * @param {String|Object} The childrenLocation or an object with a ChildrenLocation field.
 		 */
-		loadRoot: function(childrenLocation) {
+		loadRoot: function(childrenLocation, force) {
 			childrenLocation = (childrenLocation && childrenLocation.ChildrenLocation) || childrenLocation || ""; //$NON-NLS-0$
 			var _self = this;
 			return this.commandsRegistered.then(function() {
-				return _self.loadResourceList.call(_self, childrenLocation);
+				return _self.loadResourceList.call(_self, childrenLocation, force);
 			});
 		},
 		reveal: function(fileMetadata) {
@@ -119,8 +119,13 @@
 			}
 			var navHandler = this.getNavHandler();
 			if (navHandler) {
-				navHandler.cursorOn(fileMetadata, true, false, false);
-				navHandler.setSelection(fileMetadata);
+				if(fileMetadata.Location === this.treeRoot.Location && fileMetadata.Children && fileMetadata.Children.length){
+					navHandler.cursorOn(fileMetadata.Children[0], true, false, false);
+					navHandler.setSelection(fileMetadata.Children[0]);
+				} else {
+					navHandler.cursorOn(fileMetadata, true, false, false);
+					navHandler.setSelection(fileMetadata);
+				}
 			}
 		},
 		// Returns a deferred that completes once file command extensions have been processed
@@ -261,18 +266,21 @@
 	}
 	
 	ProjectNavExplorer.prototype = {
-		display: function(fileMetadata){
+		display: function(fileMetadata, redisplay){
+		this.fileMetadata = fileMetadata;
 		var that = this;
+		
 			if(fileMetadata.ProjectInfo){
-				if(this.projectLocation && this.projectLocation === fileMetadata.ProjectInfo.Location){
+				if(!redisplay && this.projectLocation && this.projectLocation === fileMetadata.ProjectInfo.Location){
 					return;
 				}
+				lib.empty(this.parentNode);
 				this.projectLocation = fileMetadata.ProjectInfo.Location;
 				this.fileClient.readProject(fileMetadata.ProjectInfo.Location).then(
 					function(projectData){
 						projectData.type = "Project";
 						that.renderer.render(projectData);
-						that.fileExplorer.loadRoot(projectData.ContentLocation).then(that.fileExplorer.reveal.bind(that.fileExplorer, fileMetadata));
+						that.fileExplorer.loadRoot(projectData.ContentLocation, redisplay).then(that.fileExplorer.reveal.bind(that.fileExplorer, fileMetadata));
 						that.updateCommands(projectData);
 					},
 					function(error){
@@ -280,8 +288,8 @@
 					}
 				);
 			} else {
-				this.projectLocation = null;
 				lib.empty(this.parentNode);
+				this.projectLocation = null;
 				var parentProject;
 				if (fileMetadata.Parents && fileMetadata.Parents.length===0){
 					parentProject = fileMetadata;
@@ -314,6 +322,13 @@
 			elem.classList.add("pageActions"); //$NON-NLS-0$
 			this.toolbarNode.appendChild(elem);
 		},
+		changedItem: function(fileMetadata){
+			if(fileMetadata){
+				this.display(fileMetadata);
+				return;
+			}
+			this.display(this.fileMetadata, true);
+		},
 		registerCommands : function(){
 			var commandRegistry = this.commandRegistry, fileClient = this.fileClient, serviceRegistry = this.serviceRegistry;
 			commandRegistry.addCommandGroup(this.addActionsScope, "orion.projectNavNewGroup", 1000, messages["Add"], null, null, "core-sprite-addcontent"); //$NON-NLS-1$ //$NON-NLS-0$
@@ -378,7 +393,6 @@
 			});
 			// If there is a target in the navigator, open this target
 			if(this.navigatorInput){
-				var _self = this;
 				this.fileClient.read(this.navigatorInput, true).then(function(fileMetadata){
 					_self.explorer.display(fileMetadata);
 				}, function(error){
diff --git a/bundles/org.eclipse.orion.client.ui/web/plugins/fileClientPlugin.js b/bundles/org.eclipse.orion.client.ui/web/plugins/fileClientPlugin.js
index 9ca96c3..f1d2572 100644
--- a/bundles/org.eclipse.orion.client.ui/web/plugins/fileClientPlugin.js
+++ b/bundles/org.eclipse.orion.client.ui/web/plugins/fileClientPlugin.js
@@ -71,12 +71,16 @@
 	temp.href = "../workspace";
 	// note global
 	var workspaceBase = makeParentRelative(temp.href);
+	
+	temp.href = "../project";
+	// note global
+	var projectBase = makeParentRelative(temp.href);
 
 	temp.href = "..";
 	var patternBase = makeParentRelative(temp.href);
 
 
-	var service = new FileServiceImpl(fileBase, workspaceBase);
+	var service = new FileServiceImpl(fileBase, workspaceBase, projectBase);
 	//provider.registerService("orion.core.file", trace(service), {Name:'Orion Content', top:fileBase, pattern:patternBase});
 	provider.registerService("orion.core.file", service, {
 		Name: 'Orion Content',  // HACK  see https://bugs.eclipse.org/bugs/show_bug.cgi?id=386509
diff --git a/bundles/org.eclipse.orion.client.ui/web/plugins/filePlugin/fileImpl.js b/bundles/org.eclipse.orion.client.ui/web/plugins/filePlugin/fileImpl.js
index 59085a3..fe2057a 100644
--- a/bundles/org.eclipse.orion.client.ui/web/plugins/filePlugin/fileImpl.js
+++ b/bundles/org.eclipse.orion.client.ui/web/plugins/filePlugin/fileImpl.js
@@ -109,9 +109,10 @@
 	 * @class Provides operations on files, folders, and projects.
 	 * @name FileServiceImpl
 	 */
-	function FileServiceImpl(fileBase, workspaceBase) {
+	function FileServiceImpl(fileBase, workspaceBase, projectBase) {
 		this.fileBase = fileBase;
 		this.workspaceBase = workspaceBase;
+		this.projectBase = projectBase;
 		this.makeAbsolute = workspaceBase && workspaceBase.indexOf("://") !== -1;
 	}
 	
@@ -242,6 +243,34 @@
 				return result;
 			}.bind(this));
 		},
+		
+		/**
+		 * Initializes a project in a folder.
+		 * @param {String} contentLocation The location of the parent folder
+		 * @return {Object} JSON representation of the created folder
+		 */
+		initProject: function(contentLocation) {
+			return xhr("POST", this.projectBase, {
+				headers: {
+					"Orion-Version": "1",
+					"X-Create-Options" : "no-overwrite",
+					"Slug": contentLocation,
+					"Content-Type": "application/json;charset=UTF-8"
+				},
+				data: JSON.stringify({
+					"ContentLocation": contentLocation
+				}),
+				timeout: 15000
+			}).then(function(result) {
+				return result.response ? JSON.parse(result.response) : null;
+			}).then(function(result) {
+				if (this.makeAbsolute) {
+					_normalizeLocations(result);
+				}
+				return result;
+			}.bind(this));
+		},
+		
 		/**
 		 * Adds a project to a workspace.
 		 * @param {String} url The workspace location
@@ -280,6 +309,35 @@
 				return result;
 			}.bind(this));
 		},
+		
+		/**
+		* @param {String} location Project location
+		* @param {Object} dependency The JSON representation of the depenency
+		* @param {String} dependency.Type Type of the depenency (i.e. "file")
+		* @param {String} dependency.Name String description of the dependency (i.e. folder name)
+		* @param {String} dependency.Location Location of the depenency understood by the plugin of given type
+		*/
+		addProjectDepenency: function(location, depenency) {
+			return xhr("PUT", location, {
+				headers: {
+					"Orion-Version": "1",
+					"X-Create-Options" : "no-overwrite",
+					"Content-Type": "application/json;charset=UTF-8"
+				},
+				data: JSON.stringify({
+					"Depenency": depenency
+				}),
+				timeout: 15000
+			}).then(function(result) {
+				return result.response ? JSON.parse(result.response) : null;
+			}).then(function(result) {
+				if (this.makeAbsolute) {
+					_normalizeLocations(result);
+				}
+				return result;
+			}.bind(this));
+		},
+		
 		/**
 		 * Creates a folder.
 		 * @param {String} parentLocation The location of the parent folder