adlnet / xAPI-Spec

The xAPI Specification describes communication about learner activity and experiences between technologies.
https://adlnet.gov/projects/xapi/
905 stars 405 forks source link

URLs as extension keys #942

Closed arnaudriegert closed 8 years ago

arnaudriegert commented 8 years ago

I'm building an LMS and I'm storing statements in a MongoDB database. MongoDB doesn't accept keys that contain dots (or dollar signs), because of the frequently used dot notation to access elements. Therefore, I'm not able to use an URL as a key for my extensions (in my case, context extensions). I see two options:

  1. Use an IRI, e.g. training-provider instead of http://id.tincanapi.com/extension/training-provider but I'm not sure it's valid and I may be faced with the case where there is no clear IRI
  2. Store my dict as an array of objects, like [{key: "http://id.tincanapi.com/extension/training-provider": value: "..."}].

Which do you think is best? Do you think it is a good thing for the specs to propose that keys should be IRIs?

creighton commented 8 years ago

I ran into the same issue for a demo last year. I chose something close to your second option. But instead of creating an array of keys and values, I just stringified the extensions value. I'm not sure how performance would be at large scale, but here's the functions if you are interested: https://github.com/creighton/itsec2015-reporting-app/blob/master/lib/util.js

arnaudriegert commented 8 years ago

@creighton Thanks, that's an interesting idea, the issue is that I won't be able to perform queries based on extension values.

creighton commented 8 years ago

Yep, good point. Sorry I was no help.

brianjmiller commented 8 years ago

On Thu, Jun 23, 2016 at 10:48 AM, Arnaud Riegert notifications@github.com wrote:

I'm building an LMS and I'm storing statements in a MongoDB database. MongoDB doesn't accept keys that contain dots (or dollar signs), because of the frequently used dot notation to access elements. Therefore, I'm not able to use an URL as a key for my extensions (in my case, context extensions). I see two options:

  1. Use an IRI, e.g. training-provider instead of http://id.tincanapi.com/extension/training-provider but I'm not sure it's valid and I may be faced with the case where there is no clear IRI

"training-provider" wouldn't be a valid IRI, and an extensions object property must be an IRI. Minimally you'd have to add a scheme to the beginning, I don't know if that would break Mongo, presumably not since it doesn't include a '.'. See RFC 3987 and RFC 3986 for more. Also note that the xAPI specification suggests that any coined IRI should be created within a namespace that you have access to use or ownership of, and ideally it'll resolve to the metadata for that term, hence the Registry that your example came from.

  1. Store my dict as an array of objects, like [{key: " http://id.tincanapi.com/extension/training-provider": value: "..."}].

Which do you think is best?

Sorry I can't provide another solution for the Mongo side. But, you mentioned you're building an LMS (presumably that wasn't a typo for LRS?) in which case the LMS could easily store a mapping of IRI extension keys to non-IRI (localized) extension keys that would allow you to accomplish the same goal while the LRS would maintain the canonical source. You could even create a serialization/deserialization algorithm for the keys themselves, for instance URL encode the bits, they'd be stored doubly encoded, but that shouldn't matter unless you are trying to make them human readable (which is part of the point of using an IRI instead of something like a hash or UUID).

Do you think it is a good thing for the specs to propose that keys should be IRIs?

That ship has sailed, but even if it hadn't my answer would still be yes. It is the best solution that gets human readability (with internalization), resolvability (as an option), global uniqueness with ownership potential, no need for centralized registration, pre-existing well defined standardization and adoption, etc.

HTH,

Brian J. Miller Rustici Software brian.miller@experienceapi.com brianmiller@residualselfimage.com

garemoko commented 8 years ago

The easiest thing to do is probably just escape them with the HTML encoding sequence (.).

https://groups.google.com/forum/#!topic/mongodb-user/nlBxnhR-BWg

arnaudriegert commented 8 years ago

Thanks @brianjmiller for the explanations that's very helpful. There is no need for my models to be "directly" human-readable when they're in the database. I can indeed use a (de)serialization algorithm and use the HTML encoding sequence as suggested by @garemoko I feel your answers suffice to close the issue.