Получить поле из mnesia

#erlang #mnesia

#эрланг #mnesia #erlang

Вопрос:

У меня есть таблица mnesia users с полем пользователя и пароля.

Данные из моей таблицы:

 [{users, <<"user_name">>, <<"password">>}].
  

Мне нужно получить пароль по имени пользователя. Я создаю:

 mnesia:dirty_read({users, <<"user_name">>}).
  

Но оно возвращает [] .

Как я могу получить пароль по имени пользователя?

Ответ №1:

Вы не указали используемый вами синтаксис записи, но он выглядит как

-запись(пользователи, {имя пользователя, пароль}).

… или что-то подобное. Итак, предположим, что при создании таблицы вы сделали что-нибудь особенное для установки идентификатора? В этом примере «имя пользователя» (первая запись в записи пользователей) должно быть идентификатором по умолчанию, если вы не сделали что-то особенное.

Если у вас по-прежнему возникают проблемы, рассмотрите возможность использования mnesia:match_object/1 или / 3. Вы указываете в синтаксисе шаблона / записи ту часть, которой вы должны соответствовать (в данном случае, имя пользователя), и используете =’‘, чтобы соответствовать всему, чего вы не знаете или о чем не заботитесь (в данном случае это была бы часть пароля).

Я надеюсь, что это поможет!

Ответ №2:

Вы можете сделать что-то вроде приведенного ниже:

YourPasswd = mnesia:ets(fun()-> mnesia:dirty_read({пользователи, идентификатор пользователя}) конец),

 укажите ваш PASSWD из 
 [] -> {ошибка, 'Пользователь не найден'};
 [{users,_UserID,Passwd}] ->
 {успех, Passwd}
 завершение.

Надеюсь, данные правильно записаны в mnesia 🙂

Ответ №3:

посмотрите на эту функцию:

-определить(ИМЯ_ТАБЛИЦЫ,пользователи).

get_password_by_username(Имя пользователя)-> 
 F = fun(U)-> mnesia: прочитать({?ИМЯ_ТАБЛИЦЫ,U}) конец, 
 mnesia: активность(транзакция,F, [Имя пользователя], mnesia_frag).

Это даст вам результат. Хорошая вещь с mnesia: activity / 4 заключается в том, что независимо от того, фрагментирована таблица или нет, ответы в порядке. удачи

Ответ №4:

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

У меня есть модуль аутентификации в одном из моих проектов, и у меня такие же цели, как у вас. Поскольку у меня пока не было возможности оптимизировать, я использую транзакции mnsesia и списки для имен пользователей и паролей.

Вот часть моего модуля аутентификации.

 -module(auth).

-export([init/1, add_user/2, start_session/2]).
-record(auth_user, {username, password}).

init(Nodes) ->
    mnesia:create_table(auth_user,
        [{disc_copies, Nodes},
        {attributes, record_info(fields, auth_user)}]).

add_user(Username, Password) ->
    T = fun() -> 
    mnesia:write(#auth_user {
                username = Username,
                password = Password})
    end,
    mnesia:transaction(T).

start_session(Username, Password) ->
    T = fun() ->
        mnesia:read(auth_user, Username)
    end,
    {atomic, Ret} = mnesia:transaction(T),
    case Ret of
    [U] ->
        if (U#auth_user.password == Password) ->
            true;
        true ->
            false
        end;
    _Else ->
        false
    end.
  

После компиляции и запуска оболочки erlang.

 Eshell V5.8.3  (abort with ^G)
1> mnesia:create_schema([node()]).
ok
3> mnesia:start().
ok
4> auth:init([node()]).
{atomic,ok}
5> auth:add_user("rodericktaylor", "password").
{atomic,ok}
6> true = auth:start_session("rodericktaylor", "password").
true
7>
  

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

 start_session_dirty(Username, Password) ->
    case mnesia:dirty_read(auth_user, Username) of
    [U] ->
        if (U#auth_user.password == Password) ->
            true;
        true ->
            false
        end;
    _Else ->
        false
    end.
  

Следующие команды в оболочке erl показывают, что это работает так, как вы ожидаете.

 12> auth:add_user(<<"rodericktaylor">>, <<"binarypassword">>).            
{atomic,ok}
14> true = auth:start_session_dirty(<<"rodericktaylor">>, <<"binarypassword">>).
true
15>
  

Я надеюсь, что я помог.