@yakuzaa/jade 0.1.11 → 0.1.13
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/commands/html.js +231 -80
- package/package.json +2 -2
package/commands/html.js
CHANGED
|
@@ -90,58 +90,86 @@ function gerarCSS(tema = {}) {
|
|
|
90
90
|
${gerarVariaveisCSS(tema)}
|
|
91
91
|
}
|
|
92
92
|
|
|
93
|
-
body {
|
|
93
|
+
html, body {
|
|
94
|
+
height: 100%;
|
|
94
95
|
font-family: var(--jade-fonte);
|
|
95
96
|
background: var(--jade-cor-fundo);
|
|
96
97
|
color: var(--jade-cor-texto);
|
|
97
|
-
|
|
98
|
+
overflow: hidden;
|
|
98
99
|
}
|
|
99
100
|
|
|
100
|
-
/*
|
|
101
|
-
#jade-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
/* Nav lateral */
|
|
107
|
-
#jade-nav {
|
|
108
|
-
width: 240px;
|
|
109
|
-
min-height: 100dvh;
|
|
101
|
+
/* ── Header fixo ─────────────────────────────── */
|
|
102
|
+
#jade-header {
|
|
103
|
+
position: fixed;
|
|
104
|
+
top: 0; left: 0; right: 0;
|
|
105
|
+
height: 52px;
|
|
110
106
|
background: var(--jade-cor-fundo-nav);
|
|
111
107
|
display: flex;
|
|
112
|
-
|
|
108
|
+
align-items: center;
|
|
109
|
+
gap: 10px;
|
|
110
|
+
padding: 0 16px 0 8px;
|
|
111
|
+
z-index: 300;
|
|
112
|
+
box-shadow: 0 1px 0 rgba(255,255,255,0.06), 0 2px 8px rgba(0,0,0,0.2);
|
|
113
113
|
flex-shrink: 0;
|
|
114
|
-
position: sticky;
|
|
115
|
-
top: 0;
|
|
116
|
-
height: 100dvh;
|
|
117
|
-
overflow-y: auto;
|
|
118
114
|
}
|
|
119
115
|
|
|
120
|
-
#jade-
|
|
121
|
-
|
|
122
|
-
|
|
116
|
+
#jade-hamburger {
|
|
117
|
+
display: flex;
|
|
118
|
+
align-items: center;
|
|
119
|
+
justify-content: center;
|
|
120
|
+
width: 40px;
|
|
121
|
+
height: 40px;
|
|
122
|
+
flex-shrink: 0;
|
|
123
|
+
border: none;
|
|
124
|
+
border-radius: var(--jade-raio);
|
|
125
|
+
background: transparent;
|
|
126
|
+
color: rgba(255,255,255,0.85);
|
|
127
|
+
cursor: pointer;
|
|
128
|
+
transition: background 0.15s;
|
|
123
129
|
}
|
|
130
|
+
#jade-hamburger:hover { background: rgba(255,255,255,0.1); }
|
|
124
131
|
|
|
125
|
-
#jade-
|
|
132
|
+
#jade-header-titulo {
|
|
126
133
|
font-size: 0.875rem;
|
|
127
134
|
font-weight: 700;
|
|
128
135
|
color: #fff;
|
|
129
|
-
letter-spacing: 0.
|
|
136
|
+
letter-spacing: 0.05em;
|
|
130
137
|
text-transform: uppercase;
|
|
138
|
+
white-space: nowrap;
|
|
139
|
+
overflow: hidden;
|
|
140
|
+
text-overflow: ellipsis;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
/* ── Layout principal (abaixo do header) ─────── */
|
|
144
|
+
#jade-app {
|
|
145
|
+
display: flex;
|
|
146
|
+
height: calc(100dvh - 52px);
|
|
147
|
+
margin-top: 52px;
|
|
148
|
+
overflow: hidden;
|
|
131
149
|
}
|
|
132
150
|
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
151
|
+
/* ── Nav lateral ─────────────────────────────── */
|
|
152
|
+
#jade-nav {
|
|
153
|
+
width: 240px;
|
|
154
|
+
height: 100%;
|
|
155
|
+
background: var(--jade-cor-fundo-nav);
|
|
156
|
+
display: flex;
|
|
157
|
+
flex-direction: column;
|
|
158
|
+
flex-shrink: 0;
|
|
159
|
+
overflow-y: auto;
|
|
160
|
+
transition: width 0.2s ease;
|
|
137
161
|
}
|
|
138
162
|
|
|
163
|
+
/* O nav-header foi movido para o #jade-header global */
|
|
164
|
+
#jade-nav-header { display: none; }
|
|
165
|
+
|
|
139
166
|
#jade-nav-lista {
|
|
140
167
|
flex: 1;
|
|
141
|
-
padding: 8px
|
|
168
|
+
padding: 8px;
|
|
142
169
|
display: flex;
|
|
143
170
|
flex-direction: column;
|
|
144
171
|
gap: 2px;
|
|
172
|
+
overflow-y: auto;
|
|
145
173
|
}
|
|
146
174
|
|
|
147
175
|
.jade-nav-item {
|
|
@@ -159,20 +187,44 @@ function gerarCSS(tema = {}) {
|
|
|
159
187
|
cursor: pointer;
|
|
160
188
|
text-align: left;
|
|
161
189
|
transition: background 0.15s, color 0.15s;
|
|
190
|
+
flex-shrink: 0;
|
|
162
191
|
}
|
|
163
|
-
|
|
164
192
|
.jade-nav-item:hover {
|
|
165
193
|
background: rgba(255,255,255,0.07);
|
|
166
194
|
color: rgba(255,255,255,0.9);
|
|
167
195
|
}
|
|
168
|
-
|
|
169
196
|
.jade-nav-ativo {
|
|
170
197
|
background: var(--jade-cor-primaria) !important;
|
|
171
198
|
color: #fff !important;
|
|
172
199
|
}
|
|
173
|
-
|
|
174
200
|
.jade-nav-icone { display: flex; align-items: center; }
|
|
175
201
|
|
|
202
|
+
/* ── Área de conteúdo ────────────────────────── */
|
|
203
|
+
#jade-conteudo {
|
|
204
|
+
flex: 1;
|
|
205
|
+
min-width: 0;
|
|
206
|
+
height: 100%;
|
|
207
|
+
padding: 24px;
|
|
208
|
+
overflow-y: auto;
|
|
209
|
+
overflow-x: hidden;
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
/* ── Overlay drawer (mobile) ─────────────────── */
|
|
213
|
+
#jade-overlay {
|
|
214
|
+
display: none;
|
|
215
|
+
position: fixed;
|
|
216
|
+
inset: 0;
|
|
217
|
+
top: 52px;
|
|
218
|
+
background: rgba(0,0,0,0.45);
|
|
219
|
+
z-index: 199;
|
|
220
|
+
opacity: 0;
|
|
221
|
+
transition: opacity 0.25s;
|
|
222
|
+
}
|
|
223
|
+
#jade-overlay.visivel {
|
|
224
|
+
display: block;
|
|
225
|
+
opacity: 1;
|
|
226
|
+
}
|
|
227
|
+
|
|
176
228
|
/* Toolbar */
|
|
177
229
|
.jade-toolbar {
|
|
178
230
|
display: flex;
|
|
@@ -186,6 +238,7 @@ function gerarCSS(tema = {}) {
|
|
|
186
238
|
.jade-busca-form { display: flex; gap: 0; }
|
|
187
239
|
.jade-busca-input {
|
|
188
240
|
flex: 1;
|
|
241
|
+
min-width: 0;
|
|
189
242
|
min-height: 44px;
|
|
190
243
|
padding: 10px 14px;
|
|
191
244
|
border: 1.5px solid var(--jade-cor-borda);
|
|
@@ -232,20 +285,12 @@ function gerarCSS(tema = {}) {
|
|
|
232
285
|
letter-spacing: 0.05em;
|
|
233
286
|
}
|
|
234
287
|
|
|
235
|
-
/* Área de conteúdo */
|
|
236
|
-
#jade-conteudo {
|
|
237
|
-
flex: 1;
|
|
238
|
-
min-width: 0;
|
|
239
|
-
padding: 24px;
|
|
240
|
-
overflow-y: auto;
|
|
241
|
-
}
|
|
242
|
-
|
|
243
288
|
/* Carregando */
|
|
244
289
|
#jade-carregando {
|
|
245
290
|
display: flex;
|
|
246
291
|
align-items: center;
|
|
247
292
|
justify-content: center;
|
|
248
|
-
|
|
293
|
+
height: 100dvh;
|
|
249
294
|
color: var(--jade-cor-texto-muted);
|
|
250
295
|
font-size: 0.9rem;
|
|
251
296
|
gap: 10px;
|
|
@@ -261,40 +306,29 @@ function gerarCSS(tema = {}) {
|
|
|
261
306
|
|
|
262
307
|
@keyframes jade-giro { to { transform: rotate(360deg); } }
|
|
263
308
|
|
|
264
|
-
/* Mobile:
|
|
265
|
-
|
|
266
|
-
|
|
309
|
+
/* Mobile: hamburger + drawer overlay */
|
|
310
|
+
/* ── Desktop: sidebar pode ser colapsada ─────── */
|
|
311
|
+
#jade-nav.jade-nav-colapsada {
|
|
312
|
+
width: 0;
|
|
313
|
+
overflow: hidden;
|
|
314
|
+
}
|
|
267
315
|
|
|
316
|
+
/* ── Mobile: drawer slide-in (abaixo do header) ─ */
|
|
317
|
+
@media (max-width: 768px) {
|
|
268
318
|
#jade-nav {
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
#jade-nav-header { display: none; }
|
|
279
|
-
|
|
280
|
-
#jade-nav-lista {
|
|
281
|
-
flex-direction: row;
|
|
282
|
-
overflow-x: auto;
|
|
283
|
-
padding: 6px 8px;
|
|
284
|
-
gap: 4px;
|
|
319
|
+
position: fixed;
|
|
320
|
+
top: 52px;
|
|
321
|
+
left: 0;
|
|
322
|
+
height: calc(100dvh - 52px);
|
|
323
|
+
z-index: 200;
|
|
324
|
+
transform: translateX(-100%);
|
|
325
|
+
transition: transform 0.25s ease;
|
|
326
|
+
box-shadow: 4px 0 16px rgba(0,0,0,0.3);
|
|
327
|
+
width: 240px !important;
|
|
285
328
|
}
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
flex-direction: column;
|
|
289
|
-
gap: 2px;
|
|
290
|
-
padding: 6px 12px;
|
|
291
|
-
font-size: 0.7rem;
|
|
292
|
-
white-space: nowrap;
|
|
293
|
-
flex-shrink: 0;
|
|
329
|
+
#jade-nav.jade-nav-aberto {
|
|
330
|
+
transform: translateX(0);
|
|
294
331
|
}
|
|
295
|
-
|
|
296
|
-
.jade-nav-icone { font-size: 1.2rem; }
|
|
297
|
-
|
|
298
332
|
#jade-conteudo { padding: 16px; }
|
|
299
333
|
}
|
|
300
334
|
`.trim();
|
|
@@ -346,31 +380,98 @@ function coletarEntidades(telas) {
|
|
|
346
380
|
for (const el of tela.elementos || []) {
|
|
347
381
|
for (const prop of el.propriedades || []) {
|
|
348
382
|
if (prop.chave === 'entidade' && prop.valor) nomes.add(String(prop.valor));
|
|
383
|
+
// Agrega referências em marcadores @funcao:Entidade:campo
|
|
384
|
+
if (typeof prop.valor === 'string' && prop.valor.startsWith('@')) {
|
|
385
|
+
const partes = prop.valor.slice(1).split(':');
|
|
386
|
+
if (partes[1]) nomes.add(partes[1]);
|
|
387
|
+
}
|
|
349
388
|
}
|
|
350
389
|
}
|
|
351
390
|
}
|
|
352
391
|
return [...nomes];
|
|
353
392
|
}
|
|
354
393
|
|
|
394
|
+
// Formata valor numérico de acordo com o campo (moeda vs número simples)
|
|
395
|
+
function formatarValor(v, campo) {
|
|
396
|
+
if (typeof v !== 'number' || isNaN(v)) return String(v ?? '');
|
|
397
|
+
const campoLower = (campo || '').toLowerCase();
|
|
398
|
+
// Campos monetários
|
|
399
|
+
if (/preco|total|valor|custo|receita|despesa|salario|pagamento|desconto|subtotal|moeda/.test(campoLower)) {
|
|
400
|
+
return v.toLocaleString('pt-BR', { style: 'currency', currency: 'BRL' });
|
|
401
|
+
}
|
|
402
|
+
// Inteiro
|
|
403
|
+
if (Number.isInteger(v)) return v.toLocaleString('pt-BR');
|
|
404
|
+
return v.toLocaleString('pt-BR', { minimumFractionDigits: 2, maximumFractionDigits: 2 });
|
|
405
|
+
}
|
|
406
|
+
|
|
407
|
+
// Resolve marcadores @funcao:Entidade:campo nos descritores de tela
|
|
408
|
+
function resolverAgregacoes(tela, dadosMap) {
|
|
409
|
+
for (const el of tela.elementos || []) {
|
|
410
|
+
for (const prop of el.propriedades) {
|
|
411
|
+
if (typeof prop.valor !== 'string' || !prop.valor.startsWith('@')) continue;
|
|
412
|
+
const [funcao, entidade, campo] = prop.valor.slice(1).split(':');
|
|
413
|
+
const registros = dadosMap[entidade] ?? [];
|
|
414
|
+
let resultado;
|
|
415
|
+
switch (funcao) {
|
|
416
|
+
case 'soma':
|
|
417
|
+
resultado = registros.reduce((s, r) => s + (Number(r[campo]) || 0), 0);
|
|
418
|
+
prop.valor = formatarValor(resultado, campo);
|
|
419
|
+
break;
|
|
420
|
+
case 'contagem':
|
|
421
|
+
resultado = registros.length;
|
|
422
|
+
prop.valor = resultado.toLocaleString('pt-BR');
|
|
423
|
+
break;
|
|
424
|
+
case 'media':
|
|
425
|
+
resultado = registros.length
|
|
426
|
+
? registros.reduce((s, r) => s + (Number(r[campo]) || 0), 0) / registros.length
|
|
427
|
+
: 0;
|
|
428
|
+
prop.valor = formatarValor(resultado, campo);
|
|
429
|
+
break;
|
|
430
|
+
case 'maximo':
|
|
431
|
+
resultado = registros.length ? Math.max(...registros.map(r => Number(r[campo]) || 0)) : 0;
|
|
432
|
+
prop.valor = formatarValor(resultado, campo);
|
|
433
|
+
break;
|
|
434
|
+
case 'minimo':
|
|
435
|
+
resultado = registros.length ? Math.min(...registros.map(r => Number(r[campo]) || 0)) : 0;
|
|
436
|
+
prop.valor = formatarValor(resultado, campo);
|
|
437
|
+
break;
|
|
438
|
+
}
|
|
439
|
+
}
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
|
|
355
443
|
async function mudarTela(nome, telas, db, ui, navItems) {
|
|
356
444
|
const idx = telas.findIndex(t => t.nome === nome);
|
|
357
445
|
if (idx < 0) return;
|
|
358
446
|
|
|
359
|
-
navItems
|
|
447
|
+
// navItems mapeia para telasNav (filtradas), mas idx é em telas (completa)
|
|
448
|
+
// Encontra o índice correto no navItems pelo nome
|
|
449
|
+
const navIdx = navItems.findIndex(b => b.dataset.tela === nome);
|
|
450
|
+
navItems.forEach((btn, i) => btn.classList.toggle('jade-nav-ativo', i === navIdx));
|
|
360
451
|
|
|
361
452
|
const tela = telas[idx];
|
|
362
453
|
const container = document.getElementById('jade-conteudo');
|
|
363
454
|
container.innerHTML = '';
|
|
364
455
|
|
|
456
|
+
// Carrega todas as entidades referenciadas (inclusive em marcadores @)
|
|
365
457
|
const dadosMap = {};
|
|
366
458
|
for (const el of tela.elementos || []) {
|
|
367
459
|
for (const prop of el.propriedades || []) {
|
|
368
|
-
|
|
369
|
-
|
|
460
|
+
const refs = [];
|
|
461
|
+
if (prop.chave === 'entidade' && prop.valor) refs.push(String(prop.valor));
|
|
462
|
+
if (typeof prop.valor === 'string' && prop.valor.startsWith('@')) {
|
|
463
|
+
const partes = prop.valor.slice(1).split(':');
|
|
464
|
+
if (partes[1]) refs.push(partes[1]);
|
|
465
|
+
}
|
|
466
|
+
for (const ref of refs) {
|
|
467
|
+
if (!dadosMap[ref]) dadosMap[ref] = await db.find(ref).catch(() => []);
|
|
370
468
|
}
|
|
371
469
|
}
|
|
372
470
|
}
|
|
373
471
|
|
|
472
|
+
// Resolve @soma, @contagem, @media antes de renderizar
|
|
473
|
+
resolverAgregacoes(tela, dadosMap);
|
|
474
|
+
|
|
374
475
|
ui.renderizarTela(tela, container, dadosMap);
|
|
375
476
|
}
|
|
376
477
|
|
|
@@ -401,6 +502,45 @@ async function iniciar() {
|
|
|
401
502
|
|
|
402
503
|
document.getElementById('jade-carregando')?.remove();
|
|
403
504
|
document.getElementById('jade-app').style.display = '';
|
|
505
|
+
document.getElementById('jade-header').style.display = '';
|
|
506
|
+
|
|
507
|
+
// ── Header + hambúrguer ──────────────────────────────────────────────────────
|
|
508
|
+
const hamburger = document.getElementById('jade-hamburger');
|
|
509
|
+
const overlay = document.getElementById('jade-overlay');
|
|
510
|
+
const navEl = document.getElementById('jade-nav');
|
|
511
|
+
const isMobile = () => window.innerWidth <= 768;
|
|
512
|
+
|
|
513
|
+
const iconeMenu = criarElementoIcone('menu', 22);
|
|
514
|
+
const iconeFechar = criarElementoIcone('fechar', 22);
|
|
515
|
+
if (iconeMenu) hamburger.appendChild(iconeMenu);
|
|
516
|
+
|
|
517
|
+
function abrirDrawer() {
|
|
518
|
+
navEl.classList.add('jade-nav-aberto');
|
|
519
|
+
overlay.classList.add('visivel');
|
|
520
|
+
hamburger.setAttribute('aria-expanded', 'true');
|
|
521
|
+
if (iconeMenu && iconeFechar && hamburger.firstChild)
|
|
522
|
+
hamburger.replaceChild(iconeFechar, hamburger.firstChild);
|
|
523
|
+
}
|
|
524
|
+
function fecharDrawer() {
|
|
525
|
+
navEl.classList.remove('jade-nav-aberto');
|
|
526
|
+
overlay.classList.remove('visivel');
|
|
527
|
+
hamburger.setAttribute('aria-expanded', 'false');
|
|
528
|
+
if (iconeMenu && hamburger.firstChild !== iconeMenu)
|
|
529
|
+
hamburger.replaceChild(iconeMenu, hamburger.firstChild);
|
|
530
|
+
}
|
|
531
|
+
function toggleSidebar() {
|
|
532
|
+
navEl.classList.toggle('jade-nav-colapsada');
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
hamburger.addEventListener('click', () => {
|
|
536
|
+
if (isMobile()) {
|
|
537
|
+
navEl.classList.contains('jade-nav-aberto') ? fecharDrawer() : abrirDrawer();
|
|
538
|
+
} else {
|
|
539
|
+
toggleSidebar();
|
|
540
|
+
}
|
|
541
|
+
});
|
|
542
|
+
overlay.addEventListener('click', fecharDrawer);
|
|
543
|
+
window.addEventListener('resize', () => { if (!isMobile()) fecharDrawer(); });
|
|
404
544
|
|
|
405
545
|
if (telas.length === 0) {
|
|
406
546
|
document.getElementById('jade-conteudo').innerHTML =
|
|
@@ -417,6 +557,7 @@ async function iniciar() {
|
|
|
417
557
|
const btn = document.createElement('button');
|
|
418
558
|
btn.className = 'jade-nav-item' + (i === 0 ? ' jade-nav-ativo' : '');
|
|
419
559
|
btn.dataset.tela = tela.nome;
|
|
560
|
+
btn.setAttribute('role', 'listitem');
|
|
420
561
|
|
|
421
562
|
const svgIcone = criarElementoIcone(nomeIcone(tela.nome), 18);
|
|
422
563
|
const spanIcone = document.createElement('span');
|
|
@@ -428,7 +569,10 @@ async function iniciar() {
|
|
|
428
569
|
spanLabel.textContent = tela.titulo || tela.nome;
|
|
429
570
|
btn.appendChild(spanLabel);
|
|
430
571
|
|
|
431
|
-
btn.addEventListener('click', () =>
|
|
572
|
+
btn.addEventListener('click', () => {
|
|
573
|
+
mudarTela(tela.nome, telas, db, ui, navItems);
|
|
574
|
+
fecharDrawer(); // fecha o drawer no mobile após navegar
|
|
575
|
+
});
|
|
432
576
|
nav.appendChild(btn);
|
|
433
577
|
navItems.push(btn);
|
|
434
578
|
});
|
|
@@ -436,7 +580,10 @@ async function iniciar() {
|
|
|
436
580
|
// Handler: jade:navegar — gaveta e navegar disparam este evento
|
|
437
581
|
window.addEventListener('jade:navegar', (e) => {
|
|
438
582
|
const nomeTela = e.detail?.tela;
|
|
439
|
-
if (nomeTela)
|
|
583
|
+
if (nomeTela) {
|
|
584
|
+
mudarTela(nomeTela, telas, db, ui, navItems);
|
|
585
|
+
fecharDrawer();
|
|
586
|
+
}
|
|
440
587
|
});
|
|
441
588
|
|
|
442
589
|
// Handler: jade:acao — dispara jade:acao:concluido após processar
|
|
@@ -496,13 +643,17 @@ ${gerarCSS(tema)}
|
|
|
496
643
|
Carregando...
|
|
497
644
|
</div>
|
|
498
645
|
|
|
646
|
+
<header id="jade-header" style="display:none">
|
|
647
|
+
<button id="jade-hamburger" aria-label="Abrir menu" aria-expanded="false"></button>
|
|
648
|
+
<span id="jade-header-titulo">${nome}</span>
|
|
649
|
+
</header>
|
|
650
|
+
|
|
651
|
+
<div id="jade-overlay" role="presentation"></div>
|
|
652
|
+
|
|
499
653
|
<div id="jade-app" style="display:none">
|
|
500
|
-
<nav id="jade-nav">
|
|
501
|
-
<div id="jade-nav-header">
|
|
502
|
-
|
|
503
|
-
<div id="jade-nav-versao">feito com Jade DSL</div>
|
|
504
|
-
</div>
|
|
505
|
-
<div id="jade-nav-lista"></div>
|
|
654
|
+
<nav id="jade-nav" aria-label="Menu de navegação">
|
|
655
|
+
<div id="jade-nav-header"></div>
|
|
656
|
+
<div id="jade-nav-lista" role="list"></div>
|
|
506
657
|
</nav>
|
|
507
658
|
<main id="jade-conteudo"></main>
|
|
508
659
|
</div>
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@yakuzaa/jade",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.13",
|
|
4
4
|
"description": "Jade DSL — linguagem empresarial em português compilada para WebAssembly. Instala compilador + runtime + CLI.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|
|
@@ -17,7 +17,7 @@
|
|
|
17
17
|
"postinstall": "node postinstall.js"
|
|
18
18
|
},
|
|
19
19
|
"dependencies": {
|
|
20
|
-
"@yakuzaa/jade-compiler": "^0.1.
|
|
20
|
+
"@yakuzaa/jade-compiler": "^0.1.15",
|
|
21
21
|
"@yakuzaa/jade-runtime": "^0.1.8"
|
|
22
22
|
},
|
|
23
23
|
"keywords": [
|