mirror of
https://github.com/danog/dart-sass.git
synced 2024-11-26 20:24:42 +01:00
Add support for the data option to the JS API (#159)
Also add renderString to the Dart API. Partially addresses #7
This commit is contained in:
parent
91ebf98c7f
commit
8f836df66c
@ -8,9 +8,14 @@
|
||||
|
||||
### Node JS API
|
||||
|
||||
* Add support for `lineFeed`, `indentWidth`, and `indentType` options to
|
||||
* Add support for `data`, `lineFeed`, `indentWidth`, and `indentType` options to
|
||||
`render()` and `renderSync()`.
|
||||
|
||||
### Dart API
|
||||
|
||||
* Add a `renderString()` method for rendering Sass source that's not in a file
|
||||
on disk.
|
||||
|
||||
## 1.0.0-beta.1
|
||||
|
||||
* Drop support for the reference combinator. This has been removed from the
|
||||
|
@ -16,7 +16,34 @@ import 'src/sync_package_resolver.dart';
|
||||
///
|
||||
/// [SyncPackageResolver]: https://www.dartdocs.org/documentation/package_resolver/latest/package_resolver/SyncPackageResolver-class.html
|
||||
///
|
||||
/// Finally throws a [SassException] if conversion fails.
|
||||
/// Throws a [SassException] if conversion fails.
|
||||
String render(String path,
|
||||
{bool color: false, SyncPackageResolver packageResolver}) =>
|
||||
r.render(path, color: color, packageResolver: packageResolver);
|
||||
|
||||
/// Converts [source] to CSS and returns the result.
|
||||
///
|
||||
/// If [indented] is `true`, this parses [source] using indented syntax;
|
||||
/// otherwise (and by default) it uses SCSS. If [color] is `true`, this will use
|
||||
/// terminal colors in warnings.
|
||||
///
|
||||
/// If [packageResolver] is provided, it's used to resolve `package:` imports.
|
||||
/// Otherwise, they aren't supported. It takes a [SyncPackageResolver][] from
|
||||
/// the `package_resolver` package.
|
||||
///
|
||||
/// [SyncPackageResolver]: https://www.dartdocs.org/documentation/package_resolver/latest/package_resolver/SyncPackageResolver-class.html
|
||||
///
|
||||
/// The [url] indicates the location from which [source] was loaded. It may may
|
||||
/// be a [String] or a [Uri].
|
||||
///
|
||||
/// Throws a [SassException] if conversion fails.
|
||||
String renderString(String source,
|
||||
{bool indented: false,
|
||||
bool color: false,
|
||||
SyncPackageResolver packageResolver,
|
||||
url}) =>
|
||||
r.renderString(source,
|
||||
indented: indented,
|
||||
color: color,
|
||||
packageResolver: packageResolver,
|
||||
url: url);
|
||||
|
@ -39,14 +39,12 @@ void main() {
|
||||
void _render(RenderOptions options,
|
||||
void callback(RenderError error, RenderResult result)) {
|
||||
try {
|
||||
var result = newRenderResult(render(options.file,
|
||||
useSpaces: options.indentType != 'tab',
|
||||
indentWidth: _parseIndentWidth(options.indentWidth),
|
||||
lineFeed: _parseLineFeed(options.linefeed)));
|
||||
callback(null, result);
|
||||
callback(null, _doRender(options));
|
||||
} on SassException catch (error) {
|
||||
// TODO: populate the error more thoroughly if possible.
|
||||
callback(newRenderError(message: error.message), null);
|
||||
callback(newRenderError(error.message), null);
|
||||
} catch (error) {
|
||||
callback(newRenderError(error.toString()), null);
|
||||
}
|
||||
}
|
||||
|
||||
@ -58,15 +56,42 @@ void _render(RenderOptions options,
|
||||
/// [render]: https://github.com/sass/node-sass#options
|
||||
RenderResult _renderSync(RenderOptions options) {
|
||||
try {
|
||||
return newRenderResult(render(options.file,
|
||||
useSpaces: options.indentType != 'tab',
|
||||
indentWidth: _parseIndentWidth(options.indentWidth),
|
||||
lineFeed: _parseLineFeed(options.linefeed)));
|
||||
return _doRender(options);
|
||||
} on SassException catch (error) {
|
||||
// TODO: populate the error more thoroughly if possible.
|
||||
jsThrow(newRenderError(message: error.message));
|
||||
throw "unreachable";
|
||||
jsThrow(newRenderError(error.message));
|
||||
} catch (error) {
|
||||
jsThrow(newRenderError(error.toString()));
|
||||
}
|
||||
throw "unreachable";
|
||||
}
|
||||
|
||||
/// Converts Sass to CSS.
|
||||
///
|
||||
/// Unlike [_render] and [_renderSync], this doesn't do any special handling for
|
||||
/// Dart exceptions.
|
||||
RenderResult _doRender(RenderOptions options) {
|
||||
String output;
|
||||
if (options.data != null) {
|
||||
if (options.file != null) {
|
||||
throw new ArgumentError(
|
||||
"options.data and options.file may not both be set.");
|
||||
}
|
||||
|
||||
output = renderString(options.data,
|
||||
useSpaces: options.indentType != 'tab',
|
||||
indentWidth: _parseIndentWidth(options.indentWidth),
|
||||
lineFeed: _parseLineFeed(options.linefeed));
|
||||
} else if (options.file != null) {
|
||||
output = render(options.file,
|
||||
useSpaces: options.indentType != 'tab',
|
||||
indentWidth: _parseIndentWidth(options.indentWidth),
|
||||
lineFeed: _parseLineFeed(options.linefeed));
|
||||
} else {
|
||||
throw new ArgumentError("Either options.data or options.file must be set.");
|
||||
}
|
||||
|
||||
return newRenderResult(output);
|
||||
}
|
||||
|
||||
/// Parses the indentation width into an [int].
|
||||
|
@ -19,8 +19,8 @@ class RenderError {
|
||||
{String message, int line, int column, int status, String file});
|
||||
}
|
||||
|
||||
RenderError newRenderError(
|
||||
{String message, int line, int column, int status, String file}) {
|
||||
RenderError newRenderError(String message,
|
||||
{int line, int column, int status, String file}) {
|
||||
var error = new RenderError._(
|
||||
message: message, line: line, column: column, status: status, file: file);
|
||||
setToString(error, () => "Error: $message");
|
||||
|
@ -8,10 +8,15 @@ import 'package:js/js.dart';
|
||||
@anonymous
|
||||
class RenderOptions {
|
||||
external String get file;
|
||||
external String get data;
|
||||
external String get indentType;
|
||||
external dynamic get indentWidth;
|
||||
external String get linefeed;
|
||||
|
||||
external factory RenderOptions(
|
||||
{String file, String indentType, indentWidth, String linefeed});
|
||||
{String file,
|
||||
String data,
|
||||
String indentType,
|
||||
indentWidth,
|
||||
String linefeed});
|
||||
}
|
||||
|
@ -12,16 +12,33 @@ import 'visitor/serialize.dart';
|
||||
/// Like [render] in `lib/sass.dart`, but provides more options to support the
|
||||
/// node-sass compatible API.
|
||||
String render(String path,
|
||||
{bool color: false,
|
||||
{bool color: false,
|
||||
SyncPackageResolver packageResolver,
|
||||
bool useSpaces: true,
|
||||
int indentWidth,
|
||||
LineFeed lineFeed}) =>
|
||||
renderString(readFile(path),
|
||||
indented: p.extension(path) == '.sass',
|
||||
color: color,
|
||||
packageResolver: packageResolver,
|
||||
useSpaces: useSpaces,
|
||||
indentWidth: indentWidth,
|
||||
lineFeed: lineFeed,
|
||||
url: p.toUri(path));
|
||||
|
||||
/// Like [renderString] in `lib/sass.dart`, but provides more options to support
|
||||
/// the node-sass compatible API.
|
||||
String renderString(String source,
|
||||
{bool indented: false,
|
||||
bool color: false,
|
||||
SyncPackageResolver packageResolver,
|
||||
bool useSpaces: true,
|
||||
int indentWidth,
|
||||
LineFeed lineFeed}) {
|
||||
var contents = readFile(path);
|
||||
var url = p.toUri(path);
|
||||
var sassTree = p.extension(path) == '.sass'
|
||||
? new Stylesheet.parseSass(contents, url: url, color: color)
|
||||
: new Stylesheet.parseScss(contents, url: url, color: color);
|
||||
LineFeed lineFeed,
|
||||
url}) {
|
||||
var sassTree = indented
|
||||
? new Stylesheet.parseSass(source, url: url, color: color)
|
||||
: new Stylesheet.parseScss(source, url: url, color: color);
|
||||
var cssTree =
|
||||
evaluate(sassTree, color: color, packageResolver: packageResolver);
|
||||
return toCss(cssTree,
|
||||
|
@ -41,6 +41,42 @@ a {
|
||||
}'''));
|
||||
});
|
||||
|
||||
test("supports relative imports for a file", () async {
|
||||
var importerPath = p.join(sandbox, 'importer.scss');
|
||||
await writeTextFile(importerPath, '@import "test"');
|
||||
expect(_renderSync(new RenderOptions(file: importerPath)), equals('''
|
||||
a {
|
||||
b: c;
|
||||
}'''));
|
||||
});
|
||||
|
||||
test("renders a string", () {
|
||||
expect(_renderSync(new RenderOptions(data: "a {b: c}")), equals('''
|
||||
a {
|
||||
b: c;
|
||||
}'''));
|
||||
});
|
||||
|
||||
test("data and file may not both be set", () {
|
||||
var error =
|
||||
_renderSyncError(new RenderOptions(data: "x {y: z}", file: sassPath));
|
||||
expect(error.toString(),
|
||||
contains('options.data and options.file may not both be set.'));
|
||||
});
|
||||
|
||||
test("one of data and file must be set", () {
|
||||
var error = _renderSyncError(new RenderOptions());
|
||||
expect(error.toString(),
|
||||
contains('Either options.data or options.file must be set.'));
|
||||
});
|
||||
|
||||
test("rejects both a file and a string", () {
|
||||
expect(_renderSync(new RenderOptions(data: "a {b: c}")), equals('''
|
||||
a {
|
||||
b: c;
|
||||
}'''));
|
||||
});
|
||||
|
||||
test("allows tab indentation", () {
|
||||
expect(_renderSync(new RenderOptions(file: sassPath, indentType: 'tab')),
|
||||
equals('''
|
||||
|
Loading…
Reference in New Issue
Block a user