Этот код потокобезопасен? Как я могу сделать это потокобезопасным? - PullRequest
6 голосов
/ 11 августа 2009

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

С учетом следующей функции:

public class SecurityService
{
    public static Guid GetCurrentUserID()
    {
        if (Thread.CurrentPrincipal is MyCustomPrincipal)
        {
            MyCustomIdentity identity = null;
            MyCustomPrincipal principal = (MyCustomPrincipal)Thread.CurrentPrincipal;
            if (principal != null)
            {
                identity = (MyCustomIdentity)principal.Identity;
            }

            if (identity != null)
            {
                return identity.UUID;
            }
        }
        return Guid.Empty;
    }
}

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

Или этот, который будет обращаться к базе данных - может ли это пойти не так?

    public static User GetCurrentUser()
    {
        var uuid = GetCurrentUserID();
        if (uuid != null)
        {
            var rUser = new UserRepository();
            return rUser.GetByID(uuid);
        }
        return null;
    }

Существует много дискуссий о принципах многопоточности, но я склонен упасть и запутаться, когда дело доходит до фактического применения его и знания, когда его применять. Любая помощь приветствуется.

Я могу объяснить больше о контексте / назначении этих функций, если неясно.

EDIT: Функция rUser.GetByID () в основном обращается к хранилищу, которое ищет базу данных, используя NHibernate. Так что я думаю, что база данных здесь является «общим ресурсом», но на самом деле она не блокируется или не модифицируется для этой операции ... в таком случае я думаю, что все в порядке ...?

Ответы [ 2 ]

12 голосов
/ 11 августа 2009

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

Оба должны быть поточно-ориентированными.

Я не могу сказать, является ли GetByID потокобезопасным или нет. Посмотрите, имеет ли он доступ к каким-либо общим / статическим ресурсам. Если это так, то он не является поточно-ориентированным без какого-либо дополнительного кода для защиты этих ресурсов.

3 голосов
/ 11 августа 2009

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...