Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fontoxpath:evaluate can't see functions defined in XQuery, but can see those defined with registerCustomXPathFunction #513

Open
rrthomas opened this issue Jul 22, 2022 · 3 comments

Comments

@rrthomas
Copy link
Contributor

Calling fontoxpath:evaluate, I am getting errors like this:

Error: XPST0017: Function Q{https://github.com/rrthomas/ruth/raw/main/ruth.dtd}r
elative-path with arity of 1 not registered. Did you mean "Q{https://github.com/
rrthomas/ruth/raw/main/ruth.dtd}real-path (xs:string)"?

Here, ruth:real-path (the function suggested) is defined with registerCustomXPathFunction, while ruth:relative-path (the function that the evaluation can't find) is defined in XQuery that has been loaded with registerXQueryModule. I don't understand why one is visible to fontoxpath:evaluate but not the other.

I pushed a branch of my project that illustrates the problem when you run npm test, but I quite understand if that is too much code to go through—I can try to prepare a MWE if that's necessary.

@DrRataplan
Copy link
Collaborator

Hey Reuben,

That is an old issue: functions that are declared with registerCustomXPathFunction are available globally. No real reason for this besides us implementing this before we've even giving XQuery a thought.

Not sure what to do here to be honest. I mean, on one hand, we can just re-import the modules-in-scope from the module that calls fontoxpath:evaluate automatically: so if the outer script contains import module namespace xxx="yyy";, also import that module when executing the fontoxpath:evaluate. This feels developer-friendly, but also not really predictable: if the queries are dynamic, they would depend on how they are used. In some contexts they would be OK, in others they would not.

On the other hand, you could add an explicit module import: fontoxpath:evaluate('import module namespace xxx="yyy"; xxx:my-function(.)', map{'.', .}). No as developer-friendly, but more explicit and predictable.

Seeing as you are basically half of the (known) user-base of this function (Fonto is the other user 😉), I'm open for discussion here! What are your thoughts?

@rrthomas
Copy link
Contributor Author

Thanks very much for your detailed, helpful and friendly reply.

My perspective is as follows: on the one hand, Ruth (my project) is basically a wrapper around XQuery (so, fontoxpath), and currently a proportion of the code is simply workarounds for gaps in fontoxpath's XQuery functionality. (This is no disrespect to fontoxpath: I seem to have a tendency to write small programs much of whose code consists of workarounds for whatever libraries I'm using.) Hence, I would like fontoxpath to be as complete an implementation of XQuery/XPath as possible.

On the other hand, I have fairly limited use cases for Ruth, so I am not testing a wide range of XQuery functionality. You could say that at present my use of XQuery is quite "deep" (I use most of the different "mechanisms") but not very "broad" (e.g. I don't use a wide range of functions).

So overall, I am happiest if over time I can reduce the amount of workaround/polyfill code I have in Ruth with principled additions to fontoxpath.

In this particular case, I tried using your tip, and indeed that makes my custom functions visible; but I then have a similar problem with a variable ruth_element which is reported as declared but not in scope. It's defined in my variables hash passed to evaluateXPath*, so why can't fontoxpath:evaluate see it?

@rrthomas
Copy link
Contributor Author

I have updated my fontoxpath-evaluate branch of Ruth to add the import module namespace statements where needed.

I find that I would also need to import other modules dynamically (for example in my cookbook example/test). This suggests that I really want your "automagic" fix above.

It would be good to better understand the downsides of doing that. I would imagine that normally I would want fontoxpath:evaluate to run in the same context as that in which it is called; though I can see that it would be useful to be able to reset/change the context.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants