Предложите пользователю входить в систему после того, как он примет определенные меры

Одна вещь можно сделать на моем рэпе лирический сайт объяснения, похожа на объяснения (после того как Вы зарегистрированы):

http://dl.getdropbox.com/u/2792776/screenshots/2010-01-17_1645.png

Я хотел бы показать "Подобные" ссылки пользователям, которые не зарегистрированы, и затем, когда незарегистрированный пользователь нажимает "Like", покажите ему лайтбокс с "Входом в систему или Регистром" форма (как Digg / Reddit)

http://dl.getdropbox.com/u/2792776/screenshots/2010-01-17_1650.png

Что лучший способ состоит в том, чтобы выполнить это?

В настоящее время я использую этот подход:

  1. Нажатие "как" СООБЩЕНИЯ к /annotations/:id/vote (тело POST указывает, любит ли пользователь или "не любит").
  2. vote Действие контроллера аннотации имеет a require_user before_filter это похоже на это:

    def require_user
      unless current_user
        store_desired_location
        flash[:notice] = "You'll need to login or register to do that"
        redirect_to login_path # map.login '/login', :controller => 'user_sessions', :action => 'new'
        return false
      end
    end
    
  3. user_sessions#new похож на это:

    def new
      @user_session = UserSession.new
      respond_to do |format|
        format.html {}
        format.js {
          render :layout => false
        }
      end
    end
    

Проблема состоит в том, что перенаправление, кажется, не работает правильно по JavaScript:

http://dl.getdropbox.com/u/2792776/screenshots/2010-01-17_1700.png

Как я заставляю это перенаправлять правильно?

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

8
задан Tom Lehman 17 January 2010 в 22:05
поделиться

2 ответа

Нет много причин, чтобы люди догадывались... Вы сказали, что можете найти журнал построения - точное местоположение любого выходного файла будет там. Чтобы убедиться, что вы видите правильный файл журнала сборки, окно вывода в VS будет иметь ссылку на файл, который был создан конкретным запуском сборки:

1>Build log was saved at "file://c:\DevTrees\cppTest\Debug\BuildLog.htm"
1>cppTest - 0 error(s), 2 warning(s)

Если у вас возникли проблемы с интерпретацией, отправьте содержимое.

-121--4716568-

Как сказано выше, просто поместите все данные, которые вы хотите получить обратно, в массив и закодируйте их.

<?php

echo json_encode(array(
    'html' => $html,
    'foo' => $bar,
    'bar' => $baz
));

?>

Также, как сказано, вам не нужен json2.js. Можно выполнить синтаксический анализ данных JSON с помощью любой из ajax-функций jQuery, указав тип данных json.

$.ajax({
    type: 'POST',
    url: 'path/to/php/script.php',
    dataType: 'json',
    data: 'foo=bar&baz=whatever',
    success: function($data) {
        var html = $data.html;
        var foo = $data.foo;
        var bar = $data.bar;

        // Do whatever.
    }
});

ИЗМЕНИТЬ В значительной степени то, что сказал Хория. Единственный вариант, который я мог бы увидеть, это если бы вы хотели все в том же массиве.

Например:

PHP:

<?php

// You have your comment array sent up as you want as $comments
// Then just prepend the HTML string onto the beginning of your comments array.
// So now $comments[0] is your HTML string and everything past that is your comments.
$comments = array_unshift($comments, $your_html_string);

echo json_encode($comments);

?>

jQuery:

$.ajax({
    type: 'POST',
    url: 'path/to/php/script.php',
    dataType: 'json',
    data: 'foo=bar&baz=whatever',
    success: function($comments) {
        // Here's your html string.
        var html = $comments[0];

        // Make sure to start at 1 or you're going to get your HTML string twice.
        // You could also skip storing it above, start at 0, and add a bit to the for loop:
        // if x == 0 then print the HTML string else print comments.
        for (var x = 1; x < $comments.length; x++) {
            // Do what you want with your comments.
            // Accessed like so:
            var name = $comments[x].name;
            var comment = $comments[x].comment;
            var datetime = $comments[x].datetime;
        }
    }
});
-121--2463759-

Здесь можно решить несколько проблем.

  1. Браузеры обычно не разрешают перенаправление на запрос POST.

  2. redirect _ to не сохраняет формат без дополнительного ввода.

  3. Расположение хранилища не сохраняет данные формы.

Все эти проблемы можно решить путем устранения перенаправлений.

Вот как я передал его в прошлом:

Вместо того, чтобы перенаправлять в required_user, рендеринг. Если фильтр перед перенаправляет или визуализирует ожидающее действие, оно отменяется. (Также нет необходимости возвращать значение false). К сожалению, этот маршрут размывает границы контроллера. Но позволяет простой HTML-откат, и предоставляет себе DRYness.

Высокоуровневое представление нового рабочего потока будет выглядеть следующим образом:

  1. Запрос на аннотации # vote (POST)
  2. required _ user filter fails
  3. rending new session
  4. reending login information and original POST data back to annotations # vote (POST)
  5. new filter in votor захватывает информацию о сеансе и регистрируется. голосование проходит, как и ожидалось. В случае неуспешного входа вернитесь к 3.
  6. аннотации # vote redirects/renders в соответствии с

Начните с переработки require_user для визуализации шаблона user_sessions#new.

def require_user
  unless current_user
    flash[:notice] = "You'll need to login or register to do that"
    @user_session ||= UserSession.new
    respond_to do |format|
      format.html {render :template => 'user_sessions/new'}
      format.js {
        render :template => 'user_sessions/new', :layout => false
      }
    end
  end
end

@ user _ session | | = UserSession.new обеспечивает возврат ошибок проверки в форму.

Теперь мы должны увеличить ваш шаблон user_session#new, чтобы он мог запомнить действие. Кроме того, если вы планируете использовать lightboxes, это должно быть частично визуализировано соответствующими RJS или new.html.erb.

Сначала мы создадим частичную для создания скрытых полей, сохраняющих данные POST, которые были бы потеряны при перенаправлении:

<% if params[:controller] == "annotations" %>
  <% content_for :old_form do %>
    <%= hidden_field_tag "annotation[song_id]", params[:annotation][:song_id] %>
    <%= hidden_field_tag "annotation[vote]", params[:annotation][:vote] %>
  <% end %>
<% end %>

Затем визуализируем частичную в частичном входе, которая займет ваш lightbox:

<%= render :partial => vote_form_replica %>

<% url = params[:controller] == "user_sessions ? user_sessions_url : {} %>
<% form_tag @user_session, :url => url do |f| %>
  <%= yield :old_form %>
  <%= f.label :user_name %>
  <%= f.text_field :user_name %>
  <%= f.label :password %>
  <%= f.password_field :password %>
  <%= submit_tag %>
<%end%>

Пустой хэш для URL в form_tag выглядит как ошибка, но не является. Это обеспечивает разноску данных формы по URL-адресу, по которому была выполнена визуализация формы. На данном этапе должны быть аннотации/: id/vote

Теперь для входа в систему новому фильтру. По существу, он будет делать то, что когда-либо UserExhiendureController # создает, без рендеринга/перенаправления. Следующее копируется из плагина проверки подлинности RESTful.

def authenticate
  self.current_user = User.authenticate(params[:login], params[:password])
  if logged_in?
    if params[:remember_me] == "1"
       current_user.remember_me unless current_user.remember_token?
       cookies[:auth_token] = { :value => self.current_user.remember_token, 
         :expires => self.current_user.remember_token_expires_at }
    end
  end
end

Все, что осталось, это убедиться, что порядок фильтрации правильный.

before_filter :authenticate, :require_user, :only => :vote

N.B.: Вероятно, вы не собираетесь использовать эту версию require_user без этой версии аутентификации, поэтому имеет смысл объединить их в единый фильтр.

И все. Способ настройки обеспечивает надежный код DRY, легко используемый повторно. Размещая новые фильтры в GroupController, они доступны в любом контроллере. С этого момента добавление этой функциональности к любым другим контроллерам/действиям занимает всего 3 простых шага:

  1. Создайте новую частичную часть, смоделированную после vote_form_replica частичной.
  2. Добавьте соответствующий оператор визуализации в новый шаблон сеанса.
  3. Примените фильтры к действиям.
3
ответ дан 6 December 2019 в 00:57
поделиться

Я бы подошел к этому так, как вы описываете в нижней части вашего вопроса. Перед первым отображением страницы проверьте, зарегистрирован ли пользователь. Если да, то ссылки "Мне нравится" должны использовать свое обычное поведение. Если нет, привяжите событие клика, чтобы показать панель регистрации/входа. В этом нет ничего такого, что нельзя было бы использовать повторно. На самом деле, мы используем именно этот метод в моей работе. Любое действие пользователя, требующее аутентификации, либо следует его нормальному поведению, либо всплывает общая панель входа, в зависимости от состояния входа на момент загрузки страницы.

0
ответ дан 6 December 2019 в 00:57
поделиться
Другие вопросы по тегам:

Похожие вопросы: