SORU
18 Ocak 2010, PAZARTESİ


Neden AKSARAY alıcılar, birden çok kez çağırır

Hadi ben böyle outputText bir bileşen belirtin ki:

<h:outputText value="#{ManagedBean.someProperty}"/>

Eğer ben günlük yazdırma iletinin alıcısı için someProperty denir ve yük sayfası, önemsiz için fark çekicidir olmak diye bir defadan fazla istek başına (iki ya da üç kez ne oldu benim açımdan):

DEBUG 2010-01-18 23:31:40,104 (ManagedBean.java:13) - Getting some property
DEBUG 2010-01-18 23:31:40,104 (ManagedBean.java:13) - Getting some property

Eğer someProperty değerini hesaplamak için pahalı ise, bu potansiyel bir sorun olabilir.

Biraz araştırdım ve bu bilinen bir sorun olduğunu düşündüm. Bir geçici çözüm vardır ve eğer zaten hesaplanan edilip edilmediğini anlamak için:

private String someProperty;

public String getSomeProperty() {
    if (this.someProperty == null) {
        this.someProperty = this.calculatePropertyValue();
    }
    return this.someProperty;
}

Bu ana sorunu ihtiyacın olmayabilir demirbaş kodu bahsetmiyorum bile özel değişkenler yükler.

Bu yaklaşımın alternatifleri nelerdir? Bir şekilde çok fazla gereksiz kod olmadan bunu başarmak için var mı? Bir taraftan bu şekilde davranan gelen OLUMSUZLUK durdurmak için var?

Giriş için teşekkürler!

CEVAP
18 Ocak 2010, PAZARTESİ


Bu ertelenmiş ifadeler #{} (not "eski" standart ifadeleri ${} Facelets JSP yerine kullanıldığında tam olarak aynı şekilde davranır). bu doğası nedeniyle oluşur Ertelenmiş ifade değildirhemendeğerlendirildi, ancak ValueExpression bir nesne olarak oluşturulan ve ifade arkasında alıcı yöntemine kodu ValueExpression#getValue() çağırdığında her yürütülür.

Bu normalde OLUMSUZLUK başına bir ya da iki kere istek-yanıt döngüsü, bileşen giriş veya çıkış bileşeni (learn it here) olup olmamasına bağlı olarak çağrılacak. Ancak, bu kadar sayabilir kalk (çok) daha yüksek olduğunda kullanılan yineleme AKSARAY bileşenleri (gibi <h:dataTable> <ui:repeat>), ya da burada ve orada bir boolean ifadesi gibi rendered öznitelik. AKSARAY (özellikle EL) önbelleği EL ifadenin değerlendirilmesi sonucu tüm bu gibi olmayacakolabilirher çağrıda farklı değerler (şu anda yineledi datatable satır bağımlı olduğunda, örneğin dönüş.

EL bir ifade değerlendirmek ve alıcı bir yöntem çağırma çok ucuz bir işlemdir, genellikle bu konuda endişe edilmemelidir. Ancak hikaye nedense alıcı yöntemi pahalı DB/iş mantığı yaparken değiştirir. Bu tekrar çalıştırılır her şey olur!

AKSARAY destek fasulye gaz giderici yöntemler, onlar bu şekilde sadece tasarlanmalıdırdönüşzaten hazır özelliği ve bir şey daha, Javabeans specification başına tam olarak. Herhangi bir pahalı DB/iş mantığı hiç yapmamalılar. Bunun için fasulye (post)kurucu, başlatma blokları ve ya (eylem)/dinleyicisi yöntemleri kullanılmalıdır. Bunlar yürütülürsadece bir kezistek tabanlı bir noktada ve tam olarak senin istediğin şey ömrü OLUMSUZLUK.

Burada farklı bir özetdoğruyollar/yük özelliği hazır.

public class Bean {

    private SomeObject someProperty;

    @PostConstruct
    public void init() {
        // In @PostConstruct (will be invoked immediately after construction and dependency/property injection).
        someProperty = loadSomeProperty();
    }

    public void preRender(ComponentSystemEvent event) {
        // Or in some SystemEvent method (e.g. <f:event type="preRenderView">).
        someProperty = loadSomeProperty();
    }           

    public void change(ValueChangeEvent event) {
        // Or in some FacesEvent method (e.g. <h:inputXxx valueChangeListener>).
        someProperty = loadSomeProperty();
    }

    public void ajaxListener(AjaxBehaviorEvent event) {
        // Or in some BehaviorEvent method (e.g. <f:ajax listener>).
        someProperty = loadSomeProperty();
    }

    public void actionListener(ActionEvent event) {
        // Or in some ActionEvent method (e.g. <h:commandXxx actionListener>).
        someProperty = loadSomeProperty();
    }

    public String submit() {
        // Or in Action method (e.g. <h:commandXxx action>).
        someProperty = loadSomeProperty();
        return "outcome";
    }

    public SomeObject getSomeProperty() {
        // Just keep getter untouched. It isn't intented to do business logic!
        return someProperty;
    }

}

Eğer vekiller, CDI gibi kullanan bean yönetimi bir çerçeve kullanıyorsanız, birden çok kez çağrılmış olabilir, çünkü bu iş için fasulye kurucu veya başlatma bloğu kullanmanız gerektiğini unutmayın.

Eğer sizin için başka yollar, bazı kısıtlayıcı tasarım gereksinimleri nedeniyle gerçekten varsa, o zaman alıcı yöntem içinde tembel yükleme tanıtmalısın. I. e. özelliği null, yük ve özelliğine atarsanız, başka bir dönüş.

    public SomeObject getSomeProperty() {
        // If there are really no other ways, introduce lazy loading.
        if (someProperty == null) {
            someProperty = loadSomeProperty();
        }

        return someProperty;
    }

Bu şekilde pahalı DB/iş mantığı gereksiz yere her alıcı çağrı idam olmayacak.

Ayrıca Bkz:

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • Jonnyriddlin1

    Jonnyriddlin

    4 Ocak 2007
  • KliptOut KwazeeKilla

    KliptOut Kwa

    24 ŞUBAT 2010
  • RayperEnglishKnight

    RayperEnglis

    24 Kasım 2008