Прокси-классы со строгой типизацией Flex для отложенного создания экземпляров

Кто-нибудь знает фреймворк, желательно какой-то способ заставить компилятор Flex запускать расширение или, возможно, просто этап сборки, на котором мы могли бы сгенерировать строго типизированные прокси-классы для моделей данных нашего приложения.

Мы хотим сделать с прокси 2 основные вещи:

  1. Во время выполнения мы хотим лениво анализировать и создавать экземпляр экземпляра при доступе (аналогично тому, как Java Hibernate имеет Lazy прокси-объекты)
  2. In an editor application we want to implement setter calls so we can track which objects have been modified
    • The Proxy is really necessary in this situation beyond things like programatically setting up ChangeWatcther's because we need to track Array adds/remove and possibly track "reference" objects so that when a "reference key" is changed we know to save those objects that are referencing it by key

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

Обычно прокси создает экземпляр объекта при первом вызове метода.

Я знаю, что мы могли бы использовать некоторые библиотеки байтового кода AS3, такие как as3-commons-bytecode .

Или, возможно, перепрофилировать генерацию кода GraniteDS.

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

Кто-нибудь знает, могу ли я сделать что-то вроде MXMLC, когда он генерирует код AS3 из файлов MXML.

Также есть ли способ контролировать «когда» в конвейере компиляции, я могу сгенерировать код, потому что у нас есть много объектов данных, использующих общедоступные поля вместо методов получения / установки, но они [Bindable] и поэтому, если бы я мог сгенерировать на основе прокси на сгенерированных методах получения / установки, которые будут работать.

Вот пример объекта данных приложения и прокси-классов:

[Bindable]
public class PersonDTO implements Serializable {
    private var _name:String;

    private var _age:Number


    public function get age():Number {
        return _age;
    }

    public function set age(a:Number):void {
        _age = a;
    }

    public function get name():String {
        return _name;
    }

    public function set name(n:String):void {
        _name = n;
    }

    public void readObject(data:*) {
        //...
    }

}

// GENERATED CLASS BASED ON PersonDTO
public class LazyProxy_PersonDTO extends PersonDTO {

    private var _instance:PersonDTO = null;
    private var _instanceData:*;

    private function getInstance():void {
        if (_instance == null) {
            _instance = new PersonDTO();
            _instance.readObject(_instanceData);
        }
    }

    override public function get age():Number {
        //Ensure object is instantiated
        return getInstance().age;
    }

    override public function get name():String {
        //Ensure object is instantiated
        return getInstance().name;
    }

}

// GENERATED CLASS BASED ON PersonDTO
public class LogChangeProxy_PersonDTO extends PersonDTO {

    //This will be set in the application
    public var instance:PersonDTO;

    //set by application
    public var dirtyWatcher:DirtyWatcherManager;

    override public function set age(a:Number):void {
        dirtyWatcher.markAsDirty(instance);
        instance.age = a;
    }

}

person Dougnukem    schedule 22.11.2011    source источник
comment
Точно сказать не могу; но посмотрите dbHibernate code.google.com/p/dphibernate. Возможно, это то, что вы ищете.   -  person JeffryHouser    schedule 22.11.2011


Ответы (1)


Если углубиться в библиотеку байтового кода AS3-Commons, похоже, что они поддерживают создание прокси-классов и перехватчиков.

  • http://www.as3commons.org/as3-commons-bytecode/proxy.html

    public class DirtyUpdateInterceptor implements IInterceptor {
    
    public function DirtyUpdateInterceptor() {
        super();
    }
    
    public function intercept(invocation:IMethodInvocation):void {
        if (invocation.kind === MethodInvocationKind.SETTER) {
            if (invocation.arguments[0] != invocation.instance[invocation.targetMember]) {
                invocation.instance.isDirty = true;
            }
        }
    }
    }
    
person Dougnukem    schedule 22.11.2011