Ans integration preparation

This commit is contained in:
anhefti 2021-05-20 12:52:18 +02:00
parent d111fd4f49
commit 58064de2e8
2 changed files with 96 additions and 27 deletions

View file

@ -20,10 +20,16 @@ import org.apache.commons.lang3.StringUtils;
import org.joda.time.DateTime; import org.joda.time.DateTime;
import org.springframework.cache.CacheManager; import org.springframework.cache.CacheManager;
import org.springframework.core.env.Environment; import org.springframework.core.env.Environment;
import org.springframework.http.client.ClientHttpRequestFactory;
import org.springframework.security.oauth2.client.OAuth2RestTemplate;
import org.springframework.security.oauth2.client.token.grant.client.ClientCredentialsResourceDetails;
import ch.ethz.seb.sebserver.ClientHttpRequestFactoryService;
import ch.ethz.seb.sebserver.gbl.api.APIMessage; import ch.ethz.seb.sebserver.gbl.api.APIMessage;
import ch.ethz.seb.sebserver.gbl.async.AsyncService; import ch.ethz.seb.sebserver.gbl.async.AsyncService;
import ch.ethz.seb.sebserver.gbl.client.ClientCredentialService;
import ch.ethz.seb.sebserver.gbl.client.ClientCredentials; import ch.ethz.seb.sebserver.gbl.client.ClientCredentials;
import ch.ethz.seb.sebserver.gbl.client.ProxyData;
import ch.ethz.seb.sebserver.gbl.model.Domain.LMS_SETUP; import ch.ethz.seb.sebserver.gbl.model.Domain.LMS_SETUP;
import ch.ethz.seb.sebserver.gbl.model.exam.Chapters; import ch.ethz.seb.sebserver.gbl.model.exam.Chapters;
import ch.ethz.seb.sebserver.gbl.model.exam.Exam; import ch.ethz.seb.sebserver.gbl.model.exam.Exam;
@ -45,11 +51,18 @@ import ch.ethz.seb.sebserver.webservice.servicelayer.lms.impl.AbstractCachedCour
public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements LmsAPITemplate { public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements LmsAPITemplate {
// TODO add needed dependencies here // TODO add needed dependencies here
private final ClientHttpRequestFactoryService clientHttpRequestFactoryService;
private final ClientCredentialService clientCredentialService;
private final APITemplateDataSupplier apiTemplateDataSupplier; private final APITemplateDataSupplier apiTemplateDataSupplier;
private final Long lmsSetupId; private final Long lmsSetupId;
protected AnsLmsAPITemplate( protected AnsLmsAPITemplate(
// TODO if you need more dependencies inject them here and set the reference // TODO if you need more dependencies inject them here and set the reference
final ClientHttpRequestFactoryService clientHttpRequestFactoryService,
final ClientCredentialService clientCredentialService,
final APITemplateDataSupplier apiTemplateDataSupplier, final APITemplateDataSupplier apiTemplateDataSupplier,
final AsyncService asyncService, final AsyncService asyncService,
final Environment environment, final Environment environment,
@ -57,6 +70,8 @@ public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements Lms
super(asyncService, environment, cacheManager); super(asyncService, environment, cacheManager);
this.clientHttpRequestFactoryService = clientHttpRequestFactoryService;
this.clientCredentialService = clientCredentialService;
this.apiTemplateDataSupplier = apiTemplateDataSupplier; this.apiTemplateDataSupplier = apiTemplateDataSupplier;
this.lmsSetupId = apiTemplateDataSupplier.getLmsSetup().id; this.lmsSetupId = apiTemplateDataSupplier.getLmsSetup().id;
} }
@ -194,35 +209,36 @@ public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements Lms
final String quizName = filterMap.getString(QuizData.FILTER_ATTR_QUIZ_NAME); final String quizName = filterMap.getString(QuizData.FILTER_ATTR_QUIZ_NAME);
final DateTime quizFromTime = (filterMap != null) ? filterMap.getQuizFromTime() : null; final DateTime quizFromTime = (filterMap != null) ? filterMap.getQuizFromTime() : null;
// TODO get all course / quiz data from remote LMS that matches the filter criteria.
// put loaded QuizData to the cache: super.putToCache(quizDataCollection);
// before returning it.
return () -> { return () -> {
// TODO get all course / quiz data from remote LMS that matches the filter criteria.
// put loaded QuizData to the cache: super.putToCache(quizDataCollection);
// before returning it.
throw new RuntimeException("TODO"); throw new RuntimeException("TODO");
}; };
} }
@Override @Override
protected Supplier<Collection<QuizData>> quizzesSupplier(final Set<String> ids) { protected Supplier<Collection<QuizData>> quizzesSupplier(final Set<String> ids) {
// TODO get all quiz / course data for specified identifiers from remote LMS
// and put it to the cache: super.putToCache(quizDataCollection);
// before returning it.
return () -> { return () -> {
// TODO get all quiz / course data for specified identifiers from remote LMS
// and put it to the cache: super.putToCache(quizDataCollection);
// before returning it.
throw new RuntimeException("TODO"); throw new RuntimeException("TODO");
}; };
} }
@Override @Override
protected Supplier<QuizData> quizSupplier(final String id) { protected Supplier<QuizData> quizSupplier(final String id) {
// TODO get the specified quiz / course data for specified identifier from remote LMS
// and put it to the cache: super.putToCache(quizDataCollection);
// before returning it.
return () -> { return () -> {
// TODO get the specified quiz / course data for specified identifier from remote LMS
// and put it to the cache: super.putToCache(quizDataCollection);
// before returning it.
throw new RuntimeException("TODO"); throw new RuntimeException("TODO");
}; };
} }
@ -230,10 +246,11 @@ public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements Lms
@Override @Override
protected Supplier<ExamineeAccountDetails> accountDetailsSupplier(final String examineeSessionId) { protected Supplier<ExamineeAccountDetails> accountDetailsSupplier(final String examineeSessionId) {
// TODO get the examinee's account details by the given examineeSessionId from remote LMS.
// Currently only the name is needed to display on monitoring view.
return () -> { return () -> {
// TODO get the examinee's account details by the given examineeSessionId from remote LMS.
// Currently only the name is needed to display on monitoring view.
throw new RuntimeException("TODO"); throw new RuntimeException("TODO");
}; };
} }
@ -250,10 +267,14 @@ public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements Lms
final String quizId = exam.externalId; final String quizId = exam.externalId;
// TODO get the SEB client restrictions that are currently set on the remote LMS for return Result.tryCatch(() -> {
// the given quiz / course derived from the given exam
return Result.ofRuntimeError("TODO"); // TODO get the SEB client restrictions that are currently set on the remote LMS for
// the given quiz / course derived from the given exam
throw new RuntimeException("TODO");
});
} }
@Override @Override
@ -261,11 +282,15 @@ public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements Lms
final String externalExamId, final String externalExamId,
final SEBRestriction sebRestrictionData) { final SEBRestriction sebRestrictionData) {
// TODO apply the given sebRestrictionData settings as current SEB client restriction setting return Result.tryCatch(() -> {
// to the remote LMS for the given quiz / course.
// Mainly SEBRestriction.configKeys and SEBRestriction.browserExamKeys
return Result.ofRuntimeError("TODO"); // TODO apply the given sebRestrictionData settings as current SEB client restriction setting
// to the remote LMS for the given quiz / course.
// Mainly SEBRestriction.configKeys and SEBRestriction.browserExamKeys
throw new RuntimeException("TODO");
});
} }
@Override @Override
@ -273,10 +298,44 @@ public class AnsLmsAPITemplate extends AbstractCachedCourseAccess implements Lms
final String quizId = exam.externalId; final String quizId = exam.externalId;
// TODO Release respectively delete all SEB client restrictions for the given return Result.tryCatch(() -> {
// course / quize on the remote LMS.
return Result.ofRuntimeError("TODO"); // TODO Release respectively delete all SEB client restrictions for the given
// course / quize on the remote LMS.
throw new RuntimeException("TODO");
});
}
// TODO: This is an example of how to create a RestTemplate for the service to access the LMS API
// The example deals with a Http based API that is secured by an OAuth2 client-credential flow.
// You might need some different template, then you have to adapt this code
// To your needs.
private OAuth2RestTemplate createRestTemplate(final String accessTokenRequestPath) {
final LmsSetup lmsSetup = this.apiTemplateDataSupplier.getLmsSetup();
final ClientCredentials credentials = this.apiTemplateDataSupplier.getLmsClientCredentials();
final ProxyData proxyData = this.apiTemplateDataSupplier.getProxyData();
final CharSequence plainClientId = credentials.clientId;
final CharSequence plainClientSecret = this.clientCredentialService
.getPlainClientSecret(credentials)
.getOrThrow();
final ClientCredentialsResourceDetails details = new ClientCredentialsResourceDetails();
details.setAccessTokenUri(lmsSetup.lmsApiUrl + accessTokenRequestPath);
details.setClientId(plainClientId.toString());
details.setClientSecret(plainClientSecret.toString());
final ClientHttpRequestFactory clientHttpRequestFactory = this.clientHttpRequestFactoryService
.getClientHttpRequestFactory(proxyData)
.getOrThrow();
final OAuth2RestTemplate template = new OAuth2RestTemplate(details);
template.setRequestFactory(clientHttpRequestFactory);
return template;
} }
} }

View file

@ -13,7 +13,9 @@ import org.springframework.context.annotation.Lazy;
import org.springframework.core.env.Environment; import org.springframework.core.env.Environment;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import ch.ethz.seb.sebserver.ClientHttpRequestFactoryService;
import ch.ethz.seb.sebserver.gbl.async.AsyncService; import ch.ethz.seb.sebserver.gbl.async.AsyncService;
import ch.ethz.seb.sebserver.gbl.client.ClientCredentialService;
import ch.ethz.seb.sebserver.gbl.model.institution.LmsSetup.LmsType; import ch.ethz.seb.sebserver.gbl.model.institution.LmsSetup.LmsType;
import ch.ethz.seb.sebserver.gbl.profile.WebServiceProfile; import ch.ethz.seb.sebserver.gbl.profile.WebServiceProfile;
import ch.ethz.seb.sebserver.gbl.util.Result; import ch.ethz.seb.sebserver.gbl.util.Result;
@ -33,15 +35,21 @@ import ch.ethz.seb.sebserver.webservice.servicelayer.lms.LmsAPITemplateFactory;
* as usual. Just add the additionally needed dependencies used to build a AnsLmsAPITemplateFactory */ * as usual. Just add the additionally needed dependencies used to build a AnsLmsAPITemplateFactory */
public class AnsLmsAPITemplateFactory implements LmsAPITemplateFactory { public class AnsLmsAPITemplateFactory implements LmsAPITemplateFactory {
private final ClientHttpRequestFactoryService clientHttpRequestFactoryService;
private final ClientCredentialService clientCredentialService;
private final AsyncService asyncService; private final AsyncService asyncService;
private final Environment environment; private final Environment environment;
private final CacheManager cacheManager; private final CacheManager cacheManager;
public AnsLmsAPITemplateFactory( public AnsLmsAPITemplateFactory(
final ClientHttpRequestFactoryService clientHttpRequestFactoryService,
final ClientCredentialService clientCredentialService,
final AsyncService asyncService, final AsyncService asyncService,
final Environment environment, final Environment environment,
final CacheManager cacheManager) { final CacheManager cacheManager) {
this.clientHttpRequestFactoryService = clientHttpRequestFactoryService;
this.clientCredentialService = clientCredentialService;
this.asyncService = asyncService; this.asyncService = asyncService;
this.environment = environment; this.environment = environment;
this.cacheManager = cacheManager; this.cacheManager = cacheManager;
@ -56,6 +64,8 @@ public class AnsLmsAPITemplateFactory implements LmsAPITemplateFactory {
public Result<LmsAPITemplate> create(final APITemplateDataSupplier apiTemplateDataSupplier) { public Result<LmsAPITemplate> create(final APITemplateDataSupplier apiTemplateDataSupplier) {
return Result.tryCatch(() -> { return Result.tryCatch(() -> {
return new AnsLmsAPITemplate( return new AnsLmsAPITemplate(
this.clientHttpRequestFactoryService,
this.clientCredentialService,
apiTemplateDataSupplier, apiTemplateDataSupplier,
this.asyncService, this.asyncService,
this.environment, this.environment,