Skip to content

Commit

Permalink
Print and rethrow errors thrown during parsing in registerXQueryModule
Browse files Browse the repository at this point in the history
This fixes parse errors in this API throwing out the raw StackTraceEntry
object, which is not a proper error.

Fixes #628
  • Loading branch information
bwrrp committed Feb 6, 2024
1 parent 07c10cb commit f54b07c
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 34 deletions.
21 changes: 13 additions & 8 deletions src/registerXQueryModule.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,12 +47,17 @@ import { NamespaceResolver } from './types/Options';
*/
export default function registerXQueryModule(
moduleString: string,
options: { debug: boolean } = { debug: false },
options: { debug: boolean } = { debug: false }

Check failure on line 50 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 50 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
): string {
const parsedModule = parseExpression(moduleString, {
allowXQuery: true,
debug: options['debug'],
});
let parsedModule;
try {
parsedModule = parseExpression(moduleString, {
allowXQuery: true,
debug: options['debug'],
});
} catch (error) {
printAndRethrowError(moduleString, error);
}

annotateAst(parsedModule, new AnnotationContext(undefined));

Expand All @@ -72,8 +77,8 @@ export default function registerXQueryModule(
namespaceResolver,
Object.create(null),
BUILT_IN_NAMESPACE_URIS.FUNCTIONS_NAMESPACE_URI,
createDefaultFunctionNameResolver(BUILT_IN_NAMESPACE_URIS.FUNCTIONS_NAMESPACE_URI),
),
createDefaultFunctionNameResolver(BUILT_IN_NAMESPACE_URIS.FUNCTIONS_NAMESPACE_URI)

Check failure on line 80 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 80 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
)

Check failure on line 81 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 81 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
);

staticContext.registerNamespace(moduleTargetPrefix, moduleTargetNamespaceURI);
Expand All @@ -89,7 +94,7 @@ export default function registerXQueryModule(
moduleDeclaration.functionDeclarations.forEach(({ namespaceURI }) => {
if (moduleTargetNamespaceURI !== namespaceURI) {
throw new Error(
'XQST0048: Functions and variables declared in a module must reside in the module target namespace.',
'XQST0048: Functions and variables declared in a module must reside in the module target namespace.'

Check failure on line 97 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 97 in src/registerXQueryModule.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
);
}
});
Expand Down
61 changes: 35 additions & 26 deletions test/specs/parsing/registerXQueryModule.tests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ declare %public function test:hello ($a) {
null,
null,
null,
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE },
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE }

Check failure on line 81 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 81 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
);

chai.assert.deepEqual(result, []);
Expand Down Expand Up @@ -112,8 +112,8 @@ declare function x:fn () external;`);
null,
undefined,
undefined,
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE },
),
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE }

Check failure on line 115 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 115 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
)

Check failure on line 116 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 116 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
).to.throw('XPST0017');

// Now register it
Expand All @@ -124,7 +124,7 @@ declare function x:fn () external;`);
},
[],
'item()',
() => 'meep',
() => 'meep'

Check failure on line 127 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 127 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
);

chai.expect(
Expand All @@ -134,8 +134,8 @@ declare function x:fn () external;`);
null,
undefined,
undefined,
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE },
),
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE }

Check failure on line 137 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 137 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
)

Check failure on line 138 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`

Check failure on line 138 in test/specs/parsing/registerXQueryModule.tests.ts

View workflow job for this annotation

GitHub Actions / Linting

Insert `,`
).to.equal('meep');
});

Expand All @@ -158,7 +158,7 @@ declare function x:fn () external;`);
},
[],
'xs:string',
() => 'meep',
() => 'meep'
);

chai.expect(() =>
Expand All @@ -168,8 +168,8 @@ declare function x:fn () external;`);
null,
undefined,
undefined,
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE },
),
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE }
)
).to.throw('External function declaration types do not match actual function');
});

Expand All @@ -192,7 +192,7 @@ declare function x:fn () external;`);
},
['xs:string'],
'item()',
() => 'meep',
() => 'meep'
);

chai.expect(() =>
Expand All @@ -202,17 +202,17 @@ declare function x:fn () external;`);
null,
undefined,
undefined,
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE },
),
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE }
)
).to.throw('External function declaration types do not match actual function');
});

it('does not support external function declarations for updating functions', () => {
chai.expect(() =>
registerXQueryModule(
`module namespace x = 'http://www.example.com';
declare %updating function x:updating-fn () external;`,
),
declare %updating function x:updating-fn () external;`
)
).to.throw('Updating external function declarations are not supported');
});

Expand All @@ -224,18 +224,18 @@ declare function x:fn () external;`);
},
[],
'item()',
() => 'meep',
() => 'meep'
);

chai.expect(() =>
registerXQueryModule(
`module namespace x = 'http://www.example.com';
declare function x:duplicate-fn () {
'maap'
};`,
),
};`
)
).to.throw(
'XQST0049: The function or variable "Q{http://www.example.com}duplicate-fn" is declared more than once.',
'XQST0049: The function or variable "Q{http://www.example.com}duplicate-fn" is declared more than once.'
);
});

Expand All @@ -247,12 +247,12 @@ declare function x:fn () external;`);
},
[],
'item()',
() => 'meep',
() => 'meep'
);

registerXQueryModule(
`module namespace x = 'http://www.example.com';
declare function x:pre-registered-fn () external;`,
declare function x:pre-registered-fn () external;`
);

chai.expect(
Expand All @@ -262,8 +262,8 @@ declare function x:fn () external;`);
null,
undefined,
undefined,
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE },
),
{ language: evaluateXPath.XQUERY_3_1_LANGUAGE }
)
).to.equal('meep');
});

Expand All @@ -288,9 +288,9 @@ $foo:var`,
null,
null,
undefined,
xQueryOptions,
xQueryOptions
),
'hello world',
'hello world'
);
});

Expand All @@ -316,7 +316,7 @@ declare function bar:baz() {

chai.assert.equal(
evaluateXPathToString(`bar:baz()`, null, null, null, xQueryOptions),
'hello world',
'hello world'
);
});

Expand All @@ -342,7 +342,16 @@ declare function bar:baz() {

chai.assert.throws(
() => evaluateXPathToString(`bar:baz()`, null, null, null, xQueryOptions),
'XPST0017',
'XPST0017'
);
});

it('throws a proper error for parse errors', () => {
chai.expect(() => {
registerXQueryModule(
`declare function local:one() { 1 }(:missing semicolon:)
declare function local:two() { 2 };`
);
}).to.throw('XPST0003: Failed to parse script. Expected ;');
});
});

0 comments on commit f54b07c

Please sign in to comment.