浏览代码

[spark] D&D import functionality for other notebook formats

Enrico Berti 10 年之前
父节点
当前提交
0d5eacffb8

+ 27 - 0
apps/spark/src/spark/static/spark/css/spark.css

@@ -523,3 +523,30 @@ table.airy tr td {
   background-color: #f5f5f5;
   background-color: #f5f5f5;
   padding: 5px;
   padding: 5px;
 }
 }
+
+.hoverMsg {
+  background: #000;
+  height: 100%;
+  left: 0;
+  opacity: .5;
+  position: fixed;
+  width: 100%;
+  top:0;
+  z-index: 10000;
+}
+
+.hoverText {
+  color: #fff;
+  font-size: 5em;
+  position: relative;
+  text-align: center;
+  top: 45%;
+  font-weight: 700;
+  text-shadow: 1px 1px 1px rgba(0,0,0,.3);
+  -webkit-animation-name: bounceInDown;
+  animation-name: bounceInDown;
+  -webkit-animation-duration: 1s;
+  animation-duration: 1s;
+  -webkit-animation-fill-mode: both;
+  animation-fill-mode: both;
+}

+ 3 - 2
apps/spark/src/spark/static/spark/js/spark.ko.js

@@ -689,11 +689,11 @@ var Notebook = function (vm, notebook) {
     self.sessions.push(session);
     self.sessions.push(session);
   };
   };
 
 
-  self.addSnippet = function (snippet) {
+  self.addSnippet = function (snippet, skipSession) {
     var _snippet = new Snippet(vm, self, snippet);
     var _snippet = new Snippet(vm, self, snippet);
     self.snippets.push(_snippet);
     self.snippets.push(_snippet);
 
 
-    if (self.getSession(_snippet.type()) == null) {
+    if (self.getSession(_snippet.type()) == null && typeof skipSession == "undefined") {
       window.setTimeout(function(){
       window.setTimeout(function(){
         self.createSession(new Session(vm, {'type': _snippet.type()}));
         self.createSession(new Session(vm, {'type': _snippet.type()}));
       }, 200);
       }, 200);
@@ -702,6 +702,7 @@ var Notebook = function (vm, notebook) {
     }
     }
 
 
     _snippet.init();
     _snippet.init();
+    return _snippet;
   };
   };
 
 
   self.createSession = function (session, callback, failCallback) {
   self.createSession = function (session, callback, failCallback) {

+ 153 - 0
apps/spark/src/spark/templates/editor_components.mako

@@ -860,12 +860,165 @@ from desktop.views import _ko
   </div>
   </div>
   <div style="position:absolute; width:100%; bottom: 0;"><a class="pointer demi-modal-chevron" data-dismiss="modal"><i class="fa fa-chevron-up"></i></a></div>
   <div style="position:absolute; width:100%; bottom: 0;"><a class="pointer demi-modal-chevron" data-dismiss="modal"><i class="fa fa-chevron-up"></i></a></div>
 </div>
 </div>
+
+<div class="hoverMsg hide">
+  <p class="hoverText">${_('Drop iPython/Zeppelin notebooks here')}</p>
+</div>
+
 </%def>
 </%def>
 
 
 
 
 <%def name="commonJS()">
 <%def name="commonJS()">
+
 <script type="text/javascript" charset="utf-8">
 <script type="text/javascript" charset="utf-8">
 
 
+  // Drag and drop iPython / Zeppelin notebooks
+  if (window.FileReader) {
+
+    var showHoverMsg = function () {
+      $(".hoverMsg").removeClass("hide");
+    };
+
+    var hideHoverMsg = function () {
+      $(".hoverText").html("${_('Drop iPython/Zeppelin notebooks here')}");
+      $(".hoverMsg").addClass("hide");
+    };
+
+    var aceChecks = 0;
+
+    function handleFileSelect(evt) {
+      evt.stopPropagation();
+      evt.preventDefault();
+      var dt = evt.dataTransfer;
+      var files = dt.files;
+      showHoverMsg();
+
+      function addMarkdown(content) {
+        var snip = viewModel.notebooks()[0].addSnippet({type: "text", result: {}}, true);
+        snip.statement_raw(markdown.toHTML(content));
+      }
+
+      function addAce(content, snippetType) {
+        var snip = viewModel.notebooks()[0].addSnippet({type: snippetType, result: {}}, true);
+        snip.statement_raw(content);
+        aceChecks++;
+        snip.checkForAce = window.setInterval(function () {
+          if (snip.ace()) {
+            window.clearInterval(snip.checkForAce);
+            aceChecks--;
+            if (aceChecks == 0) {
+              hideHoverMsg();
+            }
+          }
+        }, 100);
+      }
+
+      function addPySpark(content) {
+        addAce(content, "pyspark");
+      }
+
+      function addSql(content) {
+        addAce(content, "hive");
+      }
+
+      function addScala(content) {
+        addAce(content, "spark");
+      }
+
+      for (var i = 0, f; f = files[i]; i++) {
+        var reader = new FileReader();
+        reader.onload = (function (file) {
+          return function (e) {
+            $(".hoverText").html("<i class='fa fa-spinner fa-spin'></i>");
+            try {
+              var loaded = JSON.parse(e.target.result);
+
+              if (loaded.cells) { //ipython
+                loaded.cells.forEach(function (cell) {
+                  window.setTimeout(function () {
+                    if (cell.cell_type == "code") {
+                      addPySpark(cell.source.join("\n"));
+                    }
+                    if (cell.cell_type == "markdown") {
+                      addMarkdown(cell.source.join("\n"));
+                    }
+                  }, 10);
+                });
+              }
+
+              if (loaded.paragraphs) { //zeppelin
+                if (loaded.name) {
+                  viewModel.notebooks()[0].name(loaded.name);
+                }
+                loaded.paragraphs.forEach(function (paragraph) {
+                  if (paragraph.text) {
+                    var content = paragraph.text.split("\n");
+                    if (content[0].indexOf("%md") > -1) {
+                      content.shift();
+                      addMarkdown(content.join("\n"));
+                    }
+                    else if (content[0].indexOf("%sql") > -1 || content[0].indexOf("%hive") > -1) {
+                      content.shift();
+                      addSql(content.join("\n"));
+                    }
+                    else if (content[0].indexOf("%pyspark") > -1) {
+                      content.shift();
+                      addPySpark(content.join("\n"));
+                    }
+                    else {
+                      if (content[0].indexOf("%spark") > -1){
+                        content.shift();
+                      }
+                      addScala(content.join("\n"));
+                    }
+                  }
+                });
+              }
+            }
+            catch (e) {
+              hideHoverMsg();
+            }
+          };
+        })(f);
+        reader.readAsText(f);
+      }
+    }
+
+    function handleDragOver(evt) {
+      evt.stopPropagation();
+      evt.preventDefault();
+      evt.dataTransfer.dropEffect = "copy";
+    }
+
+    var dropZone = $("body")[0];
+    dropZone.addEventListener("dragenter", showHoverMsg, false);
+    dropZone.addEventListener("dragover", handleDragOver, false);
+    dropZone.addEventListener("drop", handleFileSelect, false);
+
+    var isDraggingOverText = false;
+
+    $(".hoverText").on("dragenter", function (e) {
+      e.preventDefault();
+      e.stopPropagation();
+      e.stopImmediatePropagation();
+      isDraggingOverText = true;
+    });
+
+    $(".hoverText").on("dragleave", function (e) {
+      e.preventDefault();
+      e.stopPropagation();
+      e.stopImmediatePropagation();
+      isDraggingOverText = false;
+    });
+
+    $(".hoverMsg").on("dragleave", function (e) {
+      if (!isDraggingOverText) {
+        hideHoverMsg();
+      }
+    });
+  }
+
+
   ace.config.set("basePath", "/static/desktop/js/ace");
   ace.config.set("basePath", "/static/desktop/js/ace");
 
 
   $.scrollbarWidth = function() {
   $.scrollbarWidth = function() {