ronantakizawa/codereview-bench huggingface dataset:
Repository: vuejs/vue-next
File: packages/runtime-core/src/renderer.ts (TypeScript)

Code before:
    anchor: RendererNode | null,
    parentComponent: ComponentInternalInstance | null,
    parentSuspense: SuspenseBoundary | null,
    namespace: ElementNamespace,
    slotScopeIds: string[] | null,
    optimized: boolean,
  ) => {
    if (n2.type === 'svg') {
      namespace = 'svg'
    } else if (n2.type === 'math') {
      namespace = 'mathml'
    }

    if (n1 == null) {
      mountElement(
        n2,
        container,
        anchor,
        parentComponent,
        parentSuspense,
        namespace,
        slotScopeIds,
        optimized,
      )
    } else {
      if (n1.el && (n1.el as VueElement)._isVueCE) {
        ;(n1.el as VueElement)._beginPatch()
      }
      try {
        patchElement(
          n1,
          n2,
          parentComponent,
          parentSuspense,
          namespace,
          slotScopeIds,
          optimized,
        )
      } finally {
        if (n1.el && (n1.el as VueElement)._isVueCE) {
          ;(n1.el as VueElement)._endPatch()
        }
      }
    }
  }

  const mountElement = (
    vnode: VNode,
    container: RendererElement,
    anchor: RendererNode | null,
    parentComponent: ComponentInternalInstance | null,

Review comment (suggestion):
Can be changed to `const isVueCE = !!(n1.el && (n1.el as any)._isVueCE)` `patchElement` may cause `n1` to be unmounted, but `n1.el` still has a value after `patchElement`

Code after:
    anchor: RendererNode | null,
    parentComponent: ComponentInternalInstance | null,
    parentSuspense: SuspenseBoundary | null,
    namespace: ElementNamespace,
    slotScopeIds: string[] | null,
    optimized: boolean,
  ) => {
    if (n2.type === 'svg') {
      namespace = 'svg'
    } else if (n2.type === 'math') {
      namespace = 'mathml'
    }

    if (n1 == null) {
      mountElement(
        n2,
        container,
        anchor,
        parentComponent,
        parentSuspense,
        namespace,
        slotScopeIds,
        optimized,
      )
    } else {
      const customElement = !!(n1.el && (n1.el as VueElement)._isVueCE)
        ? (n1.el as VueElement)
        : null
      try {
        if (customElement) {
          customElement._beginPatch()
        }
        patchElement(
          n1,
          n2,
          parentComponent,
          parentSuspense,
          namespace,
          slotScopeIds,
          optimized,
        )
      } finally {
        if (customElement) {
          customElement._endPatch()
        }
      }
    }
  }

  const mountElement = (
    vnode: VNode,
Repository: vuejs/vue-next
File: packages/runtime-vapor/src/dom/prop.ts (TypeScript)

Code before:
}

/**
 * dev only
 */
function warnOnArrayBlock(prop: string): void {
  warn(
    `Extraneous non-props attributes (` +
      `${prop}) ` +
      `were passed to component but could not be automatically inherited ` +
      `because component renders text or multiple root nodes.`,
  )
}

function setTextToBlock(block: Block, value: any): void {
  if (block instanceof Node) {
    if (block instanceof Element) {
      block.textContent = value
    } else if (__DEV__) {
      warnOnArrayBlock('textContent')
    }
  } else if (isVaporComponent(block)) {
    setTextToBlock(block.block, value)
  } else if (isArray(block)) {
    if (__DEV__) {
      warnOnArrayBlock('textContent')
    }
  } else {
    setTextToBlock(block.nodes, value)
  }
}

export function setHtml(el: TargetElement, value: any): void {
  value = value == null ? '' : value
  if (el.$html !== value) {
    el.innerHTML = el.$html = value
  }
}

export function setBlockHtml(
  block: Block & { $html?: string },
  value: any,
): void {
  value = value == null ? '' : value
  if (block.$html !== value) {
    setHtmlToBlock(block, (block.$html = value))
  }
}

function setHtmlToBlock(block: Block, value: any): void {
  if (block instanceof Node) {

Review comment (suggestion):
Is there a scenario where this could be a single-element array i.e. in which `setTextToBlock(block[0], value)` could be used? Likewise with `setHtmlToBlock`

Code after:
  }
}

/**
 * dev only
 */
function warnCannotSetProp(prop: string): void {
  warn(
    `Extraneous non-props attributes (` +
      `${prop}) ` +
      `were passed to component but could not be automatically inherited ` +
      `because component renders text or multiple root nodes.`,
  )
}

function setTextToBlock(block: Block, value: any): void {
  if (block instanceof Node) {
    if (block instanceof Element) {
      block.textContent = value
    } else if (__DEV__) {
      warnCannotSetProp('textContent')
    }
  } else if (isVaporComponent(block)) {
    setTextToBlock(block.block, value)
  } else if (isArray(block)) {
    if (__DEV__) {
      warnCannotSetProp('textContent')
    }
  } else {
    setTextToBlock(block.nodes, value)
  }
}

export function setHtml(el: TargetElement, value: any): void {
  value = value == null ? '' : unsafeToTrustedHTML(value)
  if (el.$html !== value) {
    el.innerHTML = el.$html = value
  }
}

export function setBlockHtml(
  block: Block & { $html?: string },
  value: any,
): void {
  value = value == null ? '' : value
  if (block.$html !== value) {
    setHtmlToBlock(block, (block.$html = value))
  }
}

function setHtmlToBlock(block: Block, value: any): void {
Repository: vuejs/vue-next
File: packages/runtime-vapor/__tests__/vdomInterop.spec.ts (TypeScript)

Code before:
import { defineComponent, h } from '@vue/runtime-dom'
import { makeInteropRender } from './_utils'
import { createComponent, defineVaporComponent } from '../src'

const define = makeInteropRender()

describe('vdomInterop', () => {
  describe('props', () => {
    test('prevent hasOwnProperty error when props is null', () => {
      const VaporChild = defineVaporComponent({
        props: {
          msg: String,
        },
        setup(_, { attrs }) {
          return [document.createTextNode(attrs.class || 'foo')]
        },
      })

      const { html } = define({
        setup() {
          return () => h(VaporChild as any)
        },
      }).render()

      expect(html()).toBe('foo')
    })
  })

  describe.todo('emit', () => {})

  describe.todo('slots', () => {})

  describe.todo('provide', () => {})


Review comment (suggestion):
```suggestion
    test('should work if props are not provided', () => {
```

Code after:
import { defineComponent, h } from '@vue/runtime-dom'
import { makeInteropRender } from './_utils'
import { createComponent, defineVaporComponent } from '../src'

const define = makeInteropRender()

describe('vdomInterop', () => {
  describe('props', () => {
    test('should work if props are not provided', () => {
      const VaporChild = defineVaporComponent({
        props: {
          msg: String,
        },
        setup(_, { attrs }) {
          return [document.createTextNode(attrs.class || 'foo')]
        },
      })

      const { html } = define({
        setup() {
          return () => h(VaporChild as any)
        },
      }).render()

      expect(html()).toBe('foo')
    })
  })

  describe.todo('emit', () => {})

  describe.todo('slots', () => {})

  describe.todo('provide', () => {})
Repository: vuejs/vue-next
File: packages/runtime-dom/src/components/Transition.ts (TypeScript)

Code before:
    type,
    timeout,
    propCount,
    hasTransform,
  }
}

function getTimeout(delays: string[], durations: string[]): number {
  while (delays.length < durations.length) {
    delays = delays.concat(delays)
  }
  return Math.max(...durations.map((d, i) => toMs(d) + toMs(delays[i])))
}

// Old versions of Chromium (below 61.0.3163.100) formats floating pointer
// numbers in a locale-dependent way, using a comma instead of a dot.
// If comma is not replaced with a dot, the input will be rounded down
// (i.e. acting as a floor function) causing unexpected behaviors
function toMs(s: string): number {
  // #8409 default value for CSS durations can be 'auto'
  if (s === 'auto') return 0
  return Number(s.slice(0, -1).replace(',', '.')) * 1000
}

// synchronously force layout to put elements into a certain state
export function forceReflow(): number {
  const instance = getCurrentInstance()!
  return instance.vnode.el!.ownerDocument.body.offsetHeight
}


Review comment (suggestion):
Consider adding a parameter to `forceReflow` to pass in the `el`. The places where it is called can easily access the `el`.

Code after:
    timeout,
    propCount,
    hasTransform,
  }
}

function getTimeout(delays: string[], durations: string[]): number {
  while (delays.length < durations.length) {
    delays = delays.concat(delays)
  }
  return Math.max(...durations.map((d, i) => toMs(d) + toMs(delays[i])))
}

// Old versions of Chromium (below 61.0.3163.100) formats floating pointer
// numbers in a locale-dependent way, using a comma instead of a dot.
// If comma is not replaced with a dot, the input will be rounded down
// (i.e. acting as a floor function) causing unexpected behaviors
function toMs(s: string): number {
  // #8409 default value for CSS durations can be 'auto'
  if (s === 'auto') return 0
  return Number(s.slice(0, -1).replace(',', '.')) * 1000
}

// synchronously force layout to put elements into a certain state
export function forceReflow(el?: Node): number {
  const targetDocument = el ? el.ownerDocument! : document
  return targetDocument.body.offsetHeight
}
Repository: vuejs/vue-next
File: packages/runtime-core/src/apiSetupHelpers.ts (TypeScript)

Code before:
  PP extends ComponentObjectPropsOptions = ComponentObjectPropsOptions,
>(props: PP): Prettify<Readonly<ExtractPropTypes<PP>>>
// overload 3: typed-based declaration
export function defineProps<TypeProps>(): DefineProps<
  LooseRequired<TypeProps>,
  BooleanKey<TypeProps>
>
// implementation
export function defineProps() {
  if (__DEV__) {
    warnRuntimeUsage(`defineProps`)
  }
  return null as any
}

export type DefineProps<T, BKeys extends keyof T> = Readonly<T> & {
  readonly [K in BKeys]-?: boolean
}

type BooleanKey<T, K extends keyof T = keyof T> = K extends any
  ? [T[K]] extends [boolean | undefined]
    ? boolean extends T[K]
      ? K
      : never
    : never
  : never

/**
 * Vue `<script setup>` compiler macro for declaring a component's emitted
 * events. The expected argument is the same as the component `emits` option.
 *
 * Example runtime declaration:
 * ```js
 * const emit = defineEmits(['change', 'update'])
 * ```
 *
 * Example type-based declaration:
 * ```ts
 * const emit = defineEmits<{
 *   // <eventName>: <expected arguments>
 *   change: []
 *   update: [value: number] // named tuple syntax
 * }>()
 *
 * emit('change')
 * emit('update', 1)
 * ```
 *
 * This is only usable inside `<script setup>`, is compiled away in the
 * output and should **not** be actually called at runtime.
 *

Review comment (suggestion):
```suggestion
type BooleanKey<T, K extends keyof T = keyof T> = K extends any
  ? T[K] extends boolean | undefined
    ? T[K] extends never | undefined
      ? never
      : K
    : never
  : never
```

`boolean extends T[K]` will cause that `true` or `false` is not inferred as boolean keys.

Code after:
  PP extends ComponentObjectPropsOptions = ComponentObjectPropsOptions,
>(props: PP): Prettify<Readonly<ExtractPropTypes<PP>>>
// overload 3: typed-based declaration
export function defineProps<TypeProps>(): DefineProps<
  LooseRequired<TypeProps>,
  BooleanKey<TypeProps>
>
// implementation
export function defineProps() {
  if (__DEV__) {
    warnRuntimeUsage(`defineProps`)
  }
  return null as any
}

export type DefineProps<T, BKeys extends keyof T> = Readonly<T> & {
  readonly [K in BKeys]-?: boolean
}

type BooleanKey<T, K extends keyof T = keyof T> = K extends any
  ? T[K] extends boolean | undefined
    ? T[K] extends never | undefined
      ? never
      : K
    : never
  : never

/**
 * Vue `<script setup>` compiler macro for declaring a component's emitted
 * events. The expected argument is the same as the component `emits` option.
 *
 * Example runtime declaration:
 * ```js
 * const emit = defineEmits(['change', 'update'])
 * ```
 *
 * Example type-based declaration:
 * ```ts
 * const emit = defineEmits<{
 *   // <eventName>: <expected arguments>
 *   change: []
 *   update: [value: number] // named tuple syntax
 * }>()
 *
 * emit('change')
 * emit('update', 1)
 * ```
 *
 * This is only usable inside `<script setup>`, is compiled away in the
 * output and should **not** be actually called at runtime.
 *
Repository: vuejs/vue-next
File: packages/vue-compat/__tests__/componentVModel.spec.ts (TypeScript)

Code before:
    expect(input.value).toBe('bar')
    expect(span.textContent).toBe('bar')
  }

  test('with model modifiers', async () => {
    await runTestWithModifier({
      name: 'CustomInput',
      props: ['value'],
      template: `<input :value="value" @input="$emit('input', $event.target.value)">`,
    })
  })

  test('with model modifiers and model option', async () => {
    await runTestWithModifier({
      name: 'CustomInput',
      props: ['foo'],
      model: {
        prop: 'foo',
        event: 'bar',
      },
      template: `<input :value="foo" @input="$emit('bar', $event.target.value)">`,
    })
  })

  // #14202
  test('should handle v-model deprecation warning with missing appContext (#14202)', async () => {
    const ChildComponent = {
      template: `<div @click="$emit('input', 'new val')">{{ value }}</div>`,
      props: ['value'],
    }

    const vm = new Vue({
      components: { ChildComponent },
      data() {
        return {
          myVal: 'initial',
        }
      },
      template: `
        <div>
          <child-component v-model="myVal"></child-component>
        </div>
      `,
    }).$mount() as any

    expect(vm.$el.textContent).toContain('initial')

    expect(
      (deprecationData[DeprecationTypes.COMPONENT_V_MODEL].message as Function)(
        ChildComponent,
      ),

Review comment (suggestion):
```suggestion
  test('should handle v-model deprecation warning with missing appContext', async () => {
```

Code after:
    expect(input.value).toBe('bar')
    expect(span.textContent).toBe('bar')
  }

  test('with model modifiers', async () => {
    await runTestWithModifier({
      name: 'CustomInput',
      props: ['value'],
      template: `<input :value="value" @input="$emit('input', $event.target.value)">`,
    })
  })

  test('with model modifiers and model option', async () => {
    await runTestWithModifier({
      name: 'CustomInput',
      props: ['foo'],
      model: {
        prop: 'foo',
        event: 'bar',
      },
      template: `<input :value="foo" @input="$emit('bar', $event.target.value)">`,
    })
  })

  // #14202
  test('should handle v-model deprecation warning with missing appContext', async () => {
    const ChildComponent = {
      template: `<div @click="$emit('input', 'new val')">{{ value }}</div>`,
      props: ['value'],
    }

    const vm = new Vue({
      components: { ChildComponent },
      data() {
        return {
          myVal: 'initial',
        }
      },
      template: `
        <div>
          <child-component v-model="myVal"></child-component>
        </div>
      `,
    }).$mount() as any

    expect(vm.$el.textContent).toContain('initial')

    expect(
      (deprecationData[DeprecationTypes.COMPONENT_V_MODEL].message as Function)(
        ChildComponent,
      ),
Repository: vuejs/vue-next
File: packages/runtime-vapor/src/componentSlots.ts (TypeScript)

Code before:
  owner: VaporComponentInstance | null,
): VaporComponentInstance | null {
  try {
    return currentSlotOwner
  } finally {
    currentSlotOwner = owner
  }
}

/**
 * Get the effective slot instance for accessing rawSlots and scopeId.
 * Prefers currentSlotOwner (if inside a slot), falls back to currentInstance.
 */
export function getScopeOwner(): VaporComponentInstance | null {
  return (currentSlotOwner || currentInstance) as VaporComponentInstance | null
}

/**
 * Wrap a slot function to track the slot owner.
 *
 * This ensures:
 * 1. createSlot gets rawSlots from the correct component (slot owner)
 * 2. Elements inherit the slot owner's scopeId
 */
export function withVaporCtx(fn: Function): BlockFn {
  const owner = currentInstance as VaporComponentInstance
  owner.isSlotOwner = true

  return (...args: any[]) => {
    const prevOwner = setCurrentSlotOwner(owner)
    try {
      return fn(...args)
    } finally {
      setCurrentSlotOwner(prevOwner)
    }
  }
}

export function createSlot(
  name: string | (() => string),
  rawProps?: LooseRawProps | null,
  fallback?: VaporSlot,
  noSlotted?: boolean,
  once?: boolean,
): Block {
  const _insertionParent = insertionParent
  const _insertionAnchor = insertionAnchor
  const _isLastInsertion = isLastInsertion
  if (!isHydrating) resetInsertionState()

  const instance = getScopeOwner()!

Review comment (suggestion):
The correct fix should be
```js
const owner = getScopeOwner()
```

Code after:
  owner: VaporComponentInstance | null,
): VaporComponentInstance | null {
  try {
    return currentSlotOwner
  } finally {
    currentSlotOwner = owner
  }
}

/**
 * Get the effective slot instance for accessing rawSlots and scopeId.
 * Prefers currentSlotOwner (if inside a slot), falls back to currentInstance.
 */
export function getScopeOwner(): VaporComponentInstance | null {
  return (currentSlotOwner || currentInstance) as VaporComponentInstance | null
}

/**
 * Wrap a slot function to track the slot owner.
 *
 * This ensures:
 * 1. createSlot gets rawSlots from the correct component (slot owner)
 * 2. Elements inherit the slot owner's scopeId
 */
export function withVaporCtx(fn: Function): BlockFn {
  const owner = getScopeOwner()
  return (...args: any[]) => {
    const prevOwner = setCurrentSlotOwner(owner)
    try {
      return fn(...args)
    } finally {
      setCurrentSlotOwner(prevOwner)
    }
  }
}

export function createSlot(
  name: string | (() => string),
  rawProps?: LooseRawProps | null,
  fallback?: VaporSlot,
  noSlotted?: boolean,
  once?: boolean,
): Block {
  const _insertionParent = insertionParent
  const _insertionAnchor = insertionAnchor
  const _isLastInsertion = isLastInsertion
  if (!isHydrating) resetInsertionState()

  const instance = getScopeOwner()!
  const rawSlots = instance.rawSlots
  const slotProps = rawProps
Repository: vuejs/vue-next
File: packages/runtime-dom/src/jsx.ts (TypeScript)

Code before:
  'aria-valuemin'?: Numberish | undefined
  /**
   * Defines the current value for a range widget.
   * @see aria-valuetext.
   */
  'aria-valuenow'?: Numberish | undefined
  /** Defines the human readable text alternative of aria-valuenow for a range widget. */
  'aria-valuetext'?: string | undefined
}

// Vue's style normalization supports nested arrays
export type StyleValue =
  | false
  | null
  | undefined
  | string
  | CSSProperties
  | Array<StyleValue>

// Support for `class` attribute
export type ClassValue =
  | false
  | null
  | undefined
  | string
  | Record<string, boolean>
  | Array<ClassValue>

export interface HTMLAttributes extends AriaAttributes, EventHandlers<Events> {
  innerHTML?: string | undefined

  class?: ClassValue | undefined
  style?: StyleValue | undefined

  // Standard HTML Attributes
  accesskey?: string | undefined
  contenteditable?: Booleanish | 'inherit' | 'plaintext-only' | undefined
  contextmenu?: string | undefined
  dir?: string | undefined
  draggable?: Booleanish | undefined
  enterkeyhint?:
    | 'enter'
    | 'done'
    | 'go'
    | 'next'
    | 'previous'
    | 'search'
    | 'send'
    | undefined
  /**
   * @deprecated Use `enterkeyhint` instead.

Review comment (suggestion):
Shouldn't it be `Record<string, any>` to allow non-booleans `:class="{ red: errorMessage }"`

Code after:
  'aria-valuemin'?: Numberish | undefined
  /**
   * Defines the current value for a range widget.
   * @see aria-valuetext.
   */
  'aria-valuenow'?: Numberish | undefined
  /** Defines the human readable text alternative of aria-valuenow for a range widget. */
  'aria-valuetext'?: string | undefined
}

// Vue's style normalization supports nested arrays
export type StyleValue =
  | false
  | null
  | undefined
  | string
  | CSSProperties
  | Array<StyleValue>

// Support for `class` attribute
export type ClassValue =
  | false
  | null
  | undefined
  | string
  | Record<string, any>
  | Array<ClassValue>

export interface HTMLAttributes extends AriaAttributes, EventHandlers<Events> {
  innerHTML?: string | undefined

  class?: ClassValue | undefined
  style?: StyleValue | undefined

  // Standard HTML Attributes
  accesskey?: string | undefined
  contenteditable?: Booleanish | 'inherit' | 'plaintext-only' | undefined
  contextmenu?: string | undefined
  dir?: string | undefined
  draggable?: Booleanish | undefined
  enterkeyhint?:
    | 'enter'
    | 'done'
    | 'go'
    | 'next'
    | 'previous'
    | 'search'
    | 'send'
    | undefined
  /**
   * @deprecated Use `enterkeyhint` instead.
Repository: vuejs/vue-next
File: packages/runtime-vapor/src/apiTemplateRef.ts (TypeScript)

Code before:
    return oldRef
  }
}

/**
 * Function for handling a template ref
 */
function setRef(
  instance: VaporComponentInstance,
  el: RefEl,
  ref: NodeRef,
  oldRef?: NodeRef,
  refFor = false,
  refKey?: string,
): NodeRef | undefined {
  if (!instance || instance.isUnmounted) return

  // vdom interop
  const handleVdomRef = (target: any): boolean => {
    if (isInteropEnabled && isFragment(target) && target.setRef) {
      target.setRef(instance, ref, refFor, refKey)
      return true
    }
    return false
  }
  if (handleVdomRef(el)) return

  if (isVaporComponent(el) && isAsyncWrapper(el)) {
    // unresolved: handled in DynamicFragment's updated hook
    if (!el.type.__asyncResolved) return

    // resolved: set ref to the inner component
    el = (el.block as DynamicFragment).nodes as VaporComponentInstance
  }

  const setupState: any = __DEV__ ? instance.setupState || {} : null
  const refValue = getRefValue(el)
  if (handleVdomRef(refValue)) return

  const refs =
    instance.refs === EMPTY_OBJ ? (instance.refs = {}) : instance.refs

  const canSetSetupRef = __DEV__
    ? createCanSetSetupRefChecker(setupState, refs)
    : NO

  const canSetRef = (ref: NodeRef, key?: string) => {
    if (__DEV__ && knownTemplateRefs.has(ref as any)) {
      return false
    }
    if (key && isTemplateRefKey(refs, key)) {

Review comment (suggestion):
```suggestion
  if (handleVdomRef(el)) return ref
```

Code after:
    return oldRef
  }
}

/**
 * Function for handling a template ref
 */
function setRef(
  instance: VaporComponentInstance,
  el: RefEl,
  ref: NodeRef,
  oldRef?: NodeRef,
  refFor = false,
  refKey?: string,
): NodeRef | undefined {
  if (!instance || instance.isUnmounted) return

  // vdom interop
  const handleVdomRef = (target: any): boolean => {
    if (isInteropEnabled && isFragment(target) && target.setRef) {
      target.setRef(instance, ref, refFor, refKey)
      return true
    }
    return false
  }
  if (handleVdomRef(el)) return ref

  if (isVaporComponent(el) && isAsyncWrapper(el)) {
    // unresolved: handled in DynamicFragment's updated hook
    if (!el.type.__asyncResolved) return

    // resolved: set ref to the inner component
    el = (el.block as DynamicFragment).nodes as VaporComponentInstance
  }

  const setupState: any = __DEV__ ? instance.setupState || {} : null
  const refValue = getRefValue(el)
  if (handleVdomRef(refValue)) return ref

  const refs =
    instance.refs === EMPTY_OBJ ? (instance.refs = {}) : instance.refs

  const canSetSetupRef = __DEV__
    ? createCanSetSetupRefChecker(setupState, refs)
    : NO

  const canSetRef = (ref: NodeRef, key?: string) => {
    if (__DEV__ && knownTemplateRefs.has(ref as any)) {
      return false
    }
    if (key && isTemplateRefKey(refs, key)) {