MOBILE-3661 grades: Migrate grades handlers
parent
cd6e93b9d1
commit
41f308e62e
|
@ -58,7 +58,7 @@ export class CoreLinkDirective implements OnInit {
|
|||
|
||||
// @todo: Handle split view?
|
||||
|
||||
this.element.addEventListener('click', (event) => {
|
||||
this.element.addEventListener('click', async (event) => {
|
||||
if (event.defaultPrevented) {
|
||||
return; // Link already treated, stop.
|
||||
}
|
||||
|
@ -77,7 +77,8 @@ export class CoreLinkDirective implements OnInit {
|
|||
if (CoreUtils.instance.isTrueOrOne(this.capture)) {
|
||||
href = CoreTextUtils.instance.decodeURI(href);
|
||||
|
||||
const treated = CoreContentLinksHelper.instance.handleLink(href, undefined, true, true);
|
||||
const treated = await CoreContentLinksHelper.instance.handleLink(href, undefined, true, true);
|
||||
|
||||
if (!treated) {
|
||||
this.navigate(href, openIn);
|
||||
}
|
||||
|
|
|
@ -58,6 +58,7 @@ export class CoreContentLinksHandlerBase implements CoreContentLinksHandler {
|
|||
* @param url The URL to treat.
|
||||
* @param params The params of the URL. E.g. 'mysite.com?id=1' -> {id: 1}
|
||||
* @param courseId Course ID related to the URL. Optional but recommended.
|
||||
* @param data Extra data to handle the URL.
|
||||
* @return List of (or promise resolved with list of) actions.
|
||||
*/
|
||||
getActions(
|
||||
|
@ -69,6 +70,8 @@ export class CoreContentLinksHandlerBase implements CoreContentLinksHandler {
|
|||
params: Params,
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
courseId?: number,
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
data?: unknown,
|
||||
): CoreContentLinksAction[] | Promise<CoreContentLinksAction[]> {
|
||||
return [];
|
||||
}
|
||||
|
|
|
@ -48,7 +48,7 @@ export interface CoreCourseOptionsHandler extends CoreDelegateHandler {
|
|||
* @return True or promise resolved with true if enabled.
|
||||
*/
|
||||
isEnabledForCourse(courseId: number,
|
||||
accessData: any, // @todo: define type.
|
||||
accessData: CoreCourseAccessData,
|
||||
navOptions?: CoreCourseUserAdminOrNavOptionIndexed,
|
||||
admOptions?: CoreCourseUserAdminOrNavOptionIndexed,
|
||||
): boolean | Promise<boolean>;
|
||||
|
@ -672,3 +672,6 @@ export class CoreCourseOptionsDelegateService extends CoreDelegate<CoreCourseOpt
|
|||
}
|
||||
|
||||
export class CoreCourseOptionsDelegate extends makeSingleton(CoreCourseOptionsDelegateService) {}
|
||||
|
||||
// @todo define
|
||||
export type CoreCourseAccessData = any;
|
||||
|
|
|
@ -14,9 +14,17 @@
|
|||
|
||||
import { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||
import { Routes } from '@angular/router';
|
||||
import { CoreContentLinksDelegate } from '@features/contentlinks/services/contentlinks-delegate';
|
||||
import { CoreCourseOptionsDelegate } from '@features/course/services/course-options-delegate';
|
||||
import { CoreMainMenuRoutingModule } from '@features/mainmenu/mainmenu-routing.module';
|
||||
import { CoreMainMenuTabRoutingModule } from '@features/mainmenu/mainmenu-tab-routing.module';
|
||||
import { CoreMainMenuDelegate } from '@features/mainmenu/services/mainmenu-delegate';
|
||||
import { CoreUserDelegate } from '@features/user/services/user-delegate';
|
||||
import { CoreGradesCourseOptionHandler } from './services/handlers/course-option';
|
||||
import CoreGradesMainMenuHandler, { CoreGradesMainMenuHandlerService } from './services/handlers/mainmenu';
|
||||
import { CoreGradesOverviewLinkHandler } from './services/handlers/overview-link';
|
||||
import { CoreGradesUserHandler } from './services/handlers/user';
|
||||
import { CoreGradesUserLinkHandler } from './services/handlers/user-link';
|
||||
|
||||
const routes: Routes = [
|
||||
{
|
||||
|
@ -26,8 +34,10 @@ const routes: Routes = [
|
|||
];
|
||||
|
||||
@NgModule({
|
||||
imports: [CoreMainMenuRoutingModule.forChild({ children: routes })],
|
||||
exports: [CoreMainMenuRoutingModule],
|
||||
imports: [
|
||||
CoreMainMenuTabRoutingModule.forChild(routes),
|
||||
CoreMainMenuRoutingModule.forChild({ children: routes }),
|
||||
],
|
||||
providers: [
|
||||
{
|
||||
provide: APP_INITIALIZER,
|
||||
|
@ -35,6 +45,10 @@ const routes: Routes = [
|
|||
deps: [],
|
||||
useValue: () => {
|
||||
CoreMainMenuDelegate.instance.registerHandler(CoreGradesMainMenuHandler.instance);
|
||||
CoreUserDelegate.instance.registerHandler(CoreGradesUserHandler.instance);
|
||||
CoreContentLinksDelegate.instance.registerHandler(CoreGradesUserLinkHandler.instance);
|
||||
CoreContentLinksDelegate.instance.registerHandler(CoreGradesOverviewLinkHandler.instance);
|
||||
CoreCourseOptionsDelegate.instance.registerHandler(CoreGradesCourseOptionHandler.instance);
|
||||
},
|
||||
},
|
||||
],
|
||||
|
|
|
@ -0,0 +1,113 @@
|
|||
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Injectable } from '@angular/core';
|
||||
import { CoreCourseProvider } from '@features/course/services/course';
|
||||
import {
|
||||
CoreCourseAccessData,
|
||||
CoreCourseOptionsHandler,
|
||||
CoreCourseOptionsHandlerData,
|
||||
} from '@features/course/services/course-options-delegate';
|
||||
import { CoreCourses, CoreCourseUserAdminOrNavOptionIndexed } from '@features/courses/services/courses';
|
||||
import { CoreEnrolledCourseDataWithExtraInfoAndOptions } from '@features/courses/services/courses-helper';
|
||||
import { makeSingleton } from '@singletons';
|
||||
import { CoreGrades } from '../grades';
|
||||
|
||||
/**
|
||||
* Course nav handler.
|
||||
*/
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class CoreGradesCourseOptionHandlerService implements CoreCourseOptionsHandler {
|
||||
|
||||
name = 'CoreGrades';
|
||||
priority = 400;
|
||||
|
||||
/**
|
||||
* Should invalidate the data to determine if the handler is enabled for a certain course.
|
||||
*
|
||||
* @param courseId The course ID.
|
||||
* @param navOptions Course navigation options for current user. See CoreCoursesProvider.getUserNavigationOptions.
|
||||
* @return Promise resolved when done.
|
||||
*/
|
||||
invalidateEnabledForCourse(courseId: number, navOptions?: CoreCourseUserAdminOrNavOptionIndexed): Promise<void> {
|
||||
if (navOptions && typeof navOptions.grades != 'undefined') {
|
||||
// No need to invalidate anything.
|
||||
return Promise.resolve();
|
||||
}
|
||||
|
||||
return CoreCourses.instance.invalidateUserCourses();
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the handler is enabled on a site level.
|
||||
*
|
||||
* @return Whether or not the handler is enabled on a site level.
|
||||
*/
|
||||
isEnabled(): Promise<boolean> {
|
||||
return Promise.resolve(true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Whether or not the handler is enabled for a certain course.
|
||||
*
|
||||
* @param courseId The course ID.
|
||||
* @param accessData Access type and data. Default, guest, ...
|
||||
* @param navOptions Course navigation options for current user. See CoreCoursesProvider.getUserNavigationOptions.
|
||||
* @return True or promise resolved with true if enabled.
|
||||
*/
|
||||
isEnabledForCourse(
|
||||
courseId: number,
|
||||
accessData: CoreCourseAccessData,
|
||||
navOptions?: CoreCourseUserAdminOrNavOptionIndexed,
|
||||
): boolean | Promise<boolean> {
|
||||
if (accessData && accessData.type == CoreCourseProvider.ACCESS_GUEST) {
|
||||
return false; // Not enabled for guests.
|
||||
}
|
||||
|
||||
if (navOptions && typeof navOptions.grades != 'undefined') {
|
||||
return navOptions.grades;
|
||||
}
|
||||
|
||||
return CoreGrades.instance.isPluginEnabledForCourse(courseId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the data needed to render the handler.
|
||||
*
|
||||
* @return Data or promise resolved with the data.
|
||||
*/
|
||||
getDisplayData(): CoreCourseOptionsHandlerData | Promise<CoreCourseOptionsHandlerData> {
|
||||
throw new Error('CoreGradesCourseOptionHandler.getDisplayData is not implemented');
|
||||
|
||||
// @todo
|
||||
// return {
|
||||
// title: 'core.grades.grades',
|
||||
// class: 'core-grades-course-handler',
|
||||
// component: CoreGradesCourseComponent,
|
||||
// };
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when a course is downloaded. It should prefetch all the data to be able to see the addon in offline.
|
||||
*
|
||||
* @param course The course.
|
||||
* @return Promise resolved when done.
|
||||
*/
|
||||
async prefetch(course: CoreEnrolledCourseDataWithExtraInfoAndOptions): Promise<void> {
|
||||
await CoreGrades.instance.getCourseGradesTable(course.id, undefined, undefined, true);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export class CoreGradesCourseOptionHandler extends makeSingleton(CoreGradesCourseOptionHandlerService) {}
|
|
@ -0,0 +1,57 @@
|
|||
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Injectable } from '@angular/core';
|
||||
import { CoreContentLinksHandlerBase } from '@features/contentlinks/classes/base-handler';
|
||||
import { CoreContentLinksAction } from '@features/contentlinks/services/contentlinks-delegate';
|
||||
import { CoreNavigator } from '@services/navigator';
|
||||
import { makeSingleton } from '@singletons';
|
||||
import { CoreGrades } from '../grades';
|
||||
|
||||
/**
|
||||
* Handler to treat links to overview courses grades.
|
||||
*/
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class CoreGradesOverviewLinkHandlerService extends CoreContentLinksHandlerBase {
|
||||
|
||||
name = 'CoreGradesOverviewLinkHandler';
|
||||
pattern = /\/grade\/report\/overview\/index.php/;
|
||||
|
||||
/**
|
||||
* Get the list of actions for a link (url).
|
||||
*
|
||||
* @return List of (or promise resolved with list of) actions.
|
||||
*/
|
||||
getActions(): CoreContentLinksAction[] | Promise<CoreContentLinksAction[]> {
|
||||
return [{
|
||||
action: siteId => {
|
||||
CoreNavigator.instance.navigateToSitePath('/grades', { siteId });
|
||||
},
|
||||
}];
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the handler is enabled for a certain site (site + user) and a URL.
|
||||
* If not defined, defaults to true.
|
||||
*
|
||||
* @param siteId The site ID.
|
||||
* @return Whether the handler is enabled for the URL and site.
|
||||
*/
|
||||
isEnabled(siteId: string): boolean | Promise<boolean> {
|
||||
return CoreGrades.instance.isCourseGradesEnabled(siteId);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export class CoreGradesOverviewLinkHandler extends makeSingleton(CoreGradesOverviewLinkHandlerService) {}
|
|
@ -0,0 +1,82 @@
|
|||
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Injectable } from '@angular/core';
|
||||
import { Params } from '@angular/router';
|
||||
import { CoreContentLinksAction } from '@features/contentlinks/services/contentlinks-delegate';
|
||||
import { CoreContentLinksHandlerBase } from '@features/contentlinks/classes/base-handler';
|
||||
import { CoreGrades } from '@features/grades/services/grades';
|
||||
import { CoreGradesHelper } from '@features/grades/services/grades-helper';
|
||||
import { makeSingleton } from '@singletons';
|
||||
|
||||
/**
|
||||
* Handler to treat links to user grades.
|
||||
*/
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class CoreGradesUserLinkHandlerService extends CoreContentLinksHandlerBase {
|
||||
|
||||
name = 'CoreGradesUserLinkHandler';
|
||||
pattern = /\/grade\/report(\/user)?\/index.php/;
|
||||
|
||||
/**
|
||||
* Get the list of actions for a link (url).
|
||||
*
|
||||
* @param siteIds List of sites the URL belongs to.
|
||||
* @param url The URL to treat.
|
||||
* @param params The params of the URL. E.g. 'mysite.com?id=1' -> {id: 1}
|
||||
* @param courseId Course ID related to the URL. Optional but recommended.
|
||||
* @param data Extra data to handle the URL.
|
||||
* @return List of (or promise resolved with list of) actions.
|
||||
*/
|
||||
getActions(
|
||||
siteIds: string[],
|
||||
url: string,
|
||||
params: Params,
|
||||
courseId?: number,
|
||||
data?: { cmid?: string },
|
||||
): CoreContentLinksAction[] | Promise<CoreContentLinksAction[]> {
|
||||
courseId = courseId || params.id;
|
||||
data = data || {};
|
||||
|
||||
return [{
|
||||
action: (siteId, navCtrl?): void => {
|
||||
const userId = params.userid && parseInt(params.userid, 10);
|
||||
const moduleId = data?.cmid && parseInt(data.cmid, 10) || undefined;
|
||||
|
||||
CoreGradesHelper.instance.goToGrades(courseId!, userId, moduleId, navCtrl, siteId);
|
||||
},
|
||||
}];
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the handler is enabled for a certain site (site + user) and a URL.
|
||||
* If not defined, defaults to true.
|
||||
*
|
||||
* @param siteId The site ID.
|
||||
* @param url The URL to treat.
|
||||
* @param params The params of the URL. E.g. 'mysite.com?id=1' -> {id: 1}
|
||||
* @param courseId Course ID related to the URL. Optional but recommended.
|
||||
* @return Whether the handler is enabled for the URL and site.
|
||||
*/
|
||||
isEnabled(siteId: string, url: string, params: Params, courseId?: number): boolean | Promise<boolean> {
|
||||
if (!courseId && !params.id) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return CoreGrades.instance.isPluginEnabledForCourse(courseId || params.id, siteId);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export class CoreGradesUserLinkHandler extends makeSingleton(CoreGradesUserLinkHandlerService) {}
|
|
@ -0,0 +1,118 @@
|
|||
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Injectable } from '@angular/core';
|
||||
|
||||
import { CoreGrades } from '@features/grades/services/grades';
|
||||
import { CoreUserProfile } from '@features/user/services/user';
|
||||
import {
|
||||
CoreUserDelegateService ,
|
||||
CoreUserProfileHandler,
|
||||
CoreUserProfileHandlerData,
|
||||
} from '@features/user/services/user-delegate';
|
||||
import { CoreNavigator } from '@services/navigator';
|
||||
import { CoreUtils } from '@services/utils/utils';
|
||||
import { makeSingleton } from '@singletons';
|
||||
|
||||
/**
|
||||
* Profile grades handler.
|
||||
*/
|
||||
@Injectable({ providedIn: 'root' })
|
||||
export class CoreGradesUserHandlerService implements CoreUserProfileHandler {
|
||||
|
||||
name = 'CoreGrades:viewGrades';
|
||||
priority = 400;
|
||||
type = CoreUserDelegateService.TYPE_NEW_PAGE;
|
||||
viewGradesEnabledCache = {};
|
||||
|
||||
/**
|
||||
* Clear view grades cache.
|
||||
* If a courseId and userId are specified, it will only delete the entry for that user and course.
|
||||
*
|
||||
* @param courseId Course ID.
|
||||
* @param userId User ID.
|
||||
*/
|
||||
clearViewGradesCache(courseId?: number, userId?: number): void {
|
||||
if (courseId && userId) {
|
||||
delete this.viewGradesEnabledCache[this.getCacheKey(courseId, userId)];
|
||||
} else {
|
||||
this.viewGradesEnabledCache = {};
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a cache key to identify a course and a user.
|
||||
*
|
||||
* @param courseId Course ID.
|
||||
* @param userId User ID.
|
||||
* @return Cache key.
|
||||
*/
|
||||
protected getCacheKey(courseId: number, userId: number): string {
|
||||
return courseId + '#' + userId;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if handler is enabled.
|
||||
*
|
||||
* @return Always enabled.
|
||||
*/
|
||||
isEnabled(): Promise<boolean> {
|
||||
return Promise.resolve(true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if handler is enabled for this user in this context.
|
||||
*
|
||||
* @param user User to check.
|
||||
* @param courseId Course ID.
|
||||
* @return Promise resolved with true if enabled, resolved with false otherwise.
|
||||
*/
|
||||
async isEnabledForUser(user: CoreUserProfile, courseId: number): Promise<boolean> {
|
||||
const cacheKey = this.getCacheKey(courseId, user.id);
|
||||
const cache = this.viewGradesEnabledCache[cacheKey];
|
||||
|
||||
if (typeof cache != 'undefined') {
|
||||
return cache;
|
||||
}
|
||||
|
||||
const enabled = await CoreUtils.instance.ignoreErrors(CoreGrades.instance.isPluginEnabledForCourse(courseId), false);
|
||||
|
||||
this.viewGradesEnabledCache[cacheKey] = enabled;
|
||||
|
||||
return enabled;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the data needed to render the handler.
|
||||
*
|
||||
* @return Data needed to render the handler.
|
||||
*/
|
||||
getDisplayData(): CoreUserProfileHandlerData {
|
||||
return {
|
||||
icon: 'stats-chart',
|
||||
title: 'core.grades.grades',
|
||||
class: 'core-grades-user-handler',
|
||||
action: (event, user, courseId): void => {
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
CoreNavigator.instance.navigateToSitePath(`/grades/${courseId}`, {
|
||||
params: { userId: user.id },
|
||||
});
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export class CoreGradesUserHandler extends makeSingleton(CoreGradesUserHandlerService) {}
|
Loading…
Reference in New Issue