jaded 0.3.1

jaded #

pub package style: effective dart

Port of the excellent Pug, formerly Jade view engine in Dart.

Now feature complete with the original jade view engine, begin by taking the comprehensive tour on learnjade.com and refer to jade's detailed documentation
to learn about Jade's features and syntax.

Although the aim was to have a high-fidelity port, the major syntactical difference compared with the original Jade (in JavaScript) is that the compiler only emits and executes Dart code, so any embedded code in views must be valid Dart (i.e. instead of JavaScript).

Installing via Pub #

Add this to your package's pubspec.yaml file:

dependencies:
  jaded: 0.3.1

Public API #

Compile a Directory #

Add a pre-build step and use renderDirectory to statically compile all views into a single jade.views.dart file containing a Map of all compiled Jade views, e.g:

import "dart:io";
import "package:jaded/jaded.dart" as jade;

var jadeTemplates = jade.renderDirectory('.');
new File('jade.views.dart').writeAsString(jadeTemplates);

Writes to jade.views.dart snippet:

Map<String,Function> JADE_TEMPLATES = {
  './index.jade': ([Map locals]){
     ...
  },
  './dir/page.jade': ([Map locals]){
    ...
  },
}

Usage:

import "jade.views.dart";

var render = JADE_TEMPLATES['./index.jade'];
var html = render({'title': 'Hello Jade!'});

Compile a jade view at runtime #

import "package:jaded/jaded.dart" as jade;

var renderAsync = jade.compile('string of jade', { //Optional Compiler Defaults:
  Map locals,
  String filename,
  String basedir,
  String doctype,
  bool pretty:false,
  bool compileDebug:false,
  bool debug:false,
  bool colons:false,
  bool autoSemicolons:true  
});

renderAsync(locals)
  .then((html) => print(html));

Options #

  • locals Local variable object
  • filename Used in exceptions, and required when using includes
  • basedir The basedir where views start from
  • doctype What doctype to use
  • pretty Add pretty-indentation whitespace to output (false by default)
  • debug Outputs tokens and function body generated
  • compileDebug When false no debug instrumentation is compiled
  • autoSemicolons Auto add missing semicolons at the end of new lines (true by default)

Web Frameworks #

Current Status #

All tests in jade.test.dart are now passing.

All integration test cases in /test/cases that doesn't make use of an external DSL library are passing. Specifically, the following filters are NOT supported:

filters.coffeescript.jade
filters.less.jade
filters.stylus.jade
include-filter-stylus.jade

When they become available support for external Web DSL's can be added to transformers.dart in the same way as done inside Jade's feature-rich transformers.js.

Markdown filter #

We've added the markdown filter which lets you include markdown inline:

html
  body
    :markdown
      This is _some_ awesome **markdown**

Or as an external include:

html
  body
    include some.md

Pre-compilation of .jade templates #

The recommended way to execute .jade templates is to pre-compile all views with renderDirectory() out to a static file at design time. This can be automated using the Dart Editor build system /build.dart file, which can be used to trigger the background compilation of .jade views when it detects a .jade file was saved or deleted.

This is the approach the Dart Express Web Framework takes with its express_build.dart helper that gets triggered when a '.jade' file is touched will scan all directories for an empty jade.yaml marker and recursively pre-compiles all .jade views in that directory into a single jade.views.dart file.

Compile and execute at runtime - Missing eval #

Jade relies on eval'ing code-gen to work which is a limitation in Dart that lacks eval. To get around this when compiling on the fly, we're currently wrapping the code-gen Dart inside an Isolate and writing it out to a file then immediately reading it back in with spawnUri and invoking the new code asynchronously in the runCompiledDartInIsolate() method.

Although this works, it forces us to have an async API to convert jade to html at runtime. When Dart offers a sync API for evaluating Dart code we'll convert it back to a sync API.


Contributors #

Jaded Changelog #

v. 0.1.9 - #

- for dart <=1.24.0. Updated to Pug 2 (*async) api, continues to use the .jade extension


v. 0.2.0 - #

- updated entire package, including test suite, to dart >=2.3.0

- All tests are passing #

- Added sass/scss :filter / transformer used with :sass or :scss

- Added a test.sh script to run all pertinent tests in the test folder

- updated accompanying packages, character_parser and node_shims, to work with dart >=2.3.0


v. 0.2.1 - #

- entire package linted in accordance with effective_dart and pedantic #


v. 0.2.1+1 - #

- minor doc improvements #


v. 0.2.1+2 - #


v. 0.3.0 #

- added dart_formatter to code written that is written to files for isolate reading, in order to attempt to reduce analyzer warnings and keep the file readable if needed #

- fixed a bug that broke testing functionaity #


v. 0.3.1 #

- fixed misprint in readme (did not want to add a '+' version, the versions are small enough as it is) #

example/main.dart

import 'dart:convert' as conv;
import 'dart:io';

// import 'package:jaded/jaded.dart';
import 'package:jaded/jaded.dart' as jade;
import 'package:test/test.dart';

void main() {
  var missingFilters = [
    'filters.coffeescript.jade',
    'filters.less.jade',
    'filters.stylus.jade',
    'include-filter-stylus.jade',
  ];

  var cases = Directory('cases')
      .listSync()
      .map((fse) => fse.path)
      .where((file) =>
          file.contains('.jade') &&
          !missingFilters.any((x) => file.endsWith(x)))
      .map((file) => file.replaceAll('.jade', ''));

  print('cases: ${cases.length}');

  group('test cases', () {
    void _feFunc(file) {
      print('testing $file...');

      var name = file.replaceAll(RegExp(r'[-.]'), ' ');

      test(name, () {
        var path = '$file.jade';
        var str = File(path).readAsStringSync();
        var html = File('$file.html')
            .readAsStringSync()
            .trim()
            .replaceAll(RegExp(r'\r'), '');
        var fn =
            jade.compile(str, filename: path, pretty: true, basedir: 'cases');

        fn({'title': 'Jade'}).then(expectAsync1((actual) {
          if (RegExp('filter').hasMatch(name)) {
            actual = actual.replaceAll(RegExp(r'\n'), '');
            html = html.replaceAll(RegExp(r'\n'), '');
          }

          expect(
              conv.json.encode(actual.trim()), equals(conv.json.encode(html)));
        }));
      });
    }

    cases
//      .where((String file) => file.endsWith('include-filter'))
        .forEach(_feFunc);
  });
}

Use this package as a library

1. Depend on it

Add this to your package's pubspec.yaml file:


dependencies:
  jaded: ^0.3.1

2. Install it

You can install packages from the command line:

with pub:


$ pub get

Alternatively, your editor might support pub get. Check the docs for your editor to learn more.

3. Import it

Now in your Dart code, you can use:


import 'package:jaded/jaded.dart';
  
Popularity:
Describes how popular the package is relative to other packages. [more]
4
Health:
Code health derived from static analysis. [more]
100
Maintenance:
Reflects how tidy and up-to-date the package is. [more]
100
Overall:
Weighted score of the above. [more]
52
Learn more about scoring.

We analyzed this package on Feb 19, 2020, and provided a score, details, and suggestions below. Analysis was completed with status completed using:

  • Dart: 2.7.1
  • pana: 0.13.5

Dependencies

Package Constraint Resolved Available
Direct dependencies
Dart SDK >=2.3.0 <3.0.0
character_parser ^0.3.0 0.3.0
dart_style ^1.3.3 1.3.3
markdown ^2.1.3 2.1.3
node_shims ^0.2.0 0.2.1
sass ^1.25.0 1.25.0 1.26.0-test.3
Transitive dependencies
_fe_analyzer_shared 1.0.3
analyzer 0.39.4
args 1.5.2
async 2.4.0
charcode 1.1.3
cli_repl 0.2.0+1
collection 1.14.12
convert 2.1.1
crypto 2.1.4
csslib 0.16.1
glob 1.2.0
html 0.14.0+3
http 0.12.0+4
http_parser 3.1.3
js 0.6.1+1
matcher 0.12.6
meta 1.1.8
node_interop 1.0.3
node_io 1.0.1+2
package_config 1.1.0
package_resolver 1.0.10
path 1.6.4
pub_semver 1.4.3
quiver 2.1.2+1
source_maps 0.10.9
source_span 1.6.0
stack_trace 1.9.3
stream_transform 1.1.0
string_scanner 1.0.5
term_glyph 1.1.0
tuple 1.0.3
typed_data 1.1.6
watcher 0.9.7+13
yaml 2.2.0
Dev dependencies
effective_dart any
pedantic any 1.9.0
test any