Zend get foreign ID from login table - zend-framework

I am using Zend and Doctrine to login using a table containing also a foreign ID to another table. I need to get this ID in order to use it in a Doctrine query (through the controller) to the database like this:
$q = Doctrine_Query::create()
->from('Lost_Model_Item i')
->where('i.StatID = ?', 'I need the ID here')
$result = $q->fetchArray();
I have tried to get it like this:
Zend_Auth::getInstance()->getIdentity()->ID
But it seems to not work. I am new to Zend and a bit lost here. Could you please help?
As I ma working with doctrine I have created an adapter as follow:
public function authenticate()
{
$q = Doctrine_Query::create()
->from('Lost_Model_Station u')
->where('u.username = ? AND u.password = MD5(?)',
array($this->username, $this->password)
);
$result = $q->fetchArray();
if (count($result) == 1) {
$this->_resultArray = $result[0];
return new Zend_Auth_Result(
Zend_Auth_Result::SUCCESS, $this->username, array());
} else {
return new Zend_Auth_Result(
Zend_Auth_Result::FAILURE, null,
array('Authentication unsuccessful')
);
}
}

How about using getIdentity to get the username and then use a sql join on Lost_Model_Item and Lost_Model_Station
$q = Doctrine_Query::create()
->from('Lost_Model_Item i')
->leftJoin('i.Lost_Model_Station u')
->where('u.username = ?', Zend_Auth::getInstance()->getIdentity())
$result = $q->fetchArray();
This assumes that there is a doctrine "hasOne" relation defined for Lost_Model_Station (in the base class):
public function setUp()
{
parent::setUp();
$this->hasOne('Lost_Model_Item', array(
'local' => 'StatID',
'foreign' => 'whatever_id_StatID_relates_to'));
}

Zend_Auth::getInstance()->getIdentity()->ID
well you got what you store in Identity . You need to post the code where you ask user to login . Because there you are not storing the ID inside the session storage which Zend_Auth uses . Basically do this there
$row = $this->_adapter->getResultRowObject();
Zend_Auth::getInstance()->getStorage()->write($row);
where $this->_adapter is
$this->_adapter = new Zend_Auth_Adapter_DbTable();
$this->_adapter->setTableName('users')
->setIdentityColumn('email')
->setCredentialColumn('password');

Related

How to write an extbase Repository-Method for Update in TYPO3?

I have written an update query in TYPO3, Now I need to change it to query-object repository method. How to change the code below?
public function updatePaymentDetails($uid, $txnID, $amt, $stats)
{
$itemUID = $uid;
$transID = $txnID;
$amountPaid = $amt;
$txStatus = $stats;
$tableName = 'tx_paypalpayment_domain_model_transactions AS tpp';
$whereCondition = 'tpp.uid=' . '"' . $itemUID . '"';
$setValues = ['transactionid' => $transID, 'amount' => $amountPaid, 'txnstatus' => $txStatus];
$result = $GLOBALS['TYPO3_DB']->exec_UPDATEquery($tableName, $whereCondition, $setValues);
return $result;
}
I created this much in my own idea (don't know it is correct or not), What should be the remaining portion?
public function paymentUpdate($uid, $txnID, $amt, $stats) {
$query = $this->createQuery();
$query->matching(
$query->logicalAnd(
$query->equals("transactionid", $txnID),
$query->equals("amount", $amt),
$query->equals("txnstatus", $stats)
)
);
/*--- Update Code ---*/
return $query->execute();
}
Is there any way to do that?
The TYPO3/Extbase way is to first fetch your transaction from the persistence layer then apply your changes to the domain object and then update it in your repository.
Something like below in your controller action:
$transaction = $this->transactionRepository->findByIdentifier($itemUid);
$transaction->setTransactionId($transID);
$transaction->setAmount($amountPaid);
$transaction->setStatus($txStatus);
$this->transactionRepository->update($transaction);
If you wants to do a direct update instead of first fetching the record then take a look at the \TYPO3\CMS\Core\Database\Query\QueryBuilder (Only exists in newer versions of TYPO3 - 8.7 and above). In older versions of TYPO3 you could take a look at $GLOBALS['TYPO3_DB']->exec_*.

Joomla: get all users in a usergroup

I am working on a component where I want to show all users of a specific usergroup. Right now I found two solutions for this but I'm not feeling comfortable with both of them.
Solution 1
$usersID = JAccess::getUsersByGroup(3);
$users = array();
foreach($usersID as $cUserID)
{
$users[] = JFactory::getUser($cUserID);
}
This one seems to produce two database queries every time JFactory::getUser($cUserID) is called. I really don't want this.
Solution 2
function inside model
function getUsers()
{
if(!isset($this->users))
{
$groupID = 3;
$db = JFactory::getDbo();
$query = $db->getQuery(true);
$select = array( 'users.id', 'users.name');
$where = $db->quoteName('map.group_id') . ' = ' . $groupID;
$query
->select($select)
->from( $db->quoteName('#__user_usergroup_map', 'map') )
->leftJoin( $db->quoteName('#__users', 'users') . ' ON (map.user_id = users.id)' )
->where($where);
$db->setQuery($query);
$this->users = $db->loadObjectList();
}
return $this->users;
}
This one works like a charm but I feel there should be a "more Joomla! way" of doing this. I don't like working on their tables.
Right now I'm going with solution 2 but i really wonder if there is some better way to do it.

Zend insert user and set value to max()+1

My code:
public function insertMember($member)
{
$maxOrderNumber = $this->select()
->from($this, array(new Zend_Db_Expr('max(order_number)')));
$id = $this->insert($member, $maxOrderNumber);
return $id;
}
I want to insert member to last position in members table and order_number entity. Tried with $maxOrderNumber but i keep getting 0 value in database.
Im using MySql. Also i have user_id with (AI) Autoincrement so i'm forced to function this way.
public function insertMember($member)
{
$maxOrderNumber = $this->select()
->from($this, array(new Zend_Db_Expr('max(order_number)')));
$stmt = $maxOrderNumber ->query();
$result = $stmt->fetchAll();
$id = $this->insert($member, $result ['order_number']);
return $id;
}
soemthing like that...

How to prevent SQL injection in PhalconPHP when using sql in model?

Let's say I am building a search that finds all the teacher and got an input where the user can put in the search term. I tried reading the phalcon documentation but I only see things like binding parameters. I read the other thread about needing prepare statements do I need that in Phalcon as well?
And my function in the model would be something like this:
public function findTeachers($q, $userId, $isUser, $page, $limit, $sort)
{
$sql = 'SELECT id FROM tags WHERE name LIKE "%' . $q . '%"';
$result = new Resultset(null, $this,
$this->getReadConnection()->query($sql, array()));
$tagResult = $result->toArray();
$tagList = array();
foreach ($tagResult as $key => $value) {
$tagList[] = $value['id'];
....
}
}
My question is for the Phalcon framework is there any settings or formats I should code for this line $sql = 'SELECT id FROM tags WHERE name LIKE "%' . $q . '%"';
And also any general recommendation for preventing SQL Injection in PhalconPHP controllers and index would be appreciated.
For reference:
My controller:
public function searchAction()
{
$this->view->disable();
$q = $this->request->get("q");
$sort = $this->request->get("sort");
$searchUserModel = new SearchUsers();
$loginUser = $this->component->user->getSessionUser();
if (!$loginUser) {
$loginUser = new stdClass;
$loginUser->id = '';
}
$page = $this->request->get("page");
$limit = 2;
if (!$page){
$page = 1;
}
$list = $searchUserModel->findTeachers($q, $loginUser->id, ($loginUser->id)?true:false, $page, $limit, $sort);
if ($list){
$list['status'] = true;
}
echo json_encode($list);
}
My Ajax:
function(cb){
$.ajax({
url: '/search/search?q=' + mapObject.q + '&sort=<?php echo $sort;?>' + '&page=' + mapObject.page,
data:{},
success: function(res) {
//console.log(res);
var result = JSON.parse(res);
if (!result.status){
return cb(null, result.list);
}else{
return cb(null, []);
}
},
error: function(xhr, ajaxOptions, thrownError) {
cb(null, []);
}
});
with q being the user's search term.
You should bind the query parameter to avoid an SQL injection. From what I can remember Phalcon can be a bit funny with putting the '%' wildcard in the conditions value so I put them in the bind.
This would be better than just filtering the query.
$tags = Tags::find([
'conditions' => 'name LIKE :name:',
'bind' => [
'name' => "%" . $q . "%"
]
])
Phalcon\Filter is helpful when interacting with the database.
In your controller you can say, remove everything except letters and numbers from $q.
$q = $this->request->get("q");
$q = $this->filter->sanitize($q, 'alphanum');
The shortest way for requests:
$q = $this->request->get('q', 'alphanum');

zfcuser add user role after registration

I'm using Zend Framework 2 with ZfcUser, BjyAuthorize and Doctrine for the database. Registration etc. works very well so far. My problem is, that registered users have no role assigned, so i want to add the role "user" to the user during registration.
I think i could attach this to the "register" event, but i don't know how to do that.
I hope someone can help me ...
(i used this tutorial for setting up zfcuser etc. http://samminds.com/2013/03/zfcuser-bjyauthorize-and-doctrine-working-together/)
public function onBootstrap(MvcEvent $e)
{
$zfcServiceEvents = $e->getApplication()->getServiceManager()->get('zfcuser_user_service')->getEventManager();
$zfcServiceEvents->attach('register', function($e) {
$user = $e->getParam('user');
// probably the role must be added here, with $user->addRole();
// but how do i get the user Role Entity to add from DB?
});
Building on DangelZM's answer, and using another reference (see link at end of my post) about the Event Manager, I came up with this solution which organizes the potential ZfcUser event listeners out into a user listener object.
Note: I created my own user module called NvUser, so depending on the name of your module you'll have to replace all references of NvUser to your user module name.
Summary
I created an NvUserListener object that can itself attach event listeners to the shared event manager, and house the event listener callbacks.
Inside NvUser/Module.php:
<?php
namespace NvUser;
use Zend\Mvc\MvcEvent;
use NvUser\Listener\NvUserListener;
class Module
{
public function onBootstrap(MvcEvent $mvcEvent)
{
$em = $mvcEvent->getApplication()->getEventManager();
$em->attach(new NvUserListener());
}
}
Inside NvUser/src/NvUser/Listener/NvUserListener.php:
<?php
namespace NvUser\Listener;
use Zend\EventManager\AbstractListenerAggregate;
use Zend\EventManager\EventManagerInterface;
use Zend\EventManager\Event;
class NvUserListener extends AbstractListenerAggregate
{
public function attach(EventManagerInterface $events)
{
$sharedManager = $events->getSharedManager();
$this->listeners[] = $sharedManager->attach('ZfcUser\Service\User', 'register', array($this, 'onRegister'));
$this->listeners[] = $sharedManager->attach('ZfcUser\Service\User', 'register.post', array($this, 'onRegisterPost'));
}
public function onRegister(Event $e)
{
$sm = $e->getTarget()->getServiceManager();
$em = $sm->get('doctrine.entitymanager.orm_default');
$user = $e->getParam('user');
$config = $sm->get('config');
$criteria = array('roleId' => $config['zfcuser']['new_user_default_role']);
$defaultUserRole = $em->getRepository('NvUser\Entity\Role')->findOneBy($criteria);
if ($defaultUserRole !== null)
{
$user->addRole($defaultUserRole);
}
}
public function onRegisterPost(Event $e)
{
$user = $e->getParam('user');
$form = $e->getParam('form');
// Do something after user has registered
}
}
Inside NvUser/config/module.config.php:
<?php
namespace NvUser;
return array(
'zfcuser' => array(
'new_user_default_role' => 'user',
),
);
References:
Understanding the Zend Framework 2 Event Manager
Maybe it's not the best solution, but it works for me.
Add user_role_id option in config scope.
public function onBootstrap(MvcEvent $mvcEvent)
{
$zfcServiceEvents = $mvcEvent->getApplication()->getServiceManager()->get('zfcuser_user_service')->getEventManager();
$zfcServiceEvents->attach('register', function($e) use($mvcEvent) {
$user = $e->getParam('user');
$em = $mvcEvent->getApplication()->getServiceManager()->get('doctrine.entitymanager.orm_default');
$config = $mvcEvent->getApplication()->getServiceManager()->get('config');
$defaultUserRole = $em->getRepository('SamUser\Entity\Role')->find($config['user_role_id']);
$user->addRole($defaultUserRole);
});
}
Maybe someone will offer better solution.
This work too.
public function onBootstrap(MvcEvent $mvcEvent)
{
$zfcServiceEvents = $mvcEvent->getApplication()-getServiceManager()->get('zfcuser_user_service')->getEventManager();
$zfcServiceEvents->attach('register', function($e) use($mvcEvent) {
$user = $e->getParam('user');
$em = $mvcEvent->getApplication()->getServiceManager()-get('doctrine.entitymanager.orm_default');
$defaultUserRole = $em->getRepository('SamUser\Entity\Role')-find('id_of_your_role_on_table_role_for_example: '2'');
$user->addRole($defaultUserRole);
});
}
I just used a MySQL trigger
DROP TRIGGER IF EXISTS `user_role_after_insert_trig`;
DELIMITER //
CREATE TRIGGER `user_role_after_insert_trig` AFTER INSERT ON `user`
FOR EACH ROW begin
insert into user_role_linker (user_id,role_id) values (new.user_id, 5);
end
//
DELIMITER ;