diff --git a/examples/css.html b/examples/css.html index b7c3c8e..94c8280 100644 --- a/examples/css.html +++ b/examples/css.html @@ -1 +1 @@ -CSS example

Roses are red

Violets are blue

Poems are hard

I am sorry

\ No newline at end of file +CSS example

Roses are red

Violets are blue

Poems are hard

I am sorry

\ No newline at end of file diff --git a/examples/helloWorld.html b/examples/helloWorld.html index be18f2c..7958d5f 100644 --- a/examples/helloWorld.html +++ b/examples/helloWorld.html @@ -1,3 +1 @@ -Hello World!
hello world from the nav

Basic website made with MEML!

1 + 2 = 3

BODMAS: -15

Brackets: 21

This string contains \"Excaped characters\"

Hello TrickyPR. This comes from a component!

Test

Our website! -

Hello from an imported html file!

-

Hello TrickyPR

Hello _trickypr

Who are you?!

Count: 0

Count: 1

Count: 2

Count: 3

Count: 4

Count: 5

fine \ No newline at end of file +Hello World!
hello world from the nav

Basic website made with MEML!

1 + 2 = 3

BODMAS: -15

Brackets: 21

This string contains \"Excaped characters\"

Hello TrickyPR. This comes from a component!

Test

Our website!

Hello TrickyPR

Hello _trickypr

Who are you?!

Count: 0

Count: 1

Count: 2

Count: 3

Count: 4

Count: 5

fine \ No newline at end of file diff --git a/examples/newFolder/css.html b/examples/newFolder/css.html index 3a984a8..94c8280 100644 --- a/examples/newFolder/css.html +++ b/examples/newFolder/css.html @@ -1 +1 @@ -CSS example

Roses are red

Violets are blue

Poems are hard

I am sorry

\ No newline at end of file +CSS example

Roses are red

Violets are blue

Poems are hard

I am sorry

\ No newline at end of file diff --git a/package.json b/package.json index cf35239..526bb19 100644 --- a/package.json +++ b/package.json @@ -27,7 +27,7 @@ "ast": "ts-node ./scripts/GenerateAst.ts && prettier . --write", "app": "ts-node ./src/app.ts", "build": "tsc && echo '#!/usr/bin/env node\n' > tmpfile && cat ./dist/app.js >> tmpfile && mv tmpfile ./dist/app.js", - "build:docs": "typedoc --tsconfig tsconfig.json", + "docs": "typedoc --tsconfig tsconfig.json", "examples": "yarn app --file ./css.meml --file ./helloWorld.meml --file newFolder/css.meml --src ./examples --out ./examples", "prepublishOnly": "yarn build", "quality": "jscpd src/" diff --git a/src/core.ts b/src/core.ts index b0846ff..18df8c7 100644 --- a/src/core.ts +++ b/src/core.ts @@ -64,11 +64,11 @@ import { * * # Project management * - * TODO: Should config be moved somewhere else? + * @TODO Should config be moved somewhere else? * - * TODO: Should builds be moved into separate functions? + * @TODO Should builds be moved into separate functions? * - * TODO: Move error reporting out of this class. + * @TODO Move error reporting out of this class. */ export class MemlCore { /** @@ -150,16 +150,24 @@ export class MemlCore { * for parsing */ tokenize(source: string, file = ''): Token[] { - const scanner = new Scanner(source, file) - return scanner.scanTokens() + try { + const scanner = new Scanner(source, file) + return scanner.scanTokens() + } catch (e) { + throw new Error(`${e.message}\n MemlCore.tokenize`) + } } /** * Converts the input tokens to an AST tree with a PageStmt as its root */ parse(tokens: Token[], file = ''): PageStmt { - const parser = new Parser(tokens, file) - return parser.parse() + try { + const parser = new Parser(tokens, file) + return parser.parse() + } catch (e) { + throw new Error(`${e.message}\n MemlCore.parse`) + } } /** @@ -168,8 +176,12 @@ export class MemlCore { * May write files to disk depending on your settings for `shouldLink` */ targetWeb(page: PageStmt, path = 'memory.meml'): Promise { - const target = new Web(path) - return target.convert(page) + try { + const target = new Web(path) + return target.convert(page) + } catch (e) { + throw new Error(`${e.message}\n MemlCore.targetWeb`) + } } tokenizeAndParse(source: string, file = ''): PageStmt { @@ -199,6 +211,11 @@ export class MemlCore { return this.sourceToWeb((await readFile(path)).toString(), path) } + /** + * Resets all errors generated by the compiler and linker cache. **Do not use** + * between files, only between compilations. Use `MemlCore.resetErrors()` + * between files. + */ static reset(): void { this.resetErrors() resetLinker() @@ -207,11 +224,18 @@ export class MemlCore { // ------------------------------------------------------------ // Error functions + /** + * Resets `MemlCore.hadError` and `MemlCore.errors` + */ static resetErrors(): void { this.hadError = false this.errors = '' } + /** + * Internal error reporting function for reporting an error at a specific + * token + */ static errorAtToken(token: Token, message: string, file = ''): void { if (token.type === TokenType.EOF) { this.report(token.line, ' at end', message, '', file) @@ -226,10 +250,17 @@ export class MemlCore { } } + /** + * Internal error reporting function + */ static error(line: number, message: string, file = ''): void { this.report(line, '', message, file) } + /** + * Internal error reporting function for reporting an linter warning at a specific + * token + */ static linterAtToken(token: Token, message: string): void { this.warn( token.line, @@ -240,10 +271,16 @@ export class MemlCore { ) } + /** + * Internal warning function + */ static generalWarning(line: number, message: string): void { this.warn(line, 'General', '', message) } + /** + * Private error reporting function + */ private static report( line: number, where: string, @@ -264,6 +301,9 @@ export class MemlCore { }] Error${where}: ${message}\n${this.formatContext(context)}\n` } + /** + * Private warning function + */ private static warn( line: number, type: 'Linter' | 'General', @@ -284,10 +324,16 @@ export class MemlCore { )}\n` } + /** + * Internal error formatting function + */ static formatContext(context: string): string { return ` ┃${context.replace(/\n/g, '\n ┃')}` } + /** + * Register a new loader for linking and rendering + */ static registerLoader(Loader: ILoader): void { this.globalLoaders.push(Loader) } diff --git a/src/parser/AstNodes.ts b/src/parser/AstNodes.ts new file mode 100644 index 0000000..787c964 --- /dev/null +++ b/src/parser/AstNodes.ts @@ -0,0 +1,2 @@ +export * from './Expr' +export * from './Stmt' diff --git a/src/parser/index.ts b/src/parser/index.ts index db35884..bc14908 100644 --- a/src/parser/index.ts +++ b/src/parser/index.ts @@ -1 +1,2 @@ +export * as AstNodes from './AstNodes' export * from './Parser' diff --git a/src/targets/Targets.ts b/src/targets/Targets.ts new file mode 100644 index 0000000..cd09ae8 --- /dev/null +++ b/src/targets/Targets.ts @@ -0,0 +1,2 @@ +export * from './Web' +export * from './shared' diff --git a/src/targets/imports.ts b/src/targets/imports.ts index 189710e..ac07c76 100644 --- a/src/targets/imports.ts +++ b/src/targets/imports.ts @@ -2,8 +2,9 @@ import { readFile } from 'fs/promises' import { dirname, join } from 'path' import fetch from 'node-fetch' -import { MemlCore, relativeLink } from '../index' +import { MemlCore } from '../index' import { ImportStmt } from '../parser/Stmt' +import { relativeLink } from './loaders' export async function contentImport({ isUrl, diff --git a/src/targets/index.ts b/src/targets/index.ts index 5596768..be86e90 100644 --- a/src/targets/index.ts +++ b/src/targets/index.ts @@ -1,3 +1,17 @@ -export * from './Web' -export * from './loaders' -export * from './shared' +export * as Targets from './Targets' + +/** + * Loaders are the method of resolving and loading files into the MEML web targeter. + * The easiest way to add a new language to the web target, is to add a custom + * loader. All loaders must implement {@Link ILoader} and all necessary + * methods. + * + * + * + * Additionally, if you want to use a custom loader system (e.g. webpack), you + * would implement ILoader, wipe {@Link MemlCore.globalLoaders} and add your + * own loader + * + * @TODO Migrate linker.ts to a class that can be extended and overridden for additional support of other builders (e.g. webpack) + */ +export * as Loaders from './loaders' diff --git a/src/targets/shared/TargetBase.ts b/src/targets/shared/TargetBase.ts index 3a616a4..e4710c8 100644 --- a/src/targets/shared/TargetBase.ts +++ b/src/targets/shared/TargetBase.ts @@ -2,6 +2,10 @@ import { BinaryExpr } from '../../parser/Expr' import { TokenType } from '../../scanner/TokenTypes' import { Environment, EnvStore, EnvValidTypes } from './Environment' +/** + * This is an internal class for creating a new target. You can extend it to create + * a new target. Expected to implement ExprVisitor and StmtVisitor. See `Web` + */ export class TargetBase { environment = new Environment() exports = new Map() diff --git a/tsconfig.json b/tsconfig.json index 96c1481..1dec9cb 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -18,7 +18,7 @@ }, "include": ["src/**/*"], "typedocOptions": { - "entryPoints": ["src/core.ts"], + "entryPoints": ["src/index.ts"], "out": "docs-dist" } }