ASP.NET MVC - альтернатива использованию сеанса

У меня есть представление ASP.NET MVC, которое использует jquery.Uploadify для отправки файлов на один из моих контроллеров для использования в мое приложение и один из побочных эффектов, которые я заметил с помощью Uploadify, заключается в том, что когда Flash-файл, который Uploadify использует для отправки файлов на сервер, отправляет моему контроллеру, он получает свой собственный SessionID из ASP.NET. Конечно, это было бы хорошо, если бы мой контроллер загрузки не использовал сеанс для хранения списка файлов, которые были загружены текущим пользователем для будущих манипуляций моим приложением ... Итак, учитывая эту проблему, после того, как я загружу файлы с моим представлением сеанс текущего пользователя не содержит никаких файлов, которые были только что опубликованы.

Любые предложения о том, как достичь того, чего я хочу, не полагаясь на сеансы (и, желательно, без базы данных)?


person Nathan Taylor    schedule 11.08.2009    source источник


Ответы (4)


Поскольку Uploadify - это чисто интерфейсный скрипт, я не понимаю, почему он получает сеанс из ASP.NET. Я также не совсем понимаю, в чем ваша конкретная проблема.

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

person Chris Johnston    schedule 11.08.2009
comment
По сути, это проблема, да. Я подумал о кешировании загрузок в базу данных, но это похоже на попытку забить гвоздь грузовиком ... - person Nathan Taylor; 11.08.2009

Может быть, статическая хеш-карта, ключом которой является пользователь: ip клиента? Значением будет любой объект, который вы хотите сохранить в разных сеансах.

person Freddy    schedule 11.08.2009
comment
На самом деле это совсем не плохо. Спасибо, сэр. - person Nathan Taylor; 11.08.2009
comment
Конечно, это не сработает в таком сценарии, как пользователь в кафе, хотя, если бы я должен был передать идентификатор сеанса с операцией загрузки, а затем использовать HashMap идентификаторов сеансов, я мог бы просто явно использовать предоставленный сеанс Я БЫ. Можно ли получить объект сеанса для данного идентификатора сеанса? - person Nathan Taylor; 11.08.2009
comment
Другой идентификатор сеанса указывает на то, что существует новый сеанс, старый больше недоступен (ну, не в текущем сеансе), если вы не сохраните предыдущий. Сессия - это объект, и вы можете сохранить его в своем хэше, однако я думаю, что этот обходной путь вызовет больше проблем, чем те, которые он решает. Но о каком случае вы имеете в виду в кофейне? Пользователь меняет IP-адрес? - person Freddy; 11.08.2009
comment
В сценарии кофейни будет несколько пользователей с одним и тем же IP-адресом, что сделает мой UserTable мостом для нескольких пользователей. Если вместо этого я использую идентификатор сеанса, я могу гарантировать, что значение будет уникальным. Я добавил свою реализацию UserTable в сообщение выше. Кажется, он делает то, что я хочу, хотя я еще не тестировал его тщательно. Очевидно, я не собираюсь заменять Session на UserTable, потому что мне действительно нужен только UserTable в этом одном сценарии. Тем не менее, я храню UserTable в BaseController для всеобщего доступа. - person Nathan Taylor; 11.08.2009
comment
Хорошо, понятно. Вот почему я предложил использовать «user: ip» в качестве ключа для хэш-карты. Я считаю, что эта комбинация должна быть уникальной в 99,99% случаев. - person Freddy; 11.08.2009
comment
Кстати, пользователь означает пользователя, который подключен к вашему сеансу, поэтому ваш ключ будет такой строкой, как freddy: 207.95.30.3 - person Freddy; 11.08.2009

Один момент для перекрестной проверки - вы сделали сеанс «живым», добавив в него некоторые данные перед загрузкой? ASP.NET регенерирует сеансы до тех пор, пока в нем не появятся данные.

person Wyatt Barnett    schedule 11.08.2009
comment
Да, сессия действительно прямая. Проблема касается SWFUpload, а не только меня. :) - person Nathan Taylor; 11.08.2009
comment
Попался. Я бы использовал отладчик http (например, Fiddler2) и посмотрел, что происходит в сети. Что-то здесь не совсем складывается. По крайней мере, согласно моему паучьему чутью. - person Wyatt Barnett; 12.08.2009

Это решение, которое я придумал. Я не проводил много тестов, но, похоже, это приемлемая альтернатива сеансу в моем текущем сценарии. Я буду использовать Session_End / Session_Start Global.asax, чтобы гарантировать создание и удаление строк по мере необходимости.

public class UserTable : Dictionary<string, Dictionary<string, object>>
{
    public new object this[string key]
    {
        get
        {
            object value = null;
            if (HttpContext.Current != null)
            {
                var sessionId = HttpContext.Current.Session.SessionID;
                if (ContainsKey(sessionId) && base[sessionId].ContainsKey(key))
                    value = base[sessionId][key];
            }
            else
                throw new Exception("No HttpContext present.");
            return value;
        }
        set
        {
            if (HttpContext.Current != null)
            {
                var sessionId = HttpContext.Current.Session.SessionID;
                if (!ContainsKey(sessionId))
                    Add(sessionId, new Dictionary<string, object>());
                if (!base[sessionId].ContainsKey(key))
                    base[sessionId].Add(key, value);
                else
                    base[sessionId][key] = value;
            }
            else
                throw new Exception("No HttpContext present.");
        }
    }

    public object this[string sessionId, string key]
    {
        get
        {
            object value = null;
            if (ContainsKey(sessionId) && base[sessionId].ContainsKey(key))
                value = base[sessionId][key];
            return value;
        }
        set
        {
            if (!ContainsKey(sessionId))
                Add(sessionId, new Dictionary<string, object>());
            if (!base[sessionId].ContainsKey(key))
                base[sessionId].Add(key, value);
            else
                base[sessionId][key] = value;
        }
    }

    public void Add(string sessionId)
    {
        Add(sessionId, new Dictionary<string, object>());
    }

    public void Add()
    {
        if (HttpContext.Current != null)
            Add(HttpContext.Current.Session.SessionID);
        else
            throw new Exception("No HttpContext present.");
    }

    public new void Remove(string sessionId)
    {
        base.Remove(sessionId);
    }

    public void Remove()
    {
        if (HttpContext.Current != null)
            Remove(HttpContext.Current.Session.SessionID);
        else
            throw new Exception("No HttpContext present.");
    }
}
person Nathan Taylor    schedule 11.08.2009