├── demos ├── demo-esjs-terminal │ ├── src │ │ ├── main.js │ │ └── app.esjs │ ├── public │ │ └── favicon.ico │ ├── README.md │ ├── package.json │ ├── index.html │ └── vite.config.js ├── demo-eshtml │ ├── public │ │ └── favicon.ico │ ├── indice.esjs │ ├── fuente │ │ ├── indice.esjs │ │ └── paginas │ │ │ ├── contador.esjs │ │ │ └── contador.eshtml │ ├── package.json │ ├── indice.eshtml │ └── vite.config.js └── demo-esvue │ ├── public │ └── favicon.ico │ ├── src │ ├── main.ts │ ├── GitHub.esvue │ ├── vite-env.d.ts │ └── App.esvue │ ├── package.json │ ├── index.html │ ├── vite.config.ts │ └── tsconfig.json ├── packages ├── vscode-esjs │ ├── .github │ │ ├── FUNDING.yml │ │ └── workflows │ │ │ └── release.yml │ ├── .npmrc │ ├── .vscodeignore │ ├── res │ │ └── icon.png │ ├── .gitignore │ ├── test │ │ └── index.test.ts │ ├── tsup.config.ts │ ├── tsconfig.json │ ├── syntaxes │ │ └── esvue.tmLanguage.json │ ├── languages │ │ └── esvue-language-configuration.json │ ├── README.md │ ├── src │ │ └── utils │ │ │ └── register-methods-completion.ts │ ├── LICENSE │ └── scripts │ │ └── generate-grammars-configurations.ts ├── core │ ├── test │ │ └── fixtures │ │ │ ├── extras │ │ │ ├── NeN.esjs │ │ │ ├── NeN.js │ │ │ ├── consola.js │ │ │ ├── consola.esjs │ │ │ ├── apoderado.js │ │ │ ├── apoderado.esjs │ │ │ ├── depurador.esjs │ │ │ ├── depurador.js │ │ │ ├── funcion.esjs │ │ │ ├── funcion.js │ │ │ ├── booleano.js │ │ │ ├── json.js │ │ │ ├── booleano.esjs │ │ │ ├── enterogrande.js │ │ │ ├── json.esjs │ │ │ ├── enterogrande.esjs │ │ │ ├── constantes.js │ │ │ ├── numero.js │ │ │ ├── constantes.esjs │ │ │ ├── numero.esjs │ │ │ ├── cadena.js │ │ │ ├── cadena.esjs │ │ │ ├── promesa.js │ │ │ ├── promesa.esjs │ │ │ ├── matriz.js │ │ │ ├── matriz.esjs │ │ │ ├── simbolo.js │ │ │ ├── objetos.js │ │ │ ├── objetos.esjs │ │ │ ├── simbolo.esjs │ │ │ ├── soporte.js │ │ │ ├── mate.js │ │ │ ├── soporte.esjs │ │ │ ├── mate.esjs │ │ │ ├── fecha.js │ │ │ └── navegador.js │ │ │ └── keywords │ │ │ ├── este.js │ │ │ ├── este.esjs │ │ │ ├── exportar.js │ │ │ ├── exportar.esjs │ │ │ ├── literal.js │ │ │ ├── literal.esjs │ │ │ ├── importar.js │ │ │ ├── importar.esjs │ │ │ ├── si.js │ │ │ ├── si.esjs │ │ │ ├── templateLiterals.esjs │ │ │ ├── templateLiterals.js │ │ │ ├── props.js │ │ │ ├── asincrono.js │ │ │ ├── props.esjs │ │ │ ├── tipoDe.js │ │ │ ├── asincrono.esjs │ │ │ ├── tipoDe.esjs │ │ │ ├── funcion.js │ │ │ └── funcion.esjs │ ├── src │ │ ├── vite-env.d.ts │ │ ├── compiler │ │ │ └── esbabel.compiler.ts │ │ ├── plugins │ │ │ ├── objetos │ │ │ │ └── index.ts │ │ │ ├── booleano │ │ │ │ └── index.ts │ │ │ ├── funcion │ │ │ │ └── index.ts │ │ │ ├── json │ │ │ │ └── index.ts │ │ │ ├── apoderado │ │ │ │ └── index.ts │ │ │ ├── soporte │ │ │ │ └── index.ts │ │ │ ├── promesa │ │ │ │ └── index.ts │ │ │ ├── enterogrande │ │ │ │ └── index.ts │ │ │ └── consola │ │ │ │ └── index.ts │ │ ├── keywords.ts │ │ ├── utils.ts │ │ └── index.ts │ ├── vitest.config.ts │ ├── README.md │ ├── .gitignore │ ├── tsconfig.json │ └── build.config.ts ├── esbabel │ ├── test │ │ └── fixtures │ │ │ └── esjs │ │ │ ├── NeN.esjs │ │ │ ├── NeN.js │ │ │ ├── consola.js │ │ │ ├── consola.esjs │ │ │ ├── booleano.js │ │ │ ├── booleano.esjs │ │ │ ├── este.js │ │ │ ├── este.esjs │ │ │ ├── exportar.js │ │ │ ├── exportar.esjs │ │ │ ├── literal.js │ │ │ ├── literal.esjs │ │ │ ├── importar.js │ │ │ ├── numero.js │ │ │ ├── importar.esjs │ │ │ ├── cadena.js │ │ │ ├── numero.esjs │ │ │ ├── cadena.esjs │ │ │ ├── si.js │ │ │ ├── si.esjs │ │ │ ├── templateLiterals.esjs │ │ │ ├── templateLiterals.js │ │ │ ├── array.js │ │ │ ├── array.esjs │ │ │ ├── asincrono.js │ │ │ ├── asincrono.esjs │ │ │ ├── funcion.js │ │ │ ├── funcion.esjs │ │ │ └── fecha.js │ ├── vitest.config.ts │ ├── src │ │ └── index.ts │ ├── build.config.ts │ ├── README.md │ ├── .gitignore │ ├── tsconfig.json │ └── package.json ├── prueba │ ├── lib │ │ └── vite-env.d.ts │ ├── .gitignore │ ├── README.md │ ├── vitest.config.ts │ ├── vite.config.js │ ├── tsconfig.json │ ├── package.json │ └── test │ │ └── async-prueba.test.ts ├── esjs-loader │ ├── fixtures │ │ └── test.esjs │ ├── vitest.config.ts │ ├── build.config.ts │ ├── tsconfig.json │ ├── test │ │ └── index.test.ts │ └── package.json ├── terminal │ ├── src │ │ ├── vite-env.d.ts │ │ ├── main.ts │ │ ├── style.css │ │ └── components │ │ │ └── es-terminal.ts │ ├── public │ │ └── favicon.ico │ ├── README.md │ ├── tsconfig.node.json │ ├── .gitignore │ ├── index.html │ ├── tsconfig.json │ └── vite.config.ts ├── vite-plugin-eshtml │ ├── test │ │ ├── fixtures │ │ │ └── basic │ │ │ │ ├── fuente │ │ │ │ ├── indice.esjs │ │ │ │ └── paginas │ │ │ │ │ └── licencia.eshtml │ │ │ │ └── indice.eshtml │ │ ├── __snapshots__ │ │ │ └── getEntryScripts.test.ts.snap │ │ ├── replaceEntryScript.test.ts │ │ └── getEntryScripts.test.ts │ ├── README.md │ ├── build.config.ts │ ├── src │ │ └── lib │ │ │ ├── getPage.ts │ │ │ ├── replaceEntryScript.ts │ │ │ ├── generatePagesInput.ts │ │ │ ├── getEntryScripts.ts │ │ │ └── utils.ts │ └── tsconfig.json ├── sandbox │ ├── .gitignore │ ├── README.md │ ├── tailwind.config.js │ ├── vitest.config.ts │ ├── src │ │ ├── utils │ │ │ ├── formatCode.ts │ │ │ └── generateImportFunctions.ts │ │ ├── transformers │ │ │ ├── index.ts │ │ │ ├── format.transformer.ts │ │ │ └── exportFunctions.transformer.ts │ │ ├── runtime │ │ │ └── index.ts │ │ ├── vite-env.d.ts │ │ └── compiler │ │ │ ├── constants.ts │ │ │ └── orchestrator.ts │ ├── test │ │ ├── transformers │ │ │ ├── exportFunctions.transformer.test.ts │ │ │ └── format.transformer.test.ts │ │ └── utils │ │ │ ├── generateImportFunctions.test.ts │ │ │ └── codeFrame.test.ts │ ├── tsconfig.json │ └── vite.config.js ├── prettier-plugin-esjs │ ├── .gitignore │ ├── vite.config.ts │ ├── tsconfig.json │ ├── README.md │ ├── test │ │ └── package.test.ts │ └── package.json ├── prettier-plugin-esvue │ ├── .gitignore │ ├── vite.config.ts │ ├── tsconfig.json │ ├── README.md │ ├── test │ │ └── package.test.ts │ └── package.json ├── prettier-plugin-eshtml │ ├── .gitignore │ ├── vite.config.ts │ ├── tsconfig.json │ ├── README.md │ ├── test │ │ └── package.test.ts │ └── package.json ├── eshtml │ ├── src │ │ ├── parser.ts │ │ ├── utils │ │ │ ├── replaceDocType.ts │ │ │ └── generateAttributeUsages.ts │ │ └── render.ts │ ├── build.config.ts │ ├── tsconfig.json │ └── test │ │ ├── utils │ │ └── generateAttributeUsages.test.ts │ │ ├── tags.test.ts │ │ ├── attrs.test.ts │ │ └── testUtils.ts ├── runtime │ ├── pnpm-lock.yaml │ └── package.json ├── vite-plugin-esvue │ ├── test │ │ ├── fixtures │ │ │ └── basic │ │ │ │ ├── src │ │ │ │ ├── main.ts │ │ │ │ └── App.esvue │ │ │ │ └── index.html │ │ └── vite-plugin-esvue.test.ts │ ├── build.config.ts │ ├── tsconfig.json │ └── src │ │ └── index.ts ├── language-tools │ ├── vite.config.js │ ├── src │ │ ├── generate-esvue-syntax.js │ │ ├── generate-esjs-snippets.js │ │ ├── index.js │ │ ├── generate-esvue-language-configurations.js │ │ └── generate-esjs-language-configurations.js │ ├── assets │ │ ├── esvue.tmLanguage.json │ │ └── esvue-language-configuration.json │ └── README.md ├── tiza │ ├── README.md │ ├── vite.config.js │ ├── test │ │ └── tiza.test.js │ ├── package.json │ └── src │ │ └── colors.js ├── vite-plugin-esjs │ ├── build.config.ts │ ├── tsconfig.json │ ├── src │ │ └── index.ts │ └── package.json ├── esvue │ ├── build.config.ts │ ├── tsconfig.json │ └── package.json └── cli │ ├── commands │ ├── ayuda.mjs │ ├── actualizar.mjs │ ├── ejecutar.mjs │ ├── repl.mjs │ └── crear.mjs │ ├── postinstall.js │ ├── package.json │ ├── README.md │ └── pnpm-lock.yaml ├── pnpm-workspace.yaml ├── .browserslistrc ├── .npmrc ├── apps └── playground │ ├── .npmrc │ ├── server │ ├── tsconfig.json │ └── middleware │ │ └── subdomain.ts │ ├── app │ ├── components │ │ ├── ui │ │ │ ├── sonner │ │ │ │ ├── index.ts │ │ │ │ └── Sonner.vue │ │ │ ├── separator │ │ │ │ ├── index.ts │ │ │ │ └── Separator.vue │ │ │ ├── popover │ │ │ │ ├── index.ts │ │ │ │ ├── PopoverTrigger.vue │ │ │ │ └── Popover.vue │ │ │ ├── resizable │ │ │ │ ├── index.ts │ │ │ │ └── ResizablePanelGroup.vue │ │ │ ├── tabs │ │ │ │ ├── index.ts │ │ │ │ ├── Tabs.vue │ │ │ │ ├── TabsList.vue │ │ │ │ ├── TabsContent.vue │ │ │ │ └── TabsTrigger.vue │ │ │ ├── tooltip │ │ │ │ ├── index.ts │ │ │ │ ├── TooltipTrigger.vue │ │ │ │ ├── TooltipProvider.vue │ │ │ │ └── Tooltip.vue │ │ │ ├── dialog │ │ │ │ ├── DialogClose.vue │ │ │ │ ├── DialogTrigger.vue │ │ │ │ ├── DialogHeader.vue │ │ │ │ ├── Dialog.vue │ │ │ │ ├── DialogFooter.vue │ │ │ │ ├── index.ts │ │ │ │ ├── DialogDescription.vue │ │ │ │ └── DialogTitle.vue │ │ │ ├── dropdown-menu │ │ │ │ ├── DropdownMenuGroup.vue │ │ │ │ ├── DropdownMenuShortcut.vue │ │ │ │ ├── DropdownMenuTrigger.vue │ │ │ │ ├── DropdownMenu.vue │ │ │ │ ├── DropdownMenuSub.vue │ │ │ │ ├── DropdownMenuRadioGroup.vue │ │ │ │ ├── DropdownMenuSeparator.vue │ │ │ │ ├── DropdownMenuLabel.vue │ │ │ │ ├── DropdownMenuItem.vue │ │ │ │ ├── DropdownMenuSubTrigger.vue │ │ │ │ └── index.ts │ │ │ └── button │ │ │ │ └── Button.vue │ │ ├── AppSeparator.vue │ │ ├── AppContainer.vue │ │ ├── input │ │ │ └── LanguageSwitcher.vue │ │ ├── playground │ │ │ ├── PlaygroundPanes.vue │ │ │ └── PlaygroundMobileView.vue │ │ ├── AppTabButton.vue │ │ └── AppMenu.vue │ ├── pages │ │ ├── [code].vue │ │ ├── index.vue │ │ ├── github │ │ │ └── [...repo].vue │ │ ├── login.vue │ │ └── aprender │ │ │ └── [...slug].vue │ ├── app.config.ts │ ├── constants │ │ └── app.js │ ├── utils │ │ └── cn.ts │ ├── app.vue │ ├── composables │ │ ├── dark.ts │ │ ├── useOctokit.ts │ │ ├── useCompiler.ts │ │ ├── useAuth.ts │ │ └── usePlayground.ts │ ├── middleware │ │ └── redirect.global.ts │ ├── layouts │ │ ├── default.vue │ │ └── learn.vue │ └── router.options.ts │ ├── public │ └── favicon.ico │ ├── tsconfig.json │ ├── .env.example │ ├── tailwind.config.ts │ ├── content │ ├── intermedios │ │ ├── index.md │ │ └── 1.modulos.md │ └── fundamentos │ │ ├── 11.funciones.md │ │ ├── 6.constantes.md │ │ ├── 1.hola-mundo.md │ │ ├── 4.comentarios.md │ │ ├── index.md │ │ ├── 9.flujo-de-ejecucion.md │ │ └── 3.identificadores.md │ ├── .gitignore │ ├── components.json │ └── README.md ├── scripts ├── bump.sh └── release.sh ├── .editorconfig ├── .gitignore ├── biome.json ├── package.json ├── .github └── workflows │ └── test.yml └── LICENSE /demos/demo-esjs-terminal/src/main.js: -------------------------------------------------------------------------------- 1 | import './app.esjs' 2 | -------------------------------------------------------------------------------- /packages/vscode-esjs/.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | github: [enzonotario] 2 | -------------------------------------------------------------------------------- /pnpm-workspace.yaml: -------------------------------------------------------------------------------- 1 | packages: 2 | - packages/* 3 | - demos/* 4 | -------------------------------------------------------------------------------- /.browserslistrc: -------------------------------------------------------------------------------- 1 | > 1% 2 | last 2 versions 3 | not dead 4 | not ie 11 5 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/NeN.esjs: -------------------------------------------------------------------------------- 1 | const test = esNuN('a') 2 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/NeN.js: -------------------------------------------------------------------------------- 1 | const test = isNaN('a') 2 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/consola.js: -------------------------------------------------------------------------------- 1 | console.log('test'); 2 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/NeN.esjs: -------------------------------------------------------------------------------- 1 | const test = esNuN('a') 2 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/NeN.js: -------------------------------------------------------------------------------- 1 | const test = isNaN('a') 2 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/consola.js: -------------------------------------------------------------------------------- 1 | console.log('test'); 2 | -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | shared-workspace-lockfile=false 2 | prefer-workspace-packages=true 3 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/consola.esjs: -------------------------------------------------------------------------------- 1 | consola.escribir('test'); 2 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/consola.esjs: -------------------------------------------------------------------------------- 1 | consola.escribir('test'); 2 | -------------------------------------------------------------------------------- /packages/prueba/lib/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /apps/playground/.npmrc: -------------------------------------------------------------------------------- 1 | shamefully-hoist=true 2 | strict-peer-dependencies=false 3 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/booleano.js: -------------------------------------------------------------------------------- 1 | const x = new Boolean(true) 2 | -------------------------------------------------------------------------------- /packages/esjs-loader/fixtures/test.esjs: -------------------------------------------------------------------------------- 1 | consola.escribir("Hola desde EsJS") 2 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/apoderado.js: -------------------------------------------------------------------------------- 1 | let apoderado = new Proxy({}, {}) 2 | -------------------------------------------------------------------------------- /packages/vscode-esjs/.npmrc: -------------------------------------------------------------------------------- 1 | ignore-workspace-root-check=true 2 | node-linker=hoisted 3 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/apoderado.esjs: -------------------------------------------------------------------------------- 1 | mut apoderado = crear Apoderado({}, {}) 2 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/depurador.esjs: -------------------------------------------------------------------------------- 1 | funcion hola() { 2 | depurador; 3 | } 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/depurador.js: -------------------------------------------------------------------------------- 1 | function hola() { 2 | debugger; 3 | } 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/booleano.esjs: -------------------------------------------------------------------------------- 1 | const x = crear Booleano(verdadero) 2 | -------------------------------------------------------------------------------- /packages/vscode-esjs/.vscodeignore: -------------------------------------------------------------------------------- 1 | src 2 | node_modules 3 | test 4 | .github 5 | .vscode 6 | -------------------------------------------------------------------------------- /apps/playground/server/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../.nuxt/tsconfig.server.json" 3 | } 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/funcion.esjs: -------------------------------------------------------------------------------- 1 | const miFuncion = Funcion('return "hola"'); 2 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/funcion.js: -------------------------------------------------------------------------------- 1 | const miFuncion = Function('return "hola"'); 2 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/sonner/index.ts: -------------------------------------------------------------------------------- 1 | export { default as Toaster } from './Sonner.vue' 2 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/este.js: -------------------------------------------------------------------------------- 1 | function test() { 2 | this.variable = 'hola'; 3 | } 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/este.js: -------------------------------------------------------------------------------- 1 | function test() { 2 | this.variable = 'hola'; 3 | } 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/este.esjs: -------------------------------------------------------------------------------- 1 | funcion test() { 2 | ambiente.variable = 'hola'; 3 | } 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/exportar.js: -------------------------------------------------------------------------------- 1 | export default function() { 2 | return true; 3 | } 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/este.esjs: -------------------------------------------------------------------------------- 1 | funcion test() { 2 | ambiente.variable = 'hola'; 3 | } 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/exportar.js: -------------------------------------------------------------------------------- 1 | export default function() { 2 | return true; 3 | } 4 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/separator/index.ts: -------------------------------------------------------------------------------- 1 | export { default as Separator } from './Separator.vue' 2 | -------------------------------------------------------------------------------- /packages/terminal/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | 3 | declare module 'is-number' 4 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/test/fixtures/basic/fuente/indice.esjs: -------------------------------------------------------------------------------- 1 | consola.escribir('Hola mundo desde EsJS'); 2 | -------------------------------------------------------------------------------- /packages/vscode-esjs/res/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/es-js/esjs/HEAD/packages/vscode-esjs/res/icon.png -------------------------------------------------------------------------------- /apps/playground/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/es-js/esjs/HEAD/apps/playground/public/favicon.ico -------------------------------------------------------------------------------- /demos/demo-eshtml/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/es-js/esjs/HEAD/demos/demo-eshtml/public/favicon.ico -------------------------------------------------------------------------------- /demos/demo-esvue/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/es-js/esjs/HEAD/demos/demo-esvue/public/favicon.ico -------------------------------------------------------------------------------- /packages/core/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | 3 | declare module '@putout/bundle' 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/exportar.esjs: -------------------------------------------------------------------------------- 1 | exportar porDefecto funcion() { 2 | retornar verdadero; 3 | } 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/literal.js: -------------------------------------------------------------------------------- 1 | const literal = 'si' 2 | const foo = "bar" 3 | const test = `esjs` 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/exportar.esjs: -------------------------------------------------------------------------------- 1 | exportar porDefecto funcion() { 2 | retornar verdadero; 3 | } 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/literal.js: -------------------------------------------------------------------------------- 1 | const literal = 'si' 2 | const foo = "bar" 3 | const test = `esjs` 4 | -------------------------------------------------------------------------------- /packages/terminal/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/es-js/esjs/HEAD/packages/terminal/public/favicon.ico -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/literal.esjs: -------------------------------------------------------------------------------- 1 | const literal = 'si' 2 | const foo = "bar" 3 | const test = `esjs` 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/literal.esjs: -------------------------------------------------------------------------------- 1 | const literal = 'si' 2 | const foo = "bar" 3 | const test = `esjs` 4 | -------------------------------------------------------------------------------- /packages/prueba/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .DS_Store 3 | dist 4 | dist-ssr 5 | *.local 6 | types 7 | package-lock.json 8 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/importar.js: -------------------------------------------------------------------------------- 1 | import { dirname } from 'node:path'; 2 | import * as path from 'node:path'; 3 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/importar.js: -------------------------------------------------------------------------------- 1 | import { dirname } from 'node:path'; 2 | import * as path from 'node:path'; 3 | -------------------------------------------------------------------------------- /packages/sandbox/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .DS_Store 3 | dist 4 | dist-ssr 5 | *.local 6 | types 7 | package-lock.json 8 | -------------------------------------------------------------------------------- /demos/demo-esjs-terminal/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/es-js/esjs/HEAD/demos/demo-esjs-terminal/public/favicon.ico -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/numero.js: -------------------------------------------------------------------------------- 1 | const numero = Number.parseInt('123'); 2 | 3 | const numero2 = parseInt('456'); 4 | -------------------------------------------------------------------------------- /packages/sandbox/README.md: -------------------------------------------------------------------------------- 1 | # @es-js/sandbox 2 | 3 | Crea un entorno de ejecución aislado para ejecutar código EsJS/JavaScript. 4 | -------------------------------------------------------------------------------- /demos/demo-esjs-terminal/README.md: -------------------------------------------------------------------------------- 1 | # demo 2 | 3 | [Edit on StackBlitz ⚡️](https://stackblitz.com/github/es-js/demo?file=src/app.esjs) 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/importar.esjs: -------------------------------------------------------------------------------- 1 | importar { dirname } desde 'node:path'; 2 | importar * como path desde 'node:path'; 3 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/importar.esjs: -------------------------------------------------------------------------------- 1 | importar { dirname } desde 'node:path'; 2 | importar * as path desde 'node:path'; 3 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esjs/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .DS_Store 3 | dist 4 | dist-ssr 5 | *.local 6 | types 7 | package-lock.json 8 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esvue/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .DS_Store 3 | dist 4 | dist-ssr 5 | *.local 6 | types 7 | package-lock.json 8 | -------------------------------------------------------------------------------- /apps/playground/app/pages/[code].vue: -------------------------------------------------------------------------------- 1 | 3 | 4 | 7 | -------------------------------------------------------------------------------- /apps/playground/app/pages/index.vue: -------------------------------------------------------------------------------- 1 | 3 | 4 | 7 | -------------------------------------------------------------------------------- /apps/playground/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | // https://nuxt.com/docs/guide/concepts/typescript 3 | "extends": "./.nuxt/tsconfig.json" 4 | } 5 | -------------------------------------------------------------------------------- /packages/prettier-plugin-eshtml/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | .DS_Store 3 | dist 4 | dist-ssr 5 | *.local 6 | types 7 | package-lock.json 8 | -------------------------------------------------------------------------------- /apps/playground/app/app.config.ts: -------------------------------------------------------------------------------- 1 | export default defineAppConfig({ 2 | ui: { 3 | primary: 'indigo', 4 | gray: 'cool', 5 | }, 6 | }) 7 | -------------------------------------------------------------------------------- /apps/playground/.env.example: -------------------------------------------------------------------------------- 1 | SUPABASE_URL="https://test.supabase.co" 2 | SUPABASE_KEY="test" 3 | NUXT_LOGIN_ENABLED=false 4 | NUXT_CLARITY_ID=TEST 5 | -------------------------------------------------------------------------------- /apps/playground/app/pages/github/[...repo].vue: -------------------------------------------------------------------------------- 1 | 3 | 4 | 7 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/cadena.js: -------------------------------------------------------------------------------- 1 | const foo = new String('bar'); 2 | 3 | const searchResult = foo.search('a'); 4 | 5 | foo.charAt(0); 6 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/numero.esjs: -------------------------------------------------------------------------------- 1 | const numero = Numero.interpretarEntero('123'); 2 | 3 | const numero2 = interpretarEntero('456'); 4 | -------------------------------------------------------------------------------- /packages/prettier-plugin-eshtml/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: {}, 5 | }) 6 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esjs/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: {}, 5 | }) 6 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esvue/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: {}, 5 | }) 6 | -------------------------------------------------------------------------------- /packages/sandbox/tailwind.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | darkMode: 'class', 3 | content: ['./index.html', './src/**/*.{vue,js,ts,jsx,tsx}'], 4 | } 5 | -------------------------------------------------------------------------------- /apps/playground/app/pages/login.vue: -------------------------------------------------------------------------------- 1 | 3 | 4 | 9 | -------------------------------------------------------------------------------- /demos/demo-esvue/src/main.ts: -------------------------------------------------------------------------------- 1 | import { createApp } from 'vue' 2 | import App from '@/App.esvue' 3 | 4 | const app = createApp(App) 5 | 6 | app.mount('#app') 7 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/cadena.esjs: -------------------------------------------------------------------------------- 1 | const foo = crear Cadena('bar'); 2 | 3 | const searchResult = foo.buscarRegex('a'); 4 | 5 | foo.caracterEn(0); 6 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/booleano.js: -------------------------------------------------------------------------------- 1 | const bien = Boolean(true) 2 | 3 | const mal = new Boolean(true) 4 | 5 | Boolean(true).toString() 6 | Boolean(true).valueOf() 7 | -------------------------------------------------------------------------------- /packages/prueba/README.md: -------------------------------------------------------------------------------- 1 | # @es-js/prueba 2 | 3 | Librería para ejecutar pruebas en momento de ejecución. Basado en [jstinytest](https://github.com/joewalnes/jstinytest/) 4 | -------------------------------------------------------------------------------- /packages/vscode-esjs/.gitignore: -------------------------------------------------------------------------------- 1 | .cache 2 | .DS_Store 3 | .idea 4 | *.log 5 | *.tgz 6 | *.vsix 7 | coverage 8 | dist 9 | lib-cov 10 | logs 11 | node_modules 12 | temp 13 | -------------------------------------------------------------------------------- /apps/playground/tailwind.config.ts: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | darkMode: 'class', 3 | content: [ 4 | './components/**/*.{vue,js,ts,jsx,tsx}', 5 | './app.vue', 6 | ], 7 | } 8 | -------------------------------------------------------------------------------- /packages/core/vitest.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: { 5 | include: ['test/**/*.test.ts'], 6 | }, 7 | }) 8 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/si.js: -------------------------------------------------------------------------------- 1 | const foo = 'bar' 2 | if ("bar" === foo) { 3 | return true 4 | } else if ("foo" == foo) { 5 | return true 6 | } else { 7 | return false 8 | } 9 | -------------------------------------------------------------------------------- /packages/esbabel/vitest.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: { 5 | include: ['test/**/*.test.ts'], 6 | }, 7 | }) 8 | -------------------------------------------------------------------------------- /packages/eshtml/src/parser.ts: -------------------------------------------------------------------------------- 1 | import { parser as PostHTMLParser } from 'posthtml-parser' 2 | 3 | export function parser(content: string): any[] { 4 | return PostHTMLParser(content) 5 | } 6 | -------------------------------------------------------------------------------- /packages/prueba/vitest.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: { 5 | include: ['test/**/*.test.ts'], 6 | }, 7 | }) 8 | -------------------------------------------------------------------------------- /packages/runtime/pnpm-lock.yaml: -------------------------------------------------------------------------------- 1 | lockfileVersion: '9.0' 2 | 3 | settings: 4 | autoInstallPeers: true 5 | excludeLinksFromLockfile: false 6 | 7 | importers: 8 | 9 | .: {} 10 | -------------------------------------------------------------------------------- /packages/sandbox/vitest.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: { 5 | include: ['test/**/*.test.ts'], 6 | }, 7 | }) 8 | -------------------------------------------------------------------------------- /packages/vite-plugin-esvue/test/fixtures/basic/src/main.ts: -------------------------------------------------------------------------------- 1 | import { createApp } from 'vue' 2 | import App from './App.esvue' 3 | 4 | const app = createApp(App) 5 | 6 | app.mount('#app') 7 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/si.js: -------------------------------------------------------------------------------- 1 | const foo = 'bar' 2 | if ("bar" === foo) { 3 | return true 4 | } else if ("foo" == foo) { 5 | return true 6 | } else { 7 | return false 8 | } 9 | -------------------------------------------------------------------------------- /packages/esjs-loader/vitest.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config' 2 | 3 | export default defineConfig({ 4 | test: { 5 | include: ['test/**/*.test.ts'], 6 | }, 7 | }) 8 | -------------------------------------------------------------------------------- /packages/language-tools/vite.config.js: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vitest/config'; 2 | 3 | export default defineConfig({ 4 | test: { 5 | include: ['test/**/*.test.js'], 6 | } 7 | }); 8 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/json.js: -------------------------------------------------------------------------------- 1 | const json = JSON.isRawJSON({ foo: 'bar' }) 2 | const json2 = JSON.parse(json) 3 | const json3 = JSON.rawJSON(json2) 4 | const json4 = JSON.stringify(json3) 5 | -------------------------------------------------------------------------------- /packages/vscode-esjs/test/index.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | 3 | describe('should', () => { 4 | it('exported', () => { 5 | expect(1).toEqual(1) 6 | }) 7 | }) 8 | -------------------------------------------------------------------------------- /apps/playground/app/constants/app.js: -------------------------------------------------------------------------------- 1 | export const mainDomain = ['localhost:3000', 'esjs.dev', 'editor.esjs.dev'] 2 | 3 | export const learnDomain = ['aprender.localhost.test:3000', 'aprender.esjs.dev'] 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/booleano.esjs: -------------------------------------------------------------------------------- 1 | const bien = Booleano(verdadero) 2 | 3 | const mal = crear Booleano(verdadero) 4 | 5 | Booleano(verdadero).aCadena() 6 | Booleano(verdadero).valorDe() 7 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/enterogrande.js: -------------------------------------------------------------------------------- 1 | let myNum = BigInt(1000) 2 | myNum.toLocaleString() 3 | myNum.toString() 4 | myNum.valueOf() 5 | BigInt.asIntN(64, myNum) 6 | BigInt.asUintN(64, myNum) 7 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/json.esjs: -------------------------------------------------------------------------------- 1 | const json = JSON.esJSONCrudo({ foo: 'bar' }) 2 | const json2 = JSON.analizar(json) 3 | const json3 = JSON.JSONCrudo(json2) 4 | const json4 = JSON.aTexto(json3) 5 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/si.esjs: -------------------------------------------------------------------------------- 1 | const foo = 'bar' 2 | si ("bar" === foo) { 3 | retornar verdadero 4 | } sino si ("foo" == foo) { 5 | retornar verdadero 6 | } sino { 7 | retornar falso 8 | } 9 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/si.esjs: -------------------------------------------------------------------------------- 1 | const foo = 'bar' 2 | si ("bar" === foo) { 3 | retornar verdadero 4 | } sino si ("foo" == foo) { 5 | retornar verdadero 6 | } sino { 7 | retornar falso 8 | } 9 | -------------------------------------------------------------------------------- /apps/playground/app/utils/cn.ts: -------------------------------------------------------------------------------- 1 | import { type ClassValue, clsx } from 'clsx' 2 | import { twMerge } from 'tailwind-merge' 3 | 4 | export function cn(...inputs: ClassValue[]) { 5 | return twMerge(clsx(inputs)) 6 | } 7 | -------------------------------------------------------------------------------- /packages/tiza/README.md: -------------------------------------------------------------------------------- 1 | # @es-js/tiza 2 | 3 | Librería para colorear/estilizar texto en la Terminal. Basada en [chalk-dom](https://github.com/henryhale/chalk-dom), de [Henry Hale](https://github.com/henryhale). 4 | 5 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/popover/index.ts: -------------------------------------------------------------------------------- 1 | export { default as Popover } from './Popover.vue' 2 | export { default as PopoverTrigger } from './PopoverTrigger.vue' 3 | export { default as PopoverContent } from './PopoverContent.vue' 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/enterogrande.esjs: -------------------------------------------------------------------------------- 1 | mut myNum = EnteroGrande(1000) 2 | myNum.aCadenaLocalizada() 3 | myNum.aCadena() 4 | myNum.valorDe() 5 | EnteroGrande.comoEntero(64, myNum) 6 | EnteroGrande.comoEnteroSinSigno(64, myNum) 7 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/templateLiterals.esjs: -------------------------------------------------------------------------------- 1 | const template = html` 2 | "Hola Mundo de EsJS!" 3 | "si (verdadero) {}" 4 | 'sino (falso) {}' 5 | mientras (verdadero) {} 6 | ` 7 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/templateLiterals.js: -------------------------------------------------------------------------------- 1 | const template = html` 2 | "Hola Mundo de EsJS!" 3 | "si (verdadero) {}" 4 | 'sino (falso) {}' 5 | mientras (verdadero) {} 6 | ` 7 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/templateLiterals.esjs: -------------------------------------------------------------------------------- 1 | const template = html` 2 | "Hola Mundo de EsJS!" 3 | "si (verdadero) {}" 4 | 'sino (falso) {}' 5 | mientras (verdadero) {} 6 | ` 7 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/templateLiterals.js: -------------------------------------------------------------------------------- 1 | const template = html` 2 | "Hola Mundo de EsJS!" 3 | "si (verdadero) {}" 4 | 'sino (falso) {}' 5 | mientras (verdadero) {} 6 | ` 7 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/constantes.js: -------------------------------------------------------------------------------- 1 | const x = false 2 | 3 | const y = true 4 | 5 | const n = null 6 | 7 | const i = undefined 8 | 9 | const I = Infinity 10 | 11 | const noNumero = NaN 12 | 13 | const aG = globalThis 14 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/numero.js: -------------------------------------------------------------------------------- 1 | const numero = Number.parseInt('123'); 2 | 3 | const numero2 = parseInt('456'); 4 | 5 | const numeroDecimal = Number.parseFloat('123.456'); 6 | 7 | const numeroDecimal2 = parseFloat('456.789'); 8 | -------------------------------------------------------------------------------- /packages/terminal/src/main.ts: -------------------------------------------------------------------------------- 1 | import './components/es-terminal' 2 | import { usarTerminal } from './composables/usarTerminal' 3 | 4 | export { usarTerminal } from './composables/usarTerminal' 5 | 6 | export const Terminal = usarTerminal() 7 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/array.js: -------------------------------------------------------------------------------- 1 | const matriz = Array.of([]) 2 | 3 | matriz.push('test') 4 | 5 | if (matriz.includes('test')) { 6 | matriz.pop() 7 | } 8 | 9 | matriz.length 10 | 11 | matriz.find((item) => item === 'test') 12 | -------------------------------------------------------------------------------- /packages/vscode-esjs/tsup.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'tsup' 2 | 3 | export default defineConfig({ 4 | entry: ['src/index.ts'], 5 | format: ['cjs'], 6 | shims: false, 7 | dts: false, 8 | external: ['vscode'], 9 | }) 10 | -------------------------------------------------------------------------------- /packages/terminal/README.md: -------------------------------------------------------------------------------- 1 | # @es-js/terminal 2 | 3 | Componente que renderiza una Terminal en el navegador, y permite escribir/leer datos. Basado en [XTerminal](https://github.com/henryhale/xterminal), de [Henry Hale](https://github.com/henryhale). 4 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/constantes.esjs: -------------------------------------------------------------------------------- 1 | const x = falso 2 | 3 | const y = verdadero 4 | 5 | const n = nulo 6 | 7 | const i = indefinido 8 | 9 | const I = Infinito 10 | 11 | const noNumero = NuN 12 | 13 | const aG = ambienteGlobal 14 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/resizable/index.ts: -------------------------------------------------------------------------------- 1 | export { default as ResizablePanelGroup } from './ResizablePanelGroup.vue' 2 | export { default as ResizableHandle } from './ResizableHandle.vue' 3 | export { SplitterPanel as ResizablePanel } from 'radix-vue' 4 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/array.esjs: -------------------------------------------------------------------------------- 1 | const matriz = Matriz.de([]) 2 | 3 | matriz.agregar('test') 4 | 5 | si (matriz.incluye('test')) { 6 | matriz.sacar() 7 | } 8 | 9 | matriz.longitud 10 | 11 | matriz.buscar((item) => item === 'test') 12 | -------------------------------------------------------------------------------- /packages/terminal/tsconfig.node.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "composite": true, 4 | "module": "ESNext", 5 | "moduleResolution": "Node", 6 | "allowSyntheticDefaultImports": true 7 | }, 8 | "include": ["vite.config.ts"] 9 | } 10 | -------------------------------------------------------------------------------- /packages/esbabel/src/index.ts: -------------------------------------------------------------------------------- 1 | import { tokenize } from './lexer' 2 | import { generate } from './generator' 3 | 4 | export function compile(code: string, reverse = false): string { 5 | const tokens = tokenize(code) 6 | 7 | return generate(tokens, reverse) 8 | } 9 | -------------------------------------------------------------------------------- /packages/language-tools/src/generate-esvue-syntax.js: -------------------------------------------------------------------------------- 1 | import { copyFileSync, existsSync, mkdirSync } from 'node:fs' 2 | 3 | if (!existsSync('dist')) { 4 | mkdirSync('dist') 5 | } 6 | 7 | copyFileSync('./assets/esvue.tmLanguage.json', 'dist/esvue.tmLanguage.json') 8 | -------------------------------------------------------------------------------- /apps/playground/app/app.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /packages/language-tools/src/generate-esjs-snippets.js: -------------------------------------------------------------------------------- 1 | import { copyFileSync, existsSync, mkdirSync } from 'node:fs' 2 | 3 | if (!existsSync('dist')) { 4 | mkdirSync('dist') 5 | } 6 | 7 | copyFileSync('./assets/esjs.code-snippets.json', 'dist/esjs.code-snippets.json') 8 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tabs/index.ts: -------------------------------------------------------------------------------- 1 | export { default as Tabs } from './Tabs.vue' 2 | export { default as TabsTrigger } from './TabsTrigger.vue' 3 | export { default as TabsList } from './TabsList.vue' 4 | export { default as TabsContent } from './TabsContent.vue' 5 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/numero.esjs: -------------------------------------------------------------------------------- 1 | const numero = Numero.interpretarEntero('123'); 2 | 3 | const numero2 = interpretarEntero('456'); 4 | 5 | const numeroDecimal = Numero.interpretarDecimal('123.456'); 6 | 7 | const numeroDecimal2 = interpretarDecimal('456.789'); 8 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/props.js: -------------------------------------------------------------------------------- 1 | const props = { 2 | a: Number, 3 | b: String, 4 | c: Boolean, 5 | d: Object, 6 | e: Array, 7 | f: Function, 8 | g: Symbol, 9 | h: Date, 10 | i: Error, 11 | j: RegExp, 12 | k: Map, 13 | l: Set, 14 | } 15 | -------------------------------------------------------------------------------- /apps/playground/app/composables/dark.ts: -------------------------------------------------------------------------------- 1 | import { set, useDark, useToggle } from '@vueuse/core' 2 | 3 | export const isDark = useDark() 4 | 5 | export const toggleDark = useToggle(isDark) 6 | 7 | export const setDark = (value: boolean) => { 8 | set(isDark, value) 9 | } 10 | -------------------------------------------------------------------------------- /packages/esbabel/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: ['./src/index', './src/keywords'], 5 | clean: true, 6 | declaration: true, 7 | rollup: { 8 | emitCJS: true, 9 | }, 10 | }) 11 | -------------------------------------------------------------------------------- /scripts/bump.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | set -xe 4 | 5 | # Bump all packages 6 | for PKG in ./packages/* ; do 7 | pushd $PKG 8 | echo "⚡ Bumping $PKG" 9 | 10 | # Bump version 11 | pnpm dlx @jsdevtools/version-bump-prompt 12 | 13 | popd > /dev/null 14 | done 15 | 16 | -------------------------------------------------------------------------------- /apps/playground/content/intermedios/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | navigation: false 3 | --- 4 | 5 | # Conceptos intermedios 6 | 7 | En esta sección exploraremos los conceptos intermedios de la programación en EsJS/JavaScript. 8 | 9 | ## Módulos 10 | 11 | 1. [Módulos](/intermedios/modulos) 12 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/asincrono.js: -------------------------------------------------------------------------------- 1 | async function principal() { 2 | return true 3 | } 4 | 5 | const objeto = { 6 | miFuncion: async function () { 7 | return true 8 | }, 9 | miFuncionFlecha: async () => { 10 | return true 11 | }, 12 | } 13 | 14 | principal() 15 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/props.esjs: -------------------------------------------------------------------------------- 1 | const props = { 2 | a: Numero, 3 | b: Cadena, 4 | c: Booleano, 5 | d: Objeto, 6 | e: Matriz, 7 | f: Funcion, 8 | g: Simbolo, 9 | h: Fecha, 10 | i: Error, 11 | j: ExpReg, 12 | k: Mapa, 13 | l: Conjunto, 14 | } 15 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/asincrono.js: -------------------------------------------------------------------------------- 1 | async function principal() { 2 | return true 3 | } 4 | 5 | const objeto = { 6 | miFuncion: async function () { 7 | return true 8 | }, 9 | miFuncionFlecha: async () => { 10 | return true 11 | }, 12 | } 13 | 14 | principal() 15 | -------------------------------------------------------------------------------- /packages/esjs-loader/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: ['src/index'], 5 | clean: true, 6 | declaration: true, 7 | rollup: { 8 | emitCJS: true, 9 | inlineDependencies: true, 10 | }, 11 | }) 12 | -------------------------------------------------------------------------------- /demos/demo-eshtml/indice.esjs: -------------------------------------------------------------------------------- 1 | const fechaActualElemento = document.getElementById('fecha-actual') 2 | 3 | const actualizarFechaActual = () => { 4 | fechaActualElemento.textContent = crear Fecha().aCadenaLocalizada() 5 | } 6 | 7 | actualizarFechaActual() 8 | setInterval(actualizarFechaActual, 1000) 9 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/cadena.js: -------------------------------------------------------------------------------- 1 | const foo = new String('bar'); 2 | 3 | const searchResult = foo.search('a'); 4 | 5 | foo.charAt(0); 6 | 7 | String.fromCharCode(65, 66, 67); // 'ABC' 8 | String.fromCodePoint(65, 66, 67); // 'ABC' 9 | String.raw`Hola\nMundo`; // 'Hola\\nMundo' 10 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/README.md: -------------------------------------------------------------------------------- 1 | # @es-js/vite-plugin-eshtml 2 | 3 | Vite Plugin para procesar archivos EsHTML, además de configurar el entorno Vite para iniciar desde un archivo EsHTML, basado en [vite-plugin-virtual-html-template](https://github.com/hex-ci/vite-plugin-virtual-html-template). 4 | -------------------------------------------------------------------------------- /packages/vite-plugin-esjs/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: ['src/index'], 5 | clean: true, 6 | declaration: true, 7 | rollup: { 8 | emitCJS: true, 9 | inlineDependencies: true, 10 | }, 11 | }) 12 | -------------------------------------------------------------------------------- /demos/demo-eshtml/fuente/indice.esjs: -------------------------------------------------------------------------------- 1 | const fechaActualElemento = document.getElementById('fecha-actual') 2 | 3 | const actualizarFechaActual = () => { 4 | fechaActualElemento.textContent = crear Fecha().aCadenaLocalizada() 5 | } 6 | 7 | actualizarFechaActual() 8 | setInterval(actualizarFechaActual, 1000) 9 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/tipoDe.js: -------------------------------------------------------------------------------- 1 | console.log(typeof 2); 2 | 3 | console.log(typeof "Martin Fierro"); 4 | 5 | console.log(typeof true); 6 | 7 | console.log(typeof null); 8 | 9 | console.log(typeof undefined); 10 | 11 | console.log(typeof {}); 12 | 13 | console.log(typeof []); 14 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: ['src/index'], 5 | clean: true, 6 | declaration: true, 7 | rollup: { 8 | emitCJS: true, 9 | inlineDependencies: true, 10 | }, 11 | }) 12 | -------------------------------------------------------------------------------- /packages/vite-plugin-esvue/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: ['src/index'], 5 | clean: true, 6 | declaration: true, 7 | rollup: { 8 | emitCJS: true, 9 | inlineDependencies: true, 10 | }, 11 | }) 12 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tooltip/index.ts: -------------------------------------------------------------------------------- 1 | export { default as Tooltip } from './Tooltip.vue' 2 | export { default as TooltipContent } from './TooltipContent.vue' 3 | export { default as TooltipTrigger } from './TooltipTrigger.vue' 4 | export { default as TooltipProvider } from './TooltipProvider.vue' 5 | -------------------------------------------------------------------------------- /packages/language-tools/src/index.js: -------------------------------------------------------------------------------- 1 | import './generate-esjs-syntax.js' 2 | import './generate-esvue-syntax.js' 3 | import './generate-esjs-language-configurations.js' 4 | import './generate-esvue-language-configurations.js' 5 | import './generate-esjs-snippets.js' 6 | import './generate-reserved-words-table.js' 7 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/test/__snapshots__/getEntryScripts.test.ts.snap: -------------------------------------------------------------------------------- 1 | // Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html 2 | 3 | exports[`getEntryScripts 1`] = ` 4 | Map { 5 | "/fuente/indice.js" => "/fuente/indice.esjs", 6 | "/fuente/utilidades.js" => "/fuente/utilidades.esjs", 7 | } 8 | `; 9 | -------------------------------------------------------------------------------- /demos/demo-esvue/src/GitHub.esvue: -------------------------------------------------------------------------------- 1 | 2 | 3 | Dejá tu estrella en GitHub! 4 | 5 | 6 | -------------------------------------------------------------------------------- /apps/playground/.gitignore: -------------------------------------------------------------------------------- 1 | # Nuxt dev/build outputs 2 | .output 3 | .nuxt 4 | .nitro 5 | .cache 6 | dist 7 | 8 | # Node dependencies 9 | node_modules 10 | 11 | # Logs 12 | logs 13 | *.log 14 | 15 | # Misc 16 | .DS_Store 17 | .fleet 18 | .idea 19 | 20 | # Local env files 21 | .env 22 | .env.* 23 | !.env.example 24 | -------------------------------------------------------------------------------- /packages/core/src/compiler/esbabel.compiler.ts: -------------------------------------------------------------------------------- 1 | import { compile } from '@es-js/esbabel' 2 | import type { CompileOptions, Compiler } from '../index' 3 | 4 | export class EsbabelCompiler implements Compiler { 5 | compile(code: string, options: CompileOptions) { 6 | return compile(code, options.to === 'esjs') 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/asincrono.esjs: -------------------------------------------------------------------------------- 1 | asincrono funcion principal() { 2 | retornar verdadero 3 | } 4 | 5 | const objeto = { 6 | miFuncion: asincrono funcion () { 7 | retornar verdadero 8 | }, 9 | miFuncionFlecha: asincrono () => { 10 | retornar verdadero 11 | }, 12 | } 13 | 14 | principal() 15 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/asincrono.esjs: -------------------------------------------------------------------------------- 1 | asincrono funcion principal() { 2 | retornar verdadero 3 | } 4 | 5 | const objeto = { 6 | miFuncion: asincrono funcion () { 7 | retornar verdadero 8 | }, 9 | miFuncionFlecha: asincrono () => { 10 | retornar verdadero 11 | }, 12 | } 13 | 14 | principal() 15 | -------------------------------------------------------------------------------- /packages/esvue/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: ['src/index'], 5 | clean: true, 6 | declaration: true, 7 | rollup: { 8 | emitCJS: true, 9 | inlineDependencies: true, 10 | }, 11 | externals: ['@es-js/core'], 12 | }) 13 | -------------------------------------------------------------------------------- /packages/sandbox/src/utils/formatCode.ts: -------------------------------------------------------------------------------- 1 | import parserBabel from 'prettier/parser-babel' 2 | import prettier from 'prettier/standalone' 3 | 4 | export function formatCode(code: string) { 5 | return prettier.format(code, { 6 | parser: 'babel', 7 | plugins: [parserBabel], 8 | semi: false, 9 | }) 10 | } 11 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/cadena.esjs: -------------------------------------------------------------------------------- 1 | const foo = crear Cadena('bar'); 2 | 3 | const searchResult = foo.buscarRegex('a'); 4 | 5 | foo.caracterEn(0); 6 | 7 | Cadena.desdeCodigoDeCaracter(65, 66, 67); // 'ABC' 8 | Cadena.desdePuntoDeCodigo(65, 66, 67); // 'ABC' 9 | Cadena.crudo`Hola\nMundo`; // 'Hola\\nMundo' 10 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | [*.{js,jsx,ts,tsx,vue}] 2 | indent_style = space 3 | indent_size = 2 4 | trim_trailing_whitespace = true 5 | insert_final_newline = true 6 | 7 | [packages/core/test/fixtures/**/*.{js,jsx,ts,tsx,vue}] 8 | indent_style = space 9 | indent_size = 2 10 | trim_trailing_whitespace = true 11 | insert_final_newline = true 12 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/DialogClose.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /packages/core/src/plugins/objetos/index.ts: -------------------------------------------------------------------------------- 1 | import { types } from '../tipos' 2 | import { replaceObjects } from '../utils' 3 | 4 | export const report = () => 'Converts Objects to JavaScript' 5 | 6 | export function replace() { 7 | return { 8 | ...replaceObjects({ 9 | objects: types, 10 | }), 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /packages/language-tools/src/generate-esvue-language-configurations.js: -------------------------------------------------------------------------------- 1 | import { copyFileSync, existsSync, mkdirSync } from 'node:fs' 2 | 3 | if (!existsSync('dist')) { 4 | mkdirSync('dist') 5 | } 6 | 7 | copyFileSync( 8 | './assets/esvue-language-configuration.json', 9 | 'dist/esvue-language-configuration.json', 10 | ) 11 | -------------------------------------------------------------------------------- /packages/sandbox/src/transformers/index.ts: -------------------------------------------------------------------------------- 1 | export interface Transformer { 2 | transform(code: string): string 3 | } 4 | 5 | export function applyTransformers(code: string, transformers: Transformer[]) { 6 | return transformers.reduce( 7 | (acc, transformer) => transformer.transform(acc), 8 | code, 9 | ) 10 | } 11 | -------------------------------------------------------------------------------- /packages/core/README.md: -------------------------------------------------------------------------------- 1 | # EsJS Core 2 | 3 | EsJS es un lenguaje de programación con sintaxis en Español que compila a JavaScript. Esto permite a las personas hispanohablantes escribir código de manera más familiar y accesible, sin renunciar al poder y versatilidad de JavaScript. 4 | 5 | Más información en: [https:/es.js.org/](https:/es.js.org/). 6 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/tipoDe.esjs: -------------------------------------------------------------------------------- 1 | consola.escribir(tipoDe 2); 2 | 3 | consola.escribir(tipoDe "Martin Fierro"); 4 | 5 | consola.escribir(tipoDe verdadero); 6 | 7 | consola.escribir(tipoDe nulo); 8 | 9 | consola.escribir(tipoDe indefinido); 10 | 11 | consola.escribir(tipoDe {}); 12 | 13 | consola.escribir(tipoDe []); 14 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/DialogTrigger.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/funcion.js: -------------------------------------------------------------------------------- 1 | // Este comentario no debe ser transpilado ni ninguna de los siguientes Tokens: if else while 2 | 3 | /** 4 | * Tampoco este comentario. 5 | * if else while 6 | * @returns true 7 | */ 8 | function inicio() { 9 | return true 10 | } 11 | 12 | const app = { } 13 | 14 | export default app 15 | -------------------------------------------------------------------------------- /packages/esbabel/README.md: -------------------------------------------------------------------------------- 1 | # EsJS Core 2 | 3 | EsJS es un lenguaje de programación con sintaxis en Español que compila a JavaScript. Esto permite a las personas hispanohablantes escribir código de manera más familiar y accesible, sin renunciar al poder y versatilidad de JavaScript. 4 | 5 | Más información en: [https:/es.js.org/](https:/es.js.org/). 6 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/popover/PopoverTrigger.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tooltip/TooltipTrigger.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/funcion.js: -------------------------------------------------------------------------------- 1 | // Este comentario no debe ser transpilado ni ninguna de los siguientes Tokens: if else while 2 | 3 | /** 4 | * Tampoco este comentario. 5 | * if else while 6 | * @returns true 7 | */ 8 | function inicio() { 9 | return true 10 | } 11 | 12 | const app = new Date() 13 | 14 | export default app 15 | -------------------------------------------------------------------------------- /packages/eshtml/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: ['src/index', 'src/render', 'src/parser'], 5 | clean: true, 6 | declaration: true, 7 | rollup: { 8 | emitCJS: true, 9 | inlineDependencies: true, 10 | }, 11 | externals: ['@es-js/core'], 12 | }) 13 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tooltip/TooltipProvider.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/keywords/funcion.esjs: -------------------------------------------------------------------------------- 1 | // Este comentario no debe ser transpilado ni ninguna de los siguientes Tokens: if else while 2 | 3 | /** 4 | * Tampoco este comentario. 5 | * if else while 6 | * @returns true 7 | */ 8 | funcion inicio() { 9 | retornar verdadero 10 | } 11 | 12 | const app = { } 13 | 14 | exportar porDefecto app 15 | -------------------------------------------------------------------------------- /packages/eshtml/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "lib": ["esnext", "DOM"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "jsx": "preserve", 10 | "strictNullChecks": true, 11 | "resolveJsonModule": true 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /packages/esvue/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "lib": ["esnext", "DOM"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "jsx": "preserve", 10 | "strictNullChecks": true, 11 | "resolveJsonModule": true 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /packages/prueba/vite.config.js: -------------------------------------------------------------------------------- 1 | const path = require('path') 2 | const { defineConfig } = require('vite') 3 | 4 | module.exports = defineConfig({ 5 | build: { 6 | lib: { 7 | entry: path.resolve(__dirname, 'lib/main.ts'), 8 | name: 'EsJS Prueba', 9 | fileName: (format) => `esjs-prueba.${format}.js`, 10 | }, 11 | }, 12 | }) 13 | -------------------------------------------------------------------------------- /packages/sandbox/src/runtime/index.ts: -------------------------------------------------------------------------------- 1 | import type { EjecutarOptions } from './ejecutar' 2 | import { init } from './ejecutar' 3 | import { setupWindow } from './window.js' 4 | 5 | export async function setupSandbox( 6 | ejecutarOptions: EjecutarOptions, 7 | ): Promise { 8 | await setupWindow() 9 | 10 | await init(ejecutarOptions) 11 | } 12 | -------------------------------------------------------------------------------- /packages/esjs-loader/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "lib": ["esnext", "DOM"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "jsx": "preserve", 10 | "strictNullChecks": true, 11 | "resolveJsonModule": true 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /packages/sandbox/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | 3 | declare module 'espree' 4 | 5 | declare module 'https://esm.sh/@putout/bundle@2' { 6 | const putout: any 7 | export default putout 8 | } 9 | 10 | // declare module 'SandboxFile' { 11 | // export interface SandboxFile { 12 | // converted?: any; 13 | // } 14 | // } 15 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/funcion.esjs: -------------------------------------------------------------------------------- 1 | // Este comentario no debe ser transpilado ni ninguna de los siguientes Tokens: if else while 2 | 3 | /** 4 | * Tampoco este comentario. 5 | * if else while 6 | * @returns true 7 | */ 8 | funcion inicio() { 9 | retornar verdadero 10 | } 11 | 12 | const app = crear Fecha() 13 | 14 | exportar porDefecto app 15 | -------------------------------------------------------------------------------- /packages/vite-plugin-esjs/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "lib": ["esnext", "DOM"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "jsx": "preserve", 10 | "strictNullChecks": true, 11 | "resolveJsonModule": true 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /apps/playground/app/composables/useOctokit.ts: -------------------------------------------------------------------------------- 1 | import { Octokit } from 'octokit' 2 | 3 | export default function() { 4 | const session = useSupabaseSession() 5 | 6 | if (!session.value) { 7 | throw new Error('Debes iniciar sesión para usar esta función') 8 | } 9 | 10 | return new Octokit({ 11 | auth: session.value.provider_token, 12 | }) 13 | } 14 | -------------------------------------------------------------------------------- /packages/tiza/vite.config.js: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vite' 2 | 3 | export default defineConfig({ 4 | build: { 5 | lib: { 6 | outDir: 'dist', 7 | entry: 'src/index.js', 8 | name: 'tiza', 9 | fileName: (format) => `tiza.${format}.js`, 10 | }, 11 | }, 12 | test: { 13 | include: ['test/**/*.test.js'], 14 | }, 15 | }) 16 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/src/lib/getPage.ts: -------------------------------------------------------------------------------- 1 | import { Opciones, Pagina } from '../index' 2 | 3 | export function getPage( 4 | options: Opciones, 5 | pageName: string, 6 | ): Pagina | undefined { 7 | if (pageName === 'index') { 8 | return options?.paginas?.indice ?? options?.paginas?.index 9 | } 10 | 11 | return options?.paginas?.[pageName] 12 | } 13 | -------------------------------------------------------------------------------- /packages/vite-plugin-esvue/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "lib": ["esnext", "DOM"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "jsx": "preserve", 10 | "strictNullChecks": true, 11 | "resolveJsonModule": true 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | node_modules 3 | dist 4 | 5 | 6 | # local env files 7 | .env.local 8 | .env.*.local 9 | 10 | # Log files 11 | npm-debug.log* 12 | yarn-debug.log* 13 | yarn-error.log* 14 | pnpm-debug.log* 15 | 16 | # Editor directories and files 17 | .idea 18 | .vscode 19 | *.suo 20 | *.ntvs* 21 | *.njsproj 22 | *.sln 23 | *.sw? 24 | 25 | tsconfig.tsbuildinfo 26 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuGroup.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | -------------------------------------------------------------------------------- /apps/playground/app/components/AppSeparator.vue: -------------------------------------------------------------------------------- 1 | 11 | 12 | 15 | -------------------------------------------------------------------------------- /apps/playground/app/pages/aprender/[...slug].vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 18 | -------------------------------------------------------------------------------- /packages/core/.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | -------------------------------------------------------------------------------- /packages/prettier-plugin-eshtml/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ES2018", 4 | "module": "ESNext", 5 | "lib": ["ESNext"], 6 | "moduleResolution": "Node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "strictNullChecks": true, 10 | "resolveJsonModule": true, 11 | "skipLibCheck": true, 12 | "skipDefaultLibCheck": true 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esjs/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ES2018", 4 | "module": "ESNext", 5 | "lib": ["ESNext"], 6 | "moduleResolution": "Node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "strictNullChecks": true, 10 | "resolveJsonModule": true, 11 | "skipLibCheck": true, 12 | "skipDefaultLibCheck": true 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esvue/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ES2018", 4 | "module": "ESNext", 5 | "lib": ["ESNext"], 6 | "moduleResolution": "Node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "strictNullChecks": true, 10 | "resolveJsonModule": true, 11 | "skipLibCheck": true, 12 | "skipDefaultLibCheck": true 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /packages/esbabel/.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | -------------------------------------------------------------------------------- /packages/terminal/.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | -------------------------------------------------------------------------------- /apps/playground/app/middleware/redirect.global.ts: -------------------------------------------------------------------------------- 1 | export default defineNuxtRouteMiddleware((to, from) => { 2 | if (process.client) { 3 | const redirectUrl = localStorage.getItem('redirect_url') 4 | 5 | if (redirectUrl) { 6 | localStorage.removeItem('redirect_url') 7 | return navigateTo(redirectUrl, { 8 | external: true, 9 | }) 10 | } 11 | } 12 | }) 13 | -------------------------------------------------------------------------------- /packages/vscode-esjs/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es2017", 4 | "module": "esnext", 5 | "lib": ["esnext"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "strictNullChecks": true, 10 | "resolveJsonModule": true, 11 | "skipLibCheck": true, 12 | "skipDefaultLibCheck": true 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /demos/demo-esjs-terminal/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/demo-esjs-terminal", 3 | "version": "0.0.0", 4 | "private": true, 5 | "scripts": { 6 | "dev": "vite", 7 | "build": "vite build", 8 | "serve": "vite preview" 9 | }, 10 | "devDependencies": { 11 | "@es-js/terminal": "workspace:^", 12 | "@es-js/vite-plugin-esjs": "workspace:^", 13 | "vite": "^4.5.0" 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /packages/cli/commands/ayuda.mjs: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | import { defineCommand } from 'citty' 4 | import { showUsage } from '../utils/utils.mjs' 5 | 6 | export default defineCommand({ 7 | meta: { 8 | name: 'ayuda', 9 | description: 'Muestra la ayuda del CLI.', 10 | }, 11 | 12 | async run() { 13 | await showUsage(await import('../index.js').then((r) => r.main)) 14 | }, 15 | }) 16 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/promesa.js: -------------------------------------------------------------------------------- 1 | Promise.all([1, 2, 3]).then(console.log) 2 | 3 | Promise.allSettled([1, 2, 3]).then(console.log).catch(console.error) 4 | 5 | Promise.any([1, 2, 3]).then(console.log).catch(console.error) 6 | 7 | Promise.race([1, 2, 3]).then(console.log).catch(console.error) 8 | 9 | Promise.reject('error').catch(console.error) 10 | 11 | Promise.resolve('ok').then(console.log) 12 | 13 | -------------------------------------------------------------------------------- /demos/demo-esvue/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | 3 | declare module '*.vue' { 4 | import type { DefineComponent } from 'vue' 5 | const component: DefineComponent<{}, {}, any> 6 | export default component 7 | } 8 | 9 | declare module '*.esvue' { 10 | import type { DefineComponent } from 'vue' 11 | const component: DefineComponent<{}, {}, any> 12 | export default component 13 | } 14 | -------------------------------------------------------------------------------- /packages/vite-plugin-esvue/src/index.ts: -------------------------------------------------------------------------------- 1 | import { compile } from '@es-js/esvue' 2 | import type { Plugin } from 'vite' 3 | 4 | export default function EsVue(): Plugin { 5 | return { 6 | name: 'vite-plugin-esvue', 7 | enforce: 'pre', 8 | transform(raw: string, id: string) { 9 | if (!/\.esvue$/.test(id)) { 10 | return 11 | } 12 | 13 | return compile(raw) 14 | }, 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /packages/sandbox/src/compiler/constants.ts: -------------------------------------------------------------------------------- 1 | export const IMPORT_ESJS_PRUEBA = 2 | "import { prueba, pruebas, pruebasAsincronas, afirmar, assert, afirmarIguales, afirmarSimilares, afirmarMatricesIguales, afirmarObjetosIguales, afirmarMatricesSimilares, afirmarObjetosSimilares, afirmarVerdadero, afirmarFalso, afirmarDistinto } from '@es-js/prueba'" 3 | 4 | export const IMPORT_ESJS_TERMINAL = "import { Terminal } from '@es-js/terminal'" 5 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuShortcut.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 15 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/DialogHeader.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 17 | -------------------------------------------------------------------------------- /packages/sandbox/src/transformers/format.transformer.ts: -------------------------------------------------------------------------------- 1 | import parserBabel from 'prettier/parser-babel' 2 | import prettier from 'prettier/standalone' 3 | import { Transformer } from './index' 4 | 5 | export class FormatTransformer implements Transformer { 6 | transform(code: string) { 7 | return prettier.format(code, { 8 | parser: 'babel', 9 | plugins: [parserBabel], 10 | semi: false, 11 | }) 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /packages/tiza/test/tiza.test.js: -------------------------------------------------------------------------------- 1 | import { describe, expect, test } from 'vitest' 2 | import { tiza } from '../src' 3 | 4 | describe('tiza', () => { 5 | test('tiza.subrayado.azul', () => { 6 | const result = tiza.subrayado.fondoAzul.blanco('test') 7 | const expectedResult = 8 | 'test' 9 | 10 | expect(result).toBe(expectedResult) 11 | }) 12 | }) 13 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esjs/README.md: -------------------------------------------------------------------------------- 1 | # prettier-plugin-esjs 2 | 3 | Formatea tu código EsJS con Prettier. 4 | 5 | ## Instalación 6 | 7 | ```bash 8 | $ npm install prettier-plugin-esjs -D 9 | $ yarn add prettier-plugin-esjs -D 10 | $ pnpm add prettier-plugin-esjs -D 11 | ``` 12 | 13 | ## Uso 14 | 15 | ```ts 16 | // .prettierrc.js 17 | module.exports = { 18 | plugins: [ 19 | // Agrega el plugin 20 | "prettier-plugin-esjs", 21 | ], 22 | }; 23 | ``` 24 | -------------------------------------------------------------------------------- /packages/cli/postinstall.js: -------------------------------------------------------------------------------- 1 | import { consola } from 'consola' 2 | import { colors } from 'consola/utils' 3 | import packageJson from './package.json' with { type: 'json' } 4 | 5 | const version = packageJson.version || '0.0.0' 6 | 7 | consola.log( 8 | `${colors.bgMagenta(colors.white(colors.bold(' EsJS ')))} CLI v${version} instalado correctamente 9 | 10 | Puedes ejecutar ${colors.bgWhite( 11 | colors.black(' esjs '), 12 | )} para comenzar a usarlo`, 13 | ) 14 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esvue/README.md: -------------------------------------------------------------------------------- 1 | # prettier-plugin-esvue 2 | 3 | Formatea tu código EsVue con Prettier. 4 | 5 | ## Instalación 6 | 7 | ```bash 8 | $ npm install prettier-plugin-esvue -D 9 | $ yarn add prettier-plugin-esvue -D 10 | $ pnpm add prettier-plugin-esvue -D 11 | ``` 12 | 13 | ## Uso 14 | 15 | ```ts 16 | // .prettierrc.js 17 | module.exports = { 18 | plugins: [ 19 | // Agrega el plugin 20 | "prettier-plugin-esvue", 21 | ], 22 | }; 23 | ``` 24 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/test/replaceEntryScript.test.ts: -------------------------------------------------------------------------------- 1 | // import vite from 'vite' 2 | import { expect, it } from 'vitest' 3 | import { replaceEntryScript } from '../src/lib/replaceEntryScript' 4 | 5 | it('replaceEntryScript', async () => { 6 | const html = `` 7 | 8 | const output = replaceEntryScript(html) 9 | 10 | expect(output).toBe(``) 11 | }) 12 | -------------------------------------------------------------------------------- /packages/core/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "lib": ["esnext", "DOM"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "jsx": "preserve", 10 | "strictNullChecks": true, 11 | "resolveJsonModule": true, 12 | "outDir": "./dist" 13 | }, 14 | "include": ["./src"], 15 | "exclude": ["dist", "node_modules", "**/*.spec.ts", "test"] 16 | } 17 | -------------------------------------------------------------------------------- /packages/prettier-plugin-eshtml/README.md: -------------------------------------------------------------------------------- 1 | # prettier-plugin-eshtml 2 | 3 | Formatea tu código EsHTML con Prettier. 4 | 5 | ## Instalación 6 | 7 | ```bash 8 | $ npm install prettier-plugin-eshtml -D 9 | $ yarn add prettier-plugin-eshtml -D 10 | $ pnpm add prettier-plugin-eshtml -D 11 | ``` 12 | 13 | ## Uso 14 | 15 | ```ts 16 | // .prettierrc.js 17 | module.exports = { 18 | plugins: [ 19 | // Agrega el plugin 20 | "prettier-plugin-eshtml", 21 | ], 22 | }; 23 | ``` 24 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/test/fixtures/basic/indice.eshtml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | 11 | 12 | EsHTML: HTML en Español 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/Dialog.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 15 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/promesa.esjs: -------------------------------------------------------------------------------- 1 | Promesa.todos([1, 2, 3]).luego(consola.escribir) 2 | 3 | Promesa.todosTerminados([1, 2, 3]).luego(consola.escribir).capturar(consola.error) 4 | 5 | Promesa.cualquiera([1, 2, 3]).luego(consola.escribir).capturar(consola.error) 6 | 7 | Promesa.carrera([1, 2, 3]).luego(consola.escribir).capturar(consola.error) 8 | 9 | Promesa.rechaza('error').capturar(consola.error) 10 | 11 | Promesa.resuelve('ok').luego(consola.escribir) 12 | 13 | -------------------------------------------------------------------------------- /packages/esbabel/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "lib": ["esnext", "DOM"], 6 | "moduleResolution": "node", 7 | "esModuleInterop": true, 8 | "strict": true, 9 | "jsx": "preserve", 10 | "strictNullChecks": true, 11 | "resolveJsonModule": true, 12 | "outDir": "./dist" 13 | }, 14 | "include": ["./src"], 15 | "exclude": ["dist", "node_modules", "**/*.spec.ts", "test"] 16 | } 17 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuTrigger.vue: -------------------------------------------------------------------------------- 1 | 8 | 9 | 14 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tabs/Tabs.vue: -------------------------------------------------------------------------------- 1 | 10 | 11 | 16 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tooltip/Tooltip.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 15 | -------------------------------------------------------------------------------- /apps/playground/components.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://shadcn-vue.com/schema.json", 3 | "style": "default", 4 | "typescript": true, 5 | "tsConfigPath": ".nuxt/tsconfig.json", 6 | "tailwind": { 7 | "config": "tailwind.config.js", 8 | "css": "app/styles/base.css", 9 | "baseColor": "gray", 10 | "cssVariables": true 11 | }, 12 | "framework": "nuxt", 13 | "aliases": { 14 | "components": "@/components", 15 | "utils": "@/utils/cn" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/src/lib/replaceEntryScript.ts: -------------------------------------------------------------------------------- 1 | /** 2 | * Replace EsJS entry script with a JS script that will load the EsJS script. 3 | */ 4 | export function replaceEntryScript( 5 | html: string, 6 | scriptType: string = 'module', 7 | ): string { 8 | return html.replace(/<\/script>/g, (m, p1) => { 9 | return `` 13 | }) 14 | } 15 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/test/fixtures/basic/fuente/paginas/licencia.eshtml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 10 | 11 | 12 | EsHTML: HTML en Español 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /packages/vscode-esjs/syntaxes/esvue.tmLanguage.json: -------------------------------------------------------------------------------- 1 | {"fileTypes":[".esvue"],"name":"EsVue","scopeName":"source.esvue","patterns":[{"include":"#frontmatter"},{"include":"source.vue"}],"repository":{"frontmatter":{"comment":"The frontmatter is treated as comments in order to get the \"faded\" look","begin":"\\A(-{3})\\s*$","beginCaptures":{"1":{"name":"comment"}},"contentName":"source.esjs","patterns":[{"include":"source.esjs"}],"end":"(^|\\G)(-{3})|\\.{3}\\s*$","endCaptures":{"2":{"name":"comment"}}}}} -------------------------------------------------------------------------------- /apps/playground/app/composables/useCompiler.ts: -------------------------------------------------------------------------------- 1 | import { type CompileOptions } from '@es-js/core' 2 | import { EssucraseCompiler } from '@es-js/core/compiler/essucrase.compiler' 3 | import putout from '@putout/bundle' 4 | 5 | export const useCompiler = () => { 6 | function compile(code: string, options: CompileOptions) { 7 | const compiler = new EssucraseCompiler(putout) 8 | return compiler?.compile(code, options) ?? code 9 | } 10 | 11 | return { 12 | compile, 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/matriz.js: -------------------------------------------------------------------------------- 1 | const matriz = Array.of([]) 2 | 3 | matriz.push('test') 4 | 5 | if (matriz.includes('test')) { 6 | matriz.pop() 7 | } 8 | 9 | matriz.length; 10 | 11 | matriz.find((item) => item === 'test') 12 | 13 | Array.from([1, 2, 3]) 14 | 15 | Array.fromAsync([1, 2, 3]) 16 | 17 | Array.isArray([]) 18 | 19 | Array.of([1, 2, 3]) 20 | 21 | const a = Array(5) 22 | const lista = [] 23 | lista.filter((item) => item === 'test').map((item) => item + 'test') 24 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/DialogFooter.vue: -------------------------------------------------------------------------------- 1 | 7 | 8 | 20 | -------------------------------------------------------------------------------- /apps/playground/content/fundamentos/11.funciones.md: -------------------------------------------------------------------------------- 1 | # Funciones 2 | 3 | Una función es una porción de código que, al ser llamada, ejecuta una serie de instrucciones y produce un resultado. Puede recibir datos de entrada (parámetros) y devolver datos de salida (el resultado). 4 | 5 | En EsJS, las funciones se declaran con la palabra clave `funcion`: 6 | 7 | ::content-code 8 | ```esjs 9 | funcion sumar(a, b) { 10 | retornar a + b 11 | } 12 | 13 | consola.escribir(sumar(1, 2)); 14 | ``` 15 | :: 16 | -------------------------------------------------------------------------------- /packages/vscode-esjs/.github/workflows/release.yml: -------------------------------------------------------------------------------- 1 | name: Release 2 | 3 | on: 4 | push: 5 | tags: 6 | - 'v*' 7 | 8 | jobs: 9 | release: 10 | runs-on: ubuntu-latest 11 | steps: 12 | - uses: actions/checkout@v3 13 | with: 14 | fetch-depth: 0 15 | 16 | - uses: actions/setup-node@v3 17 | with: 18 | node-version: 16.x 19 | 20 | - run: npx changelogithub 21 | env: 22 | GITHUB_TOKEN: ${{secrets.GITHUB_TOKEN}} 23 | -------------------------------------------------------------------------------- /packages/vite-plugin-esvue/test/fixtures/basic/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | EsVue 9 | 10 | 11 | 12 |
13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /scripts/release.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | set -xe 4 | 5 | # Build all once to ensure things are nice 6 | pnpm build 7 | 8 | # Install all dependencies 9 | pnpm -r install 10 | 11 | # Release packages 12 | for PKG in ./packages/* ; do 13 | pushd $PKG 14 | echo "⚡ Publishing $PKG" 15 | 16 | # Temporarily disable errexit for publish 17 | set +e 18 | 19 | # Publish 20 | pnpm publish --no-git-checks --force 21 | 22 | # Re-enable errexit 23 | set -e 24 | 25 | popd > /dev/null 26 | done 27 | -------------------------------------------------------------------------------- /demos/demo-esjs-terminal/src/app.esjs: -------------------------------------------------------------------------------- 1 | importar { Terminal } desde '@es-js/terminal' 2 | 3 | asincrono funcion inicio() { 4 | Terminal.limpiar() 5 | 6 | Terminal.escribir('Ingresa un valor:') 7 | 8 | const resultado = esperar Terminal.leer() 9 | 10 | Terminal.escribir({ 11 | Resultado: resultado, 12 | Tipo: tipoDe resultado, 13 | }) 14 | 15 | Terminal.escribir('Presiona ENTER para volver a iniciar') 16 | 17 | esperar Terminal.leerEnter() 18 | 19 | esperar inicio() 20 | } 21 | 22 | inicio() 23 | -------------------------------------------------------------------------------- /packages/core/build.config.ts: -------------------------------------------------------------------------------- 1 | import { defineBuildConfig } from 'unbuild' 2 | 3 | export default defineBuildConfig({ 4 | entries: [ 5 | './src/index', 6 | './src/keywords', 7 | './src/utils', 8 | './src/plugins/index', 9 | './src/compiler/esbabel.compiler', 10 | './src/compiler/essucrase.compiler', 11 | ], 12 | clean: true, 13 | declaration: true, 14 | rollup: { 15 | emitCJS: true, 16 | inlineDependencies: true, 17 | }, 18 | externals: ['@putout/bundle'], 19 | }) 20 | -------------------------------------------------------------------------------- /packages/terminal/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | EsJS Terminal 8 | 9 | 10 |
11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/popover/Popover.vue: -------------------------------------------------------------------------------- 1 | 10 | 11 | 16 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/matriz.esjs: -------------------------------------------------------------------------------- 1 | const matriz = Matriz.de([]) 2 | 3 | matriz.agregar('test') 4 | 5 | si (matriz.incluye('test')) { 6 | matriz.sacar() 7 | } 8 | 9 | matriz.longitud; 10 | 11 | matriz.buscar((item) => item === 'test') 12 | 13 | Matriz.desde([1, 2, 3]) 14 | 15 | Matriz.desdeAsincrono([1, 2, 3]) 16 | 17 | Matriz.esMatriz([]) 18 | 19 | Matriz.de([1, 2, 3]) 20 | 21 | const a = Matriz(5) 22 | const lista = [] 23 | lista.filtrar((item) => item === 'test').mapear((item) => item + 'test') 24 | -------------------------------------------------------------------------------- /packages/eshtml/test/utils/generateAttributeUsages.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | import { generateAttributeUsages } from '../../src/utils/generateAttributeUsages' 3 | 4 | describe('generateAttributeUsages', () => { 5 | it.skip('generates attribute usages', async () => { 6 | try { 7 | const attributeUsages = generateAttributeUsages() 8 | 9 | expect(attributeUsages).toMatchSnapshot() 10 | } catch (error) { 11 | console.error({ error }) 12 | } 13 | }) 14 | }) 15 | -------------------------------------------------------------------------------- /apps/playground/app/components/AppContainer.vue: -------------------------------------------------------------------------------- 1 | 17 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenu.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 15 | -------------------------------------------------------------------------------- /packages/core/src/plugins/booleano/index.ts: -------------------------------------------------------------------------------- 1 | import { replaceInstanceof, replaceObjects } from '../utils' 2 | 3 | export const report = () => 'Converts Booleano methods to JavaScript' 4 | 5 | export const methods = new Map([]) 6 | 7 | export const objects = new Map([['Booleano', 'Boolean']]) 8 | 9 | export function replace() { 10 | return { 11 | ...replaceInstanceof({ 12 | from: 'Booleano', 13 | to: 'Boolean', 14 | }), 15 | ...replaceObjects({ 16 | objects, 17 | }), 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /packages/core/src/plugins/funcion/index.ts: -------------------------------------------------------------------------------- 1 | import { replaceInstanceof, replaceObjects } from '../utils' 2 | 3 | export const report = () => 'Converts Funcion methods to JavaScript' 4 | 5 | export const methods = new Map([]) 6 | 7 | export const objects = new Map([['Funcion', 'Function']]) 8 | 9 | export function replace() { 10 | return { 11 | ...replaceInstanceof({ 12 | from: 'Funcion', 13 | to: 'Function', 14 | }), 15 | ...replaceObjects({ 16 | objects, 17 | }), 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuSub.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 20 | -------------------------------------------------------------------------------- /packages/sandbox/test/transformers/exportFunctions.transformer.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | import { ExportFunctionsTransformer } from '../../src/transformers/exportFunctions.transformer' 3 | 4 | describe('ExportFunctionsTransformer', () => { 5 | it('adds export to function', () => { 6 | const code = `function foo() { 7 | return 'foo'; 8 | } 9 | ` 10 | const expected = `export function foo() { 11 | return 'foo'; 12 | }` 13 | expect(new ExportFunctionsTransformer().transform(code)).toBe(expected) 14 | }) 15 | }) 16 | -------------------------------------------------------------------------------- /demos/demo-esjs-terminal/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | EsJS - JavaScript en Español 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /demos/demo-esvue/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/demo-esvue", 3 | "version": "0.0.0", 4 | "private": true, 5 | "scripts": { 6 | "dev": "vite --host", 7 | "build": "vue-tsc --noEmit && vite build", 8 | "preview": "vite preview" 9 | }, 10 | "dependencies": { 11 | "@es-js/vite-plugin-esvue": "workspace:^", 12 | "vue": "^3.3.8" 13 | }, 14 | "devDependencies": { 15 | "@types/node": "^20.9.0", 16 | "@vitejs/plugin-vue": "^4.4.1", 17 | "typescript": "^5.2.2", 18 | "vite": "^4.5.0", 19 | "vue-tsc": "^1.8.22" 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /apps/playground/app/components/input/LanguageSwitcher.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 21 | -------------------------------------------------------------------------------- /packages/cli/commands/actualizar.mjs: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | import { defineCommand } from 'citty' 4 | import { consola } from 'consola' 5 | import { execSync as exec } from 'node:child_process' 6 | import { showUsage } from '../utils/utils.mjs' 7 | 8 | export default defineCommand({ 9 | meta: { 10 | name: 'actualizar', 11 | description: 'Actualiza el CLI de EsJS.', 12 | }, 13 | 14 | async run() { 15 | try { 16 | exec('npm install -g es.js@latest', { stdio: 'inherit' }) 17 | } catch (e) { 18 | consola.error(e) 19 | } 20 | }, 21 | }) 22 | -------------------------------------------------------------------------------- /packages/terminal/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "moduleResolution": "Node", 7 | "strict": true, 8 | "jsx": "preserve", 9 | "resolveJsonModule": true, 10 | "isolatedModules": true, 11 | "esModuleInterop": true, 12 | "lib": ["ESNext", "DOM"], 13 | "skipLibCheck": true, 14 | "noEmit": true 15 | }, 16 | "include": ["src/**/*.ts", "src/**/*.d.ts", "src/**/*.tsx", "src/**/*.vue"], 17 | "references": [{ "path": "./tsconfig.node.json" }] 18 | } 19 | -------------------------------------------------------------------------------- /packages/eshtml/test/tags.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | import { getDictionary, htmlTags } from '../src/tags' 3 | 4 | describe('Dictionary completeness test', () => { 5 | it('should contain all htmlTags', () => { 6 | const dictionary = getDictionary() 7 | const dictionaryKeys = Array.from(dictionary.values()) 8 | 9 | htmlTags.forEach((keyword) => { 10 | if (!dictionaryKeys.includes(keyword)) { 11 | console.log('Missing keyword:', keyword) 12 | } 13 | 14 | expect(dictionaryKeys).toContain(keyword) 15 | }) 16 | }) 17 | }) 18 | -------------------------------------------------------------------------------- /packages/terminal/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { resolve } from 'path' 2 | import { defineConfig } from 'vite' 3 | import dts from 'vite-plugin-dts' 4 | 5 | // https://vitejs.dev/config/ 6 | export default defineConfig({ 7 | build: { 8 | lib: { 9 | entry: resolve(__dirname, 'src/main.ts'), 10 | name: 'EsTerminal', 11 | fileName: (format) => `terminal.${format}.js`, 12 | }, 13 | }, 14 | plugins: [ 15 | dts({ 16 | staticImport: true, 17 | skipDiagnostics: false, 18 | rollupTypes: true, 19 | insertTypesEntry: true, 20 | }), 21 | ], 22 | }) 23 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "esnext", 4 | "module": "esnext", 5 | "strict": true, 6 | "noUnusedLocals": true, 7 | "moduleResolution": "node", 8 | "declaration": true, 9 | "emitDeclarationOnly": true, 10 | "esModuleInterop": true, 11 | "resolveJsonModule": true, 12 | "forceConsistentCasingInFileNames": true, 13 | "noImplicitAny": true, 14 | "outDir": "dist", 15 | "lib": ["esnext"], 16 | "sourceMap": true 17 | }, 18 | "include": ["./src"], 19 | "exclude": ["node_modules"] 20 | } 21 | -------------------------------------------------------------------------------- /apps/playground/server/middleware/subdomain.ts: -------------------------------------------------------------------------------- 1 | import { getHeaders } from 'h3' 2 | import { mainDomain } from '~/constants/app' 3 | 4 | export default defineEventHandler((event) => { 5 | const headers = getHeaders(event) 6 | const hostname = headers.host ?? 'esjs.dev' 7 | 8 | if (!mainDomain.includes(hostname)) { 9 | const currentHost = hostname.match(/^[^.]*/g)[0] 10 | event.context.subdomain = currentHost 11 | 12 | setCookie(event, 'subdomain', currentHost) 13 | 14 | if (headers.referer) { 15 | setCookie(event, 'currentUrl', headers.referer) 16 | } 17 | } 18 | }) 19 | -------------------------------------------------------------------------------- /packages/eshtml/test/attrs.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | import { getDictionary, htmlAttrs } from '../src/attrs' 3 | 4 | describe('Dictionary completeness test', () => { 5 | it('should contain all htmlAttrs', () => { 6 | const dictionary = getDictionary() 7 | const dictionaryKeys = Array.from(dictionary.values()) 8 | 9 | htmlAttrs.forEach((keyword) => { 10 | if (!dictionaryKeys.includes(keyword)) { 11 | console.log('Missing keyword:', keyword) 12 | } 13 | 14 | expect(dictionaryKeys).toContain(keyword) 15 | }) 16 | }) 17 | }) 18 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuRadioGroup.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 20 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/src/lib/generatePagesInput.ts: -------------------------------------------------------------------------------- 1 | import { Opciones } from '../index' 2 | import { getPage } from './getPage' 3 | 4 | export function generatePagesInput( 5 | input: any, 6 | options: Opciones, 7 | ): Record { 8 | const newInput: Record = { ...input } 9 | 10 | for (const pageName of Object.keys(options?.paginas || {})) { 11 | const page = getPage(options, pageName) 12 | if (page && !newInput[pageName]) { 13 | const pagePath = `${pageName}.html` 14 | newInput[pageName] = pagePath 15 | } 16 | } 17 | 18 | return newInput 19 | } 20 | -------------------------------------------------------------------------------- /packages/prueba/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "sourceMap": true, 10 | "resolveJsonModule": true, 11 | "esModuleInterop": true, 12 | "emitDeclarationOnly": true, 13 | "declaration": true, 14 | "declarationMap": true, 15 | "declarationDir": "./types", 16 | "noUnusedLocals": true, 17 | "noUnusedParameters": true, 18 | "noImplicitReturns": true 19 | }, 20 | "include": ["./lib"] 21 | } 22 | -------------------------------------------------------------------------------- /packages/vscode-esjs/languages/esvue-language-configuration.json: -------------------------------------------------------------------------------- 1 | {"comments":{"lineComment":"//","blockComment":["/*","*/"]},"brackets":[["{","}"],["[","]"],["(",")"]],"autoClosingPairs":[{"open":"{","close":"}"},{"open":"[","close":"]"},{"open":"(","close":")"},{"open":"\"","close":"\"","notIn":["string"]},{"open":"'","close":"'","notIn":["string","comment"]},{"open":"`","close":"`","notIn":["string","comment"]},{"open":"/**","close":" */","notIn":["string"]}],"surroundingPairs":[["{","}"],["[","]"],["(",")"],["\"","\""],["'","'"],["`","`"]],"folding":{"markers":{"start":"^<(template|style|script)[^>]*>","end":"^"}}} -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/index.ts: -------------------------------------------------------------------------------- 1 | export { default as Dialog } from './Dialog.vue' 2 | export { default as DialogClose } from './DialogClose.vue' 3 | export { default as DialogTrigger } from './DialogTrigger.vue' 4 | export { default as DialogHeader } from './DialogHeader.vue' 5 | export { default as DialogTitle } from './DialogTitle.vue' 6 | export { default as DialogDescription } from './DialogDescription.vue' 7 | export { default as DialogContent } from './DialogContent.vue' 8 | export { default as DialogScrollContent } from './DialogScrollContent.vue' 9 | export { default as DialogFooter } from './DialogFooter.vue' 10 | -------------------------------------------------------------------------------- /packages/sandbox/test/transformers/format.transformer.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | import { FormatTransformer } from '../../src/transformers/format.transformer' 3 | 4 | describe('FormatTransformer', () => { 5 | it('formats code correctly', () => { 6 | const code = ` 7 | import { a } from 'a' 8 | import { b } from 'b' 9 | 10 | function foo() { return a + b } 11 | ` 12 | 13 | const expected = `import { a } from "a" 14 | import { b } from "b" 15 | 16 | function foo() { 17 | return a + b 18 | } 19 | ` 20 | 21 | expect(new FormatTransformer().transform(code)).toBe(expected) 22 | }) 23 | }) 24 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/src/lib/getEntryScripts.ts: -------------------------------------------------------------------------------- 1 | /** 2 | * Get entry scripts from HTML. 3 | */ 4 | export function getEntryScripts(html: string): Map { 5 | const matches = html.match(/<\/script>/g) 6 | 7 | if (!matches) { 8 | return new Map() 9 | } 10 | 11 | const entryScripts = new Map() 12 | 13 | for (const match of matches) { 14 | const src = match.match(/<\/script>/)?.[1] 15 | 16 | if (src) { 17 | entryScripts.set(src.replace('.esjs', '.js'), src) 18 | } 19 | } 20 | 21 | return entryScripts 22 | } 23 | -------------------------------------------------------------------------------- /packages/sandbox/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "module": "ESNext", 6 | "lib": ["ESNext", "DOM"], 7 | "moduleResolution": "Node", 8 | "strict": true, 9 | "sourceMap": true, 10 | "resolveJsonModule": true, 11 | "esModuleInterop": true, 12 | "emitDeclarationOnly": true, 13 | "declaration": true, 14 | "declarationMap": true, 15 | "declarationDir": "./types", 16 | "noUnusedLocals": true, 17 | "noUnusedParameters": true, 18 | "noImplicitReturns": true, 19 | "allowJs": true 20 | }, 21 | "include": ["./src"] 22 | } 23 | -------------------------------------------------------------------------------- /apps/playground/app/layouts/default.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 22 | -------------------------------------------------------------------------------- /packages/eshtml/src/utils/replaceDocType.ts: -------------------------------------------------------------------------------- 1 | import { CompileOptions } from '../index' 2 | 3 | export function replaceDocType(code: string, options: CompileOptions): string { 4 | const fromDocType = 5 | options?.from === 'html' ? '' : '' 6 | const toDocType = 7 | options?.to === 'html' ? '' : '' 8 | const fromDocTypeRegex = new RegExp(escapeRegExp(fromDocType), 'gi') 9 | return code.replace(fromDocTypeRegex, toDocType) 10 | } 11 | 12 | function escapeRegExp(string: string): string { 13 | return string.replace(/[.*+?^${}()|[\]\\]/g, '\\$&') // Escapa caracteres especiales para regex 14 | } 15 | -------------------------------------------------------------------------------- /packages/vite-plugin-esvue/test/fixtures/basic/src/App.esvue: -------------------------------------------------------------------------------- 1 | 2 | import { ref } from 'vue' 3 | 4 | const contador = ref(0) 5 | 6 | const aumentarContador = () => { 7 | contador.value++ 8 | } 9 | 10 | const resetearContador = () => { 11 | contador.value = 0 12 | } 13 | 14 | 15 | 16 | 17 | 18 | Hola desde EsJS + EsVue! 19 | Contador: {{contador}} 20 | Aumentar contador 21 | Resetear contador 22 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /apps/playground/app/composables/useAuth.ts: -------------------------------------------------------------------------------- 1 | export default function() { 2 | const supabase = useSupabaseClient() 3 | 4 | async function login() { 5 | // Save current URL to redirect the user back to it after signing in. 6 | const currentUrl = window.location.href 7 | localStorage.setItem('redirect_url', currentUrl) 8 | 9 | const { data, error } = await supabase.auth.signInWithOAuth({ 10 | provider: 'github', 11 | options: { 12 | scopes: 'read:org, repo', 13 | }, 14 | }) 15 | } 16 | 17 | function logout() { 18 | supabase.auth.signOut() 19 | } 20 | 21 | return { 22 | login, 23 | logout, 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /apps/playground/app/composables/usePlayground.ts: -------------------------------------------------------------------------------- 1 | import { useEventBus } from '@vueuse/core' 2 | 3 | export const usePlayground = () => { 4 | const bus = useEventBus('editor_code') 5 | 6 | function handleWindowKeyup($event: any) { 7 | if ($event.key === 'Escape') { 8 | bus.emit('focus') 9 | } 10 | } 11 | 12 | function handleWindowClose($event: any) { 13 | // Cancelar el cierre de la ventana 14 | $event.preventDefault() 15 | // Chrome requiere que se establezca la propiedad returnValue en una cadena vacía 16 | $event.returnValue = '' 17 | } 18 | 19 | return { 20 | handleWindowKeyup, 21 | handleWindowClose, 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /apps/playground/app/layouts/learn.vue: -------------------------------------------------------------------------------- 1 | 12 | 13 | 24 | -------------------------------------------------------------------------------- /packages/sandbox/test/utils/generateImportFunctions.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | import { generateImportFunctions } from '../../src/utils/generateImportFunctions' 3 | 4 | describe('generateImportFunctions', () => { 5 | it('imports functions', () => { 6 | const code = `export function foo() { 7 | return 'foo'; 8 | } 9 | 10 | export async function bar() { 11 | return 'bar'; 12 | }` 13 | 14 | const expected = `import { foo } from './foo' 15 | import { bar } from './foo'` 16 | 17 | expect( 18 | generateImportFunctions({ 19 | code, 20 | modulePath: './foo', 21 | }), 22 | ).toBe(expected) 23 | }) 24 | }) 25 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/simbolo.js: -------------------------------------------------------------------------------- 1 | const foo = Symbol("foo") 2 | 3 | foo.valueOf() === "foo" 4 | foo.toString() === "foo" 5 | 6 | class Validador { 7 | get [Symbol.toStringTag]() { 8 | return 'Validador'; 9 | } 10 | } 11 | 12 | Symbol.iterator.description; 13 | 14 | Symbol.asyncIterator; 15 | Symbol.hasInstance; 16 | Symbol.isConcatSpreadable; 17 | Symbol.iterator; 18 | Symbol.match; 19 | Symbol.matchAll; 20 | Symbol.replace; 21 | Symbol.search; 22 | Symbol.species; 23 | Symbol.split; 24 | Symbol.toPrimitive; 25 | Symbol.toStringTag; 26 | Symbol.unscopables; 27 | 28 | let sym = Symbol.for("foo"); 29 | Symbol.keyFor(sym) === "foo"; 30 | -------------------------------------------------------------------------------- /packages/eshtml/src/render.ts: -------------------------------------------------------------------------------- 1 | import { render as renderPostHTML } from 'posthtml-render' 2 | import { getDictionary } from './tags' 3 | 4 | const dictionary = getDictionary(true) 5 | 6 | export function render(tree: any): string { 7 | return renderPostHTML(tree, { 8 | singleTags: [ 9 | 'area', 10 | 'base', 11 | 'br', 12 | 'col', 13 | 'command', 14 | 'embed', 15 | 'hr', 16 | 'img', 17 | 'input', 18 | 'keygen', 19 | 'link', 20 | 'menuitem', 21 | 'meta', 22 | 'param', 23 | 'source', 24 | 'track', 25 | 'wbr', 26 | ].map((tag) => dictionary.get(tag) || tag), 27 | }) 28 | } 29 | -------------------------------------------------------------------------------- /demos/demo-esjs-terminal/vite.config.js: -------------------------------------------------------------------------------- 1 | import { URL, fileURLToPath } from 'node:url' 2 | import { defineConfig } from 'vite' 3 | import EsJS from '@es-js/vite-plugin-esjs' 4 | 5 | // https://vitejs.dev/config/ 6 | export default defineConfig({ 7 | plugins: [ 8 | // https://github.com/es-js/esjs 9 | EsJS(), 10 | ], 11 | resolve: { 12 | alias: { 13 | '@': fileURLToPath(new URL('./src', import.meta.url)), 14 | }, 15 | extensions: [ 16 | '.js', 17 | '.json', 18 | '.jsx', 19 | '.mjs', 20 | '.ts', 21 | '.tsx', 22 | '.vue', 23 | '.esjs', 24 | ], 25 | }, 26 | server: { 27 | port: 3000, 28 | }, 29 | }) 30 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/objetos.js: -------------------------------------------------------------------------------- 1 | const numero = Number(1); 2 | 3 | const cadena = String('Hola'); 4 | 5 | const booleano = Boolean(true); 6 | 7 | const objeto = new Object({}); 8 | 9 | const matriz = new Array([[1, 2], [3, 4]]); 10 | 11 | const f = Function(() => {}); 12 | 13 | const simbolo = Symbol('Simbolo'); 14 | 15 | const fecha = new Date(); 16 | 17 | const error = Error('Error'); 18 | 19 | const expReg = RegExp(/ExpReg/); 20 | 21 | const mapa = new Map([['clave', 'valor']]); 22 | 23 | const conjunto = new Set([1, 2, 3]); 24 | 25 | const apoderado = new Proxy({}, {}); 26 | 27 | const enteroGrande = BigInt(1n); 28 | 29 | const documento = Document(document); 30 | -------------------------------------------------------------------------------- /apps/playground/app/router.options.ts: -------------------------------------------------------------------------------- 1 | import type { RouterOptions } from '@nuxt/schema' 2 | export default { 3 | routes: (_routes) => { 4 | const { ssrContext } = useNuxtApp() 5 | let subdomain = useCookie('subdomain').value 6 | if (ssrContext?.event.context.subdomain) { 7 | subdomain = ssrContext?.event.context.subdomain 8 | } 9 | 10 | if (subdomain === 'aprender') { 11 | const learnRoutes = _routes 12 | .filter(i => i.name === 'aprender-slug') 13 | .map(i => ({ 14 | ...i, 15 | path: '/:slug(.*)*', 16 | })) 17 | 18 | return learnRoutes 19 | } 20 | 21 | return _routes 22 | }, 23 | } 24 | -------------------------------------------------------------------------------- /packages/vite-plugin-esjs/src/index.ts: -------------------------------------------------------------------------------- 1 | import { compile } from '@es-js/core' 2 | import { splitCodeImports } from '@es-js/core/utils' 3 | import type { Plugin } from 'vite' 4 | 5 | export default function EsJS(options = {}): Plugin { 6 | return { 7 | name: 'vite-plugin-esjs', 8 | enforce: 'pre', 9 | transform(raw: string, id: string) { 10 | if (!/\.esjs$/.test(id)) { 11 | return 12 | } 13 | 14 | const compiled = compile(raw, { 15 | compiler: 'essucrase', 16 | }) 17 | 18 | const { imports, codeWithoutImports } = splitCodeImports(compiled) 19 | 20 | return `${imports} 21 | 22 | ${codeWithoutImports}` 23 | }, 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /packages/core/src/keywords.ts: -------------------------------------------------------------------------------- 1 | import { 2 | arrayMethods, 3 | consoleMethods, 4 | constantLanguage, 5 | dateMethods, 6 | keywordControl, 7 | keywords, 8 | mathMethods, 9 | metaVariable, 10 | numberMethods, 11 | promiseMethods, 12 | storageType, 13 | stringMethods, 14 | supportFunction, 15 | variableLanguage, 16 | } from '@es-js/esbabel/keywords' 17 | 18 | export { 19 | keywordControl, 20 | constantLanguage, 21 | variableLanguage, 22 | storageType, 23 | metaVariable, 24 | supportFunction, 25 | promiseMethods, 26 | dateMethods, 27 | arrayMethods, 28 | mathMethods, 29 | numberMethods, 30 | consoleMethods, 31 | stringMethods, 32 | keywords, 33 | } 34 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuSeparator.vue: -------------------------------------------------------------------------------- 1 | 19 | 20 | 23 | -------------------------------------------------------------------------------- /apps/playground/content/fundamentos/6.constantes.md: -------------------------------------------------------------------------------- 1 | # Constantes 2 | 3 | Una constante es similar a una variable, pero su valor no puede ser alterado durante la ejecución del programa. Es decir, es un valor fijo. 4 | 5 | En EsJS, las constantes se declaran con la palabra clave `const`. 6 | 7 | ::content-code 8 | ```esjs 9 | const PI = 3.14159265359; 10 | 11 | consola.escribir(PI); 12 | ``` 13 | :: 14 | 15 | Por ejemplo, al código anterior se le puede agregar una variable `radio` y luego calcular el área de un círculo. 16 | 17 | ::content-code 18 | ```esjs 19 | const PI = 3.14159265359; 20 | 21 | var radio = 5; 22 | 23 | var area = PI * radio * radio; 24 | 25 | consola.escribir(area); 26 | ``` 27 | :: 28 | -------------------------------------------------------------------------------- /packages/core/src/plugins/json/index.ts: -------------------------------------------------------------------------------- 1 | import { replaceObjectStaticMethods } from '../utils' 2 | 3 | export const report = () => 'Converts JSON methods to JavaScript' 4 | 5 | export const methods = new Map([]) 6 | 7 | export const staticMethods = new Map([ 8 | ['esJSONCrudo', 'isRawJSON'], 9 | ['analizar', 'parse'], 10 | ['JSONCrudo', 'rawJSON'], 11 | ['aTexto', 'stringify'], 12 | ]) 13 | 14 | export const objects = new Map([['Fecha', 'Date']]) 15 | 16 | export function replace() { 17 | return { 18 | ...replaceObjectStaticMethods({ 19 | from: 'JSON', 20 | to: 'JSON', 21 | methods: staticMethods, 22 | }), 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /apps/playground/content/fundamentos/1.hola-mundo.md: -------------------------------------------------------------------------------- 1 | # Hola Mundo! 2 | 3 | El primer programa que se suele escribir en cualquier lenguaje de programación es el famoso "Hola Mundo!". Es decir, un programa que muestre el mensaje "Hola Mundo!" en la pantalla. 4 | 5 | En EsJS puedes imprimir texto en la consola del navegador utilizando la función `escribir` del objeto `consola`. 6 | 7 | ::content-code 8 | ```esjs 9 | consola.escribir("Hola Mundo!"); 10 | ``` 11 | :: 12 | 13 | EsJS también cuenta con un Modo Terminal que te permite escribir programas con una interfaz sencilla. 14 | 15 | ::content-code 16 | ```esjs 17 | importar { Terminal } desde "@es-js/terminal" 18 | 19 | Terminal.escribir("Hola Mundo!"); 20 | ``` 21 | :: 22 | 23 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/objetos.esjs: -------------------------------------------------------------------------------- 1 | const numero = Numero(1); 2 | 3 | const cadena = Cadena('Hola'); 4 | 5 | const booleano = Booleano(verdadero); 6 | 7 | const objeto = crear Objeto({}); 8 | 9 | const matriz = crear Matriz([[1, 2], [3, 4]]); 10 | 11 | const f = Funcion(() => {}); 12 | 13 | const simbolo = Simbolo('Simbolo'); 14 | 15 | const fecha = crear Fecha(); 16 | 17 | const error = Error('Error'); 18 | 19 | const expReg = ExpReg(/ExpReg/); 20 | 21 | const mapa = crear Mapa([['clave', 'valor']]); 22 | 23 | const conjunto = crear Conjunto([1, 2, 3]); 24 | 25 | const apoderado = crear Apoderado({}, {}); 26 | 27 | const enteroGrande = EnteroGrande(1n); 28 | 29 | const documento = Documento(document); 30 | -------------------------------------------------------------------------------- /demos/demo-esvue/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | EsVue / EsJS - Lenguaje de programación con sintaxis en Español basado en JavaScript 9 | 10 | 11 | 12 |
13 | 14 | 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /demos/demo-esvue/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { URL, fileURLToPath } from 'node:url' 2 | import { defineConfig } from 'vite' 3 | import vue from '@vitejs/plugin-vue' 4 | import EsVue from '@es-js/vite-plugin-esvue' 5 | 6 | export default defineConfig({ 7 | plugins: [ 8 | vue({ 9 | include: [/\.vue$/, /\.esvue$/], 10 | }), 11 | EsVue(), 12 | ], 13 | resolve: { 14 | alias: { 15 | '@': fileURLToPath(new URL('./src', import.meta.url)), 16 | }, 17 | extensions: [ 18 | '.js', 19 | '.json', 20 | '.jsx', 21 | '.mjs', 22 | '.ts', 23 | '.tsx', 24 | '.vue', 25 | '.esjs', 26 | '.esvue', 27 | ], 28 | }, 29 | server: { 30 | port: 3000, 31 | }, 32 | }) 33 | -------------------------------------------------------------------------------- /packages/sandbox/vite.config.js: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vite' 2 | import dts from 'vite-plugin-dts' 3 | 4 | export default defineConfig({ 5 | plugins: [dts()], 6 | build: { 7 | rollupOptions: { 8 | external: ['@es-js/terminal', '@es-js/prueba', '@es-js/tiza'], 9 | }, 10 | lib: { 11 | entry: { 12 | render: './src/render/index.ts', 13 | runtime: './src/runtime/index.ts', 14 | compiler: './src/compiler/index.ts', 15 | 'utils/processSandboxedFiles': './src/utils/processSandboxedFiles.ts', 16 | 'utils/processSandboxedCode': './src/utils/processSandboxedCode.ts', 17 | }, 18 | name: 'EsJS Sandbox', 19 | formats: ['es', 'cjs'], 20 | }, 21 | }, 22 | }) 23 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/simbolo.esjs: -------------------------------------------------------------------------------- 1 | const foo = Simbolo("foo") 2 | 3 | foo.valorDe() === "foo" 4 | foo.aCadena() === "foo" 5 | 6 | clase Validador { 7 | get [Simbolo.aCadenaEtiqueta]() { 8 | retornar 'Validador'; 9 | } 10 | } 11 | 12 | Simbolo.iterador.descripcion; 13 | 14 | Simbolo.iteradorAsincrono; 15 | Simbolo.tieneInstancia; 16 | Simbolo.esConcatenableExtendido; 17 | Simbolo.iterador; 18 | Simbolo.coincidir; 19 | Simbolo.coincidirTodo; 20 | Simbolo.reemplazar; 21 | Simbolo.buscarRegex; 22 | Simbolo.derivados; 23 | Simbolo.dividir; 24 | Simbolo.aPrimitivo; 25 | Simbolo.aCadenaEtiqueta; 26 | Simbolo.excluibles; 27 | 28 | mut sym = Simbolo.para("foo"); 29 | Simbolo.paraLlave(sym) === "foo"; 30 | -------------------------------------------------------------------------------- /packages/runtime/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/runtime", 3 | "version": "0.0.1-beta.1", 4 | "description": "Ejecuta EsJS y EsHtml facilmente con una etiqueta!", 5 | "license": "MIT", 6 | "type": "module", 7 | "main": "./src/index.js", 8 | "author": { 9 | "name": "Creadores Program Trollhunters501", 10 | "url": "https://github.com/Creadores-Program/EsJS-Script-tag" 11 | }, 12 | "repository": { 13 | "type": "git", 14 | "url": "git+https://github.com/es-js/esjs.git", 15 | "directory": "packages/runtime" 16 | }, 17 | "keywords": [ 18 | "esjs", 19 | "navegadores", 20 | "scripts", 21 | "CreadoresProgram", 22 | "eshtml" 23 | ] 24 | } 25 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tabs/TabsList.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 26 | -------------------------------------------------------------------------------- /packages/prettier-plugin-eshtml/test/package.test.ts: -------------------------------------------------------------------------------- 1 | import { createRequire } from 'node:module' 2 | import { fileURLToPath } from 'node:url' 3 | 4 | import { expect, it } from 'vitest' 5 | 6 | it.skip('should be importable', async () => { 7 | const imported = await import('..') 8 | 9 | expect(imported).toMatchSnapshot() 10 | }) 11 | 12 | it.skip('should be requireable', () => { 13 | const imported = createRequire(import.meta.url)('..') 14 | 15 | expect(imported).toMatchSnapshot() 16 | }) 17 | 18 | it('should be resolvable', () => { 19 | const actualPath = fileURLToPath( 20 | new URL('../dist/index.cjs', import.meta.url), 21 | ) 22 | 23 | const resolved = require.resolve('..') 24 | 25 | expect(resolved).toEqual(actualPath) 26 | }) 27 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esjs/test/package.test.ts: -------------------------------------------------------------------------------- 1 | import { createRequire } from 'node:module' 2 | import { fileURLToPath } from 'node:url' 3 | 4 | import { expect, it } from 'vitest' 5 | 6 | it.skip('should be importable', async () => { 7 | const imported = await import('..') 8 | 9 | expect(imported).toMatchSnapshot() 10 | }) 11 | 12 | it.skip('should be requireable', () => { 13 | const imported = createRequire(import.meta.url)('..') 14 | 15 | expect(imported).toMatchSnapshot() 16 | }) 17 | 18 | it('should be resolvable', () => { 19 | const actualPath = fileURLToPath( 20 | new URL('../dist/index.cjs', import.meta.url), 21 | ) 22 | 23 | const resolved = require.resolve('..') 24 | 25 | expect(resolved).toEqual(actualPath) 26 | }) 27 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esvue/test/package.test.ts: -------------------------------------------------------------------------------- 1 | import { createRequire } from 'node:module' 2 | import { fileURLToPath } from 'node:url' 3 | 4 | import { expect, it } from 'vitest' 5 | 6 | it.skip('should be importable', async () => { 7 | const imported = await import('..') 8 | 9 | expect(imported).toMatchSnapshot() 10 | }) 11 | 12 | it.skip('should be requireable', () => { 13 | const imported = createRequire(import.meta.url)('..') 14 | 15 | expect(imported).toMatchSnapshot() 16 | }) 17 | 18 | it('should be resolvable', () => { 19 | const actualPath = fileURLToPath( 20 | new URL('../dist/index.cjs', import.meta.url), 21 | ) 22 | 23 | const resolved = require.resolve('..') 24 | 25 | expect(resolved).toEqual(actualPath) 26 | }) 27 | -------------------------------------------------------------------------------- /apps/playground/app/components/playground/PlaygroundPanes.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 21 | -------------------------------------------------------------------------------- /demos/demo-eshtml/fuente/paginas/contador.esjs: -------------------------------------------------------------------------------- 1 | const valorContador = document.getElementById('valor-contador') 2 | const botonIncrementar = document.getElementById('incrementar') 3 | const botonDecrementar = document.getElementById('decrementar') 4 | const botonReiniciar = document.getElementById('reiniciar') 5 | 6 | mut contador = 0 7 | 8 | funcion actualizarContador() { 9 | valorContador.textContent = contador 10 | } 11 | 12 | botonIncrementar.addEventListener('click', () => { 13 | contador++ 14 | actualizarContador() 15 | }) 16 | 17 | botonDecrementar.addEventListener('click', () => { 18 | contador-- 19 | actualizarContador() 20 | }) 21 | 22 | botonReiniciar.addEventListener('click', () => { 23 | contador = 0 24 | actualizarContador() 25 | }) 26 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/button/Button.vue: -------------------------------------------------------------------------------- 1 | 17 | 18 | 27 | -------------------------------------------------------------------------------- /biome.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://biomejs.dev/schemas/1.7.2/schema.json", 3 | "formatter": { 4 | "indentStyle": "space" 5 | }, 6 | "files": { 7 | "include": [ 8 | "scripts/**/*.js", 9 | "packages/**/*.js", 10 | "packages/**/*.ts", 11 | "packages/**/*.mjs" 12 | ], 13 | "ignore": ["**/test/fixtures/**", "**/dist/**"] 14 | }, 15 | "organizeImports": { 16 | "enabled": true 17 | }, 18 | "linter": { 19 | "enabled": true, 20 | "rules": { 21 | "recommended": true, 22 | "suspicious": { 23 | "noExplicitAny": "warn" 24 | } 25 | } 26 | }, 27 | "javascript": { 28 | "formatter": { 29 | "quoteStyle": "single", 30 | "semicolons": "asNeeded" 31 | } 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tabs/TabsContent.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 23 | -------------------------------------------------------------------------------- /packages/core/src/plugins/apoderado/index.ts: -------------------------------------------------------------------------------- 1 | import { 2 | replaceInstanceof, 3 | replaceObjects, 4 | replaceObjectStaticMethods, 5 | } from '../utils' 6 | 7 | export const report = () => 'Converts Apoderado methods to JavaScript' 8 | 9 | export const staticMethods = new Map([ 10 | ['revocable', 'revocable'], 11 | ]) 12 | 13 | export const objects = new Map([['Apoderado', 'Proxy']]) 14 | 15 | export function replace() { 16 | return { 17 | ...replaceObjectStaticMethods({ 18 | from: 'Apoderado', 19 | to: 'Proxy', 20 | methods: staticMethods, 21 | }), 22 | ...replaceInstanceof({ 23 | from: 'Apoderado', 24 | to: 'Proxy', 25 | }), 26 | ...replaceObjects({ 27 | objects, 28 | }), 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/DialogDescription.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 25 | -------------------------------------------------------------------------------- /demos/demo-eshtml/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/demo-eshtml", 3 | "version": "0.0.0", 4 | "private": true, 5 | "scripts": { 6 | "dev": "vite --host", 7 | "build": "vite build", 8 | "preview": "vite preview", 9 | "format": "prettier --write ." 10 | }, 11 | "dependencies": { 12 | "@es-js/vite-plugin-eshtml": "workspace:^" 13 | }, 14 | "devDependencies": { 15 | "@es-js/vite-plugin-esjs": "0.1.0-beta.1", 16 | "prettier": "^3.3.3", 17 | "prettier-plugin-eshtml": "0.0.1-alpha.0", 18 | "prettier-plugin-esjs": "0.1.0-beta.1", 19 | "vite": "^5.3.3" 20 | }, 21 | "prettier": { 22 | "plugins": [ 23 | "prettier-plugin-eshtml", 24 | "prettier-plugin-esjs" 25 | ], 26 | "singleQuote": true, 27 | "semi": false 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/test/getEntryScripts.test.ts: -------------------------------------------------------------------------------- 1 | // import vite from 'vite' 2 | import { expect, it } from 'vitest' 3 | import { getEntryScripts } from '../src/lib/getEntryScripts' 4 | 5 | it('getEntryScripts', async () => { 6 | const html = ` 7 | 8 | 9 | 10 | 11 | 12 | 13 | EsHTML 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | ` 22 | 23 | const output = getEntryScripts(html) 24 | 25 | expect(output).toMatchSnapshot() 26 | }) 27 | -------------------------------------------------------------------------------- /packages/esjs-loader/test/index.test.ts: -------------------------------------------------------------------------------- 1 | import { spawnSync } from 'child_process' 2 | import { execPath } from 'process' 3 | import { fileURLToPath } from 'url' 4 | import { describe, expect, it } from 'vitest' 5 | 6 | describe('esjs-loader', () => { 7 | it('can load .esjs files', async () => { 8 | const loader = fileURLToPath(new URL('../dist/index.mjs', import.meta.url)) 9 | const fixture = fileURLToPath( 10 | new URL('../fixtures/test.esjs', import.meta.url), 11 | ) 12 | 13 | const { status, stderr, stdout } = spawnSync( 14 | execPath, 15 | ['--experimental-loader', loader, fixture], 16 | { encoding: 'utf8' }, 17 | ) 18 | 19 | console.error(stderr) 20 | 21 | expect(status).toBe(0) 22 | expect(stdout).toBe('Hola desde EsJS\n') 23 | }) 24 | }) 25 | -------------------------------------------------------------------------------- /packages/language-tools/src/generate-esjs-language-configurations.js: -------------------------------------------------------------------------------- 1 | import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs' 2 | 3 | if (!existsSync('dist')) { 4 | mkdirSync('dist') 5 | } 6 | 7 | const data = readFileSync('./assets/javascript-language-configuration.json') 8 | 9 | const jsonData = JSON.parse(data) 10 | 11 | jsonData.onEnterRules = [ 12 | ...jsonData.onEnterRules, 13 | { 14 | beforeText: { 15 | pattern: '^\\s*(\\bcaso\\s.+:|\\bporDefecto:)$', 16 | }, 17 | afterText: { 18 | pattern: '^(?!\\s*(\\bcaso\\b|\\bporDefecto\\b))', 19 | }, 20 | action: { 21 | indent: 'indent', 22 | }, 23 | }, 24 | ] 25 | 26 | const output = JSON.stringify(jsonData, null, '\t') 27 | 28 | writeFileSync('dist/esjs-language-configuration.json', output) 29 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/sonner/Sonner.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 23 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuLabel.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 25 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/soporte.js: -------------------------------------------------------------------------------- 1 | const timeout = setTimeout(() => { 2 | console.log('timeout') 3 | }) 4 | 5 | const interval = setInterval(() => { 6 | console.log('interval') 7 | }) 8 | 9 | console.log(isNaN('a')) 10 | 11 | clearTimeout(timeout) 12 | 13 | clearInterval(interval) 14 | 15 | alert('alert') 16 | 17 | prompt('prompt') 18 | 19 | confirm('confirm') 20 | 21 | fetch('https://jsonplaceholder.typicode.com/todos/1').then((respuesta) => { return respuesta.json() }) 22 | 23 | console.log(decodeURI('https://jsonplaceholder.typicode.com/todos/1')) 24 | 25 | console.log(decodeURIComponent('https%3A%2F%2Fjsonplaceholder.typicode.com%2Ftodos%2F1')) 26 | 27 | console.log(encodeURI('https://jsonplaceholder.typicode.com/todos/1')) 28 | 29 | console.log(encodeURIComponent('https://jsonplaceholder.typicode.com/todos/1')) 30 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dialog/DialogTitle.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 30 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/mate.js: -------------------------------------------------------------------------------- 1 | const x = 2 2 | let y = 3 3 | 4 | Math.abs(x) 5 | Math.acos(x) 6 | Math.acosh(x) 7 | Math.asin(x) 8 | Math.asinh(x) 9 | Math.atan(x) 10 | Math.atan2(x, y) 11 | Math.atanh(x) 12 | Math.cbrt(x) 13 | Math.ceil(x) 14 | Math.clz32(x) 15 | Math.cos(x) 16 | Math.cosh(x) 17 | Math.exp(x) 18 | Math.expm1(x) 19 | Math.floor(x) 20 | Math.fround(x) 21 | Math.hypot(x, y) 22 | Math.imul(x, y) 23 | Math.log(x) 24 | Math.log10(x) 25 | Math.log1p(x) 26 | Math.log2(x) 27 | Math.max(x, y) 28 | Math.min(x, y) 29 | Math.pow(x, y) 30 | Math.random() 31 | Math.round(x) 32 | Math.sign(x) 33 | Math.sin(x) 34 | Math.sinh(x) 35 | 36 | const a = Math.PI 37 | const b = Math.E 38 | const c = Math.LN2 39 | const d = Math.LN10 40 | const e = Math.LOG2E 41 | const f = Math.LOG10E 42 | const g = Math.SQRT1_2 43 | const h = Math.SQRT2 44 | -------------------------------------------------------------------------------- /demos/demo-eshtml/indice.eshtml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 9 | 10 | 11 | 12 | EsHTML: HTML en Español 13 | 14 | 15 | Fecha y hora actual: Cargando... 16 | 17 | 18 | Ejemplos en EsHTML/EsJS 19 | 20 | 21 | 22 | Contador Reactivo 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /packages/terminal/src/style.css: -------------------------------------------------------------------------------- 1 | @import 'xterminal/dist/xterminal.css'; 2 | 3 | :host { 4 | --xt-bg: #ffffff; 5 | --xt-fg: #000000; 6 | } 7 | 8 | .dark { 9 | --xt-bg: #121212; 10 | --xt-fg: #efefef; 11 | } 12 | 13 | @keyframes blink { 14 | 0% { opacity: 0; } 15 | 50% { opacity: 1; } 16 | 100% { opacity: 0; } 17 | } 18 | 19 | .xt-cursor { 20 | animation: blink 1s linear infinite; 21 | } 22 | 23 | .cargando:after { 24 | animation: changeContent 0.8s linear infinite; 25 | content: "⠋"; 26 | } 27 | 28 | @keyframes changeContent { 29 | 10% { content: "⠙"; } 30 | 20% { content: "⠹"; } 31 | 30% { content: "⠸"; } 32 | 40% { content: "⠼"; } 33 | 50% { content: "⠴"; } 34 | 60% { content: "⠦"; } 35 | 70% { content: "⠧"; } 36 | 80% { content: "⠇"; } 37 | 90% { content: "⠏"; } 38 | } 39 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/resizable/ResizablePanelGroup.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 22 | -------------------------------------------------------------------------------- /demos/demo-eshtml/fuente/paginas/contador.eshtml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 9 | 10 | 11 | 12 | EsHTML: HTML en Español 13 | Contador reactivo 14 | El valor actual es: 0 15 | Incrementar 16 | Decrementar 17 | Reiniciar 18 | 19 | 20 | 21 | Volver al índice 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /packages/vscode-esjs/README.md: -------------------------------------------------------------------------------- 1 | # vscode-esjs 2 | 3 | Visual Studio Marketplace Version 4 | 5 | Soporte para el lenguaje EsJS. 6 | 7 | ## EsJS: JavaScript con sintaxis en Español 8 | 9 | EsJS es un lenguaje de programación con sintaxis en Español que compila a JavaScript. Esto permite a las personas hispanohablantes escribir código de manera más familiar y accesible, sin renunciar al poder y versatilidad de JavaScript. 10 | 11 | Más información en: [https:/es.js.org/](https:/es.js.org/). 12 | 13 | ## Licencia 14 | 15 | Licencia [MIT](./LICENSE) © 2022-presente [Enzo Notario](https://github.com/enzonotario). 16 | -------------------------------------------------------------------------------- /demos/demo-esvue/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "baseUrl": ".", 4 | "target": "esnext", 5 | "useDefineForClassFields": true, 6 | "allowSyntheticDefaultImports": true, 7 | "composite": true, 8 | "module": "esnext", 9 | "moduleResolution": "node", 10 | "strict": true, 11 | "jsx": "preserve", 12 | "sourceMap": false, 13 | "resolveJsonModule": true, 14 | "esModuleInterop": true, 15 | "lib": ["esnext", "dom"], 16 | "paths": { 17 | "@/*": ["src/*"] 18 | }, 19 | "skipLibCheck": true, 20 | "allowJs": true, 21 | "strictNullChecks": true 22 | }, 23 | "include": [ 24 | "src/**/*.ts", 25 | "src/**/*.d.ts", 26 | "src/**/*.tsx", 27 | "src/**/*.vue", 28 | "src/**/*.esjs", 29 | "src/**/*.esvue", 30 | "vite.config.ts", 31 | ], 32 | "exclude": ["dist", "node_modules"] 33 | } 34 | -------------------------------------------------------------------------------- /packages/core/src/plugins/soporte/index.ts: -------------------------------------------------------------------------------- 1 | import { replaceKeywords } from '../utils' 2 | 3 | export const report = () => 'Converts support functions to JavaScript' 4 | 5 | export const keywords = new Map([ 6 | ['establecerTemporizador', 'setTimeout'], 7 | ['establecerIntervalo', 'setInterval'], 8 | ['esNuN', 'isNaN'], 9 | ['limpiarTemporizador', 'clearTimeout'], 10 | ['limpiarIntervalo', 'clearInterval'], 11 | ['alerta', 'alert'], 12 | ['preguntar', 'prompt'], 13 | ['confirmar', 'confirm'], 14 | ['consultar', 'fetch'], 15 | ['decodificarURI', 'decodeURI'], 16 | ['decodificarComponenteURI', 'decodeURIComponent'], 17 | ['codificarURI', 'encodeURI'], 18 | ['codificarComponenteURI', 'encodeURIComponent'], 19 | ]) 20 | 21 | export function replace() { 22 | return { 23 | ...replaceKeywords({ 24 | keywords, 25 | }), 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /packages/sandbox/test/utils/codeFrame.test.ts: -------------------------------------------------------------------------------- 1 | import { codeFrameColumns } from '../../src/utils/codeFrameColumns.ts' 2 | import { describe, expect, it } from 'vitest' 3 | 4 | describe('codeFrame', () => { 5 | it('unify duplicated imports', () => { 6 | const code = ` 7 | funcion sumar(a, b) 8 | retornar a + b 9 | } 10 | 11 | consola.escribir(sumar(5, 3)) // Salida: 8 12 | ` 13 | 14 | const expected = ` 1 | 15 | 2 | funcion sumar(a, b) 16 | > 3 | retornar a + b 17 | | ^ 18 | 4 | } 19 | 5 | 20 | 6 | consola.escribir(sumar(5, 3)) // Salida: 8` 21 | 22 | expect( 23 | codeFrameColumns( 24 | code, 25 | { 26 | start: { line: 3, column: 13 }, 27 | }, 28 | { 29 | highlightCode: false, 30 | }, 31 | ), 32 | ).toBe(expected) 33 | }) 34 | }) 35 | -------------------------------------------------------------------------------- /apps/playground/content/fundamentos/4.comentarios.md: -------------------------------------------------------------------------------- 1 | # Comentarios 2 | 3 | Los comentarios son líneas de código que son ignoradas intencionalmente por el intérprete de EsJS. Son útiles para agregar notas al código o explicar su funcionamiento. 4 | 5 | En EsJS existen dos tipos de comentarios: de una línea y de múltiples líneas. 6 | 7 | ## Comentarios de una línea 8 | 9 | Los comentarios de una línea comienzan con `//` y terminan al final de la línea. 10 | 11 | ::content-code 12 | ```esjs 13 | // Este es un comentario de una línea 14 | 15 | consola.escribir("Hola Mundo!"); 16 | ``` 17 | :: 18 | 19 | ## Comentarios de múltiples líneas 20 | 21 | Los comentarios de múltiples líneas comienzan con `/*` y terminan con `*/`. 22 | 23 | ::content-code 24 | ```esjs 25 | /* 26 | Este es un comentario 27 | de múltiples líneas 28 | */ 29 | 30 | consola.escribir("Hola Mundo!"); 31 | ``` 32 | :: 33 | -------------------------------------------------------------------------------- /demos/demo-esvue/src/App.esvue: -------------------------------------------------------------------------------- 1 | 2 | importar { ref } desde 'vue'; 3 | importar GitHub desde './GitHub.esvue'; 4 | 5 | var contador = ref(0); 6 | 7 | funcion aumentarContador() { 8 | contador.value++; 9 | } 10 | 11 | funcion resetearContador() { 12 | contador.value = 0 13 | } 14 | 15 | 16 | 17 | 18 | 19 | 20 | Hola desde EsJS + EsVue! 21 | Contador: {{contador}} 22 | Aumentar contador 23 | Resetear contador 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | -------------------------------------------------------------------------------- /packages/language-tools/assets/esvue.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "fileTypes": [".esvue"], 3 | "name": "EsVue", 4 | "scopeName": "source.esvue", 5 | "patterns": [ 6 | { 7 | "include": "#frontmatter" 8 | }, 9 | { 10 | "include": "source.vue" 11 | } 12 | ], 13 | "repository": { 14 | "frontmatter": { 15 | "comment": "The frontmatter is treated as comments in order to get the \"faded\" look", 16 | "begin": "\\A(-{3})\\s*$", 17 | "beginCaptures": { 18 | "1": { 19 | "name": "comment" 20 | } 21 | }, 22 | "contentName": "source.esjs", 23 | "patterns": [ 24 | { 25 | "include": "source.esjs" 26 | } 27 | ], 28 | "end": "(^|\\G)(-{3})|\\.{3}\\s*$", 29 | "endCaptures": { 30 | "2": { 31 | "name": "comment" 32 | } 33 | } 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "esjs", 3 | "version": "0.0.0", 4 | "description": "JavaScript con sintaxis en Español", 5 | "main": "index.js", 6 | "scripts": { 7 | "build": "pnpm --stream -r run build", 8 | "bump": "/bin/bash scripts/bump.sh", 9 | "release": "/bin/bash scripts/release.sh", 10 | "test": "pnpm --stream -r run test:run", 11 | "sherif": "pnpm dlx sherif@latest --fix", 12 | "format": "pnpm biome format --write ." 13 | }, 14 | "author": "Enzo Notario ", 15 | "license": "MIT", 16 | "keywords": [ 17 | "esjs", 18 | "español", 19 | "javascript" 20 | ], 21 | "devDependencies": { 22 | "@biomejs/biome": "1.7.2", 23 | "bumpp": "^9.2.0", 24 | "consola": "^3.2.3", 25 | "globby": "^14.0.0", 26 | "jiti": "^1.21.0", 27 | "pathe": "^1.1.1" 28 | }, 29 | "private": true, 30 | "packageManager": "pnpm@9.1.1" 31 | } 32 | -------------------------------------------------------------------------------- /packages/eshtml/test/testUtils.ts: -------------------------------------------------------------------------------- 1 | import htmlMinifier from 'html-minifier' 2 | import { Options } from 'prettier' 3 | import htmlParser from 'prettier/parser-html' 4 | import prettier from 'prettier/standalone' 5 | 6 | export async function formatWithPrettier( 7 | code: string, 8 | options?: Partial, 9 | ): Promise { 10 | return prettier.format(code, { 11 | parser: 'html', 12 | // @ts-ignore 13 | plugins: [htmlParser], 14 | semi: false, 15 | ...options, 16 | }) 17 | } 18 | 19 | export function minifyHtml(code: string): string { 20 | return htmlMinifier.minify(code, { 21 | collapseWhitespace: true, 22 | removeComments: true, 23 | }) 24 | } 25 | 26 | export function compareHtml(code1: string, code2: string): boolean { 27 | const formatted1 = minifyHtml(code1) 28 | const formatted2 = minifyHtml(code2) 29 | return formatted1 === formatted2 30 | } 31 | -------------------------------------------------------------------------------- /demos/demo-eshtml/vite.config.js: -------------------------------------------------------------------------------- 1 | import { URL, fileURLToPath } from 'node:url' 2 | import { defineConfig } from 'vite' 3 | import EsJS from '@es-js/vite-plugin-esjs' 4 | import EsHTML from '@es-js/vite-plugin-eshtml' 5 | 6 | export default defineConfig({ 7 | plugins: [ 8 | EsJS(), 9 | EsHTML({ 10 | paginas: { 11 | contador: { 12 | entrada: 'fuente/paginas/contador.esjs', 13 | plantilla: 'fuente/paginas/contador.eshtml', 14 | titulo: 'Contador reactivo', 15 | }, 16 | }, 17 | }), 18 | ], 19 | resolve: { 20 | alias: { 21 | '@': fileURLToPath(new URL('./fuente', import.meta.url)), 22 | }, 23 | extensions: [ 24 | '.js', 25 | '.json', 26 | '.jsx', 27 | '.mjs', 28 | '.ts', 29 | '.tsx', 30 | '.esjs', 31 | '.eshtml', 32 | ], 33 | }, 34 | server: { 35 | port: 3000, 36 | }, 37 | }) 38 | -------------------------------------------------------------------------------- /.github/workflows/test.yml: -------------------------------------------------------------------------------- 1 | name: Test 2 | 3 | on: 4 | push: 5 | branches: 6 | - main 7 | - develop 8 | 9 | pull_request: 10 | types: [opened, synchronize] 11 | 12 | jobs: 13 | test: 14 | runs-on: ubuntu-latest 15 | timeout-minutes: 15 16 | strategy: 17 | matrix: 18 | node-version: [18.x, 20.x, 22.x] 19 | 20 | steps: 21 | - name: Checkout code 22 | uses: actions/checkout@v3 23 | 24 | - name: Setup Node.js 25 | uses: actions/setup-node@v3 26 | with: 27 | node-version: ${{ matrix.node-version }} 28 | 29 | - name: Install pnpm 30 | uses: pnpm/action-setup@v4.0.0 31 | with: 32 | version: 9.1.1 33 | 34 | - name: Install dependencies 35 | run: pnpm install 36 | 37 | - name: Build 38 | run: pnpm build 39 | 40 | - name: Run test 41 | run: pnpm -r test:run 42 | -------------------------------------------------------------------------------- /packages/prueba/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/prueba", 3 | "version": "0.0.11", 4 | "scripts": { 5 | "dev": "vite", 6 | "build": "tsc && vite build", 7 | "watch": "concurrently \"tsc --watch\" \"vite build --watch\"", 8 | "test": "vitest", 9 | "test:run": "vitest run", 10 | "prepublishOnly": "pnpm run build" 11 | }, 12 | "devDependencies": { 13 | "browser-or-node": "^3.0.0", 14 | "concurrently": "^7.6.0", 15 | "log-symbols": "^5.1.0", 16 | "typescript": "^4.9.5", 17 | "vite": "^5.4.11", 18 | "vitest": "^2.1.5" 19 | }, 20 | "main": "./dist/esjs-prueba.umd.js", 21 | "module": "./dist/esjs-prueba.es.js", 22 | "exports": { 23 | ".": { 24 | "import": "./dist/esjs-prueba.es.js", 25 | "require": "./dist/esjs-prueba.umd.js" 26 | } 27 | }, 28 | "types": "./types/main.d.ts", 29 | "files": [ 30 | "/dist", 31 | "/types" 32 | ] 33 | } 34 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/soporte.esjs: -------------------------------------------------------------------------------- 1 | const timeout = establecerTemporizador(() => { 2 | consola.escribir('timeout') 3 | }) 4 | 5 | const interval = establecerIntervalo(() => { 6 | consola.escribir('interval') 7 | }) 8 | 9 | consola.escribir(esNuN('a')) 10 | 11 | limpiarTemporizador(timeout) 12 | 13 | limpiarIntervalo(interval) 14 | 15 | alerta('alert') 16 | 17 | preguntar('prompt') 18 | 19 | confirmar('confirm') 20 | 21 | consultar('https://jsonplaceholder.typicode.com/todos/1').luego((respuesta) => { retornar respuesta.json() }) 22 | 23 | consola.escribir(decodificarURI('https://jsonplaceholder.typicode.com/todos/1')) 24 | 25 | consola.escribir(decodificarComponenteURI('https%3A%2F%2Fjsonplaceholder.typicode.com%2Ftodos%2F1')) 26 | 27 | consola.escribir(codificarURI('https://jsonplaceholder.typicode.com/todos/1')) 28 | 29 | consola.escribir(codificarComponenteURI('https://jsonplaceholder.typicode.com/todos/1')) 30 | -------------------------------------------------------------------------------- /packages/vscode-esjs/src/utils/register-methods-completion.ts: -------------------------------------------------------------------------------- 1 | import vscode from 'vscode' 2 | 3 | export function registerMethods(prefix: string, keywords: Map) { 4 | return vscode.languages.registerCompletionItemProvider( 5 | '*', 6 | { 7 | provideCompletionItems( 8 | document: vscode.TextDocument, 9 | position: vscode.Position, 10 | ) { 11 | const linePrefix = document 12 | .lineAt(position) 13 | .text.substr(0, position.character) 14 | 15 | if (!linePrefix.endsWith(prefix)) { 16 | return undefined 17 | } 18 | 19 | return [ 20 | ...Array.from(keywords).map( 21 | ([esjsKeyword]) => 22 | new vscode.CompletionItem( 23 | String(esjsKeyword), 24 | vscode.CompletionItemKind.Method, 25 | ), 26 | ), 27 | ] 28 | }, 29 | }, 30 | '.', 31 | ) 32 | } 33 | -------------------------------------------------------------------------------- /apps/playground/app/components/playground/PlaygroundMobileView.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 26 | -------------------------------------------------------------------------------- /packages/terminal/src/components/es-terminal.ts: -------------------------------------------------------------------------------- 1 | import { usarTerminal } from '../composables/usarTerminal' 2 | import style from '../style.css?inline' 3 | 4 | class EsTerminal extends HTMLElement { 5 | #shadowRoot: ShadowRoot 6 | 7 | constructor() { 8 | super() 9 | 10 | this.#shadowRoot = this.attachShadow({ mode: 'open' }) 11 | 12 | this.#shadowRoot.innerHTML = ` 13 | 16 | 17 |
18 | ` 19 | } 20 | 21 | connectedCallback() { 22 | usarTerminal().iniciar( 23 | this.#shadowRoot.querySelector('div') as HTMLElement, 24 | { 25 | theme: this.getAttribute('tema') === 'oscuro' ? 'dark' : 'light', 26 | }, 27 | ) 28 | } 29 | 30 | disconnectedCallback() { 31 | usarTerminal().destruir() 32 | } 33 | } 34 | 35 | if (!customElements.get('es-terminal')) 36 | customElements.define('es-terminal', EsTerminal) 37 | -------------------------------------------------------------------------------- /packages/cli/commands/ejecutar.mjs: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | import { compile } from '@es-js/core' 4 | import { defineCommand } from 'citty' 5 | import { consola } from 'consola' 6 | import { readFile } from 'node:fs/promises' 7 | 8 | export default defineCommand({ 9 | meta: { 10 | name: 'ejecutar', 11 | description: 'Ejecuta un archivo (script) de EsJS.', 12 | }, 13 | 14 | args: { 15 | archivo: { 16 | type: 'positional', 17 | description: 'Nombre del archivo (script) a ejecutar.', 18 | required: true, 19 | }, 20 | }, 21 | 22 | async run({ args }) { 23 | const contenido = await readFile(args.archivo, { 24 | encoding: 'utf-8', 25 | }) 26 | 27 | const js = compile(contenido, { 28 | compiler: 'essucrase', 29 | }) 30 | 31 | try { 32 | // biome-ignore lint/security/noGlobalEval: This is a CLI tool. 33 | eval(js) 34 | } catch (err) { 35 | consola.error(err) 36 | } 37 | }, 38 | }) 39 | -------------------------------------------------------------------------------- /apps/playground/content/fundamentos/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | navigation: false 3 | --- 4 | 5 | # Fundamentos 6 | 7 | En esta sección exploraremos los fundamentos de la programación en EsJS/JavaScript. 8 | 9 | ## Introducción 10 | 11 | 1. [Hola Mundo!](/fundamentos/hola-mundo) 12 | 1. [Glosario general](/fundamentos/glosario-general) 13 | 1. [Identificadores](/fundamentos/identificadores) 14 | 1. [Comentarios](/fundamentos/comentarios) 15 | 16 | ## Estructuras de datos 17 | 18 | 1. [Variables](/fundamentos/variables) 19 | 1. [Constantes](/fundamentos/constantes) 20 | 1. [Tipos de datos](/fundamentos/tipos-de-datos) 21 | 1. [Operadores](/fundamentos/operadores) 22 | 23 | ## Estructuras de control 24 | 25 | 1. [Flujo de ejecución](/fundamentos/flujo-de-ejecucion) 26 | 2. [Condicionales](/fundamentos/condicionales) 27 | 3. [Bucles](/fundamentos/bucles) 28 | 29 | ## Funciones 30 | 31 | 1. [Funciones](/fundamentos/funciones) 32 | 33 | ## Módulos 34 | 35 | 1. [Módulos](/fundamentos/modulos) 36 | -------------------------------------------------------------------------------- /packages/cli/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "es.js", 3 | "version": "0.0.1-alpha.13", 4 | "description": "CLI para el lenguaje de programación EsJS", 5 | "type": "module", 6 | "main": "index.js", 7 | "bin": { 8 | "esjs": "./index.js" 9 | }, 10 | "scripts": { 11 | "test": "echo \"Error: no test specified\" && exit 1", 12 | "test:run": "echo \"Error: no test specified\"", 13 | "postinstall": "node postinstall.js" 14 | }, 15 | "repository": { 16 | "type": "git", 17 | "url": "git+https://github.com/es-js/esjs.git", 18 | "directory": "packages/cli" 19 | }, 20 | "author": "Enzo Notario ", 21 | "license": "MIT", 22 | "keywords": [ 23 | "esjs", 24 | "cli" 25 | ], 26 | "bugs": { 27 | "url": "https://github.com/es-js/esjs/issues" 28 | }, 29 | "homepage": "https://github.com/es-js/esjs#readme", 30 | "dependencies": { 31 | "@es-js/core": "latest", 32 | "citty": "^0.1.4", 33 | "consola": "^3.2.3" 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /packages/tiza/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/tiza", 3 | "version": "1.0.2", 4 | "description": "Librería para colorear/estilizar texto en la Terminal de EsJS. Basada en chalk-dom", 5 | "author": "Enzo Notario ", 6 | "scripts": { 7 | "dev": "vite", 8 | "build": "vite build", 9 | "test": "vitest", 10 | "test:run": "vitest run", 11 | "prepublishOnly": "pnpm run build" 12 | }, 13 | "keywords": [ 14 | "esjs", 15 | "tiza", 16 | "chalk-dom", 17 | "chalk", 18 | "consola", 19 | "colorear", 20 | "estilizar" 21 | ], 22 | "license": "MIT", 23 | "devDependencies": { 24 | "tailwindcss": "^3.3.3", 25 | "vite": "^4.4.9", 26 | "vitest": "^0.34.1" 27 | }, 28 | "main": "./dist/tiza.es.js", 29 | "module": "./dist/tiza.es.js", 30 | "exports": { 31 | ".": { 32 | "import": "./dist/tiza.es.js", 33 | "require": "./dist/tiza.umd.js" 34 | } 35 | }, 36 | "files": [ 37 | "/dist" 38 | ] 39 | } 40 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esjs/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "prettier-plugin-esjs", 3 | "version": "0.1.0-beta.2", 4 | "license": "MIT", 5 | "type": "module", 6 | "main": "./dist/index.cjs", 7 | "types": "./dist/index.d.ts", 8 | "exports": { 9 | ".": { 10 | "types": "./dist/index.d.ts", 11 | "default": "./dist/index.cjs" 12 | } 13 | }, 14 | "files": [ 15 | "dist" 16 | ], 17 | "scripts": { 18 | "build": "pkgroll", 19 | "start": "tsx src/index.ts", 20 | "test": "vitest", 21 | "test:run": "vitest run", 22 | "typecheck": "tsc --noEmit", 23 | "watch": "pkgroll --watch", 24 | "prepublishOnly": "pnpm run build" 25 | }, 26 | "devDependencies": { 27 | "@es-js/core": "workspace:*", 28 | "@prettier/sync": "^0.5.2", 29 | "@types/node": "^20.14.12", 30 | "pkgroll": "^2.4.1", 31 | "prettier": "^3.3.3", 32 | "tsx": "^4.16.2", 33 | "typescript": "^5.5.4", 34 | "vite": "^5.3.4", 35 | "vitest": "^2.0.4" 36 | }, 37 | "peerDependencies": { 38 | "prettier": "^3.0.0" 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /packages/language-tools/README.md: -------------------------------------------------------------------------------- 1 | # @es-js/language-tools 2 | 3 | Genera los archivos de sintaxis y configuración de los lenguajes EsJS y EsVue. 4 | 5 | - esjs.tmLanguage.json: Basado en la [extensión de JavaScript de VSCode](https://github.com/microsoft/vscode/tree/main/extensions/javascript), al cual se le agrega un repositorio `esjs` (con los tokens de EsJS), y luego se hace uso de este repositorio cada vez que se hace uso del repositorio `source.js#comment`. 6 | - esvue.tmLanguage.json: Basado en el [Frontmatter de Astro](https://github.com/withastro/language-tools/blob/main/packages/vscode/syntaxes/astro.tmLanguage.json), la primera parte la interpreta como `source.esjs`; el resto como `source.vue`. 7 | - esjs-language-configuration.json: Basado en la [extensión de JavaScript de VSCode](https://github.com/microsoft/vscode/tree/main/extensions/javascript), al cual se le agrega un único caso de identación para los tokens `caso` y `porDefecto`. 8 | - esvue-language-configuration.json: Simplemente una copia de [Vetur](https://github.com/vuejs/vetur). 9 | -------------------------------------------------------------------------------- /packages/tiza/src/colors.js: -------------------------------------------------------------------------------- 1 | import tailwindColors from 'tailwindcss/colors' 2 | 3 | const colorsMap = { 4 | rojo: tailwindColors.red, 5 | verde: tailwindColors.green, 6 | amarillo: tailwindColors.yellow, 7 | azul: tailwindColors.blue, 8 | magenta: tailwindColors.fuchsia, 9 | cian: tailwindColors.cyan, 10 | gris: tailwindColors.gray, 11 | indigo: tailwindColors.indigo, 12 | morado: tailwindColors.purple, 13 | } 14 | 15 | export const colors = { 16 | negro: tailwindColors.black, 17 | blanco: tailwindColors.white, 18 | } 19 | 20 | for (const color in colorsMap) { 21 | for (const level of [50, 100, 200, 300, 400, 500, 600, 700, 800, 900]) { 22 | const propertyName = `${color}${level}` 23 | colors[propertyName] = colorsMap[color][level] 24 | 25 | if (level === 500) { 26 | colors[color] = colorsMap[color][500] 27 | } 28 | } 29 | } 30 | 31 | for (const c in colors) { 32 | if (Object.hasOwnProperty.call(colors, c)) { 33 | colors[`fondo${c[0].toUpperCase()}${c.slice(1)}`] = colors[c] 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /apps/playground/README.md: -------------------------------------------------------------------------------- 1 | # Editor EsJS 2 | 3 | Editor de código para el lenguaje de programación EsJS. 4 | 5 | > https://editor.esjs.dev/ 6 | 7 | ## Setup 8 | 9 | Make sure to install the dependencies: 10 | 11 | ```bash 12 | # npm 13 | npm install 14 | 15 | # pnpm 16 | pnpm install 17 | 18 | # yarn 19 | yarn install 20 | ``` 21 | 22 | ## Development Server 23 | 24 | Start the development server on `http://localhost:3000`: 25 | 26 | ```bash 27 | # npm 28 | npm run dev 29 | 30 | # pnpm 31 | pnpm run dev 32 | 33 | # yarn 34 | yarn dev 35 | ``` 36 | 37 | ## Production 38 | 39 | Build the application for production: 40 | 41 | ```bash 42 | # npm 43 | npm run build 44 | 45 | # pnpm 46 | pnpm run build 47 | 48 | # yarn 49 | yarn build 50 | ``` 51 | 52 | Locally preview production build: 53 | 54 | ```bash 55 | # npm 56 | npm run preview 57 | 58 | # pnpm 59 | pnpm run preview 60 | 61 | # yarn 62 | yarn preview 63 | ``` 64 | 65 | Check out the [deployment documentation](https://nuxt.com/docs/getting-started/deployment) for more information. 66 | -------------------------------------------------------------------------------- /packages/vite-plugin-eshtml/src/lib/utils.ts: -------------------------------------------------------------------------------- 1 | import { compile as EsHTMLCompile } from '@es-js/eshtml' 2 | 3 | export function compile(eshtml: string): string { 4 | return EsHTMLCompile(eshtml, { from: 'eshtml', to: 'html' }) 5 | } 6 | 7 | export function dfs(keys: string[], value: any, res: Record) { 8 | if (keys.length) { 9 | const strItem = keys.shift() 10 | if (!keys.length) { 11 | res[strItem!] = value 12 | } else { 13 | const tmp = res[strItem!] ? res[strItem!] : (res[strItem!] = {}) 14 | dfs(keys, value, tmp) 15 | } 16 | } 17 | return res 18 | } 19 | 20 | export function dfs2( 21 | rebuildData: Record, 22 | key: string, 23 | value: Record, 24 | ) { 25 | const tmp = rebuildData[key] ? rebuildData[key] : (rebuildData[key] = {}) 26 | if (Object.prototype.toString.call(value).slice(8, -1) === 'Object') { 27 | const nextKey = Object.keys(value)[0] 28 | dfs2(tmp, nextKey, value[nextKey]) 29 | } else { 30 | rebuildData[key] = value 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /packages/prettier-plugin-eshtml/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "prettier-plugin-eshtml", 3 | "version": "0.0.1-beta.1", 4 | "license": "MIT", 5 | "type": "module", 6 | "main": "./dist/index.cjs", 7 | "types": "./dist/index.d.ts", 8 | "exports": { 9 | ".": { 10 | "types": "./dist/index.d.ts", 11 | "default": "./dist/index.cjs" 12 | } 13 | }, 14 | "files": [ 15 | "dist" 16 | ], 17 | "scripts": { 18 | "build": "pkgroll", 19 | "start": "tsx src/index.ts", 20 | "test": "vitest", 21 | "test:run": "vitest run", 22 | "typecheck": "tsc --noEmit", 23 | "watch": "pkgroll --watch", 24 | "prepublishOnly": "pnpm run build" 25 | }, 26 | "devDependencies": { 27 | "@es-js/core": "workspace:*", 28 | "@es-js/eshtml": "workspace:*", 29 | "@prettier/sync": "^0.5.2", 30 | "@types/node": "^20.14.12", 31 | "pkgroll": "^2.4.1", 32 | "prettier": "^3.3.3", 33 | "tsx": "^4.16.2", 34 | "typescript": "^5.5.4", 35 | "vite": "^5.3.4", 36 | "vitest": "^2.0.4" 37 | }, 38 | "peerDependencies": { 39 | "prettier": "^3.0.0" 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuItem.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 29 | -------------------------------------------------------------------------------- /packages/eshtml/src/utils/generateAttributeUsages.ts: -------------------------------------------------------------------------------- 1 | import fs from 'fs' 2 | import attributes from './attributes.json' with { type: 'json' } 3 | 4 | export function generateAttributeUsages() { 5 | const output: any = [] 6 | 7 | for (const { Attribute, Elements } of attributes) { 8 | const elements = Elements.split(',') 9 | .map((el) => el.trim()) 10 | .map((el) => el.replace(/<|>/g, '')) // Remove < and > from the element name 11 | .map((el) => { 12 | if (el === 'Global attribute') { 13 | return '__GLOBAL__' 14 | } 15 | 16 | return el 17 | }) 18 | 19 | output[Attribute] = elements 20 | } 21 | 22 | const fileContent = `export const attributeUsages = { 23 | ${Object.entries(output) 24 | .map(([key, value]) => { 25 | return `'${key}': ${JSON.stringify(value)},` 26 | }) 27 | .join('\n')} 28 | } 29 | ` 30 | 31 | fs.writeFileSync('src/utils/attributeUsages.ts', fileContent) 32 | 33 | return fs.readFileSync('src/utils/attributeUsages.ts', 'utf-8') 34 | } 35 | -------------------------------------------------------------------------------- /packages/core/src/plugins/promesa/index.ts: -------------------------------------------------------------------------------- 1 | import { 2 | replaceExpressionMethods, 3 | replaceObjects, 4 | replaceObjectStaticMethods, 5 | } from '../utils' 6 | 7 | export const report = () => 'Converts Promesa methods to JavaScript' 8 | 9 | export const methods = new Map([ 10 | ['capturar', 'catch'], 11 | ['finalmente', 'finally'], 12 | ['luego', 'then'], 13 | ]) 14 | 15 | export const staticMethods = new Map([ 16 | ['todos', 'all'], 17 | ['todosTerminados', 'allSettled'], 18 | ['cualquiera', 'any'], 19 | ['carrera', 'race'], 20 | ['rechaza', 'reject'], 21 | ['resuelve', 'resolve'], 22 | ]) 23 | 24 | export const objects = new Map([['Promesa', 'Promise']]) 25 | 26 | export function replace() { 27 | return { 28 | ...replaceObjectStaticMethods({ 29 | from: 'Promesa', 30 | to: 'Promise', 31 | methods: staticMethods, 32 | }), 33 | ...replaceExpressionMethods({ 34 | methods, 35 | }), 36 | ...replaceObjects({ 37 | objects, 38 | }), 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /packages/vite-plugin-esjs/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/vite-plugin-esjs", 3 | "version": "0.1.0-beta.2", 4 | "description": "Vite Plugin para EsJS", 5 | "scripts": { 6 | "build": "unbuild", 7 | "prepublishOnly": "pnpm run build" 8 | }, 9 | "repository": { 10 | "type": "git", 11 | "url": "git+https://github.com/es-js/esjs.git", 12 | "directory": "packages/vite-plugin-esjs" 13 | }, 14 | "author": "Enzo Notario ", 15 | "license": "MIT", 16 | "keywords": [ 17 | "esjs", 18 | "vite", 19 | "plugin" 20 | ], 21 | "dependencies": { 22 | "vite": "^4.5.0" 23 | }, 24 | "devDependencies": { 25 | "@es-js/core": "workspace:*", 26 | "@types/node": "^20.9.0", 27 | "typescript": "^5.2.2", 28 | "unbuild": "^2.0.0" 29 | }, 30 | "type": "module", 31 | "exports": { 32 | ".": { 33 | "import": "./dist/index.mjs", 34 | "require": "./dist/index.cjs" 35 | } 36 | }, 37 | "main": "./dist/index.cjs", 38 | "types": "./dist/index.d.ts", 39 | "files": [ 40 | "dist" 41 | ] 42 | } 43 | -------------------------------------------------------------------------------- /packages/cli/README.md: -------------------------------------------------------------------------------- 1 | # EsJS CLI 2 | 3 | CLI para el lenguaje de programación **EsJS**. 4 | 5 | ## Instalación 6 | 7 | Para instalar el CLI de **EsJS** ejecuta el siguiente comando: 8 | 9 | ``` 10 | npm i -g es.js 11 | ``` 12 | 13 | De esta forma tendrás acceso a los comandos de **EsJS** desde cualquier lugar de tu sistema ejecutando: 14 | 15 | ``` 16 | esjs 17 | ``` 18 | 19 | 20 | ## Comandos 21 | 22 | El CLI de **EsJS** cuenta con los siguientes comandos: 23 | 24 | | Command | Action | 25 | |-----------------|----------------------------------------------------------------| 26 | | `esjs ayuda` | Muestra la ayuda del CLI. | 27 | | `esjs repl` | Inicia el REPL de **EsJS**. | 28 | | `esjs ejecutar` | Ejecuta un archivo (script) de **EsJS**. | 29 | | `esjs compilar` | Compila un archivo o directorio de **EsJS** a **JavaScript**. | 30 | | `esjs crear` | Crea un nuevo proyecto de **EsJS**. | 31 | -------------------------------------------------------------------------------- /packages/esjs-loader/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "esjs-loader", 3 | "version": "0.0.1", 4 | "description": "Módulo EsJS para Node.js", 5 | "scripts": { 6 | "build": "unbuild", 7 | "prepublishOnly": "pnpm run build" 8 | }, 9 | "repository": { 10 | "type": "git", 11 | "url": "git+https://github.com/es-js/esjs.git", 12 | "directory": "packages/esjs-loader" 13 | }, 14 | "author": "Enzo Notario ", 15 | "license": "MIT", 16 | "keywords": [ 17 | "esjs", 18 | "loader", 19 | "node" 20 | ], 21 | "dependencies": { 22 | "vite": "^4.5.0" 23 | }, 24 | "devDependencies": { 25 | "@es-js/core": "workspace:*", 26 | "@types/node": "^20.9.0", 27 | "typescript": "^5.2.2", 28 | "unbuild": "^2.0.0", 29 | "vitest": "^2.1.5" 30 | }, 31 | "type": "module", 32 | "exports": { 33 | ".": { 34 | "import": "./dist/index.mjs", 35 | "require": "./dist/index.cjs" 36 | } 37 | }, 38 | "main": "./dist/index.cjs", 39 | "types": "./dist/index.d.ts", 40 | "files": [ 41 | "dist" 42 | ] 43 | } 44 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/DropdownMenuSubTrigger.vue: -------------------------------------------------------------------------------- 1 | 21 | 22 | 34 | -------------------------------------------------------------------------------- /packages/language-tools/assets/esvue-language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | "comments": { 3 | "lineComment": "//", 4 | "blockComment": [ "/*", "*/" ] 5 | }, 6 | "brackets": [ 7 | ["{", "}"], 8 | ["[", "]"], 9 | ["(", ")"] 10 | ], 11 | "autoClosingPairs": [ 12 | { "open": "{", "close": "}" }, 13 | { "open": "[", "close": "]" }, 14 | { "open": "(", "close": ")" }, 15 | { "open": "\"", "close": "\"", "notIn": ["string"] }, 16 | { "open": "'", "close": "'", "notIn": ["string", "comment"] }, 17 | { "open": "`", "close": "`", "notIn": ["string", "comment"] }, 18 | { "open": "/**", "close": " */", "notIn": ["string"] } 19 | ], 20 | "surroundingPairs": [ 21 | ["{", "}"], 22 | ["[", "]"], 23 | ["(", ")"], 24 | ["\"", "\""], 25 | ["'", "'"], 26 | ["`", "`"] 27 | ], 28 | "folding": { 29 | "markers": { 30 | "start": "^<(template|style|script)[^>]*>", 31 | "end": "^" 32 | } 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /packages/prettier-plugin-esvue/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "prettier-plugin-esvue", 3 | "version": "0.0.1-beta.1", 4 | "license": "MIT", 5 | "type": "module", 6 | "main": "./dist/index.cjs", 7 | "types": "./dist/index.d.ts", 8 | "exports": { 9 | ".": { 10 | "types": "./dist/index.d.ts", 11 | "default": "./dist/index.cjs" 12 | } 13 | }, 14 | "files": [ 15 | "dist" 16 | ], 17 | "scripts": { 18 | "build": "pkgroll", 19 | "start": "tsx src/index.ts", 20 | "test": "vitest", 21 | "test:run": "vitest run", 22 | "typecheck": "tsc --noEmit", 23 | "watch": "pkgroll --watch", 24 | "prepublishOnly": "pnpm run build" 25 | }, 26 | "devDependencies": { 27 | "@es-js/core": "workspace:*", 28 | "@es-js/eshtml": "workspace:*", 29 | "@es-js/esvue": "workspace:*", 30 | "@prettier/sync": "^0.5.2", 31 | "@types/node": "^20.14.12", 32 | "pkgroll": "^2.4.1", 33 | "prettier": "^3.3.3", 34 | "tsx": "^4.16.2", 35 | "typescript": "^5.5.4", 36 | "vite": "^5.3.4", 37 | "vitest": "^2.0.4" 38 | }, 39 | "peerDependencies": { 40 | "prettier": "^3.0.0" 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /packages/sandbox/src/compiler/orchestrator.ts: -------------------------------------------------------------------------------- 1 | export class OrchestratorFile { 2 | filename: string 3 | template: string 4 | script: string 5 | style: string 6 | 7 | compiled = { 8 | js: '', 9 | css: '', 10 | ssr: '', 11 | } 12 | 13 | constructor( 14 | filename: string, 15 | template: string | undefined, 16 | script: string | undefined, 17 | style?: string, 18 | ) { 19 | this.filename = filename 20 | this.template = template || '' 21 | this.script = script || '' 22 | this.style = style || '' 23 | } 24 | 25 | get code() { 26 | return this.script 27 | } 28 | } 29 | 30 | export interface OrchestratorFiles { 31 | [key: string]: OrchestratorFile 32 | } 33 | 34 | export interface Orchestrator { 35 | files: OrchestratorFiles 36 | errors: (string | Error)[] 37 | runtimeErrors: (string | Error)[] 38 | } 39 | 40 | export const MAIN_FILE = 'codigo.esjs' 41 | export const MAIN_TESTS_FILE = 'pruebas.esjs' 42 | 43 | export const orchestrator: Orchestrator = { 44 | files: {}, 45 | errors: [], 46 | runtimeErrors: [], 47 | } 48 | -------------------------------------------------------------------------------- /packages/esvue/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/esvue", 3 | "version": "0.0.1-beta.2", 4 | "description": "EsVue: Vue en Español", 5 | "scripts": { 6 | "build": "unbuild", 7 | "prepublishOnly": "npm run build" 8 | }, 9 | "repository": { 10 | "type": "git", 11 | "url": "git+https://github.com/es-js/esjs.git", 12 | "directory": "packages/esvue" 13 | }, 14 | "author": "Enzo Notario ", 15 | "license": "MIT", 16 | "keywords": [ 17 | "esjs", 18 | "esvue" 19 | ], 20 | "devDependencies": { 21 | "@es-js/core": "workspace:*", 22 | "@es-js/eshtml": "workspace:*", 23 | "@types/hast": "^3.0.4", 24 | "@types/node": "^20.14.9", 25 | "typescript": "^5.5.2", 26 | "unbuild": "^2.0.0", 27 | "vite": "^5.3.2", 28 | "vitest": "^2.1.5" 29 | }, 30 | "type": "module", 31 | "exports": { 32 | ".": { 33 | "import": "./dist/index.mjs", 34 | "require": "./dist/index.cjs" 35 | } 36 | }, 37 | "main": "./dist/index.cjs", 38 | "types": "./dist/index.d.ts", 39 | "files": [ 40 | "dist" 41 | ] 42 | } 43 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/mate.esjs: -------------------------------------------------------------------------------- 1 | const x = 2 2 | mut y = 3 3 | 4 | Mate.absoluto(x) 5 | Mate.arcocoseno(x) 6 | Mate.arcocosenoHiperbolico(x) 7 | Mate.arcoseno(x) 8 | Mate.arcosenoHiperbolico(x) 9 | Mate.arcotangente(x) 10 | Mate.arcotangente2(x, y) 11 | Mate.arcotangenteHiperbolica(x) 12 | Mate.raizCubica(x) 13 | Mate.redondearHaciaArriba(x) 14 | Mate.cerosALaIzquierdaEn32Bits(x) 15 | Mate.coseno(x) 16 | Mate.cosenoHiperbolico(x) 17 | Mate.exponencial(x) 18 | Mate.exponencialMenos1(x) 19 | Mate.redondearHaciaAbajo(x) 20 | Mate.redondearAComaFlotante(x) 21 | Mate.hipotenusa(x, y) 22 | Mate.multiplicacionEntera(x, y) 23 | Mate.logaritmo(x) 24 | Mate.logaritmoBase10(x) 25 | Mate.logaritmoDe1Mas(x) 26 | Mate.logaritmoBase2(x) 27 | Mate.maximo(x, y) 28 | Mate.minimo(x, y) 29 | Mate.potencia(x, y) 30 | Mate.aleatorio() 31 | Mate.redondear(x) 32 | Mate.signo(x) 33 | Mate.seno(x) 34 | Mate.senoHiperbolico(x) 35 | 36 | const a = Mate.PI 37 | const b = Mate.E 38 | const c = Mate.LN2 39 | const d = Mate.LN10 40 | const e = Mate.LOG2E 41 | const f = Mate.LOG10E 42 | const g = Mate.RAIZ1_2 43 | const h = Mate.RAIZ2 44 | -------------------------------------------------------------------------------- /packages/core/src/plugins/enterogrande/index.ts: -------------------------------------------------------------------------------- 1 | import { 2 | replaceExpressionMethods, 3 | replaceInstanceof, 4 | replaceObjects, 5 | replaceObjectStaticMethods, 6 | } from '../utils' 7 | 8 | export const report = () => 'Converts EnteroGrande methods to JavaScript' 9 | 10 | export const staticMethods = new Map([ 11 | ['comoEntero', 'asIntN'], 12 | ['comoEnteroSinSigno', 'asUintN'], 13 | ]) 14 | 15 | export const methods = new Map([ 16 | ['aCadenaLocalizada', 'toLocaleString'], 17 | ['aCadena', 'toString'], 18 | ['valorDe', 'valueOf'], 19 | ]) 20 | 21 | export const objects = new Map([['EnteroGrande', 'BigInt']]) 22 | 23 | export function replace() { 24 | return { 25 | ...replaceObjectStaticMethods({ 26 | from: 'EnteroGrande', 27 | to: 'BigInt', 28 | methods: staticMethods, 29 | }), 30 | ...replaceExpressionMethods({ 31 | methods, 32 | }), 33 | ...replaceInstanceof({ 34 | from: 'EnteroGrande', 35 | to: 'BigInt', 36 | }), 37 | ...replaceObjects({ 38 | objects, 39 | }), 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/tabs/TabsTrigger.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 28 | -------------------------------------------------------------------------------- /apps/playground/app/components/AppTabButton.vue: -------------------------------------------------------------------------------- 1 | 18 | 19 | 40 | -------------------------------------------------------------------------------- /packages/sandbox/src/transformers/exportFunctions.transformer.ts: -------------------------------------------------------------------------------- 1 | import escodegen from 'escodegen' 2 | import * as espree from 'espree' 3 | import { Transformer } from './index' 4 | 5 | /** 6 | * Agrega `export` a las funciones declaradas. 7 | */ 8 | export class ExportFunctionsTransformer implements Transformer { 9 | transform(code: string) { 10 | const ast = espree.parse(code, { 11 | range: true, 12 | ecmaVersion: 'latest', 13 | jsx: false, 14 | loc: true, 15 | tolerant: true, 16 | sourceType: 'module', 17 | }) 18 | 19 | ast.body.forEach((node: any) => { 20 | if (node.type === 'FunctionDeclaration') { 21 | // Crear el nodo de exportación 22 | const exportNode = { 23 | type: 'ExportNamedDeclaration', 24 | declaration: node, 25 | source: null, 26 | specifiers: [], 27 | } 28 | 29 | // Reemplazar el nodo de la función con el nodo de exportación 30 | const index = ast.body.indexOf(node) 31 | ast.body[index] = exportNode 32 | } 33 | }) 34 | 35 | return escodegen.generate(ast) 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /packages/cli/commands/repl.mjs: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | import { compile } from '@es-js/core' 4 | import { defineCommand } from 'citty' 5 | import repl from 'node:repl' 6 | 7 | export default defineCommand({ 8 | meta: { 9 | name: 'repl', 10 | description: 'REPL para el lenguaje de programación EsJS.', 11 | }, 12 | 13 | async run({ args }) { 14 | const replServer = repl.start({ 15 | prompt: '> ', 16 | eval: (cmd, context, filename, callback) => { 17 | let error 18 | let result 19 | try { 20 | const js = compile(cmd, { 21 | compiler: 'essucrase', 22 | }) 23 | 24 | // biome-ignore lint/security/noGlobalEval: This is a CLI tool. 25 | result = eval(js) 26 | } catch (exception) { 27 | error = exception?.message ? exception.message : exception 28 | } 29 | 30 | callback(error, result) 31 | }, 32 | ignoreUndefined: true, 33 | }) 34 | 35 | // Setup history. 36 | const NODE_REPL_HISTORY = process.env.NODE_REPL_HISTORY 37 | replServer.setupHistory(NODE_REPL_HISTORY, () => {}) 38 | }, 39 | }) 40 | -------------------------------------------------------------------------------- /packages/cli/pnpm-lock.yaml: -------------------------------------------------------------------------------- 1 | lockfileVersion: '9.0' 2 | 3 | settings: 4 | autoInstallPeers: true 5 | excludeLinksFromLockfile: false 6 | 7 | importers: 8 | 9 | .: 10 | dependencies: 11 | '@es-js/core': 12 | specifier: latest 13 | version: 0.1.0-alpha.12 14 | citty: 15 | specifier: ^0.1.4 16 | version: 0.1.6 17 | consola: 18 | specifier: ^3.2.3 19 | version: 3.2.3 20 | 21 | packages: 22 | 23 | '@es-js/core@0.1.0-alpha.12': 24 | resolution: {integrity: sha512-UB+baLhIasXVjRiNHfn3xvzWcQbNK6uVywIyYasP1dsPRs9hKz4TM7BiVSfOKtqox612Si73DT/xniw98TZe/Q==} 25 | 26 | citty@0.1.6: 27 | resolution: {integrity: sha512-tskPPKEs8D2KPafUypv2gxwJP8h/OaJmC82QQGGDQcHvXX43xF2VDACcJVmZ0EuSxkpO9Kc4MlrA3q0+FG58AQ==} 28 | 29 | consola@3.2.3: 30 | resolution: {integrity: sha512-I5qxpzLv+sJhTVEoLYNcTW+bThDCPsit0vLNKShZx6rLtpilNpmmeTPaeqJb9ZE9dV3DGaeby6Vuhrw38WjeyQ==} 31 | engines: {node: ^14.18.0 || >=16.10.0} 32 | 33 | snapshots: 34 | 35 | '@es-js/core@0.1.0-alpha.12': {} 36 | 37 | citty@0.1.6: 38 | dependencies: 39 | consola: 3.2.3 40 | 41 | consola@3.2.3: {} 42 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022-present Enzo Notario 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /packages/sandbox/src/utils/generateImportFunctions.ts: -------------------------------------------------------------------------------- 1 | import * as espree from 'espree' 2 | 3 | /** 4 | * Genera los imports a partir de las funciones exportadas. 5 | * 6 | * Por ejemplo, para el módulo `./foo`, y para el código: 7 | * 8 | * ```js 9 | * export function foo() { 10 | * return 'foo'; 11 | * } 12 | * ``` 13 | * 14 | * Genera: 15 | * 16 | * ```js 17 | * import { foo } from './foo' 18 | * ``` 19 | */ 20 | export function generateImportFunctions({ 21 | code, 22 | modulePath, 23 | }: { 24 | code: string 25 | modulePath: string 26 | }) { 27 | const ast = espree.parse(code, { 28 | range: true, 29 | ecmaVersion: 'latest', 30 | jsx: false, 31 | loc: true, 32 | tolerant: true, 33 | sourceType: 'module', 34 | }) 35 | 36 | const namedExports = ast.body.filter( 37 | (node: any) => 38 | node.type === 'ExportNamedDeclaration' && 39 | node.declaration?.type === 'FunctionDeclaration', 40 | ) 41 | 42 | const imports = namedExports.map( 43 | (node: any) => 44 | `import { ${node.declaration?.id?.name} } from '${modulePath}'`, 45 | ) 46 | 47 | return imports.join('\n') 48 | } 49 | -------------------------------------------------------------------------------- /packages/prueba/test/async-prueba.test.ts: -------------------------------------------------------------------------------- 1 | import { describe, expect, it } from 'vitest' 2 | import { 3 | afirmar, 4 | afirmarIguales, 5 | afirmarSimilares, 6 | pruebasAsincronas, 7 | } from '../lib/main' 8 | 9 | describe('pruebas', () => { 10 | it('can run async pruebas', async () => { 11 | await expect( 12 | await pruebasAsincronas({ 13 | async basica() { 14 | afirmar(true) 15 | afirmarSimilares(1, '1') 16 | afirmarIguales(2, 2) 17 | }, 18 | }), 19 | ).toStrictEqual({ 20 | numeroPruebas: 1, 21 | exitosas: 1, 22 | fallidas: 0, 23 | sinAfirmaciones: 0, 24 | }) 25 | }) 26 | 27 | it('throws when async pruebas fails', async () => { 28 | await expect( 29 | async () => 30 | await pruebasAsincronas({ 31 | 'falla afirmar': async function () { 32 | afirmar(await test(false)) 33 | }, 34 | }), 35 | ).rejects.toThrowError() 36 | }) 37 | }) 38 | 39 | async function test(value) { 40 | return new Promise((resolve) => { 41 | setTimeout(() => { 42 | resolve(value) 43 | }, 1000) 44 | }) 45 | } 46 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/separator/Separator.vue: -------------------------------------------------------------------------------- 1 | 16 | 17 | 36 | -------------------------------------------------------------------------------- /packages/core/src/utils.ts: -------------------------------------------------------------------------------- 1 | const IMPORTS_REGEX = 2 | /import(?:["'\s]*([\w*{}\n\r\t, ]+)from\s*)?["'\s].*([@\w/_-]+)["'\s].*/g 3 | 4 | export interface SplitCodeImports { 5 | codeWithoutImports: string 6 | imports: string 7 | hasImports: boolean 8 | } 9 | 10 | export function splitCodeImports(code: string): SplitCodeImports { 11 | const codeWithoutImports: string = replaceImportsWith(code, '') 12 | const imports: string = extractImportsFrom(code) ?? '' 13 | const hasImports: boolean = Boolean(imports) 14 | 15 | return { 16 | codeWithoutImports, 17 | imports, 18 | hasImports, 19 | } 20 | } 21 | 22 | function replaceImportsWith(code: string, replacement: string): string { 23 | return code.replace(IMPORTS_REGEX, replacement).trim() 24 | } 25 | 26 | function extractImportsFrom(code: string): string | null { 27 | return code.match(IMPORTS_REGEX)?.join('\n') ?? null 28 | } 29 | 30 | export function invertMap(map: Map): Map { 31 | const invertedMap = new Map() 32 | for (const [key, value] of map.entries()) { 33 | invertedMap.set(value, key) 34 | } 35 | 36 | return invertedMap 37 | } 38 | -------------------------------------------------------------------------------- /packages/esbabel/test/fixtures/esjs/fecha.js: -------------------------------------------------------------------------------- 1 | const fecha = Date() 2 | 3 | fecha.getDate() 4 | fecha.getDay() 5 | fecha.getFullYear() 6 | fecha.getHours() 7 | fecha.getMilliseconds() 8 | fecha.getMinutes() 9 | fecha.getMonth() 10 | fecha.getSeconds() 11 | fecha.getTime() 12 | fecha.getTimezoneOffset() 13 | fecha.getUTCDate() 14 | fecha.getUTCDay() 15 | fecha.getUTCFullYear() 16 | fecha.getUTCHours() 17 | fecha.getUTCMilliseconds() 18 | fecha.getUTCMinutes() 19 | fecha.getUTCMonth() 20 | fecha.getUTCSeconds() 21 | fecha.now() 22 | fecha.parse() 23 | fecha.setDate() 24 | fecha.setFullYear() 25 | fecha.setHours() 26 | fecha.setMilliseconds() 27 | fecha.setMinutes() 28 | fecha.setMonth() 29 | fecha.setSeconds() 30 | fecha.setTime() 31 | fecha.setUTCDate() 32 | fecha.setUTCFullYear() 33 | fecha.setUTCHours() 34 | fecha.setUTCMilliseconds() 35 | fecha.setUTCMinutes() 36 | fecha.setUTCMonth() 37 | fecha.setUTCSeconds() 38 | fecha.toDateString() 39 | fecha.toISOString() 40 | fecha.toJSON() 41 | fecha.toLocaleDateString() 42 | fecha.toLocaleString() 43 | fecha.toLocaleTimeString() 44 | fecha.toString() 45 | fecha.toTimeString() 46 | fecha.toUTCString() 47 | fecha.UTC() 48 | fecha.valueOf() 49 | -------------------------------------------------------------------------------- /packages/cli/commands/crear.mjs: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | import { execSync as exec } from 'node:child_process' 4 | import { defineCommand } from 'citty' 5 | import { consola } from 'consola' 6 | 7 | export default defineCommand({ 8 | meta: { 9 | name: 'crear', 10 | description: 'Crea un nuevo proyecto EsJS.', 11 | }, 12 | 13 | args: { 14 | tipo: { 15 | type: 'positional', 16 | description: 'Tipo de proyecto a crear', 17 | required: false, 18 | }, 19 | nombre: { 20 | type: 'positional', 21 | description: 'Nombre del proyecto', 22 | required: false, 23 | }, 24 | directorio: { 25 | type: 'string', 26 | description: 'Directorio donde se creará el proyecto', 27 | required: false, 28 | }, 29 | }, 30 | 31 | async run({ args }) { 32 | const tipo = args.tipo || '' 33 | const nombre = args.nombre || '' 34 | const directorio = args.directorio || '' 35 | 36 | const comando = `npx create-esjs@latest ${tipo} ${nombre} ${directorio}` 37 | 38 | try { 39 | exec(comando, { stdio: 'inherit' }) 40 | } catch (e) { 41 | consola.error(e) 42 | } 43 | }, 44 | }) 45 | -------------------------------------------------------------------------------- /packages/core/src/index.ts: -------------------------------------------------------------------------------- 1 | import putout from '@putout/bundle' 2 | import { EsbabelCompiler } from './compiler/esbabel.compiler' 3 | import { EssucraseCompiler } from './compiler/essucrase.compiler' 4 | 5 | export type AvailableLanguages = 'esjs' | 'js' 6 | 7 | export interface Compiler { 8 | compile(code: string, options: CompileOptions): string 9 | } 10 | 11 | export interface CompileOptions { 12 | from?: AvailableLanguages 13 | to?: AvailableLanguages 14 | compiler?: 'essucrase' | 'esbabel' 15 | } 16 | 17 | export function compile( 18 | code: string, 19 | options: CompileOptions = { 20 | from: 'esjs', 21 | to: 'js', 22 | compiler: 'essucrase', 23 | } as CompileOptions, 24 | ) { 25 | if (!options.from) { 26 | options.from = 'esjs' 27 | } 28 | 29 | if (!options.to) { 30 | options.to = 'js' 31 | } 32 | 33 | if (!options.compiler) { 34 | options.compiler = 'essucrase' 35 | } 36 | 37 | const compiler: Compiler = 38 | options?.compiler === 'essucrase' 39 | ? new EssucraseCompiler(putout) 40 | : new EsbabelCompiler() 41 | 42 | return compiler.compile(code, options) 43 | } 44 | 45 | export { compile as transpile } 46 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/fecha.js: -------------------------------------------------------------------------------- 1 | const fecha = new Date() 2 | 3 | fecha.getDate() 4 | fecha.getDay() 5 | fecha.getFullYear() 6 | fecha.getHours() 7 | fecha.getMilliseconds() 8 | fecha.getMinutes() 9 | fecha.getMonth() 10 | fecha.getSeconds() 11 | fecha.getTime() 12 | fecha.getTimezoneOffset() 13 | fecha.getUTCDate() 14 | fecha.getUTCDay() 15 | fecha.getUTCFullYear() 16 | fecha.getUTCHours() 17 | fecha.getUTCMilliseconds() 18 | fecha.getUTCMinutes() 19 | fecha.getUTCMonth() 20 | fecha.getUTCSeconds() 21 | fecha.setDate() 22 | fecha.setFullYear() 23 | fecha.setHours() 24 | fecha.setMilliseconds() 25 | fecha.setMinutes() 26 | fecha.setMonth() 27 | fecha.setSeconds() 28 | fecha.setTime() 29 | fecha.setUTCDate() 30 | fecha.setUTCFullYear() 31 | fecha.setUTCHours() 32 | fecha.setUTCMilliseconds() 33 | fecha.setUTCMinutes() 34 | fecha.setUTCMonth() 35 | fecha.setUTCSeconds() 36 | fecha.toDateString() 37 | fecha.toISOString() 38 | fecha.toJSON() 39 | fecha.toLocaleDateString() 40 | fecha.toLocaleString() 41 | fecha.toLocaleTimeString() 42 | fecha.toString() 43 | fecha.toTimeString() 44 | fecha.toUTCString() 45 | fecha.valueOf() 46 | 47 | Date.now() 48 | Date.parse() 49 | Date.UTC() 50 | -------------------------------------------------------------------------------- /apps/playground/app/components/AppMenu.vue: -------------------------------------------------------------------------------- 1 | 14 | 15 | 42 | -------------------------------------------------------------------------------- /apps/playground/app/components/ui/dropdown-menu/index.ts: -------------------------------------------------------------------------------- 1 | export { DropdownMenuPortal } from 'radix-vue' 2 | 3 | export { default as DropdownMenu } from './DropdownMenu.vue' 4 | export { default as DropdownMenuTrigger } from './DropdownMenuTrigger.vue' 5 | export { default as DropdownMenuContent } from './DropdownMenuContent.vue' 6 | export { default as DropdownMenuGroup } from './DropdownMenuGroup.vue' 7 | export { default as DropdownMenuRadioGroup } from './DropdownMenuRadioGroup.vue' 8 | export { default as DropdownMenuItem } from './DropdownMenuItem.vue' 9 | export { default as DropdownMenuCheckboxItem } from './DropdownMenuCheckboxItem.vue' 10 | export { default as DropdownMenuRadioItem } from './DropdownMenuRadioItem.vue' 11 | export { default as DropdownMenuShortcut } from './DropdownMenuShortcut.vue' 12 | export { default as DropdownMenuSeparator } from './DropdownMenuSeparator.vue' 13 | export { default as DropdownMenuLabel } from './DropdownMenuLabel.vue' 14 | export { default as DropdownMenuSub } from './DropdownMenuSub.vue' 15 | export { default as DropdownMenuSubTrigger } from './DropdownMenuSubTrigger.vue' 16 | export { default as DropdownMenuSubContent } from './DropdownMenuSubContent.vue' 17 | -------------------------------------------------------------------------------- /packages/core/src/plugins/consola/index.ts: -------------------------------------------------------------------------------- 1 | import { replaceObjectStaticMethods } from '../utils' 2 | 3 | export const report = () => 'Converts consola to console' 4 | 5 | export const methods = new Map([ 6 | ['afirmar', 'assert'], 7 | ['limpiar', 'clear'], 8 | ['contar', 'count'], 9 | ['reiniciarContador', 'countReset'], 10 | ['depurar', 'debug'], 11 | ['listar', 'dir'], 12 | ['listarXml', 'dirxml'], 13 | ['error', 'error'], 14 | ['agrupar', 'group'], 15 | ['agruparColapsado', 'groupCollapsed'], 16 | ['finalizarAgrupacion', 'groupEnd'], 17 | ['info', 'info'], 18 | ['escribir', 'log'], 19 | ['perfil', 'profile'], 20 | ['finalizarPerfil', 'profileEnd'], 21 | ['tabla', 'table'], 22 | ['tiempo', 'time'], 23 | ['finalizarTiempo', 'timeEnd'], 24 | ['registrarTiempo', 'timeLog'], 25 | ['marcaDeTiempo', 'timeStamp'], 26 | ['rastrear', 'trace'], 27 | ['advertencia', 'warn'], 28 | ]) 29 | 30 | export const objects = new Map([['consola', 'console']]) 31 | 32 | export function replace() { 33 | return { 34 | ...replaceObjectStaticMethods({ 35 | from: 'consola', 36 | to: 'console', 37 | methods, 38 | }), 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /packages/vscode-esjs/LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022-present Enzo Notario 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /apps/playground/content/intermedios/1.modulos.md: -------------------------------------------------------------------------------- 1 | # Módulos 2 | 3 | Los módulos son una forma de organizar el código en archivos separados. Cada módulo tiene su propio ámbito, por lo que no hay que preocuparse de que las variables o funciones de un módulo interfieran con las de otro. 4 | 5 | ## Importar módulos 6 | 7 | Para importar un módulo se utiliza la palabra clave `importar` seguida del nombre del módulo y el nombre de la variable que se utilizará para acceder a él. 8 | 9 | Por ejemplo, EsJS dispone de un módulo llamado `Terminal` que permite escribir en la pantalla. Para utilizarlo, se debe importar el módulo y luego llamar a la función `escribir`. 10 | 11 | ::content-code 12 | ```esjs 13 | importar { Terminal } desde "@es-js/terminal" 14 | 15 | Terminal.escribir("Hola Mundo"); 16 | ``` 17 | :: 18 | 19 | ## Exportar módulos 20 | 21 | Para exportar un módulo se utiliza la palabra clave `exportar` seguida del nombre del módulo y el nombre de la variable que se utilizará para acceder a él. 22 | 23 | ::content-code 24 | ```esjs 25 | exportar const PI = 3.14159265359; 26 | 27 | exportar funcion areaCirculo(radio) { 28 | retornar PI * radio * radio; 29 | } 30 | 31 | consola.escribir(areaCirculo(5)); 32 | ``` 33 | :: 34 | -------------------------------------------------------------------------------- /packages/core/test/fixtures/extras/navegador.js: -------------------------------------------------------------------------------- 1 | navigator.credentials; 2 | navigator.deviceMemory; 3 | navigator.hardwareConcurrency; 4 | navigator.language; 5 | navigator.languages; 6 | navigator.maxTouchPoints; 7 | navigator.onLine; 8 | navigator.pdfViewerEnabled; 9 | navigator.userAgent; 10 | navigator.webdriver; 11 | navigator.connection; 12 | navigator.cookieEnabled; 13 | navigator.geolocation; 14 | navigator.keyboard; 15 | navigator.locks; 16 | navigator.mediaCapabilities; 17 | navigator.mediaDevices; 18 | navigator.mediaSession; 19 | navigator.permissions; 20 | navigator.presentation; 21 | navigator.serviceWorker; 22 | navigator.storage; 23 | navigator.userActivation; 24 | navigator.userAgentData; 25 | navigator.windowControlsOverlay; 26 | navigator.hid; 27 | navigator.serial; 28 | navigator.xr; 29 | navigator.bluetooth; 30 | navigator.clipboard; 31 | navigator.canShare() 32 | navigator.clearAppBadge() 33 | navigator.getBattery() 34 | navigator.registerProtocolHandler() 35 | navigator.requestMediaKeySystemAccess() 36 | navigator.requestMIDIAccess() 37 | navigator.sendBeacon() 38 | navigator.setAppBadge() 39 | navigator.share() 40 | navigator.vibrate() 41 | navigator.getNotifications() 42 | -------------------------------------------------------------------------------- /packages/vite-plugin-esvue/test/vite-plugin-esvue.test.ts: -------------------------------------------------------------------------------- 1 | // import vite from 'vite' 2 | import path from 'path' 3 | import url from 'url' 4 | import { beforeAll, it } from 'vitest' 5 | // import EsVuePlugin from "../dist/index.mjs"; 6 | 7 | // declare global { 8 | // namespace NodeJS { 9 | // interface Global { 10 | // } 11 | // } 12 | // } 13 | 14 | const __dirname = path.dirname(url.fileURLToPath(import.meta.url)) 15 | 16 | let vite: typeof import('vite') 17 | let vitePluginVue: typeof import('@vitejs/plugin-vue') 18 | let EsVuePlugin: typeof import('../src/index') 19 | 20 | beforeAll(async () => { 21 | vite = await import('vite') 22 | vitePluginVue = await import('@vitejs/plugin-vue') 23 | EsVuePlugin = await import('../src/index') 24 | }) 25 | 26 | it('build', async () => { 27 | await vite.build({ 28 | root: path.join(__dirname, 'fixtures', 'basic'), 29 | configFile: false, 30 | logLevel: 'error', 31 | plugins: [ 32 | EsVuePlugin.default(), 33 | vitePluginVue.default({ 34 | include: [/\.vue$/, /\.esvue$/], 35 | }), 36 | ], 37 | build: { 38 | write: true, 39 | minify: false, 40 | }, 41 | define: { 42 | global: 'window', 43 | }, 44 | }) 45 | }) 46 | -------------------------------------------------------------------------------- /packages/vscode-esjs/scripts/generate-grammars-configurations.ts: -------------------------------------------------------------------------------- 1 | const { writeFileSync } = require('node:fs') 2 | const axios = require('axios') 3 | 4 | const BASE_URL = 'https://unpkg.com/@es-js/language-tools@latest/dist/' 5 | 6 | const grammars = ['esjs.tmLanguage.json', 'esvue.tmLanguage.json'] 7 | 8 | const configurations = [ 9 | 'esjs-language-configuration.json', 10 | 'esvue-language-configuration.json', 11 | ] 12 | 13 | const snippets = ['esjs.code-snippets.json'] 14 | 15 | for (const grammar of grammars) { 16 | downloadFile(`${BASE_URL}${grammar}`, `./syntaxes/${grammar}`) 17 | } 18 | for (const conf of configurations) { 19 | downloadFile(`${BASE_URL}${conf}`, `./languages/${conf}`) 20 | } 21 | for (const snippet of snippets) { 22 | downloadFile(`${BASE_URL}${snippet}`, `./snippets/${snippet}`) 23 | } 24 | 25 | async function downloadFile(url: string, destination: string) { 26 | try { 27 | const response = await axios.get(url, { 28 | headers: { 'Accept-Encoding': 'gzip,deflate,compress' }, 29 | }) 30 | const data = response.data 31 | writeFileSync(destination, JSON.stringify(data)) 32 | } catch (error) { 33 | console.error(`Cant download ${url} to ${destination}`) 34 | throw error 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /apps/playground/content/fundamentos/9.flujo-de-ejecucion.md: -------------------------------------------------------------------------------- 1 | # Flujo de ejecución 2 | 3 | El **flujo de ejecución** de un programa es el orden en el que se ejecutan las instrucciones. En EsJS, el flujo de ejecución es **secuencial**, es decir, las instrucciones se ejecutan una tras otra, en el orden en el que aparecen en el código. 4 | 5 | ## Instrucción 6 | 7 | Una **instrucción** representa una acción que el programa debe realizar. En EsJS, las instrucciones se separan por punto y coma (`;`), aunque no es necesario escribir un punto y coma al final de cada instrucción. 8 | 9 | ::content-code 10 | ```esjs 11 | consola.escribir("Hola Mundo!"); 12 | consola.escribir("Desde EsJS"); 13 | ``` 14 | :: 15 | 16 | ## Bloques de código 17 | 18 | En EsJS, las instrucciones se agrupan en **bloques de código**. Un bloque de código es una secuencia de instrucciones encerradas entre llaves (`{}`). 19 | 20 | Por ejemplo: 21 | 22 | ::content-code 23 | ```esjs 24 | { 25 | consola.escribir("Hola"); 26 | consola.escribir("Mundo!"); 27 | } 28 | ``` 29 | :: 30 | 31 | En este caso, el bloque de código contiene dos instrucciones: `consola.escribir("Hola");` y `consola.escribir("Mundo!");`. Estas instrucciones se ejecutan en el orden en el que aparecen en el código. 32 | 33 | -------------------------------------------------------------------------------- /packages/esbabel/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@es-js/esbabel", 3 | "version": "0.0.1-beta.2", 4 | "type": "module", 5 | "scripts": { 6 | "build": "unbuild", 7 | "test": "vitest", 8 | "test:run": "vitest run", 9 | "prepublishOnly": "npm run build" 10 | }, 11 | "keywords": [ 12 | "esjs", 13 | "lenguaje-programacion", 14 | "español", 15 | "spanish" 16 | ], 17 | "devDependencies": { 18 | "@types/node": "^20.9.0", 19 | "typescript": "^5.2.2", 20 | "unbuild": "^2.0.0", 21 | "vite": "^5.1.1", 22 | "vitest": "^2.1.5" 23 | }, 24 | "exports": { 25 | ".": { 26 | "types": "./dist/index.d.ts", 27 | "import": "./dist/index.mjs", 28 | "require": "./dist/index.cjs" 29 | }, 30 | "./keywords": { 31 | "types": "./dist/keywords.d.ts", 32 | "import": "./dist/keywords.mjs", 33 | "require": "./dist/keywords.cjs" 34 | } 35 | }, 36 | "main": "./dist/index.cjs", 37 | "module": "./dist/index.mjs", 38 | "types": "./dist/index.d.ts", 39 | "typesVersions": { 40 | "*": { 41 | "*": [ 42 | "./dist/*", 43 | "./dist/index.d.ts", 44 | "./dist/keywords.d.ts" 45 | ] 46 | } 47 | }, 48 | "files": [ 49 | "dist" 50 | ] 51 | } 52 | -------------------------------------------------------------------------------- /apps/playground/content/fundamentos/3.identificadores.md: -------------------------------------------------------------------------------- 1 | # Identificadores 2 | 3 | Así como en la vida real le ponemos nombres a las distintas cosas que nos rodean, en EsJS le ponemos nombres a las distintas partes de nuestro programa. A estos nombres los llamamos **identificadores**. 4 | 5 | Un identificador es una secuencia de caracteres que identifica una variable, constante, función, clase, etc. En EsJS, los identificadores pueden contener letras, dígitos, guiones bajos (`_`) y signos de dólar (`$`), y deben comenzar con una letra, un guión bajo o un signo de dólar. 6 | 7 | En el ejemplo de "Hola Mundo!" que vimos anteriormente, se hace uso de dos identificadores: `consola` y `escribir`. La `consola` es un objeto que representa la consola del navegador, y `escribir` es una función que permite escribir un mensaje en la consola. 8 | 9 | ::content-code 10 | ```esjs 11 | consola.escribir("Hola Mundo!"); 12 | ``` 13 | :: 14 | 15 | Es importante tener en cuenta que los identificadores son *case sensitive*, es decir, distinguen entre mayúsculas y minúsculas. Por ejemplo, `consola` y `Consola` son dos identificadores distintos. Por lo tanto, el siguiente código generará un error: 16 | 17 | ::content-code 18 | ```esjs 19 | Consola.escribir("Hola Mundo!"); 20 | ``` 21 | :: 22 | --------------------------------------------------------------------------------