Получение asp.net для хранения viewstate в сеансе вместо того, чтобы набирать html - PullRequest
7 голосов
/ 07 января 2011

Я пытаюсь заставить asp.net хранить viewstate в сеансе, а не заполнять html.

Теперь я прочитал, что asp.net поставляется с SessionPageStatePersister, который можно использовать вместоHiddenFieldPageStatePersister по умолчанию для этого.Мне было интересно, как я собираюсь добавить его?

Это то, что я получил до сих пор: я думаю, мне нужно создать PageAdapter, который возвращает SessionPageStatePersister из его метода GetStatePersister, и каким-то образом получить страницу дляиспользуйте этот страничный адаптер.Но у Page.PageAdapter есть только геттер, поэтому я не уверен, как вы его установите.

См. Заголовок «Примечания» здесь: http://msdn.microsoft.com/en-us/library/system.web.ui.hiddenfieldpagestatepersister.aspx

Спасибо!

Ответы [ 3 ]

9 голосов
/ 07 января 2011

Вы уверены, что хотите это сделать? Есть проблемы

  1. Как вы держите отдельные страницы отдельно? Конечно, вы можете добавить префикс имени сеанса к странице, например. Сеанс ["/ default.aspx-Viewstate"], но что происходит, когда пользователь открывает несколько экземпляров страницы?
  2. Итак, чтобы решить, что вы помещаете скрытое поле с, скажем, GUID на каждой странице, которое затем используете в качестве ключа. Таким образом, размер вашей сессии растет. И растет. И растет. Как вы узнаете, если / когда вы можете безопасно удалить вещи?

Если вы настаиваете на заголовке этого чтения, то все, что вам нужно сделать, это извлечь класс из страницы и переопределить LoadPageStateFromPersistenceMedium () и SavePageStateToPersistenceMedium (). Но ты возненавидишь себя и в конце концов разорвет это.

Просто убедитесь, что на вашем сервере включено сжатие HTTP, и, пожалуйста, позаботьтесь о чем-то другом.

7 голосов
/ 10 января 2011

Для чего стоит, вот код, который я в конечном итоге использовал, чтобы решить проблему с большими изображениями: перемещение представления состояния из html.Просто вставьте это в свой mypage.aspx.cs:

// Inspired by: http://aspalliance.com/72
const string ViewStateFieldName = "__VIEWSTATEKEY";
const string RecentViewStateQueue = "RecentViewStateQueue";
const int RecentViewStateQueueMaxLength = 5;

protected override object LoadPageStateFromPersistenceMedium()
{
    // The cache key for this viewstate is stored where the viewstate normally is, so grab it
    string viewStateKey = Request.Form[ViewStateFieldName] as string;
    if (viewStateKey == null) return null;

    // Grab the viewstate data from the cache using the key to look it up
    string viewStateData = Cache[viewStateKey] as string;
    if (viewStateData == null) return null;

    // Deserialise it
    return new LosFormatter().Deserialize(viewStateData);
}

protected override void SavePageStateToPersistenceMedium(object viewState)
{
    // Serialise the viewstate information
    StringBuilder _viewState = new StringBuilder();
    StringWriter _writer = new StringWriter(_viewState);
    new LosFormatter().Serialize(_writer, viewState);

    // Give this viewstate a random key
    string viewStateKey = Guid.NewGuid().ToString();

    // Store the viewstate in the cache
    Cache.Add(viewStateKey, _viewState.ToString(), null, Cache.NoAbsoluteExpiration, TimeSpan.FromMinutes(Session.Timeout), CacheItemPriority.Normal, null);

    // Store the viewstate's cache key in the viewstate hidden field, so on postback we can grab it from the cache
    ClientScript.RegisterHiddenField(ViewStateFieldName, viewStateKey);

    // Some tidying up: keep track of the X most recent viewstates for this user, and remove old ones
    var recent = Session[RecentViewStateQueue] as Queue<string>;
    if (recent == null) Session[RecentViewStateQueue] = recent = new Queue<string>();
    recent.Enqueue(viewStateKey); // Add this new one so it'll get removed later
    while (recent.Count > RecentViewStateQueueMaxLength) // If we've got lots in the queue, remove the old ones
    Cache.Remove(recent.Dequeue());
}

И для супер-простого способа использования SessionPageStatePersister снова поместите это в mypage.aspx.cs:

protected override PageStatePersister PageStatePersister
{
    get
    {
        return new SessionPageStatePersister(this);
    }
}
5 голосов
/ 07 января 2011

Чтобы использовать ваш собственный класс PageAdapter, вы должны зарегистрировать его в файле .browser. Вам нужно добавить (если у вас его еще нет) каталог App_Browsers. Затем добавьте файл .browser со следующим XML

<browsers>
    <browser refID="Default">
        <controlAdapters>
           <adapter controlType="System.Web.UI.Page" adapterType="{Your adapter type}" />
        </controlAdapters>
    </browser>
</browsers> 

замените {ваш тип адаптера} на ваш тип адаптера.

Подробнее здесь

Надеюсь, это поможет.

...