Przeglądaj źródła

refactor content transclusion

Evan You 11 lat temu
rodzic
commit
400f8bf686

+ 1 - 0
component.json

@@ -20,6 +20,7 @@
     "src/batcher.js",
     "src/cache.js",
     "src/compiler/compile.js",
+    "src/compiler/content.js",
     "src/compiler/transclude.js",
     "src/config.js",
     "src/directive.js",

+ 3 - 2
src/api/lifecycle.js

@@ -64,9 +64,10 @@ exports.$destroy = function (remove, deferCleanup) {
  * decompile function.
  *
  * @param {Element|DocumentFragment} el
+ * @param {Vue} [host]
  * @return {Function}
  */
 
-exports.$compile = function (el) {
-  return compile(el, this.$options, true)(this, el)
+exports.$compile = function (el, host) {
+  return compile(el, this.$options, true, host)(this, el)
 }

+ 13 - 68
src/compiler/compile.js

@@ -26,11 +26,11 @@ module.exports = compile
  * @param {Element|DocumentFragment} el
  * @param {Object} options
  * @param {Boolean} partial
- * @param {Boolean} transcluded
+ * @param {Vue} [host] - host vm of transcluded content
  * @return {Function}
  */
 
-function compile (el, options, partial, transcluded) {
+function compile (el, options, partial, host) {
   // link function for the node itself.
   var nodeLinkFn = !partial
     ? compileRoot(el, options)
@@ -53,27 +53,17 @@ function compile (el, options, partial, transcluded) {
    * @return {Function|undefined}
    */
 
-  function compositeLinkFn (vm, el) {
+  return function compositeLinkFn (vm, el) {
     // save original directive count before linking
     // so we can capture the directives created during a
     // partial compilation.
     var originalDirCount = vm._directives.length
-    var parentOriginalDirCount =
-      vm.$parent && vm.$parent._directives.length
     // cache childNodes before linking parent, fix #657
     var childNodes = _.toArray(el.childNodes)
-    // if this is a transcluded compile, linkers need to be
-    // called in source scope, and the host needs to be
-    // passed down.
-    var source = transcluded ? vm.$parent : vm
-    var host = transcluded ? vm : undefined
     // link
-    if (nodeLinkFn) nodeLinkFn(source, el, host)
-    if (childLinkFn) childLinkFn(source, childNodes, host)
-
-    var selfDirs = vm._directives.slice(originalDirCount)
-    var parentDirs = vm.$parent &&
-      vm.$parent._directives.slice(parentOriginalDirCount)
+    if (nodeLinkFn) nodeLinkFn(vm, el, host)
+    if (childLinkFn) childLinkFn(vm, childNodes, host)
+    var dirs = vm._directives.slice(originalDirCount)
 
     /**
      * The linker function returns an unlink function that
@@ -83,38 +73,15 @@ function compile (el, options, partial, transcluded) {
      * @param {Boolean} destroying
      */
     return function unlink (destroying) {
-      teardownDirs(vm, selfDirs, destroying)
-      if (parentDirs) {
-        teardownDirs(vm.$parent, parentDirs)
+      var i = dirs.length
+      while (i--) {
+        dirs[i]._teardown()
+        if (!destroying) {
+          vm._directives.$remove(dirs[i])
+        }
       }
     }
   }
-
-  // transcluded linkFns are terminal, because it takes
-  // over the entire sub-tree.
-  if (transcluded) {
-    compositeLinkFn.terminal = true
-  }
-
-  return compositeLinkFn
-}
-
-/**
- * Teardown a subset of directives on a vm.
- *
- * @param {Vue} vm
- * @param {Array} dirs
- * @param {Boolean} destroying
- */
-
-function teardownDirs (vm, dirs, destroying) {
-  var i = dirs.length
-  while (i--) {
-    dirs[i]._teardown()
-    if (!destroying) {
-      vm._directives.$remove(dirs[i])
-    }
-  }
 }
 
 /**
@@ -201,13 +168,6 @@ function compileNode (node, options) {
 
 function compileElement (el, options) {
   var hasAttrs = el.hasAttributes()
-  if (hasAttrs && checkTransclusion(el)) {
-    // unwrap textNode
-    if (el.hasAttribute('__vue__wrap')) {
-      el = el.firstChild
-    }
-    return compile(el, options._parent.$options, true, true)
-  }
   // check element directives
   var linkFn = checkElementDirectives(el, options)
   // check terminal direcitves (repeat & if)
@@ -708,19 +668,4 @@ function directiveComparator (a, b) {
   a = a.def.priority || 0
   b = b.def.priority || 0
   return a > b ? 1 : -1
-}
-
-/**
- * Check whether an element is transcluded
- *
- * @param {Element} el
- * @return {Boolean}
- */
-
-var transcludedFlagAttr = '__vue__transcluded'
-function checkTransclusion (el) {
-  if (el.nodeType === 1 && el.hasAttribute(transcludedFlagAttr)) {
-    el.removeAttribute(transcludedFlagAttr)
-    return true
-  }
-}
+}

+ 62 - 0
src/compiler/content.js

@@ -0,0 +1,62 @@
+var _ = require('../util')
+
+// This is the elementDirective that handles <content>
+// transclusions. It relies on the raw content of an
+// instance being stored as `$options._content` during
+// the transclude phase.
+
+module.exports = {
+
+  bind: function () {
+    var vm = this.vm
+    var contentOwner = vm
+    // we need find the content owner, which is the closest
+    // non-inline-repeater instance.
+    while (contentOwner.$options._repeat) {
+      contentOwner = contentOwner.$parent
+    }
+    var raw = contentOwner.$options._content
+    var content
+    if (!raw) {
+      // fallback content
+      // extract as a fragment
+      content = _.extractContent(this.el, true)
+      this.compile(content, vm)
+      return
+    }
+    var parent = contentOwner.$parent
+    var selector = this.el.getAttribute('select')
+    if (!selector) {
+      // default content
+      // Importent: clone the rawContent before extracting
+      // content because the <content> may be inside a v-if
+      // and need to be compiled more than once.
+      content = _.extractContent(raw.cloneNode(true), true)
+      this.compile(content, parent, vm)
+    } else {
+      // select content
+      selector = vm.$interpolate(selector)
+      content = raw.querySelector(selector)
+      // only allow top-level select
+      if (content && content.parentNode === raw) {
+        // same deal, clone the node for v-if
+        content = content.cloneNode(true)
+        this.compile(content, parent, vm)
+      }
+    }
+  },
+
+  compile: function (content, owner, host) {
+    if (owner) {
+      this.unlink = owner.$compile(content, host)
+    }
+    _.replace(this.el, content)
+  },
+
+  unbind: function () {
+    if (this.unlink) {
+      this.unlink()
+    } 
+  }
+
+}

+ 2 - 118
src/compiler/transclude.js

@@ -1,7 +1,6 @@
 var _ = require('../util')
 var config = require('../config')
 var templateParser = require('../parsers/template')
-var transcludedFlagAttr = '__vue__transcluded'
 
 /**
  * Process an element or a DocumentFragment based on a
@@ -24,26 +23,6 @@ module.exports = function transclude (el, options) {
   if (options) {
     options._containerAttrs = extractAttrs(el)
   }
-  // Mark content nodes and attrs so that the compiler
-  // knows they should be compiled in parent scope.
-  if (options && options._asComponent) {
-    var i = el.childNodes.length
-    while (i--) {
-      var node = el.childNodes[i]
-      if (node.nodeType === 1) {
-        node.setAttribute(transcludedFlagAttr, '')
-      } else if (node.nodeType === 3 && node.data.trim()) {
-        // wrap transcluded textNodes in spans, because
-        // raw textNodes can't be persisted through clones
-        // by attaching attributes.
-        var wrapper = document.createElement('span')
-        wrapper.textContent = node.data
-        wrapper.setAttribute('__vue__wrap', '')
-        wrapper.setAttribute(transcludedFlagAttr, '')
-        el.replaceChild(wrapper, node)
-      }
-    }
-  }
   // for template tags, what we want is its content as
   // a documentFragment (for block instances)
   if (el.tagName === 'TEMPLATE') {
@@ -77,7 +56,7 @@ function transcludeTemplate (el, options) {
   if (!frag) {
     _.warn('Invalid template option: ' + template)
   } else {
-    var rawContent = options._content || _.extractContent(el)
+    options._content = _.extractContent(el)
     var replacer = frag.firstChild
     if (options.replace) {
       if (
@@ -88,117 +67,22 @@ function transcludeTemplate (el, options) {
         // block instance. (#835)
         replacer.hasAttribute(config.prefix + 'repeat')
       ) {
-        transcludeContent(frag, rawContent)
         return frag
       } else {
         options._replacerAttrs = extractAttrs(replacer)
         mergeAttrs(el, replacer)
-        transcludeContent(replacer, rawContent)
         return replacer
       }
     } else {
       el.appendChild(frag)
-      transcludeContent(el, rawContent)
       return el
     }
   }
 }
 
-/**
- * Resolve <content> insertion points mimicking the behavior
- * of the Shadow DOM spec:
- *
- *   http://w3c.github.io/webcomponents/spec/shadow/#insertion-points
- *
- * @param {Element|DocumentFragment} el
- * @param {Element} raw
- */
-
-function transcludeContent (el, raw) {
-  var outlets = getOutlets(el)
-  var i = outlets.length
-  if (!i) return
-  var outlet, select, selected, j, main
-
-  function isDirectChild (node) {
-    return node.parentNode === raw
-  }
-
-  // first pass, collect corresponding content
-  // for each outlet.
-  while (i--) {
-    outlet = outlets[i]
-    if (raw) {
-      select = outlet.getAttribute('select')
-      if (select) {  // select content
-        selected = raw.querySelectorAll(select)
-        if (selected.length) {
-          // according to Shadow DOM spec, `select` can
-          // only select direct children of the host node.
-          // enforcing this also fixes #786.
-          selected = [].filter.call(selected, isDirectChild)
-        }
-        outlet.content = selected.length
-          ? selected
-          : _.toArray(outlet.childNodes)
-      } else { // default content
-        main = outlet
-      }
-    } else { // fallback content
-      outlet.content = _.toArray(outlet.childNodes)
-    }
-  }
-  // second pass, actually insert the contents
-  for (i = 0, j = outlets.length; i < j; i++) {
-    outlet = outlets[i]
-    if (outlet !== main) {
-      insertContentAt(outlet, outlet.content)
-    }
-  }
-  // finally insert the main content
-  if (main) {
-    insertContentAt(main, _.toArray(raw.childNodes))
-  }
-}
-
-/**
- * Get <content> outlets from the element/list
- *
- * @param {Element|Array} el
- * @return {Array}
- */
-
-var concat = [].concat
-function getOutlets (el) {
-  return _.isArray(el)
-    ? concat.apply([], el.map(getOutlets))
-    : el.querySelectorAll
-      ? _.toArray(el.querySelectorAll('content'))
-      : []
-}
-
-/**
- * Insert an array of nodes at outlet,
- * then remove the outlet.
- *
- * @param {Element} outlet
- * @param {Array} contents
- */
-
-function insertContentAt (outlet, contents) {
-  // not using util DOM methods here because
-  // parentNode can be cached
-  var parent = outlet.parentNode
-  for (var i = 0, j = contents.length; i < j; i++) {
-    parent.insertBefore(contents[i], outlet)
-  }
-  parent.removeChild(outlet)
-}
-
 /**
  * Helper to extract a component container's attribute names
- * into a map. The resulting map will be used in compiler to
- * determine whether an attribute is transcluded.
+ * into a map.
  *
  * @param {Element} el
  * @return {Object}

+ 3 - 0
src/directives/repeat.js

@@ -132,6 +132,7 @@ module.exports = {
       merged._asComponent = true
       merged._parent = this.vm
       this.template = transclude(this.template, merged)
+      this.content = merged._content
       // Important: mark the template as a root node so that
       // custom element components don't get compiled twice.
       // fixes #822
@@ -365,6 +366,8 @@ module.exports = {
       _host: this._host,
       _linkFn: this._linkFn,
       _meta: meta,
+      _content: this.content,
+      _repeat: this.inherit,
       data: data,
       inherit: this.inherit,
       template: this.inlineTempalte

+ 7 - 5
src/vue.js

@@ -35,11 +35,13 @@ extend(Vue, require('./api/global'))
  */
 
 Vue.options = {
-  directives  : require('./directives'),
-  filters     : require('./filters'),
-  transitions : {},
-  components  : {},
-  elementDirectives: {}
+  directives: require('./directives'),
+  filters: require('./filters'),
+  transitions: {},
+  components: {},
+  elementDirectives: {
+    content: require('./compiler/content')
+  }
 }
 
 /**

+ 0 - 33
test/unit/specs/compiler/compile_spec.js

@@ -267,39 +267,6 @@ if (_.inBrowser) {
       expect(vm._bindDir.calls.count()).toBe(0)
     })
 
-    it('should handle nested transclusions', function (done) {
-      vm = new Vue({
-        el: el,
-        template:
-          '<testa>' +
-            '<testb>' +
-              '<div v-repeat="list">{{$value}}</div>' +
-            '</testb>' +
-          '</testa>',
-        data: {
-          list: [1,2]
-        },
-        components: {
-          testa: { template: '<content></content>' },
-          testb: { template: '<content></content>' }
-        }
-      })
-      expect(el.innerHTML).toBe(
-        '<testa><testb>' +
-          '<div>1</div><div>2</div>' +
-        '</testb></testa>'
-      )
-      vm.list.push(3)
-      _.nextTick(function () {
-        expect(el.innerHTML).toBe(
-          '<testa><testb>' +
-            '<div>1</div><div>2</div><div>3</div>' +
-          '</testb></testa>'
-        )
-        done()
-      })
-    })
-
     it('should handle container/replacer directives with same name', function () {
       var parentSpy = jasmine.createSpy()
       var childSpy = jasmine.createSpy()

+ 224 - 0
test/unit/specs/compiler/content_spec.js

@@ -0,0 +1,224 @@
+var Vue = require('../../../../src/vue')
+var _ = require('../../../../src/util')
+
+describe('Content Transclusion', function () {
+
+  var el, vm, options
+  beforeEach(function () {
+    el = document.createElement('div')
+    options = {
+      el: el
+    }
+  })
+
+  function mount () {
+    vm = new Vue(options)
+  }
+
+  it('default content', function () {
+    el.innerHTML = '<p>hi</p>'
+    options.template = '<div><content></content></div>'
+    mount()
+    expect(el.firstChild.tagName).toBe('DIV')
+    expect(el.firstChild.firstChild.tagName).toBe('P')
+    expect(el.firstChild.firstChild.textContent).toBe('hi')
+  })
+
+  it('fallback content', function () {
+    options.template = '<content><p>fallback</p></content>'
+    mount()
+    expect(el.firstChild.tagName).toBe('P')
+    expect(el.firstChild.textContent).toBe('fallback')
+  })
+
+  it('fallback content with multiple select', function () {
+    el.innerHTML = '<p class="b">select b</p>'
+    options.template = '<content select=".a"><p>fallback a</p></content><content select=".b">fallback b</content>'
+    mount()
+    expect(el.childNodes.length).toBe(2)
+    expect(el.firstChild.textContent).toBe('fallback a')
+    expect(el.lastChild.textContent).toBe('select b')
+  })
+
+  it('content transclusion with replace', function () {
+    el.innerHTML = '<p>hi</p>'
+    options.template = '<div><div><content></content></div></div>'
+    options.replace = true
+    mount()
+    var res = vm.$el
+    expect(res).not.toBe(el)
+    expect(res.firstChild.tagName).toBe('DIV')
+    expect(res.firstChild.firstChild.tagName).toBe('P')
+    expect(res.firstChild.firstChild.textContent).toBe('hi')
+  })
+
+  it('block instance content transclusion', function () {
+    el.innerHTML = '<p>hi</p><span>ho</span>'
+    options.template = '<div></div><content select="p"></content><content select="span"></content>'
+    options.replace = true
+    mount()
+    expect(getChild(1).tagName).toBe('DIV')
+    expect(getChild(2).tagName).toBe('P')
+    expect(getChild(3).tagName).toBe('SPAN')
+
+    function getChild (n) {
+      var el = vm._blockStart
+      while (n--) {
+        el = el.nextSibling
+      }
+      return el
+    }
+  })
+
+  it('select should only match children', function () {
+    el.innerHTML = '<p class="b">select b</p><span><p class="b">nested b</p></span><span><p class="c">nested c</p></span>'
+    options.template = '<content select=".a"><p>fallback a</p></content><content select=".b">fallback b</content><content select=".c">fallback c</content>'
+    mount()
+    expect(el.childNodes.length).toBe(3)
+    expect(el.firstChild.textContent).toBe('fallback a')
+    expect(el.childNodes[1].textContent).toBe('select b')
+    expect(el.lastChild.textContent).toBe('fallback c')
+  })
+
+  it('should accept expressions in selectors', function () {
+    el.innerHTML = '<p>one</p><p>two</p>'
+    options.template = '<content select="p:nth-child({{i}})"></content>'
+    options.data = {
+      i: 2
+    }
+    mount()
+    expect(el.innerHTML).toBe('<p>two</p>')
+  })
+
+  it('content should be dynamic and compiled in parent scope', function (done) {
+    var vm = new Vue({
+      el: el,
+      data: {
+        msg: 'hello'
+      },
+      template: '<test>{{msg}}</test>',
+      components: {
+        test: {
+          template: '<content></content>'
+        }
+      }
+    })
+    expect(el.innerHTML).toBe('<test>hello</test>')
+    vm.msg = 'what'
+    _.nextTick(function () {
+      expect(el.innerHTML).toBe('<test>what</test>')
+      done()
+    })
+  })
+  
+  it('v-if with content transclusion', function (done) {
+    var vm = new Vue({
+      el: el,
+      data: {
+        a: 1,
+        show: true
+      },
+      template: '<test show="{{show}}">{{a}}</test>',
+      components: {
+        test: {
+          props: ['show'],
+          template: '<div v-if="show"><content></cotent></div>'
+        }
+      }
+    })
+    expect(el.textContent).toBe('1')
+    vm.a = 2
+    _.nextTick(function () {
+      expect(el.textContent).toBe('2')
+      vm.show = false
+      _.nextTick(function () {
+        expect(el.textContent).toBe('')
+        vm.show = true
+        vm.a = 3
+        _.nextTick(function () {
+          expect(el.textContent).toBe('3')
+          done()
+        })
+      })
+    })
+  })
+
+  it('inline v-repeat', function () {
+    el.innerHTML = '<p>1</p><p>2</p><p>3</p>'
+    var vm = new Vue({
+      el: el,
+      template: '<div v-repeat="list"><content select="p:nth-child({{$index + 1}})"></content></div>',
+      data: {
+        list: 0
+      },
+      beforeCompile: function () {
+        this.list = this.$options._content.querySelectorAll('p').length
+      }
+    })
+    expect(el.innerHTML).toBe('<div><p>1</p></div><div><p>2</p></div><div><p>3</p></div>')
+  })
+
+  it('v-repeat + component + parent directive + transclusion', function (done) {
+    var vm = new Vue({
+      el: el,
+      template: '<test v-repeat="list" v-class="cls">{{msg}}</test>',
+      data: {
+        cls: 'parent',
+        msg: 'hi',
+        list: [{a:1},{a:2},{a:3}]
+      },
+      components: {
+        test: {
+          replace: true,
+          template: '<div class="child">{{a}} <content></content></div>'
+        }
+      }
+    })
+    var markup = vm.list.map(function (item) {
+      return '<div class="child parent">' + item.a + ' hi</div>'
+    }).join('')
+    expect(el.innerHTML).toBe(markup)
+    vm.msg = 'ho'
+    markup = vm.list.map(function (item) {
+      return '<div class="child parent">' + item.a + ' ho</div>'
+    }).join('')
+    _.nextTick(function () {
+      expect(el.innerHTML).toBe(markup)
+      done()
+    })
+  })
+
+  it('nested transclusions', function (done) {
+    vm = new Vue({
+      el: el,
+      template:
+        '<testa>' +
+          '<testb>' +
+            '<div v-repeat="list">{{$value}}</div>' +
+          '</testb>' +
+        '</testa>',
+      data: {
+        list: [1,2]
+      },
+      components: {
+        testa: { template: '<content></content>' },
+        testb: { template: '<content></content>' }
+      }
+    })
+    expect(el.innerHTML).toBe(
+      '<testa><testb>' +
+        '<div>1</div><div>2</div>' +
+      '</testb></testa>'
+    )
+    vm.list.push(3)
+    _.nextTick(function () {
+      expect(el.innerHTML).toBe(
+        '<testa><testb>' +
+          '<div>1</div><div>2</div><div>3</div>' +
+        '</testb></testa>'
+      )
+      done()
+    })
+  })
+
+})

+ 0 - 56
test/unit/specs/compiler/transclude_spec.js

@@ -63,62 +63,6 @@ if (_.inBrowser) {
       expect(res.childNodes[2].nodeType).toBe(3)
     })
 
-    it('content transclusion', function () {
-      el.innerHTML = '<p>hi</p>'
-      options.template = '<div><content></content></div>'
-      var res = transclude(el, options)
-      expect(res.firstChild.tagName).toBe('DIV')
-      expect(res.firstChild.firstChild.tagName).toBe('P')
-      expect(res.firstChild.firstChild.textContent).toBe('hi')
-    })
-
-    it('fallback content', function () {
-      options.template = '<content><p>fallback</p></content>'
-      var res = transclude(el, options)
-      expect(res.firstChild.tagName).toBe('P')
-      expect(res.firstChild.textContent).toBe('fallback')
-    })
-
-    it('fallback content with multiple select', function () {
-      el.innerHTML = '<p class="b">select b</p>'
-      options.template = '<content select=".a"><p>fallback a</p></content><content select=".b">fallback b</content>'
-      var res = transclude(el, options)
-      expect(res.childNodes.length).toBe(2)
-      expect(res.firstChild.textContent).toBe('fallback a')
-      expect(res.lastChild.textContent).toBe('select b')
-    })
-
-    it('content transclusion with replace', function () {
-      el.innerHTML = '<p>hi</p>'
-      options.template = '<div><div><content></content></div></div>'
-      options.replace = true
-      var res = transclude(el, options)
-      expect(res).not.toBe(el)
-      expect(res.firstChild.tagName).toBe('DIV')
-      expect(res.firstChild.firstChild.tagName).toBe('P')
-      expect(res.firstChild.firstChild.textContent).toBe('hi')
-    })
-
-    it('block instance content transclusion', function () {
-      el.innerHTML = '<p>hi</p><span>ho</span>'
-      options.template = '<div></div><content select="p"></content><content select="span"></content>'
-      options.replace = true
-      var res = transclude(el, options)
-      expect(res.childNodes[1].tagName).toBe('DIV')
-      expect(res.childNodes[2].tagName).toBe('P')
-      expect(res.childNodes[3].tagName).toBe('SPAN')
-    })
-
-    it('select should only match children', function () {
-      el.innerHTML = '<p class="b">select b</p><span><p class="b">nested b</p></span><span><p class="c">nested c</p></span>'
-      options.template = '<content select=".a"><p>fallback a</p></content><content select=".b">fallback b</content><content select=".c">fallback c</content>'
-      var res = transclude(el, options)
-      expect(res.childNodes.length).toBe(3)
-      expect(res.firstChild.textContent).toBe('fallback a')
-      expect(res.childNodes[1].textContent).toBe('select b')
-      expect(res.lastChild.textContent).toBe('fallback c')
-    })
-
     it('replacer attr should overwrite container attr of same name, except class should be merged', function () {
       el.setAttribute('class', 'test')
       el.setAttribute('title', 'parent')

+ 0 - 32
test/unit/specs/directives/if_spec.js

@@ -176,38 +176,6 @@ if (_.inBrowser) {
       expect(hasWarned(_, 'already mounted instance')).toBe(true)
     })
 
-    it('v-if with content transclusion', function (done) {
-      var vm = new Vue({
-        el: el,
-        data: {
-          a: 1,
-          show: true
-        },
-        template: '<test show="{{show}}">{{a}}</test>',
-        components: {
-          test: {
-            props: ['show'],
-            template: '<div v-if="show"><content></cotent></div>'
-          }
-        }
-      })
-      expect(el.textContent).toBe('1')
-      vm.a = 2
-      _.nextTick(function () {
-        expect(el.textContent).toBe('2')
-        vm.show = false
-        _.nextTick(function () {
-          expect(el.textContent).toBe('')
-          vm.show = true
-          vm.a = 3
-          _.nextTick(function () {
-            expect(el.textContent).toBe('3')
-            done()
-          })
-        })
-      })
-    })
-
     it('call attach/detach for transcluded components', function (done) {
       document.body.appendChild(el)
       var attachSpy = jasmine.createSpy('attached')

+ 0 - 30
test/unit/specs/directives/repeat_spec.js

@@ -322,36 +322,6 @@ if (_.inBrowser) {
       }
     })
 
-    it('component + parent directive + transclusion', function (done) {
-      var vm = new Vue({
-        el: el,
-        template: '<test v-repeat="list" v-class="cls">{{msg}}</test>',
-        data: {
-          cls: 'parent',
-          msg: 'hi',
-          list: [{a:1},{a:2},{a:3}]
-        },
-        components: {
-          test: {
-            replace: true,
-            template: '<div class="child">{{a}} <content></content></div>'
-          }
-        }
-      })
-      var markup = vm.list.map(function (item) {
-        return '<div class="child parent">' + item.a + ' hi</div>'
-      }).join('')
-      expect(el.innerHTML).toBe(markup)
-      vm.msg = 'ho'
-      markup = vm.list.map(function (item) {
-        return '<div class="child parent">' + item.a + ' ho</div>'
-      }).join('')
-      _.nextTick(function () {
-        expect(el.innerHTML).toBe(markup)
-        done()
-      })
-    })
-
     it('array filters', function (done) {
       var vm = new Vue({
         el: el,

+ 0 - 1
test/unit/specs/instance/init_spec.js

@@ -14,7 +14,6 @@ describe('Instance Init', function () {
 
   var options = {
     a: 2,
-    _anonymous: true,
     el: {}
   }