diff --git a/src/addon/mod/book/components/index/index.ts b/src/addon/mod/book/components/index/index.ts index 40717a6fc..ee66c3b9a 100644 --- a/src/addon/mod/book/components/index/index.ts +++ b/src/addon/mod/book/components/index/index.ts @@ -119,6 +119,7 @@ export class AddonModBookIndexComponent extends CoreCourseModuleMainResourceComp protected fetchContent(refresh?: boolean): Promise { const promises = []; let downloadFailed = false; + let downloadFailError; // Try to get the book data. promises.push(this.bookProvider.getBook(this.courseId, this.module.id).then((book) => { @@ -129,9 +130,10 @@ export class AddonModBookIndexComponent extends CoreCourseModuleMainResourceComp })); // Download content. This function also loads module contents if needed. - promises.push(this.prefetchDelegate.download(this.module, this.courseId).catch(() => { + promises.push(this.prefetchDelegate.download(this.module, this.courseId).catch((error) => { // Mark download as failed but go on since the main files could have been downloaded. downloadFailed = true; + downloadFailError = error; if (!this.module.contents.length) { // Try to load module contents for offline usage. @@ -163,7 +165,7 @@ export class AddonModBookIndexComponent extends CoreCourseModuleMainResourceComp return this.loadChapter(this.currentChapter).then(() => { if (downloadFailed && this.appProvider.isOnline()) { // We could load the main file but the download failed. Show error message. - this.domUtils.showErrorModal('core.errordownloadingsomefiles', true); + this.showErrorDownloadingSomeFiles(downloadFailError); } }).catch(() => { // Ignore errors, they're handled inside the loadChapter function. diff --git a/src/addon/mod/imscp/components/index/index.ts b/src/addon/mod/imscp/components/index/index.ts index c6690b324..a17aa8de4 100644 --- a/src/addon/mod/imscp/components/index/index.ts +++ b/src/addon/mod/imscp/components/index/index.ts @@ -76,6 +76,7 @@ export class AddonModImscpIndexComponent extends CoreCourseModuleMainResourceCom */ protected fetchContent(refresh?: boolean): Promise { let downloadFailed = false; + let downloadFailError; const promises = []; promises.push(this.imscpProvider.getImscp(this.courseId, this.module.id).then((imscp) => { @@ -83,9 +84,10 @@ export class AddonModImscpIndexComponent extends CoreCourseModuleMainResourceCom this.dataRetrieved.emit(imscp); })); - promises.push(this.imscpPrefetch.download(this.module, this.courseId).catch(() => { + promises.push(this.imscpPrefetch.download(this.module, this.courseId).catch((error) => { // Mark download as failed but go on since the main files could have been downloaded. downloadFailed = true; + downloadFailError = error; return this.courseProvider.loadModuleContents(this.module, this.courseId).catch((error) => { // Error getting module contents, fail. @@ -109,7 +111,7 @@ export class AddonModImscpIndexComponent extends CoreCourseModuleMainResourceCom }).then(() => { if (downloadFailed && this.appProvider.isOnline()) { // We could load the main file but the download failed. Show error message. - this.domUtils.showErrorModal('core.errordownloadingsomefiles', true); + this.showErrorDownloadingSomeFiles(downloadFailError); } }).finally(() => { diff --git a/src/addon/mod/page/components/index/index.ts b/src/addon/mod/page/components/index/index.ts index 9ee38717e..b8300246a 100644 --- a/src/addon/mod/page/components/index/index.ts +++ b/src/addon/mod/page/components/index/index.ts @@ -78,11 +78,13 @@ export class AddonModPageIndexComponent extends CoreCourseModuleMainResourceComp */ protected fetchContent(refresh?: boolean): Promise { let downloadFailed = false; + let downloadFailError; // Download content. This function also loads module contents if needed. - return this.pagePrefetch.download(this.module, this.courseId).catch(() => { + return this.pagePrefetch.download(this.module, this.courseId).catch((error) => { // Mark download as failed but go on since the main files could have been downloaded. downloadFailed = true; + downloadFailError = error; }).then(() => { if (!this.module.contents.length) { // Try to load module contents for offline usage. @@ -132,7 +134,7 @@ export class AddonModPageIndexComponent extends CoreCourseModuleMainResourceComp if (downloadFailed && this.appProvider.isOnline()) { // We could load the main file but the download failed. Show error message. - this.domUtils.showErrorModal('core.errordownloadingsomefiles', true); + this.showErrorDownloadingSomeFiles(downloadFailError); } })); diff --git a/src/addon/mod/resource/components/index/index.ts b/src/addon/mod/resource/components/index/index.ts index c05b4f15e..8875bae06 100644 --- a/src/addon/mod/resource/components/index/index.ts +++ b/src/addon/mod/resource/components/index/index.ts @@ -110,10 +110,12 @@ export class AddonModResourceIndexComponent extends CoreCourseModuleMainResource if (this.resourceHelper.isDisplayedInIframe(this.module)) { let downloadFailed = false; + let downloadFailError; - return this.prefetchHandler.download(this.module, this.courseId).catch(() => { + return this.prefetchHandler.download(this.module, this.courseId).catch((error) => { // Mark download as failed but go on since the main files could have been downloaded. downloadFailed = true; + downloadFailError = error; }).then(() => { return this.resourceHelper.getIframeSrc(this.module).then((src) => { this.mode = 'iframe'; @@ -131,7 +133,7 @@ export class AddonModResourceIndexComponent extends CoreCourseModuleMainResource if (downloadFailed && this.appProvider.isOnline()) { // We could load the main file but the download failed. Show error message. - this.domUtils.showErrorModal('core.errordownloadingsomefiles', true); + this.showErrorDownloadingSomeFiles(downloadFailError); } }); }); diff --git a/src/core/course/classes/main-resource-component.ts b/src/core/course/classes/main-resource-component.ts index 87691f7d8..50f432894 100644 --- a/src/core/course/classes/main-resource-component.ts +++ b/src/core/course/classes/main-resource-component.ts @@ -17,7 +17,7 @@ import { NavController } from 'ionic-angular'; import { TranslateService } from '@ngx-translate/core'; import { CoreLoggerProvider } from '@providers/logger'; import { CoreDomUtilsProvider } from '@providers/utils/dom'; -import { CoreTextUtilsProvider } from '@providers/utils/text'; +import { CoreTextUtilsProvider, CoreTextErrorObject } from '@providers/utils/text'; import { CoreCourseHelperProvider } from '@core/course/providers/helper'; import { CoreCourseModuleMainComponent, CoreCourseModuleDelegate } from '@core/course/providers/module-delegate'; import { CoreCourseSectionPage } from '@core/course/pages/section/section.ts'; @@ -265,6 +265,20 @@ export class CoreCourseModuleMainResourceComponent implements OnInit, OnDestroy, this.courseHelper.confirmAndRemoveFiles(this.module, this.courseId); } + /** + * Show an error occurred while downloading files. + * + * @param error The specific error. + */ + protected showErrorDownloadingSomeFiles(error: string | CoreTextErrorObject): void { + const errorMessage = this.textUtils.buildSeveralParagraphsMessage([ + this.translate.instant('core.errordownloadingsomefiles'), + error, + ]); + + this.domUtils.showErrorModal(errorMessage); + } + /** * Component being destroyed. */ diff --git a/src/core/courses/providers/course-link-handler.ts b/src/core/courses/providers/course-link-handler.ts index b94813f4c..c7fdd7df4 100644 --- a/src/core/courses/providers/course-link-handler.ts +++ b/src/core/courses/providers/course-link-handler.ts @@ -178,8 +178,9 @@ export class CoreCoursesCourseLinkHandler extends CoreContentLinksHandlerBase { error = this.translate.instant('core.courses.notenroled'); } - const body = this.translate.instant('core.twoparagraphs', - { p1: error, p2: this.translate.instant('core.confirmopeninbrowser') }); + const body = this.textUtils.buildSeveralParagraphsMessage( + [error, this.translate.instant('core.confirmopeninbrowser')]); + this.domUtils.showConfirm(body).then(() => { this.sitesProvider.getCurrentSite().openInBrowserWithAutoLogin(url); }).catch(() => { diff --git a/src/providers/utils/text.ts b/src/providers/utils/text.ts index 0f1202161..8565b6dfc 100644 --- a/src/providers/utils/text.ts +++ b/src/providers/utils/text.ts @@ -18,6 +18,16 @@ import { ModalController, Platform } from 'ionic-angular'; import { TranslateService } from '@ngx-translate/core'; import { CoreLangProvider } from '../lang'; +/** + * Different type of errors the app can treat. + */ +export type CoreTextErrorObject = { + message?: string; + error?: string; + content?: string; + body?: string; +}; + /* * "Utils" service with helper functions for text. */ @@ -122,6 +132,38 @@ export class CoreTextUtilsProvider { return result; } + /** + * Build a message with several paragraphs. + * + * @param paragraphs List of paragraphs. + * @return Built message. + */ + buildSeveralParagraphsMessage(paragraphs: (string | CoreTextErrorObject)[]): string { + // Filter invalid messages, and convert them to messages in case they're errors. + const messages: string[] = []; + + paragraphs.forEach((paragraph) => { + // If it's an error, get its message. + const message = this.getErrorMessageFromError(paragraph); + + if (paragraph) { + messages.push(message); + } + }); + + if (messages.length < 2) { + return messages[0] || ''; + } + + let builtMessage = messages[0]; + + for (let i = 1; i < messages.length; i++) { + builtMessage = this.translate.instant('core.twoparagraphs', { p1: builtMessage, p2: messages[i] }); + } + + return builtMessage; + } + /** * Convert size in bytes into human readable format * @@ -449,7 +491,7 @@ export class CoreTextUtilsProvider { * @param error Error object. * @return Error message, undefined if not found. */ - getErrorMessageFromError(error: any): string { + getErrorMessageFromError(error: string | CoreTextErrorObject): string { if (typeof error == 'string') { return error; }