Skip to content

Publicación ​

Este documento explica cómo publicar @lh-ui/vue3 en el registro público npm y cómo hospedarlo en un servidor privado (dos enfoques: enlace directo al tarball y metadatos de registry).

La publicación admite dos canales: manual y automático por CI: localmente se ejecutan los comandos de changeset, y una persona confirma el número de versión y las notas de cambios antes de publicar el paquete (apartado «Flujo de publicación» más abajo); al hacer push a main cuando hay cambios en .changeset/**, GitHub Actions ejecuta automáticamente version + publish (apartado «Publicación automática con GitHub Actions»).

Preparación ​

1. Cuenta npm y propiedad del scope ​

  • Registra una cuenta en npm y activa la verificación en dos pasos (2FA).

  • Confirma que tu cuenta tiene permiso de publicación en el scope @lh-ui: los scopes se asignan por orden de llegada; la primera cuenta que publique un paquete @lh-ui/* se convierte en propietaria del scope.

  • Inicia sesión localmente:

    bash
    npm whoami          # Confirma la cuenta actualmente identificado
    npm login           # Si no estás identificado, sigue las indicaciones para completar el login + 2FA

2. Confirmar que el registry apunta al repositorio público ​

El .npmrc de la raíz del repositorio solo configura shamefully-hoist = true, no fija el registry, de modo que por defecto se usa https://registry.npmjs.org/. El publishConfig de package.json también bloquea el repositorio público:

json
"publishConfig": {
  "access": "public",
  "registry": "https://registry.npmjs.org/"
}

No escribas una dirección de registry privado en el .npmrc de la raíz del repositorio: eso desviaría también la publicación hacia el origen privado. Para cambiar el registry temporalmente, usa el .npmrc de nivel de usuario fuera del proyecto o un parámetro de línea de comandos.

3. Qué incluye una publicación ​

La lista blanca files solo publica los artefactos de compilación: es/ (ESM + tipos + estilos de componentes), lib/ (CJS) y dist/ (UMD + estilos completos). El código fuente, la documentación, las pruebas y los scripts se excluyen mediante .npmignore. Al ejecutar el comando de publicación, prepublishOnly ejecuta primero pnpm build automáticamente, de modo que no es necesario compilar a mano de antemano.

Flujo de publicación ​

Paso 1: escribir el changeset ​

Todo cambio visible para el usuario debería tener su changeset. Si este cambio ya lo tiene, salta al paso 2.

bash
pnpm changeset

Sigue las indicaciones interactivas para elegir @lh-ui/vue3, el tipo de bump (major / minor / patch) y la descripción de los cambios.

Nota: los changesets de este repositorio son acumulativos. Actualmente hay decenas de changesets sin consumir acumulados en .changeset/; al ejecutar changeset version en el paso 2 se consumirán todos de una sola vez y se fusionarán en una única versión. Si quieres publicar por lotes, primero debes usar ramas de git o mover manualmente parte de los archivos de changeset para controlar el ritmo.

Paso 2: subir el número de versión y generar el CHANGELOG ​

bash
pnpm changeset:version

Este comando:

  • Calcula el nuevo número de versión a partir del nivel de bump más alto de los changesets y lo escribe en package.json
  • Agrega todos los changesets para generar CHANGELOG.md
  • Elimina los .changeset/*.md consumidos (en config.json, commit: false, no se confirma automáticamente)

Tras ejecutarlo, revisa manualmente:

bash
git status              # Confirma que los changesets se han consumido y que se ha generado el CHANGELOG
git diff package.json   # Confirma que el número de versión es el esperado

Paso 3: publicar ​

bash
pnpm changeset:publish

Internamente ejecuta pnpm publish; el flujo es:

  1. Dispara prepublishOnly → pnpm build (compilación completa: ESM / CJS / UMD / tipos / estilos)
  2. Empaqueta según publishConfig y lo publica en el registro público npm
  3. Genera y envía la etiqueta de git (con el formato @lh-ui/vue3@<version>)

Como publishConfig.access es public, los paquetes con scope también serán visibles públicamente, sin necesidad de añadir --access public.

Paso 4: enviar (lo ejecutas tú) ​

bash
git push --follow-tags

Autocomprobación antes de publicar ​

Antes de publicar oficialmente, usa una ejecución dry-run para revisar el contenido real del paquete:

bash
npm pack --dry-run

Confirma que la salida:

  • Solo contiene los tres directorios es/, lib/ y dist/
  • No incluye src/, packages/, docs/, tests/, scripts/, ai/
  • El tamaño es razonable (el paquete UMD completo ocupa unos 600 KB y los estilos completos unos 700 KB, dentro del rango esperado)

Verificación después de publicar ​

bash
# 1. La nueva versión es visible en npm
npm view @lh-ui/vue3
npm view @lh-ui/vue3 versions

# 2. Crea un proyecto aislado para probar los tres formatos de módulo
pnpm create vite verify-pkg --template vue-ts
cd verify-pkg && pnpm add @lh-ui/vue3

En el proyecto aislado, verifica uno a uno:

Elemento a verificarEscritura
Importación completa (ESM)import LhUiPlus from '@lh-ui/vue3' + import '@lh-ui/vue3/dist/index.css'
Importación a demanda de componentesimport { LhButton } from '@lh-ui/vue3'
Importación a demanda de estilos (requiere sass)import '@lh-ui/vue3/style/button'
Importación a demanda de estilos (sin sass)import '@lh-ui/vue3/style-css/button'
Utilidades de temaimport { getThemeVars } from '@lh-ui/vue3/theme'
CDN (tras unos minutos, actualiza)https://unpkg.com/@lh-ui/vue3

Alojamiento en servidor propio (tarball estático) ​

El registro público npm es el canal de publicación principal; si necesitas un mirror autohospedado (uso en intranet, npm bloqueado o deseo de fijar una versión concreta), colocar el tarball en tu propio servidor es la solución más ligera, sin necesidad de montar un registry npm privado.

1. Empaquetar el tarball ​

bash
pnpm build
npm pack

El nombre del archivo generado es lh-ui-vue3-<version>.tgz: npm transforma el @lh-ui/ del scope en lh-ui-vue3- (la barra se convierte en guion). También puedes confirmar con npm pack --dry-run de antemano.

2. Subirlo al servidor ​

Siguiendo la convención de directorios del sitio nginx existente (el sitio de documentación se despliega en /home/webuser/nginx/lh-ui/vue3/), crea debajo un directorio packages/ y organiza los archivos por versión:

/home/webuser/nginx/lh-ui/vue3/
├── index.html              # Sitio de documentación
└── packages/
    ├── 1.0.0/
    │   └── lh-ui-vue3-1.0.0.tgz
    ├── 1.1.0/
    │   └── lh-ui-vue3-1.1.0.tgz
    └── latest              # Enlace simbólico a la versión recomendada actual
        └── lh-ui-vue3-1.1.0.tgz

URL correspondiente:

https://www.lhgb.top/lhui/vue3/packages/1.0.0/lh-ui-vue3-1.0.0.tgz

packages/ es un directorio de archivos estáticos; basta con reutilizar la configuración nginx del sitio existente, sin añadir un nuevo location:

nginx
# El location ya existente del sitio de documentación cubre el prefijo /lhui/vue3/,
# de modo que packages/ es automáticamente accesible como subdirectorio; solo asegúrate
# de que el Content-Type del .tgz permite la descarga (el octet-stream por defecto de nginx sirve)
location /lhui/vue3/ {
    alias /home/webuser/nginx/lh-ui/vue3/;
    autoindex off;
}

3. Instalar desde el servidor privado ​

Tres formas equivalentes, a elegir una:

bash
# pnpm
pnpm add https://www.lhgb.top/lhui/vue3/packages/1.0.0/lh-ui-vue3-1.0.0.tgz

# npm
npm install https://www.lhgb.top/lhui/vue3/packages/1.0.0/lh-ui-vue3-1.0.0.tgz

# yarn
yarn add https://www.lhgb.top/lhui/vue3/packages/1.0.0/lh-ui-vue3-1.0.0.tgz

O directamente en package.json:

json
{
  "dependencies": {
    "@lh-ui/vue3": "https://www.lhgb.top/lhui/vue3/packages/1.0.0/lh-ui-vue3-1.0.0.tgz"
  }
}

4. Consideraciones ​

  • Omite la resolución de dependencias del registry: la instalación del tarball no consulta el registry; las dependencias proceden directamente de lo declarado dentro del tarball. Este paquete no tiene dependencies en tiempo de ejecución, únicamente peerDependencies.vue, de modo que el proyecto de consumo puede instalarlo y ejecutarlo siempre que tenga Vue 3.
  • Sin metadatos de versión: npm update no funciona con dependencias de tarball; las actualizaciones deben hacer cambiando la URL manualmente (o modificando el enlace simbólico latest y reinstalando). Adecuado como mirror de versión fijada, no para actualizaciones frecuentes.
  • https es obligatorio: pnpm / npm / yarn rechazan por defecto las direcciones tarball en http.
  • En pnpm-lock.yaml aparecerá la URL completa + hash de integridad: en el trabajo en equipo el archivo de bloqueo reproduce la instalación correctamente, sin necesidad de acceder a npm.

Alojamiento en servidor propio (metadatos de registry) ​

El enlace directo al tarball anterior funciona, pero npm update no surge efecto y el lockfile contiene una URL. Si prefieres que el lado de consumo pueda hacer pnpm add @lhgb/vue3 como un paquete normal, con resolución de versiones y dist-tags, puedes hacer que el directorio estático de Nginx sirva adicionalmente unos metadatos de registry npm falsificados, actuando como registry de solo lectura. Ambos enfoques pueden coexistir.

1. Empaquetar ​

bash
pnpm build
node scripts/pack-private.mjs

Lo que hace el script: renombra los mismos artefactos de compilación como @lhgb/vue3 (únicamente difieren name y publishConfig), npm pack genera el tarball, calcula integrity (sha512) y shasum (sha1), monta el JSON de metadatos de registry y lo saca a private-registry/:

private-registry/
├── @lhgb/vue3              # JSON de metadatos (sin extensión)
└── tarballs/@lhgb/vue3/
    └── lhgb-vue3-1.0.0.tgz

Parámetros habituales:

  • --dry-run: solo imprime la lista de archivos que se generarían y los metadatos, sin escribir a disco; sirve para revisar antes de publicar
  • --incremental: lee los metadatos existentes y fusiona la nueva versión, evitando sobrescribir versiones históricas

2. Desplegar en el servidor ​

Sube el contenido de private-registry/ al directorio del servidor y aplica el location de scripts/nginx-private-registry.conf.example (el mismo Nginx que el sitio de documentación /lhui/vue3/, con un location independiente):

/home/webuser/nginx/registry/
├── @lhgb/vue3
└── tarballs/@lhgb/vue3/
    └── lhgb-vue3-1.0.0.tgz

La clave de la configuración de Nginx es default_type application/json: los archivos de metadatos no tienen extensión y, si no se declara el tipo a la fuerza, el cliente los interpretará como texto plano y fallará. La configuración completa se encuentra en scripts/nginx-private-registry.conf.example (el .tgz debe colocarse solo en un location de expresión regular de nivel superior, no anidado dentro de ^~ /lhgb/, de lo contrario la coincidencia de prefijo saltaría la expresión regular):

nginx
location ^~ /lhgb/ {
  alias /home/webuser/nginx/registry/;
  default_type application/json;
  autoindex off;
  expires 5m;
}

location ~ ^/lhgb/(.+\.tgz)$ {
  alias /home/webuser/nginx/registry/$1;
  default_type application/octet-stream;
  expires 1y;
  add_header Cache-Control "public, immutable" always;
}

3. Instalar desde el registry privado ​

Añade una línea al .npmrc de nivel de proyecto o de usuario:

ini
@lhgb:registry=https://www.lhgb.top/lhgb

Los tres gestores de paquetes son uniformes:

bash
pnpm add @lhgb/vue3
# o
npm install @lhgb/vue3
# o
yarn add @lhgb/vue3

4. Relación con el paquete público ​

@lhgb/vue3 y @lh-ui/vue3 comparten origen y versión: los artefactos de compilación son exactamente iguales; únicamente difieren name y registry, y son intercambiables:

  • Para escenarios de intranet / npm bloqueado / necesidad de fijar el origen de publicación, usa @lhgb/vue3
  • Para escenarios orientados al exterior, donde quieres que los CDN unpkg / jsdelivr puedan servirlo, usa @lh-ui/vue3

5. Consideraciones ​

  • Los metadatos deben actualizarse de forma incremental: tras cada publicación, fusiona la nueva versión con --incremental; sobrescribir directamente perdería los metadatos de las versiones históricas y las versiones antiguas no podrían instalarse.
  • El tarball no se puede mover: la URL tarball de los metadatos es una ruta absoluta; la ubicación del archivo y la URL deben corresponderse una a una.
  • https es igualmente obligatorio: pnpm / npm / yarn rechazan por defecto las direcciones http.
  • No escribas el registry @lhgb en el .npmrc de la raíz del repositorio: el .npmrc raíz solo debe conservar shamefully-hoist = true; la dirección del registry privado va en el .npmrc de nivel de usuario ~/.npmrc, para no contaminar la cadena de publicación.

Publicación automática con GitHub Actions ​

Además del flujo manual, .github/workflows/release.yml ofrece un canal de publicación automática:

  • Condición de disparo: push a main con cambios en .changeset/** o package.json; o disparo manual desde la página Actions del repositorio (workflow_dispatch).
  • Comportamiento: tras ejecutar pnpm build + pnpm verify:dts ejecuta el version + publish de changesets/action; cuando no hay changesets pendientes de publicación no hace nada, de modo que mantenerlo enganchado al push es seguro.
  • Secreto necesario: configura NPM_TOKEN en los Settings del repositorio → Secrets and variables → Actions: genera un Granular Access Token en npm y marca el permiso de publish para la organización @lh-ui.

Los canales manual y automático pueden coexistir: pnpm changeset:publish local es adecuado para escenarios en los que se quiere confirmar manualmente cada publicación; el CI es adecuado para publicar de forma acumulativa una vez consolidados los changesets.

Rollback ​

bash
# Marcar una versión como obsoleta (recomendado; no afecta a los usuarios que ya la tienen instalada)
npm deprecate @lh-ui/vue3@1.0.0 "Esta versión tiene un problema xx; actualiza a 1.0.1"

# Retirar definitivamente: solo es posible dentro de las 72 horas siguientes a la publicación y sin que otros paquetes dependan de ella
npm unpublish @lh-ui/vue3@1.0.0

La caché de los CDN (unpkg / jsdelivr) caduca al cabo de unas horas o de un día; tras el rollback puedes verificar en un proyecto aislado, usando una URL con número de versión, que la versión antigua sigue siendo instalable.

La belleza de la tradición, el cimiento del código