2017-02-21 19 views
3

В рамках проекта Aurelia у меня есть модель представления, что я хочу поддерживать состояние между навигацией маршрутизатора. Я думал, что добавление @singleton() к моему классу модели представления выполнит это.Aurelia Singleton View model

Фактически, я создал простой проект Aurelia, где это работает. Я могу перемещаться в сторону и обратно на ту же страницу, и состояние сохраняется. Мой конструктор называется только первым, когда я перехожу к этой странице.

import { singleton } from 'aurelia-framework'; 

@singleton() 
export class Welcome { 
    heading = 'Welcome to the Aurelia Navigation App!'; 

    constructor() { 
     console.log('constructor'); 
    } 

    activate() { 
     console.log('activate'); 
    } 

    attached() { 
     console.log('attached'); 
    } 
} 

Однако в моем более крупном приложении это не работает. Я добавляю декоратор, и конструктор моей модели представления по-прежнему называется вторым, когда я перехожу к этой странице. (Я даже скопировал эту модель представления в мое более крупное приложение и не рассматривался как синглтон.)

Очевидно, что между этими двумя проектами должно быть что-то другое. Однако я не вижу никакой разницы. Есть ли настройка, которую я мог бы установить, чтобы переопределить поведение @singleton()?

+2

https://github.com/aurelia/dependency-injection/issues/65 –

ответ

1

Вероятно, у вас есть несколько экземпляров пользовательского элемента singleton - по определению один синглтон не может иметь несколько экземпляров самого себя. То, что вы хотите, представляет собой модель представления, которая создается один раз и повторно используется.

Это решение, которое я использовал успешно. Идея состоит в том, чтобы создать экземпляр модели глобального представления, который был создан один раз, и есть представление контроллера, которое использует это для создания представления/vm.

HTML

<template> 
    <require from="yourView.html"></require> 
    <p> parentClass.html </p> 
    <compose view="yourView.html" view-model.bind="singletonViewModel"></compose> 
</template> 

JS

import { YourView } from 'yourView'; 
export class parentClass { 
    // constructor for parentClass will run multiple times. 
    constructor() { 
    /** this is the key, you must instantiate a custom view model once 
    on some globally singleton object like window or global in Node */ 
    if (typeof window.yourView === 'undefined') { 
     window.yourView = new YourView(); 
    } 
    } 

    bind() { 
    this.singletonViewModel = window.yourView; 
    } 
} 

Все, что вы делаете в этой точке зрения модели будет сохраняться теперь между навигаций и конструктор будет вызван только один раз. прикрепленные() и снятые() для модели с одноэлементным окном будут активироваться так, как вы ожидали.

Также обратите внимание, что вы можете использовать это для кэширования нескольких экземпляров моделей просмотра, с которыми вы можете переключаться между ними. Мое приложение имеет глобальную службу для отслеживания нескольких виртуальных машин, которые строят/возвращают виртуальную машину по запросу. Преимущество в этом заключается в том, что я могу выполнять тяжелую обработку один раз на этапе конструктора, а затем никогда не беспокоиться об этом.

1

Получается, что решение было обновлено jspm. Я думал, что удаление jspm_packages и запуск jspm install будет эквивалентным. Но это не так.

Теперь, когда мои модули Aurelia обновлены, декоратор singleton() отлично работает.