I've created a small module that I would like to link account notes with users.
I have written the beginnings of the module that includes a form for adding notes and date created. This works when I access mydomain.com/admin/user_notes.
My question is, how do I get this form to display in the admin section of the site on a users orders history page. eg mydomain.com/users/1245/order-history
I would like our admins who have a specific role to be able to add notes when they view a users order history page.
Thanks in advance for any advice.
you could use a block, create one with the hook_block_info and hook_block_view function.
Like this:
function tips_block_info() {
$block['yourBlockName'] = array(
'info' => t('This my created block'),
'cache' => DRUPAL_NO_CACHE, // Disable caching if you need/want to
);
return $block;
}
Thisby will create an empty block, to fill it with content use hook_block_view:
function moduleName_block_view($delta = '') {
$block = array();
switch($delta) {
// The delta of your block will be the key from the $block array we set in hook_block_info
case 'yourBlockName':
// Set the block title
$block['subject'] = 'Hey I\'m your block title';
$block['content'] = 'Block content goes here can also be the output of any function';
break;
}
return $block;
}
Don't forget to set access permission for your block if you need any, you can do that by editing the block on the block admin page.
Relevant Drupal API links:
hook_block_info
hook_block_view
Related
im learning about angularjs and laravel. Basically i use angular to fetch my data in the forms and than send it to laravel to grab my variables and than create the record, the problem is with one input field (mobile), if i fill the mobile input it doesnt give me any problems, but if i leave it empty (since is not required input) it fails to create the record and give me a undefined index.
How can i make in Laravel to create anyway the record if one variable in my case is empty or not created?
php code:
public function registerUser($inputData)
{
$user = \DB::transaction(function () use ($inputData)
{
$user = User::create([
'email' => $inputData['user']['email'],
'name' => $inputData['user']['name'],
'surname' => $inputData['user']['surname'],
'mobilephone' => $inputData['user']['mobilephone'],
'birth_date' => Carbon::createFromFormat('d-m-Y', $inputData['user']['birth_date']),
]);
$user->save();
//Return the User
return $user;
});
//Return the User instance
return $user;
}
From what you are describing, when you don't fill in the mobile number the front end doesn't send an object which includes "$inputData['user']['mobilephone']". Which would cause an error in the script and prevent it from running. Please post the angular code responsible for transmitting the user information.
If my assumption is correct, you either need to check that these properties all exist in the $inputData before referencing them or have the front end add a dummy value when no value is provided.
OR What ever is holding the record (MySQL or whatever) may not allow this field to be null which would again prevent the insertion. But your description suggests this isn't it.
I'm trying to print a few fields in a block on each profile page.
The block needs to display the fields of the user being viewed, not the logged in user.
$account = user_load($node->uid); - doesn't work. user->uid doesn't either.
Globals user will return the logged in users info.
Not exactly sure how I'm supposed to load anything into a block. Any idea?
Assuming you're viewing a user profile with a URL path like this
drupal/user/USER_ID
You can do as follows :
// Option 1
$user = explode('/', current_path());
$user_id = end($user);
// Option 2
// $path = explode('/', current_path());
// $user_id = $path[count($path)-1];
$account = user_load($user_id, true);
Documentation current_path()
This way you get the last part of the URL and pass it to the user_load function. We set true as second parameter so it loads from the DB and not the cache.
Another way to do the same without breaking the URL into pieces is to use arg() to get the parameters
In this case the code would look like this
// Option 3
// drupal/user/USER_ID
// drupal = arg(0)
// user = arg(1)
// USER_ID = arg(2)
$account = user_load(arg(2), true);
In both cases check that $user_id is an integer, do not let it pass at least is an integer, then you can check the result of user_load.
Update
If you are using the user's name in the URL you can load a full user object by using user_load_by_name()
So the code would change a little bit. Try this :
$account = user_load_by_name(arg(2));
I used arg for simplicity, you can get the user's name from URL as you want.
Hope it helps.
I am using drupal commerce module, i have an issue with anonymous users, when users click on add to cart button, cart is showing extra items which are added by other anonymous users.
I am using custom code for add to cart using ajax. following is the code.
// Add a product to cart on ajax call.
function mymodule_custom_add_to_cart($product_id,$uid){
$line_item = commerce_product_line_item_new(commerce_product_load($product_id));
commerce_cart_product_add($uid, $line_item);
$order = commerce_cart_order_load($uid);
commerce_cart_order_refresh($order);
// loads data array from order object
$data = mymoudle_custom_cart_load_all_variables($order->order_id);
$jsonencoded = json_encode($data);
print $jsonencoded;
}
I dont know why all anonymous users are getting same products in there cart.
Please help me to find out the issue.
UPDATE 1:
I have changed the code for anonymous user as following, then i am getting an error: EntityMetadataWrapperException: Unable to get the data property data as the parent data structure is not set. in EntityStructureWrapper->getPropertyValue() (line 451 of /entity.wrapper.inc
CHANGED CODE
// Add a product to cart on ajax call.
function mymodule_custom_add_to_cart($product_id,$uid){
if($uid == 0){
$order_id = commerce_cart_order_id($uid);
if($order_id == false){
$order = commerce_cart_order_new(0, 'checkout_checkout');
} else {
$order = commerce_order_load($order_id);
}
// Load whatever product represents the item the customer will be
// paying for and create a line item for it.
$product = commerce_product_load($product_id);
$line_item = commerce_product_line_item_new($product, 1, $order->order_id);
commerce_line_item_save($line_item);
// Add the line item to the order using fago's rockin' wrapper.
$order_wrapper = entity_metadata_wrapper('commerce_order', $order);
$order_wrapper->commerce_line_items[] = $line_item;
// Save the order again to update its line item reference field.
commerce_order_save($order);
// loads data array from order object
$data = mymoudle_custom_cart_load_all_variables($order->order_id);
$jsonencoded = json_encode($data);
print $jsonencoded;
}else{
$line_item = commerce_product_line_item_new(commerce_product_load($product_id));
commerce_cart_product_add($uid, $line_item);
$order = commerce_cart_order_load($uid);
commerce_cart_order_refresh($order);
// loads data array from order object
$data = mymoudle_custom_cart_load_all_variables($order->order_id);
$jsonencoded = json_encode($data);
print $jsonencoded;
}
}
UPDATE 2: ISSUE RESOLVED.
Site is crawling by googlebot, which is clicking addtocart link and its adding an product to anonymous user account automatically, so i removed link for addtocart button and used commerce addtocart form.
All anonymous users have uid zero (see documentation). That is the reason why all the items added by different anonymous users are being added to the same shopping cart.
How does one go about creating multiple new users, say in a loop, from an array in a different controller?
I have an issue where attempting to create multiple users in a form submit fails, but creating a single new user works as designed. It appears the issue may be when saving the new user and then bringing the new user_id back in the return statement. Although the new id comes back, subsequent users (2nd, 3rd, etc) all get the same id value, and it appears that the subsequent $this->save calls modify the first created user rather than create add'l ones. Any none of the new users appear in the database. (again, the problem only happens when more than one new users will be created.)
My one small clue is that if I var_dump($user) in my importPublicLDAPUser() function (user.php) just after the $user = $this->save(array('User' => array( ... ))); then for the first element I see both 'modified' and 'created', whereas I see only 'modified' for the rest. This leads me to believe there's a step missing, like the user needs to be saved or commit (??) before the next user can be be created.
I tried changing this to $user = $this->User->save(array('group_id' => 3, ... and adding a 'create' before: $this->User->create(); but these produce errors 'Call to a member function save() on a non-object' and 'Call to a member function create() on a non-object'.
My application manages documents. Each document can have many authors, so it has controllers for: docs, doc-types, users, groups, and authors.
When a new document is entered, the form allows selection of multiple users to create 'Author' records. In addition to the local users table, it also searches our LDAP server (both via auto-sugggest) and also allows input into a text field. So, Authors are selected from
the existing table of users
via the LDAP helper
free text entry.
This result is two arrays: $Authors (from local users tables), and $badAuthors (LDAP and text-input) which the app then tries to add to the local users table when the form is submitted.
The form works just fine if:
one or more authors are added from local users table;
a single author is added from LDAP (succeeds in creating a new entry in users table), and zero or more local users
a single author is added from text input (also succeeds), and zero or more local users
However if two or more non-local users are added ($badAuthors has more than one element) then the form fails. "fails" means that either the Author or User save routine failed, and so it skips the Document commit $this->Docu->commit(); and I spit out an error via ajaxResponse. Thus, the app works as designed, but only with one new User entry at a time, even though the form is designed to allow Authors/badAuthors to be >1.
What I don't understand is why when I loop through bad authors why it doesn't correctly add the users if $badAuthors has more than one element.
As the user enters each name (which is checked against the users table and LDAP via ajax helpers, etc) and then selected, an author_name_list array is built. And then:
foreach($this->params['form']['author_name_list'] as $author_name){
$user_id = $this->Docu->User->field('id',array('User.name' => $author_name));
if($user_id){
$Authors['Author'][]=array(
'docu_id'=>$this->Docu->id
,'user_id'=>$user_id
);
}else{
$badAuthors[] = array('name'=>$author_name);
}
}
So $badAuthors is now those found in LDAP or entered manually.
So now I try to create/save all badAuthors...
docu controller (docu_controller.php):
if(count($badAuthors)){
foreach($badAuthors as $key => $author){
$this->Memo->User->create(); // ** <-- this was missing!! **
if($ldap_author = $this->Docu->User->importPublicLDAPUser($author['name'])){
unset($badAuthors[$key]);
$Authors['Author'] []= array(
'docu_id'=>$this->Docu->id
,'user_id'=>$ldap_author['User']['id']
,'precedence' => $author['precedence']
);
} elseif ($new_author = $this->Docu->User->newReadonlyUser($author['name'])) {
unset($badAuthors[$key]);
$Authors['Author'] []= array(
'docu_id'=>$this->Docu->id
,'user_id'=>$new_author['User']['id']
,'precedence' => $author['precedence']
);
}
}
}
if(!count($badAuthors)){
$authors_saved = true;
foreach($Authors['Author'] as $author_arr){
$this->Docu->Author->create();
if(!$this->Docu->Author->save(array('Author' => $author_arr))){
$authors_saved = false;
break;
}
}
}
user model (user.php)
function afterSave($created) {
if (!$created) {
$parent = $this->parentNode();
$parent = $this->node($parent);
$node = $this->node();
$aro = $node[0];
$aro['Aro']['parent_id'] = $parent[0]['Aro']['id'];
$this->Aro->save($aro);
}
}
function importPublicLDAPUser($cn){
App::import('Vendor','adLDAP',array('file'=>'adLDAP.php'));
$oLDAP = new adLDAP(Configure::read('LDAP_options.email'));
$oLDAP->authenticate(NULL, NULL);
$filter = '(&(cn='.$oLDAP->ldap_escape($cn).'))';
$ldap_res = #$oLDAP->search($filter, array('cn', 'uid','profitcenter'),1);
if(isset($ldap_res['count']) && ($ldap_res['count'] > 0)){//found it
$user = $this->save(array('User' => array(
'group_id' => 3,
'name' => $ldap_res[0]['cn'][0],
'username' => $ldap_res[0]['uid'][0],
'grpnum' => pc2grpnum($ldap_res[0]['profitcenter'][0])
)));
if($user){
$user['User']['id'] = $this->id;
}
return ($user ? $user : false);
}else{
return false;
}
}
Any suggestions? Thanks!!
It turns out that in my docu_controller.php I was missing a create() call. It seems that without a create, an object can still be saved/created when the other controller does a commit(). So before adding the create(), prior to the commit, in later loop iterations I was still modifying the original object, not any new ones. By adding a create in the controller, the save in the method function acts on the new user for each loop iteration.
in controller:
if(count($badAuthors)){
foreach($badAuthors as $key => $author){
$this->Memo->User->create();
if($ldap_author = $this->Memo->User->importPublicLDAPUser($author['name'])){
in method:
function importPublicLDAPUser($cn){
....
$user = $this->save(array('User' => array(...
I try to use existing model data inside a models callback function in CakePHP 2.1 but can't get it working.
What I do is I try to get a users role in the beforeValidate() callback and check if it's empty. If yes, I'll set it. Normally I do it like this, and for the first creation of the record it works pretty well.
if (empty($this->data[$this->alias]['role']))
$this->data[$this->alias]['role'] = 'user';
The problem is, every time an existing record (user) gets updated, the role will be set again.
Question: So, how do I check if the field role is already set in the record data, not the post data (seems like $this->data[$this->alias] only contains POST data)?
There are three solutions to this problem as I can see it.
Set a default value in the database column (easiest, best?)
Add role to your inputs everytime.
Lookup the user and add a role if it's missing
The first two options seem obvious, so I'll just illustrate the last.
public function beforeValidate() {
if (!empty($this->id) {
$this->data[$this->alias][$this->primaryKey] = $this->id;
}
if (!empty($this->data[$this->alias][$this->primaryKey])) {
// user exists, check their data
$id = $this->data[$this->alias][$this->primaryKey];
$user = $this->find('first', array(
'conditions' => array($this->primaryKey => $id)
));
$this->data[$this->alias]['role'] = $user[$this->alias]['role'];
}
if (empty($this->data[$this->alias]['role'])) {
// new user but missing a role
$this->data[$this->alias]['role'] = 'user';
}
return true;
}
This callback will check if an ID was passed, and if so it will look up the user and populate the role field. Then, it checks for an empty role and fills it with the default if necessary. Obviously he more code you have, the more possibilities for bugs, so I suggest the first option for default column values.
try:
if (empty($this->data[$this->alias]['role']) && empty($this->role)) {
$this->data[$this->alias]['role'] = 'user';
}