library mustache_test;

import 'package:unittest/unittest.dart';
import 'package:mustache/mustache.dart';

const MISMATCHED_TAG = 'Mismatched tag';
const UNEXPECTED_EOF = 'Unexpected end of input';
const BAD_VALUE_SECTION = 'Invalid value type for section';
const BAD_VALUE_INV_SECTION = 'Invalid value type for inverse section';
const BAD_TAG_NAME = 'Tag contained invalid characters in name';
const VALUE_NULL = 'Value was null or missing';

main() {
	group('Basic', () {
		test('Variable', () {
			var output = parse('_{{var}}_')
				.renderString({"var": "bob"});
			expect(output, equals('_bob_'));
		});
		test('Comment', () {
			var output = parse('_{{! i am a comment ! }}_').renderString({});
			expect(output, equals('__'));
		});
	});
	group('Section', () {
		test('Map', () {
			var output = parse('{{#section}}_{{var}}_{{/section}}')
				.renderString({"section": {"var": "bob"}});
			expect(output, equals('_bob_'));
		});
		test('List', () {
			var output = parse('{{#section}}_{{var}}_{{/section}}')
				.renderString({"section": [{"var": "bob"}, {"var": "jim"}]});
			expect(output, equals('_bob__jim_'));
		});
		test('Empty List', () {
			var output = parse('{{#section}}_{{var}}_{{/section}}')
				.renderString({"section": []});
			expect(output, equals(''));
		});
		test('False', () {
			var output = parse('{{#section}}_{{var}}_{{/section}}')
				.renderString({"section": false});
			expect(output, equals(''));
		});
		test('Invalid value', () {
			var ex = renderFail(
				'{{#section}}_{{var}}_{{/section}}',
				{"section": 42});
			expect(ex is FormatException, isTrue);
			expect(ex.message, startsWith(BAD_VALUE_SECTION));
		});
		test('True', () {
			var output = parse('{{#section}}_ok_{{/section}}')
				.renderString({"section": true});
			expect(output, equals('_ok_'));
		});
		test('Nested', () {
			var output = parse('{{#section}}.{{var}}.{{#nested}}_{{nestedvar}}_{{/nested}}.{{/section}}')
				.renderString({"section": {
					"var": "bob",
					"nested": [
						{"nestedvar": "jim"},
						{"nestedvar": "sally"}
					]
				}});
			expect(output, equals('.bob._jim__sally_.'));
		});
	});

	group('Inverse Section', () {
		test('Map', () {
			var output = parse('{{^section}}_{{var}}_{{/section}}')
				.renderString({"section": {"var": "bob"}});
			expect(output, equals(''));
		});
		test('List', () {
			var output = parse('{{^section}}_{{var}}_{{/section}}')
				.renderString({"section": [{"var": "bob"}, {"var": "jim"}]});
			expect(output, equals(''));
		});
		test('Empty List', () {
			var output = parse('{{^section}}_ok_{{/section}}')
				.renderString({"section": []});
			expect(output, equals('_ok_'));
		});
		test('False', () {
			var output = parse('{{^section}}_ok_{{/section}}')
				.renderString({"section": false});
			expect(output, equals('_ok_'));
		});
		test('Invalid value', () {
			var ex = renderFail(
				'{{^section}}_{{var}}_{{/section}}',
				{"section": 42});
			expect(ex is FormatException, isTrue);
			expect(ex.message, startsWith(BAD_VALUE_INV_SECTION));
		});
		test('True', () {
			var output = parse('{{^section}}_ok_{{/section}}')
				.renderString({"section": true});
			expect(output, equals(''));
		});
	});

	group('Html escape', () {

		test('Escape at start', () {
			var output = parse('_{{var}}_')
				.renderString({"var": "&."});
			expect(output, equals('_&amp;._'));
		});

		test('Escape at end', () {
			var output = parse('_{{var}}_')
				.renderString({"var": ".&"});
			expect(output, equals('_.&amp;_'));
		});

		test('&', () {
			var output = parse('_{{var}}_')
				.renderString({"var": "&"});
			expect(output, equals('_&amp;_'));
		});

		test('<', () {
			var output = parse('_{{var}}_')
				.renderString({"var": "<"});
			expect(output, equals('_&lt;_'));
		});

		test('>', () {
			var output = parse('_{{var}}_')
				.renderString({"var": ">"});
			expect(output, equals('_&gt;_'));
		});

		test('"', () {
			var output = parse('_{{var}}_')
				.renderString({"var": '"'});
			expect(output, equals('_&quot;_'));
		});

		test("'", () {
			var output = parse('_{{var}}_')
				.renderString({"var": "'"});
			expect(output, equals('_&#x27;_'));
		});

		test("/", () {
			var output = parse('_{{var}}_')
				.renderString({"var": "/"});
			expect(output, equals('_&#x2F;_'));
		});

	});

	group('Invalid format', () {
		test('Mismatched tag', () {
			var source = '{{#section}}_{{var}}_{{/notsection}}';
			var ex = renderFail(source, {"section": {"var": "bob"}});
			expectFail(ex, 1, 25, 'Mismatched tag');
		});

		test('Unexpected EOF', () {
			var source = '{{#section}}_{{var}}_{{/section';
			var ex = renderFail(source, {"section": {"var": "bob"}});
			expectFail(ex, 1, source.length + 2, UNEXPECTED_EOF);
		});

		test('Bad tag name, open section', () {
			var source = r'{{#section$%$^%}}_{{var}}_{{/section}}';
			var ex = renderFail(source, {"section": {"var": "bob"}});
			expectFail(ex, null, null, BAD_TAG_NAME);
		});

		test('Bad tag name, close section', () {
			var source = r'{{#section}}_{{var}}_{{/section$%$^%}}';
			var ex = renderFail(source, {"section": {"var": "bob"}});
			expectFail(ex, null, null, BAD_TAG_NAME);
		});

		test('Bad tag name, variable', () {
			var source = r'{{#section}}_{{var$%$^%}}_{{/section}}';
			var ex = renderFail(source, {"section": {"var": "bob"}});
			expectFail(ex, null, null, BAD_TAG_NAME);
		});

	});

	group('Lenient', () {
		test('Odd section name', () {
			var output = parse(r'{{#section$%$^%}}_{{var}}_{{/section$%$^%}}', lenient: true)
				.renderString({r'section$%$^%': {'var': 'bob'}}, lenient: true);
			expect(output, equals('_bob_'));
		});

		test('Odd variable name', () {
			var output = parse(r'{{#section}}_{{var$%$^%}}_{{/section}}', lenient: true)
				.renderString({'section': {r'var$%$^%': 'bob'}}, lenient: true);
		});

		test('Null variable', () {
			var output = parse(r'{{#section}}_{{var}}_{{/section}}', lenient: true)
				.renderString({'section': {'var': null}}, lenient: true);
			expect(output, equals('__'));
		});

		test('Null section', () {
			var output = parse('{{#section}}_{{var}}_{{/section}}', lenient: true)
				.renderString({"section": null}, lenient: true);
			expect(output, equals(''));
		});

// Known failure
//		test('Null inverse section', () {
//			var output = parse('{{^section}}_{{var}}_{{/section}}', lenient: true)
//				.renderString({"section": null}, lenient: true);
//			expect(output, equals(''));
//		});

	});

	group('Escape tags', () {
		test('{{{ ... }}}', () {
			var output = parse('{{{blah}}}')
				.renderString({'blah': '&'});
			expect(output, equals('&'));
		});
		test('{{& ... }}', () {
			var output = parse('{{{blah}}}')
				.renderString({'blah': '&'});
			expect(output, equals('&'));
		});
	});

	group('Patial tag', () {
		test('Unimplemented', () {
			var fn = () => parse('{{>partial}}').renderString({});
			expect(fn, throwsUnimplementedError);
		});
	});

	group('Other', () {
		test('Standalone line', () {
			var val = parse('|\n{{#bob}}\n{{/bob}}\n|').renderString({'bob': []});
			expect(val, equals('|\n|'));
		});
	});

	group('Array indexing', () {
		test('Basic', () {
			var val = parse('{{array.1}}').renderString({'array': [1, 2, 3]});
			expect(val, equals('2'));
		});
		test('RangeError', () {
			var error = renderFail('{{array.5}}', {'array': [1, 2, 3]});
			expect(error, isRangeError);
		});
	});
}

renderFail(source, values) {
	try {
		parse(source).renderString(values);
		return null;
	} catch (e) {
		return e;
	}
}

expectFail(ex, int line, int column, [String msgStartsWith]) {
		expect(ex, isFormatException);
		expect(ex is MustacheFormatException, isTrue);
		if (line != null)
			expect(ex.line, equals(line));
		if (column != null)
			expect(ex.column, equals(column));
		if (msgStartsWith != null)
			expect(ex.message, startsWith(msgStartsWith));
}