diff --git a/app/components/ak-select/before-option/index.ts b/app/components/ak-select/before-option/index.ts index 47579a1cc..5727fcbf7 100644 --- a/app/components/ak-select/before-option/index.ts +++ b/app/components/ak-select/before-option/index.ts @@ -56,5 +56,6 @@ export default class AkSelectBeforeOptionComponent extends Component extends PowerSelectArgs { renderInPlace?: boolean; error?: boolean; loadingMessage?: string; - selectedItemComponent?: string; labelTypographyVariant?: AkSelectLabelTypographyVariant; labelTypographyColor?: AkSelectLabelTypographyColor; verticalPosition?: 'above' | 'below' | 'auto'; diff --git a/app/components/file-details/compliance-insights/index.ts b/app/components/file-details/compliance-insights/index.ts index a4b42f049..cf3ee2718 100644 --- a/app/components/file-details/compliance-insights/index.ts +++ b/app/components/file-details/compliance-insights/index.ts @@ -101,8 +101,7 @@ export default class FileDetailsComplianceInsightsComponent extends Component; }; } diff --git a/app/components/file-details/vulnerability-analysis-details/regulatory-content/hipaa/index.ts b/app/components/file-details/vulnerability-analysis-details/regulatory-content/hipaa/index.ts index c3fc3a1a6..d1eaf93ae 100644 --- a/app/components/file-details/vulnerability-analysis-details/regulatory-content/hipaa/index.ts +++ b/app/components/file-details/vulnerability-analysis-details/regulatory-content/hipaa/index.ts @@ -1,9 +1,10 @@ import Component from '@glimmer/component'; -import HipaaModel from 'irene/models/hipaa'; +import type { AsyncHasMany } from '@ember-data/model'; +import type HipaaModel from 'irene/models/hipaa'; export interface FileDetailsVulnerabilityAnalysisDetailsRegulatoryContentHipaaSignature { Args: { - contents: HipaaModel[]; + contents: AsyncHasMany; }; } diff --git a/app/components/file-details/vulnerability-analysis-details/regulatory-content/index.ts b/app/components/file-details/vulnerability-analysis-details/regulatory-content/index.ts index 104ffb6ac..fad50e1bb 100644 --- a/app/components/file-details/vulnerability-analysis-details/regulatory-content/index.ts +++ b/app/components/file-details/vulnerability-analysis-details/regulatory-content/index.ts @@ -1,12 +1,14 @@ import { action } from '@ember/object'; import Component from '@glimmer/component'; import { tracked } from '@glimmer/tracking'; +import type Model from '@ember-data/model'; +import type { AsyncHasMany } from '@ember-data/model'; export interface FileDetailsVulnerabilityAnalysisDetailsRegulatoryContentSignature< - T extends object, + T extends Model, > { Args: { - contents: T[]; + contents: AsyncHasMany; hasMoreDetails?: boolean; }; Blocks: { @@ -20,7 +22,7 @@ export interface FileDetailsVulnerabilityAnalysisDetailsRegulatoryContentSignatu } export default class FileDetailsVulnerabilityAnalysisDetailsRegulatoryContentComponent< - T extends object, + T extends Model, > extends Component< FileDetailsVulnerabilityAnalysisDetailsRegulatoryContentSignature > { diff --git a/app/components/file-details/vulnerability-analysis-details/regulatory-content/nist/index.ts b/app/components/file-details/vulnerability-analysis-details/regulatory-content/nist/index.ts index e64a3c10a..5e4f18fef 100644 --- a/app/components/file-details/vulnerability-analysis-details/regulatory-content/nist/index.ts +++ b/app/components/file-details/vulnerability-analysis-details/regulatory-content/nist/index.ts @@ -1,13 +1,14 @@ import { action } from '@ember/object'; import Component from '@glimmer/component'; import { tracked } from '@glimmer/tracking'; +import type { AsyncHasMany } from '@ember-data/model'; -import Nistsp800171Model from 'irene/models/nistsp800171'; -import Nistsp80053Model from 'irene/models/nistsp80053'; +import type Nistsp800171Model from 'irene/models/nistsp800171'; +import type Nistsp80053Model from 'irene/models/nistsp80053'; export interface FileDetailsVulnerabilityAnalysisDetailsRegulatoryContentNistSignature { Args: { - contents: (Nistsp800171Model | Nistsp80053Model)[]; + contents: AsyncHasMany; }; } diff --git a/app/components/file-details/vulnerability-analysis/table/index.ts b/app/components/file-details/vulnerability-analysis/table/index.ts index 49d57d59a..d545c0092 100644 --- a/app/components/file-details/vulnerability-analysis/table/index.ts +++ b/app/components/file-details/vulnerability-analysis/table/index.ts @@ -154,7 +154,7 @@ export default class FileDetailsVulnerabilityAnalysisTableComponent extends Comp const vulnerabilityType = parseInt(String(type)); if (vulnerabilityType === ENUMS.VULNERABILITY_TYPE.UNKNOWN) { - return this.analyses.toArray(); + return this.analyses.slice(); } const filteredAnalysis = this.analyses?.filter((a) => diff --git a/app/components/file/report-drawer/va-reports/index.ts b/app/components/file/report-drawer/va-reports/index.ts index 399440342..5e87fef20 100644 --- a/app/components/file/report-drawer/va-reports/index.ts +++ b/app/components/file/report-drawer/va-reports/index.ts @@ -77,11 +77,11 @@ export default class FileReportDrawerVaReportsComponent extends Component -1; + /** + * Checks if an environment variable is registered + * @param {string} envKey - The key of the environment variable + * @returns {boolean} True if the environment variable is registered + */ + isRegisteredEnv(envKey) { + return this.envHandlerConst.possibleENVS.includes(envKey); } - isAvailableInENV(env_key) { + /** + * Checks if an environment variable is available in any environment + * @param {string} envKey - The key of the environment variable + * @returns {boolean} True if the environment variable is available + */ + isAvailableInENV(envKey) { return ( - this.isAvailableInRuntimeENV(env_key) || - this.isAvailableInProcessENV(env_key) + this.isAvailableInRuntimeENV(envKey) || + this.isAvailableInProcessENV(envKey) ); } + /** + * Gets the runtime configuration object + * @returns {Object} The runtime configuration object + */ getRuntimeObject() { - if (this.isRuntimeAvailable()) { - return runtimeGlobalConfig; // eslint-disable-line - } - return {}; + // eslint-disable-next-line + return this.isRuntimeAvailable() ? runtimeGlobalConfig : {}; } - isAvailableInRuntimeENV(env_key) { - const runtimeObj = this.getRuntimeObject(); - return env_key in runtimeObj; + /** + * Checks if an environment variable is available in runtime environment + * @param {string} envKey - The key of the environment variable + * @returns {boolean} True if the environment variable is available in runtime + */ + isAvailableInRuntimeENV(envKey) { + return envKey in this.getRuntimeObject(); } - isAvailableInProcessENV(env_key) { - return env_key in this.envHandlerConst.processENV; + /** + * Checks if an environment variable is available in process environment + * @param {string} envKey - The key of the environment variable + * @returns {boolean} True if the environment variable is available in process + */ + isAvailableInProcessENV(envKey) { + return envKey in this.envHandlerConst.processENV; } - assertEnvKey(env_key) { - if (!this.isRegisteredEnv(env_key)) { - throw new Error(`ENV: ${env_key} not registered`); + /** + * Asserts that an environment variable is registered + * @param {string} envKey - The key of the environment variable + * @throws {Error} If the environment variable is not registered + */ + assertEnvKey(envKey) { + if (!this.isRegisteredEnv(envKey)) { + throw new Error(`ENV: ${envKey} not registered`); } } + /** + * Checks if a value is true + * @param {*} value - The value to check + * @returns {boolean} True if the value is true + */ isTrue(value) { - value = String(value).toLowerCase(); - return value === 'true'; + return String(value).toLowerCase() === 'true'; } - getBoolean(env_key) { - return this.isTrue(this.getEnv(env_key)); + /** + * Gets the boolean value of an environment variable + * @param {string} envKey - The key of the environment variable + * @returns {boolean} The boolean value of the environment variable + */ + getBoolean(envKey) { + return this.isTrue(this.getEnv(envKey)); } - getDefault(env_key) { - this.assertEnvKey(env_key); - return this.envHandlerConst.defaults[env_key]; + /** + * Gets the default value of an environment variable + * @param {string} envKey - The key of the environment variable + * @returns {*} The default value of the environment variable + */ + getDefault(envKey) { + this.assertEnvKey(envKey); + + return this.envHandlerConst.defaults[envKey]; } - getValueForPlugin(env_key) { + /** + * Gets the value for a plugin + * @param {string} envKey - The key of the environment variable + * @returns {boolean} The value for the plugin + */ + getValueForPlugin(envKey) { const enterpriseKey = 'ENTERPRISE'; + this.assertEnvKey(enterpriseKey); - this.assertEnvKey(env_key); + this.assertEnvKey(envKey); - if (this.isAvailableInENV(env_key)) { - return this.getBoolean(env_key); + if (this.isAvailableInENV(envKey)) { + return this.getBoolean(envKey); } if (this.isAvailableInENV(enterpriseKey)) { return !this.getBoolean(enterpriseKey); } - return this.getDefault(env_key); + return this.getDefault(envKey); } } const handler = new ENVHandler(ENV.ENVHandlerCONST); -const initialize = function (application) { - // inject Ajax - application.inject('route', 'ajax', 'service:ajax'); - application.inject('component', 'ajax', 'service:ajax'); - - // Inject notify - application.inject('route', 'notify', 'service:notifications'); - application.inject('component', 'notify', 'service:notifications'); - application.inject('authenticator', 'notify', 'service:notifications'); - - // Inject realtime - application.inject('component', 'realtime', 'service:realtime'); - - // Inject Store - application.inject('component', 'store', 'service:store'); - +/** + * Initializes the application + * @param {Object} application - The application instance + */ +const initialize = (application) => { ENV.host = handler.getEnv('IRENE_API_HOST'); ENV.isEnterprise = handler.getBoolean('ENTERPRISE'); ENV.showLicense = handler.getBoolean('IRENE_SHOW_LICENSE'); - ENV.whitelabel = Object.assign({}, ENV.whitelabel, { + ENV.whitelabel = { + ...ENV.whitelabel, enabled: handler.getBoolean('WHITELABEL_ENABLED'), - }); + }; + if (ENV.whitelabel.enabled) { - ENV.whitelabel = Object.assign({}, ENV.whitelabel, { - enabled: handler.getBoolean('WHITELABEL_ENABLED'), // adding for consistency + ENV.whitelabel = { + ...ENV.whitelabel, name: handler.getEnv('WHITELABEL_NAME'), logo: handler.getEnv('WHITELABEL_LOGO'), theme: handler.getEnv('WHITELABEL_THEME'), favicon: handler.getEnv('WHITELABEL_FAVICON'), - }); + }; } + ENV.enableHotjar = handler.getValueForPlugin('IRENE_ENABLE_HOTJAR'); ENV.enablePendo = handler.getValueForPlugin('IRENE_ENABLE_PENDO'); ENV.enableCSB = handler.getValueForPlugin('IRENE_ENABLE_CSB'); @@ -146,14 +203,12 @@ const initialize = function (application) { installHotjar(); customerSuccessBox(); - // Inject ENV + // Register ENV if (ENV.environment !== 'test') { - // FIXME: Fix this test properly application.register('env:main', ENV, { singleton: true, instantiate: false, }); - return application.inject('component', 'env', 'env:main'); } }; @@ -163,4 +218,5 @@ const IreneInitializer = { }; export { initialize }; + export default IreneInitializer; diff --git a/app/mixins/base-model.ts b/app/mixins/base-model.ts index 0a0ce98fe..2f69ab6df 100644 --- a/app/mixins/base-model.ts +++ b/app/mixins/base-model.ts @@ -1,37 +1,11 @@ -/* eslint-disable ember/no-new-mixins, ember/no-get, ember/no-computed-properties-in-native-classes */ import Model, { AsyncBelongsTo, attr, belongsTo } from '@ember-data/model'; -import { computed } from '@ember/object'; -import Mixin from '@ember/object/mixin'; import { isEmpty } from '@ember/utils'; import UserModel from 'irene/models/user'; -const BaseModelMixin = Mixin.create({ - createdBy: belongsTo('user'), - createdOn: attr('date'), - updatedOn: attr('date'), - uuid: attr('string'), - - createdOnHumanized: computed('createdOn', function () { - const createdOn = this.get('createdOn'); - if (isEmpty(createdOn)) { - return; - } - return `${createdOn.toLocaleDateString()}`; - }), - - createdOnDateTime: computed('createdOn', function () { - const createdOn = this.get('createdOn'); - if (isEmpty(createdOn)) { - return; - } - return `${createdOn.toDateString()}, ${createdOn.toLocaleTimeString()}`; - }), -}); - // Class based mixin support for non classic models export class ModelBaseMixin extends Model { - @belongsTo('user') + @belongsTo('user', { async: true, inverse: null }) declare createdBy: AsyncBelongsTo; @attr('date') @@ -61,5 +35,3 @@ export class ModelBaseMixin extends Model { return `${createdOn.toDateString()}, ${createdOn.toLocaleTimeString()}`; } } - -export default BaseModelMixin; diff --git a/app/models/analysis.ts b/app/models/analysis.ts index dded418e2..56a7358ab 100644 --- a/app/models/analysis.ts +++ b/app/models/analysis.ts @@ -85,57 +85,57 @@ export default class AnalysisModel extends Model { declare overriddenDate: Date | null; @attr('number') - declare analiserVersion: string; + declare analiserVersion: number; - @hasMany('attachment') + @hasMany('attachment', { async: true, inverse: null }) declare attachments: AsyncHasMany; - @hasMany('owasp') + @hasMany('owasp', { async: true, inverse: null }) declare owasp: AsyncHasMany; - @hasMany('owaspmobile2024') + @hasMany('owaspmobile2024', { async: true, inverse: null }) declare owaspmobile2024: AsyncHasMany; - @hasMany('owaspapi2023') + @hasMany('owaspapi2023', { async: true, inverse: null }) declare owaspapi2023: AsyncHasMany; - @hasMany('cwe') + @hasMany('cwe', { async: true, inverse: null }) declare cwe: AsyncHasMany; - @hasMany('asvs') + @hasMany('asvs', { async: true, inverse: null }) declare asvs: AsyncHasMany; - @hasMany('masvs') + @hasMany('masvs', { async: true, inverse: null }) declare masvs: AsyncHasMany; - @hasMany('mstg') + @hasMany('mstg', { async: true, inverse: null }) declare mstg: AsyncHasMany; - @hasMany('pcidss') + @hasMany('pcidss', { async: true, inverse: null }) declare pcidss: AsyncHasMany; - @hasMany('pcidss4') + @hasMany('pcidss4', { async: true, inverse: null }) declare pcidss4: AsyncHasMany; - @hasMany('hipaa') + @hasMany('hipaa', { async: true, inverse: null }) declare hipaa: AsyncHasMany; - @hasMany('gdpr') + @hasMany('gdpr', { async: true, inverse: null }) declare gdpr: AsyncHasMany; - @hasMany('nistsp800171') + @hasMany('nistsp800171', { async: true, inverse: null }) declare nistsp800171: AsyncHasMany; - @hasMany('nistsp80053') + @hasMany('nistsp80053', { async: true, inverse: null }) declare nistsp80053: AsyncHasMany; - @hasMany('sama') + @hasMany('sama', { async: true, inverse: null }) declare sama: AsyncHasMany; - @belongsTo('vulnerability') + @belongsTo('vulnerability', { async: true, inverse: null }) declare vulnerability: AsyncBelongsTo; - @belongsTo('file', { inverse: 'analyses' }) + @belongsTo('file', { inverse: 'analyses', async: true }) declare file: AsyncBelongsTo; @attr('date') diff --git a/app/models/file.ts b/app/models/file.ts index 0285e342e..2fda6d75f 100644 --- a/app/models/file.ts +++ b/app/models/file.ts @@ -109,28 +109,28 @@ export default class FileModel extends ModelBaseMixin { @attr('boolean') declare canRunAutomatedDynamicscan: boolean; - @hasMany('tag', { async: false }) + @hasMany('tag', { async: false, inverse: null }) declare tags: SyncHasMany; - @hasMany('file-report', { async: true }) + @hasMany('file-report', { async: true, inverse: null }) declare reports: AsyncHasMany; @hasMany('analysis', { inverse: 'file', async: false }) declare analyses: SyncHasMany; - @belongsTo('project', { inverse: 'files' }) + @belongsTo('project', { inverse: 'files', async: true }) declare project: AsyncBelongsTo; - @belongsTo('profile', { inverse: 'files' }) + @belongsTo('profile', { inverse: 'files', async: true }) declare profile: AsyncBelongsTo; - @belongsTo('sbom-file', { inverse: 'file' }) + @belongsTo('sbom-file', { inverse: 'file', async: true }) declare sbFile: AsyncBelongsTo; - @belongsTo('submission') + @belongsTo('submission', { async: true, inverse: null }) declare submission: AsyncBelongsTo; - @belongsTo('file', { inverse: null }) + @belongsTo('file', { inverse: null, async: true }) declare previousFile: AsyncBelongsTo; analysesSorting = ['computedRisk:desc']; diff --git a/app/models/organization-archive.ts b/app/models/organization-archive.ts index f53645903..8f2e60a91 100644 --- a/app/models/organization-archive.ts +++ b/app/models/organization-archive.ts @@ -48,7 +48,7 @@ export default class OrganizationArchiveModel extends Model { @attr('date') declare availableUntil: Date; - @belongsTo('organization-user', { inverse: null }) + @belongsTo('organization-user', { inverse: null, async: true }) declare generatedBy: AsyncBelongsTo; @attr('date') diff --git a/app/models/organization-member.ts b/app/models/organization-member.ts index b95056618..54a7d356f 100644 --- a/app/models/organization-member.ts +++ b/app/models/organization-member.ts @@ -10,7 +10,7 @@ import OrganizationTeamModel from './organization-team'; import OrganizationUserModel from './organization-user'; export default class OrganizationMemberModel extends Model { - @belongsTo('organization-user') + @belongsTo('organization-user', { async: true, inverse: null }) declare member: AsyncBelongsTo; @attr('number') @@ -28,7 +28,7 @@ export default class OrganizationMemberModel extends Model { @attr('date') declare lastLoggedIn: Date; - @hasMany('organization-team') + @hasMany('organization-team', { async: true, inverse: null }) declare teams: AsyncHasMany; } diff --git a/app/models/organization-namespace.ts b/app/models/organization-namespace.ts index 71a30b994..9e8e04c76 100644 --- a/app/models/organization-namespace.ts +++ b/app/models/organization-namespace.ts @@ -19,13 +19,13 @@ export default class OrganizationNamespaceModel extends Model { @attr('boolean') declare isApproved: boolean; - @belongsTo('organization') + @belongsTo('organization', { async: true, inverse: null }) declare organization: AsyncBelongsTo; - @belongsTo('organization-user') + @belongsTo('organization-user', { async: true, inverse: null }) declare requestedBy: AsyncBelongsTo; - @belongsTo('organization-user') + @belongsTo('organization-user', { async: true, inverse: null }) declare approvedBy: AsyncBelongsTo; @attr('number') diff --git a/app/models/organization-project.ts b/app/models/organization-project.ts index ce9a22508..7ff339e6d 100644 --- a/app/models/organization-project.ts +++ b/app/models/organization-project.ts @@ -22,10 +22,10 @@ export default class OrganizationProjectModel extends Model { @attr('number') declare activeProfileId: number; - @belongsTo('organization') + @belongsTo('organization', { async: true, inverse: null }) declare organization: AsyncBelongsTo; - @hasMany('file', { inverse: 'project' }) + @hasMany('file', { inverse: 'project', async: true }) declare files: AsyncHasMany; @attr('string') diff --git a/app/models/organization-team.ts b/app/models/organization-team.ts index fc2163ed2..9163b81dd 100644 --- a/app/models/organization-team.ts +++ b/app/models/organization-team.ts @@ -15,7 +15,7 @@ export default class OrganizationTeamModel extends Model { @attr('string') declare name: string; - @hasMany('organization-team-member') + @hasMany('organization-team-member', { async: true, inverse: null }) declare members: AsyncHasMany; @attr('string') diff --git a/app/models/organization.ts b/app/models/organization.ts index 60413b927..5c085af9c 100644 --- a/app/models/organization.ts +++ b/app/models/organization.ts @@ -31,16 +31,16 @@ export default class OrganizationModel extends Model { @attr('boolean') declare mandatoryMfa: boolean; - @hasMany('organization-member') + @hasMany('organization-member', { async: true, inverse: null }) declare members: AsyncHasMany; - @hasMany('organization-namespace') + @hasMany('organization-namespace', { async: true, inverse: null }) declare namespaces: AsyncHasMany; - @hasMany('organization-project') + @hasMany('organization-project', { async: true, inverse: null }) declare projects: AsyncHasMany; - @hasMany('organization-team') + @hasMany('organization-team', { async: true, inverse: null }) declare teams: AsyncHasMany; @attr() diff --git a/app/models/profile.ts b/app/models/profile.ts index 2675a3c4c..6cad5b2b9 100644 --- a/app/models/profile.ts +++ b/app/models/profile.ts @@ -117,7 +117,7 @@ export default class ProfileModel extends Model { @attr declare dsAutomatedDeviceType: number; - @hasMany('file', { inverse: 'profile' }) + @hasMany('file', { inverse: 'profile', async: true }) declare files: AsyncHasMany; @attr diff --git a/app/models/project.ts b/app/models/project.ts index 154c2de8c..fea58979a 100644 --- a/app/models/project.ts +++ b/app/models/project.ts @@ -55,16 +55,16 @@ export default class ProjectModel extends ModelBaseMixin { @attr('date') declare lastFileCreatedOn: Date; - @belongsTo('user', { inverse: 'ownedProjects' }) + @belongsTo('user', { inverse: 'ownedProjects', async: true }) declare owner: AsyncBelongsTo; - @belongsTo('file') + @belongsTo('file', { async: true, inverse: null }) declare lastFileId: AsyncBelongsTo; @alias('lastFileId') declare lastFile: ComputedProperty; - @hasMany('file', { inverse: 'project' }) + @hasMany('file', { inverse: 'project', async: true }) declare files: AsyncHasMany; get pdfPassword() { diff --git a/app/models/sbom-file.ts b/app/models/sbom-file.ts index 4b59b265c..f0f637364 100644 --- a/app/models/sbom-file.ts +++ b/app/models/sbom-file.ts @@ -15,10 +15,10 @@ export enum SbomScanStatus { export default class SbomFileModel extends Model { @service declare intl: IntlService; - @belongsTo('file') + @belongsTo('file', { async: true, inverse: 'sbFile' }) declare file: AsyncBelongsTo; - @belongsTo('sbom-project') + @belongsTo('sbom-project', { async: true, inverse: null }) declare sbProject: AsyncBelongsTo; @attr('number') diff --git a/app/models/sbom-project.ts b/app/models/sbom-project.ts index 84ccce195..89b3924fe 100644 --- a/app/models/sbom-project.ts +++ b/app/models/sbom-project.ts @@ -4,10 +4,10 @@ import ProjectModel from './project'; import SbomFileModel from './sbom-file'; export default class SbomProjectModel extends Model { - @belongsTo('project') + @belongsTo('project', { async: true, inverse: null }) declare project: AsyncBelongsTo; - @belongsTo('sbom-file') + @belongsTo('sbom-file', { async: true, inverse: null }) declare latestSbFile: AsyncBelongsTo | null; } diff --git a/app/models/sbom-report.ts b/app/models/sbom-report.ts index 8be9ae6c1..c4ab96828 100644 --- a/app/models/sbom-report.ts +++ b/app/models/sbom-report.ts @@ -12,7 +12,7 @@ export enum SbomReportStatus { } export default class SbomReportModel extends Model { - @belongsTo('sbom-file') + @belongsTo('sbom-file', { async: true, inverse: null }) declare sbFile: AsyncBelongsTo | null; @attr('string') diff --git a/app/models/submission.ts b/app/models/submission.ts index 09ee81245..223171e30 100644 --- a/app/models/submission.ts +++ b/app/models/submission.ts @@ -24,7 +24,7 @@ export const submissionStatusProgressPercentage = { }; export default class SubmissionModel extends ModelBaseMixin { - @belongsTo('user', { inverse: 'submissions' }) + @belongsTo('user', { inverse: 'submissions', async: true }) declare user: AsyncBelongsTo; @attr('string') diff --git a/app/models/user.ts b/app/models/user.ts index eaeba9896..71b8f726a 100644 --- a/app/models/user.ts +++ b/app/models/user.ts @@ -32,16 +32,16 @@ export default class UserModel extends Model { @attr('string') declare lastName: string; - @hasMany('project', { inverse: 'owner' }) + @hasMany('project', { inverse: 'owner', async: true }) declare ownedProjects: AsyncHasMany; - @hasMany('project') + @hasMany('project', { async: true, inverse: null }) declare projects: AsyncHasMany; - @hasMany('pricing') + @hasMany('pricing', { async: true, inverse: null }) declare pricings: AsyncHasMany; - @hasMany('submission', { inverse: 'user' }) + @hasMany('submission', { inverse: 'user', async: true }) declare submissions: AsyncHasMany; @attr('string') diff --git a/config/environment.js b/config/environment.js index c651f715d..8957e62e9 100644 --- a/config/environment.js +++ b/config/environment.js @@ -198,7 +198,7 @@ module.exports = function (environment) { }, rootURL: '/', favicon: '/images/favicon.ico', - locationType: 'auto', + locationType: 'history', modulePrefix: 'irene', environment: environment, enableHotjar: handler.getValueForPlugin('IRENE_ENABLE_HOTJAR'),