@es-plus/vue2

es-plus for Vue 2 + Element UI: configuration-driven enterprise components, sharing the same JSON config schema as @es-plus/vue3 (Vue 3 + Element Plus)
2,121 14
Install
npm install @es-plus/vue2
Latest Version:1.4.0
Vue:2
License:MIT
Last Updated:Oct 24, 2026
Links: GitHub  ·  npm
Maintainer: jiaaowuhan

@es-plus/vue2

Vue 2 + Element UI renderer for the es-plus ecosystem — sharing the same JSON-schema CRUD configuration as the Vue 3 renderer (@es-plus/vue3).

npm version Vue 2 Element UI License: MIT

Why @es-plus/vue2

  • Same config, two frameworks — a single columns / formItemList definition powers both Vue 2 and Vue 3 deployments. No rewrites when migrating, no divergence between teams on different stacks.
  • AI-friendly schema-driven CRUD — built around a stable JSON Schema, ideal for code-gen, MCP tools, and LLM workflows.
  • Element UI parity — bundles EsForm, EsTable, EsDialog, EsCrudPage, useDialog, plus the same httpRequest / permission / global-config plumbing.

Compatibility

Dependency Supported
Vue ^2.6.14 (Vue 2.7's native Composition API is preferred)
@vue/composition-api ^1.7.0 (required only on Vue ≤ 2.6)
Element UI ^2.15.0
@es-plus/core ^1.0.0

Install

# Vue 2.7+ — only vue and element-ui needed.
# Since 1.1.1, @vue/composition-api is inlined into the dist, so it does NOT
# need to be in your dependencies. The polyfill code is shipped but never
# executed on Vue 2.7+ (the runtime selects Vue's native Composition API).
npm install @es-plus/vue2 element-ui vue@^2.7

# Vue 2.6.x — install @vue/composition-api alongside; EsPlus.install()
# will call Vue.use(VueCompositionAPI) automatically.
npm install @es-plus/vue2 element-ui @vue/composition-api vue@^2.6

Setup

// Since 1.1.0, @es-plus/vue2 auto-detects the host Vue version at runtime
// and wires the Composition API source for you — do NOT add
// `Vue.use(VueCompositionAPI)` in main.js:
//   - Vue 2.7+: uses Vue's native Composition API; polyfill is inlined into
//               the dist (since 1.1.1) and remains as dead code at runtime.
//   - Vue 2.6 : EsPlus.install() calls Vue.use(VueCompositionAPI) for you
//               (using the inlined polyfill instance).
// (On Vue 2.7, if both natives setup and the polyfill plugin are active,
//  setup() runs twice — the install() function logs a warning and you
//  should remove your manual Vue.use(VueCompositionAPI).)

import Vue from 'vue'
import ElementUI from 'element-ui'
import 'element-ui/lib/theme-chalk/index.css'

import EsPlus from '@es-plus/vue2'
import '@es-plus/vue2/dist/style.css'

import { configureEsPlus } from '@es-plus/core/config'

Vue.use(ElementUI)
Vue.use(EsPlus)

configureEsPlus({
  httpRequest: async ({ url, method, data }) => {
    return fetch(url, { method, body: JSON.stringify(data) }).then(r => r.json())
  },
  configTableOut: (res) => ({ list: res.data.records, total: res.data.total }),
  permission: (code) => store.state.permissions.includes(code),
})

Quick example

<template>
  <es-table
    :columns="columns"
    :api-params="apiParams"
    :btn-config="btnConfig"
    :form-item-list="searchForm"
  />
</template>

<script>
export default {
  data: () => ({
    apiParams: { url: '/api/users', method: 'GET' },
    columns: [
      { prop: 'name', label: '姓名', width: 120 },
      { prop: 'status', label: '状态', formatter: row => row.status === 1 ? '启用' : '禁用' },
      { label: '操作', btnList: [
        { name: '编辑', click: (row) => this.edit(row) },
        { name: '删除', type: 'danger', click: (row) => this.remove(row) },
      ] },
    ],
    searchForm: [
      { prop: 'keyword', label: '关键词', formtype: 'Input' },
      { prop: 'status', label: '状态', formtype: 'Select', options: [
        { label: '启用', value: 1 }, { label: '禁用', value: 0 },
      ] },
    ],
    btnConfig: [
      { name: '新增', type: 'primary', code: 1, click: () => this.create() },
    ],
  }),
}
</script>

The same columns / searchForm / btnConfig arrays work unchanged in @es-plus/vue3 — only Vue.use() and the import path differ.

Components

Component Purpose
EsForm Configuration-driven form with row/col layout, fold/unfold, validation
EsTable Configuration-driven table with toolbar, pagination, search form, cross-page selection
EsDialog Programmable dialog used by useDialog
EsCrudPage Schema-driven CRUD page assembling EsTable + EsForm + useDialog
useDialog Imperative dialog API (open, close, confirm)

Sharing the same config across Vue 2 and Vue 3

The columns / formItemList / btnConfig / apiParams shapes live in @es-plus/core. Use them as the single source of truth for configs that ship to both renderers:

// shared/employee.config.ts
import type { ColumnConfig, FormItemConfig } from '@es-plus/core/types'

export const employeeColumns: ColumnConfig[] = [/* ... */]
export const employeeForm: FormItemConfig[] = [/* ... */]
// vue3/EmployeePage.vue   AND   vue2/EmployeePage.vue
import { employeeColumns, employeeForm } from '@/shared/employee.config'

Differences vs @es-plus/vue3

Feature Vue 3 (@es-plus/vue3) Vue 2 (@es-plus/vue2)
Virtual scrolling (virtual: true) Yes (el-table-v2) Not supported — Element UI has no el-table-v2 (warns and degrades)
update:dataSource (two-way sync) Emitted Not emitted — table data stays internal in httpRequest mode; read it via the table instance instead
EsForm toolbar dropdown (custom query / custom table / refresh) Yes Not implemented
ElConfigProvider locale/size injection Yes Use Element UI's global Vue.use(ElementUI, { locale, size })
Icons Element Plus icon components Element UI class strings (el-icon-edit) — converted automatically when needed
Default size default (Element Plus) mini — matches Element UI v2 visual density

validateField / useDialog return the same Promise / { instance, close, destroy } shapes as Vue 3, so await form.validateField('name') and const { close } = dialog({...}) are portable across ends.

update:dataSource is intentionally absent: emitting it re-created a .sync reactivity feedback loop under Vue 2.6 + @vue/composition-api. The same class of loop was solved for update:pagination with a value-snapshot guard, but the equivalent guard has not been built for table data.

size values written for Vue 3 (large / default / small) are auto-mapped into Element UI's (medium / small / mini) so configs remain portable.

Migration from Vue 3

You generally don't migrate — you target both. If you do:

  1. Replace import EsPlus from '@es-plus/vue3' with import EsPlus from '@es-plus/vue2'.
  2. Swap vue@3 + element-plus for vue@2 + element-ui (and @vue/composition-api if on 2.6).
  3. Drop virtual: true on tables (or keep it — it's silently ignored).
  4. <script setup> and <el-icon><Delete/></el-icon> aren't Vue 2 syntax — convert to Options API / template strings as appropriate.

Repository

Monorepo: github.com/liujiaao/es-plus

License

MIT © liujiaao

Related Packages

@es-plus/vue3

es-plus for Vue 3 + Element Plus: configuration-driven enterprise components, sh...

1,208 14
@es-plus/adapter-antdv

ES-Plus Ant Design Vue adapter — configuration-driven enterprise components (EsF...

782 14
ll-form-table

基于vue2.6和element-ui封装的以数据驱动视图的表单表格组件,将表单、表格由`templat...

330 0
vue-element-pro-components

This is a vue2、element-ui based component library

1,555 4
@itagan/form-table

Vue 2.7 + Element UI editable form table component.

1,461 0

Version History

Version Released Vue License
1.4.0 ^2.6.14 || ^2.7.0 MIT
1.3.0 ^2.6.14 || ^2.7.0 MIT
1.2.0 ^2.6.14 || ^2.7.0 MIT
1.1.4 ^2.6.14 || ^2.7.0 MIT
1.1.3 ^2.6.14 || ^2.7.0 MIT