背景参照については、参照:Magento:オブザーバーを外部スクリプトで動作させるにはどうすればよいですか?
フロントエンドコントローラーのアクションを外部スクリプトから「複製」するための推奨される方法を尋ねたいと思いました。MagentoEE1.12の外部SSOログインを作成しています。
私のコードは、phpファイルに次のように存在します。test.phpを作成し、ユーザー(185)をユーザーIDに置き換えることで、テストできます。ページに移動してから、もう一度移動します。ログインおよびログアウトしていることに気付くでしょうが、adminではオンラインとして表示されません。読む...
<?php
umask(0);
require_once 'app/Mage.php';
Mage::app("default");
// Set the session to frontend according to many suggestions
Mage::getSingleton("core/session", array("name" => "frontend"));
// Alan Storm suggestion to load specific area in Magento (frontend)
Mage::app()->loadArea(Mage_Core_Model_App_Area::AREA_FRONTEND);
// Load My Specific User
$user = Mage::getModel('customer/customer')->load(185)->setWebsiteId(Mage::app()->getStore()->getWebsiteId());
// Get the session object
$session = Mage::getSingleton('customer/session');
// Make it look good for debugging
echo "<PRE>";
// Toggle the customer logged in / logged out upon page load
if ($session->isLoggedIn())
{
try
{
$session->session->setCustomer($user);
echo "LOGGED IN<br>";
var_dump($session->getCustomer()->getIsJustConfirmed());
} catch (Mage_Core_Exception $e) {
$message = $e->getMessage();
var_dump($message);
}
} else {
$session->logout();
}
var_dump($session->getCustomer());
echo $session->isLoggedIn() ? $user->getName().' is online!' : 'not logged in';
?>
このコードはユーザーにログインしますが、Mage_Log、Mage_Persistent、またはconfig.xmlのフロントエンド領域にアタッチされたcontroller_action_predispatchおよびcontroller_action_postdispatchイベントに依存するコントローラーのない他のモジュールは起動しません。
Mage_Logは、customer_loginを監視してbindCustomerLogin()関数を起動する(上記のAlan Stormの提案を使用しているため)が、コントローラーディスパッチが起動せず、モジュールが正しく機能しないという状況の完璧な例です。
これらの他のモジュールは、外部スクリプト(またはcontroller_front_init_routersイベントを監視しているグローバルオブザーバー)からどのようにトリガーされる可能性がありますか?
編集: 解決策これが上記のベンチマークによる提案の最終結果です...私はMage_Customerコントローラーをエミュレートしています。以下のスクリプトは、COMPLETEmagentoログインを実行する方法を示しています。広範囲にテストされていませんが、ユーザーがバックエンドにログインしていることを示しています。これは私がこれまでに見た中で最も完全なソリューションです。
public function autoMageLogin() {
// Include the controller itself so the object can be used
include ('/var/www/app/code/core/Mage/Customer/controllers/AccountController.php');
// Configure Magento to think its using the frontend
Mage::getSingleton("core/session", array("name" => "frontend"));
Mage::getConfig()->init();
Mage::getConfig()->loadEventObservers('frontend');
Mage::app()->addEventArea('frontend');
Mage::app()->loadArea(Mage_Core_Model_App_Area::AREA_FRONTEND);
// Prepare the request as if it were coming from the specific
// controller (I've chosed Mage_Customer as my chosen controller
// to 'emulate' in php code
$request = Mage::app()->getRequest();
$request->setRouteName('customer');
$request->setControllerModule('Mage_Customer');
$request->setRoutingInfo('');
$request->setModuleName('customer');
$request->setControllerName('account');
$request->setModuleKey('module');
$request->setControllerKey('account');
$request->setActionName('loginPost');
$request->setActionKey('action');
$response = Mage::app()->getResponse();
// Instantiate a new AccountController object using the modified request
// and the modified response (see the include() above)
$accountControl = new Mage_Customer_AccountController($request, $response);
// Dispatch events associated to the controller
Mage::dispatchEvent('controller_action_predispatch', array('controller_action' => $accountControl));
Mage::dispatchEvent('controller_action_predispatch_customer', array('controller_action' => $accountControl));
Mage::dispatchEvent('controller_action_predispatch_customer_account_loginPost', array('controller_action' => $accountControl));
// Load the current user
$user = Mage::getModel('customer/customer')->load(185)->setWebsiteId(Mage::app()->getStore()->getWebsiteId());
// Grab the current session
$session = Mage::getSingleton('customer/session');
// From this point forward, emulate the controller actions
if (!$session->isLoggedIn()){
try{
$session->setCustomerAsLoggedIn($user);
$session->renewSession();
echo "LOGGED IN<br>";
} catch (Mage_Core_Exception $e) {
$message = $e->getMessage();
var_dump($message);
}
} else {
echo "LOGGED OUT<br>";
$session->logout();
}
// Now fire the post controller action events
Mage::dispatchEvent('controller_action_postdispatch_customer_account_loginPost', array('controller_action'=>$accountControl));
Mage::dispatchEvent('controller_action_postdispatch_customer', array('controller_action'=>$accountControl));
Mage::dispatchEvent('controller_action_postdispatch', array('controller_action'=>$accountControl));
// log to the screen and be done
var_dump($session->getCustomer());
echo $session->isLoggedIn() ? $session->getCustomer()->getName().' is online!' : 'not logged in';
die();
}