Как хранить пользовательские данные в сложном объекте в боте

Я пытаюсь сохранить объект в UserData бота.

Прежде всего, у меня есть следующий класс:

public class PersonalData 
{
    public string Name { get; set; }
    public int Age { get; set; } 
}

В моем классе Luis мне нужна переменная типа PersonalData.

public class Luis : LuisDialog<object> 
{
    PersonalData personalData;

Это уже приводит к проблеме, что отладчик никогда не заходит ни в какие мои интенты. Что случилось с этим?

Теперь, если я создам объект PersonalData с таким намерением:

PersonalData personalData = new PersonalData();

он будет успешно создан. Но когда я хочу присвоить значение своему объекту

if (!context.UserData.TryGetValue(ContextConstants.personalData, out personalData)) 
{
        personalData.Name = userName;
        context.UserData.SetValue(ContextConstants.personalData, personalData.Name);
}

Как только программа пытается установить personalData.Name в userName, я получаю NullReferenceException, а мой объект PersonalData равен нулю. Я дважды проверил, что имя пользователя не пусто.

Что мне не хватает?

Заранее спасибо!


person Soeren    schedule 13.01.2017    source источник


Ответы (1)


Если вы используете UserData, зачем вам нужна переменная в вашем диалоге?

Если вы хотите иметь переменную, ваш PersonalData должен быть сериализуемым, поэтому вам нужно будет добавить в класс атрибут [Serializable].

Но вместо того, чтобы сохранять переменную в диалоговом окне, вы всегда должны обращаться к объекту PersonalData, который вы будете сохранять в сумке UserData.

Теперь, когда вы устанавливаете значение, вместо сохранения всего объекта вы просто сохраняете имя, поэтому, когда вы извлекаете личные данные из пакета UserData, вы извлекаете имя, а не объект, поэтому вы получить NullReferenceException, потому что personalData.Name не существует.

Я думаю, что код должен быть:

if (!context.UserData.TryGetValue(ContextConstants.personalData, out personalData)) 
{
        personalData.Name = userName;
        context.UserData.SetValue(ContextConstants.personalData, personalData);
}

Чтобы узнать больше о состоянии, вы также можете посмотреть это образец.

person Ezequiel Jadib    schedule 13.01.2017
comment
Мне пришлось инициализировать мой объект PersonalData после оператора IF следующим образом: personalData = new PersonalData(); и тогда он отлично работал с вашим решением. - person Soeren; 23.01.2017
comment
Я понял, что если функция TryGetValue дает сбой, выходное значение устанавливается равным нулю. Вот почему нужно сначала инициализировать объектную переменную, а затем устанавливать какие-либо значения. - person Soeren; 23.01.2017