Sharebar?

LTI 1.3 clarifications

LTI 1.3 clarifications

I’m not sure if I’m bad at reading specs or whether some things are just ambiguous, but I was hoping someone could verify my understanding of a few LTI 1.3 issues.

1) For a given issuer, there can be multiple client_id values. Can the service URLs vary based on the client_id, or are they always linked only to the issuer?

2) Deployment ids are unique across the issuer, even if they’re associated with different client_ids. In other words, it’s safe to store deployments using issuer + deployment_id as the key (like in the php LTI library) and we don’t need to key it with the client_id.

3) Advantage access tokens are based on the issuer+client_id and scope, so a token cache should be keyed on issuer+client_id and scope (e.g. tokens don’t work for the entire issuer, just for one client_id).

4) If a launch is using LTI 1.3, a deep linking request will be version 2.0 request, and I don’t have to worry about supporting earlier formats of Deep Linking / Content Selection requests.

Also, some questions about the Grade Service.

5) Is it safe to assume the “lineitem” value for a link won’t change? As in, is it safe to cache this value rather than looking it up every time (like the php LTI library does). I ask because in LTI 1.1, Moodle changed the lti_sourcedid with every launch, which made it harder to cache.

6) From my understanding, if a “lineitem” value is passed, it means the LMS already has a grade column for that link. If there isn’t a “lineitem” value, but there is a “lineitem” scope, then the tool will need to call that service to create a lineitem before sending a grade. Is that correct? Or do we need to query the lineitem service first to see if there’s a column they just didn’t send?

7) If the course is copied in the LMS, and the links previously each had a single grade column associated, can a tool safely assume the LMS will associate the LMS links with the columns and send a “lineitem” with the launch? Or will the tool need to plan to query the “lineitems” service to find the grade column? If the latter, I’m assuming the “tag” or “resourceId” would be used to find the right lineitem. From the specs it sounds like “resourceId” would be the one to use, since it is preserved in course copies?

8) If a link has multiple line items associated with it, the specs make it sound like no “lineitem” will be passed, and there’s no indication that a lineitem might exist. In that case, I’m assuming the tool needs to query the lineitems service and use the “tag” or “resourceId” to see if a lineitem exists?

Thanks!

1) For a given issuer, there

1) For a given issuer, there can be multiple client_id values. Can the service URLs vary based on the client_id, or are they always linked only to the issuer?

Yes there can be multiple client_ids for an issuer pointing to the same tool. The way that you would make a distinction between them is by having an id in the in the OIDC login initiation url as a path or query parameter.

2) Deployment ids are unique across the issuer, even if they’re associated with different client_ids. In other words, it’s safe to store deployments using issuer + deployment_id as the key (like in the php LTI library) and we don’t need to key it with the client_id.

I would not make that assumption, it is made in the case of the PHP library because it currently only supports 1 client per issuer (this is something i intend to change and have a fix for, however it is a breaking change and not backwards compatible if people are already using the library)

3) Advantage access tokens are based on the issuer+client_id and scope, so a token cache should be keyed on issuer+client_id and scope (e.g. tokens don’t work for the entire issuer, just for one client_id).

That is correct. i would recommend using issuer+client_id+sha1(scopes) ir something similar as your cache key

4) If a launch is using LTI 1.3, a deep linking request will be version 2.0 request, and I don’t have to worry about supporting earlier formats of Deep Linking / Content Selection requests.

Deep linking 2.0 only supports LTI 1.3, Deep Linking 1.0 (or content item) is for LTI 1.0/1

5) Is it safe to assume the “lineitem” value for a link won’t change? As in, is it safe to cache this value rather than looking it up every time (like the php LTI library does). I ask because in LTI 1.1, Moodle changed the lti_sourcedid with every launch, which made it harder to cache.

Lineitem ids should not change and are safe to store for use later (this has to be the case so that flows like automated grading can be supported that return a grade at a different time to the initial launch)

6) From my understanding, if a “lineitem” value is passed, it means the LMS already has a grade column for that link. If there isn’t a “lineitem” value, but there is a “lineitem” scope, then the tool will need to call that service to create a lineitem before sending a grade. Is that correct? Or do we need to query the lineitem service first to see if there’s a column they just didn’t send?

The "lineitem" value will be sent if there is exactly one lineitem associated with the resource link, if there are more than one, then none are sent. I would recommend querying the lineitems container first to see if there is a lineitem before just creating another one.

7) If the course is copied in the LMS, and the links previously each had a single grade column associated, can a tool safely assume the LMS will associate the LMS links with the columns and send a “lineitem” with the launch? Or will the tool need to plan to query the “lineitems” service to find the grade column? If the latter, I’m assuming the “tag” or “resourceId” would be used to find the right lineitem. From the specs it sounds like “resourceId” would be the one to use, since it is preserved in course copies?

 You cannot guaruntee that the grade column will be copied with a course (most LMSs let you chose what you want copied over). If they were attached to the "resourceLinkId" (the platform's id) and copied then the new column should point to the new "resourceLinkId" given to the copied link. If you have attached a lineitem to a "resourceId" (tool's id) then that value will be the same after copy. However, columns linked using "resourceId" won't show in the "lineitem" value, because they are not attached to a platform resource link.

8) If a link has multiple line items associated with it, the specs make it sound like no “lineitem” will be passed, and there’s no indication that a lineitem might exist. In that case, I’m assuming the tool needs to query the lineitems service and use the “tag” or “resourceId” to see if a lineitem exists?

Yes, it would query the lineitems either by "tag", "resourceId", or "resourceLinkId" depending on your usecase. A reason to use each would be:

  • resourceLinkId - You have a resource unique to the resource link the platform gave you and only have one type of grade to pass back
  • resourceLinkId + tag - You have a resource unique to the resource link the platform gave you and have multiple types of grade (tag would tell you the type of grade) 
  • resourceId - You have a resource that can be accessed from many links in the platform and it only has one type of grade
  • resourceId + tag - You have a resource that can be accessed from many links in the platform and have multiple types of grade (tag would tell you the type of grade) 

 

Hope that answered your questions. There are still a couple of things lacking in the PHP 1.3 library which is where i'm guessing some of these questions have come from. There are a number of improvements I've been meaning to make, but haven't gotten round to. When i get some free time i will try to fix some thing like supporting multiple client_ids for an issuer and linking a lineitem to a resourceLinkId, or i'm happy to take pull requests from people wishing to contribute 

Thanks

Martin

Integrations software engineer @ Turnitin

    Thanks, that's very helpful!

    Thanks, that's very helpful!

    One more question: The LTI spec for Context claims mentions both Context.id and Context.id.history. How can id be both a string and an object, or am I misunderstanding how to read those?

    Context.id and Context.id

    Context.id and Context.id.history are subsitution variables, not deanitions of an object.

    What this means is that if a platform is told to send a tool a custom parameter with the value of $Context.id.history then they should replace it with the array that the substitution variable represents

    Hope that helps, and sorry for the slow reply

    A little followup on 1: You

    A little followup on 1: You said "The way that you would make a distinction between them is by having an id in the in the OIDC login initiation url as a path or query parameter.", but the LTI specs have client_id as an (optional) login parameter, which seems like it could be used for that.

    Do any of the LMSs that allow multiple client_ids for the same issuer not send that value?

    I do not know a definative

    I do not know a definative answer on this one, but I would plan for the assumption that you don't have the client_id at the initiation login and use it as extra clarification if you do

    Second followup on #1

    Sorry to reply on a 3 year old post, but this is the first (and seemingly only) resource I find, searching about LTI 1.3 client_id and urls. There was a second half to the question on #1, namely "Can the service URLs vary based on the client_id, or are they always linked only to the issuer?" I didn't see an answer to this. We are in the process of upgrading to 1.3, and in database design we are trying to figure out if the service URLs (authorization, token, and jwks endpoints) should be associated on the issuer level, or on the client level. It seems like based on the Dynamic Registration candidate spec (https://www.imsglobal.org/spec/lti-dr/v1p0) that these service URLs are consistent per the issuer, considering they are given in the platform configuration, rather than the tool configuration response (when you receive the client_id). I just wanted to double check that's right. Thanks!