MyBB Community Forums

Full Version: MentionMe (MyAlerts Integrated Mention)
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
Pages: 1 2 3
Yeah, it should be possible. I need to look into the best way of doing it though.
(2012-12-11, 09:26 PM)euantor Wrote: [ -> ]Yeah, it should be possible. I need to look into the best way of doing it though.

No rush mate Smile

Thanks for all your help.

(2012-12-11, 07:42 PM)Shade Wrote: [ -> ]Did the alerts settings hook worked for you? Seems that it adds nothing in UCP alerts settings list.

Now I remember what it was!

You have to create a setting for your plugin called 'myalerts_alert_yourplugin' (if you don't have any settings at all you'll have to make a group too) and that setting (in Admin CP) must be set to Yes and then the setting will appear. Smile

Triple post for the win! Big Grin

On making settings for a new alert on by default, I did come up with something that works. I would welcome any suggestions to make it better or more efficient as I am treading in deep waters for my skill level Blush

// Set Mention alerts on by default
	$possible_settings = array(
			'rep',
			'pm',
			'buddylist',
			'quoted',
			'post_threadauthor',
			);
			
	$plugins->run_hooks('myalerts_possible_settings', $possible_settings);
	$possible_settings = array_flip($possible_settings);
	$possible_settings = array_fill_keys(array_keys($possible_settings), 0);
	
	$query = $db->simple_select('users', 'uid, myalerts_settings', '', array());
	
	while($settings = $db->fetch_array($query))
	{
		$alert_settings = json_decode($settings['myalerts_settings']);
		
		$my_settings = array_merge($possible_settings, (array) $alert_settings);
		$my_settings = array_intersect_key($my_settings, $possible_settings);
		$my_settings['mention'] = 'on';
		
		$db->update_query('users', array('myalerts_settings' => $db->escape_string(json_encode($my_settings))), 'uid=' . $settings['uid']);
	}

But, like I said, it works Smile
Can you give me the myalerts_alert_yourplugin ACP setting add you mentioned above? I'm learning how to develop a plugin and I don't really know where to begin Blush

Seems I succeeded into adding settings to myalerts existing ones with the following code:

$query = $db->simple_select("settinggroups", "gid", "name='myalerts'");
	$gid = intval($db->fetch_field($query, "gid"));
	
	$myextension_settings = array(
		"name" => "myalerts_alert_revoke",
		"title" => $lang->setting_myextension_alert_revokewarn,
		"description" => $lang->setting_myextension_alert_revokewarn_desc,
		"optionscode" => "yesno",
		"value" => "1",
		"disporder" => "20",
		"gid" => $gid,
	);
	$db->insert_query("settings", $myextension_settings);

Either is by default set to "on", I have necessarily to update settings in ACP with the Update settings button to affect UCP settings and see my custom options finally. I don't know how to make it automatically, without updating settings manually, though.

My fault - it works pretty well. Now I'm ready to develop my MyAlerts Extension plugin! A special thanks to you euan and Wildcard!
(2012-12-12, 11:16 AM)Shade Wrote: [ -> ]Can you give me the myalerts_alert_yourplugin ACP setting add you mentioned above?

Looks you have it under control Smile

In fact, I actually added my own settings group unnecessarily and I will probably use your method to add the setting to MyAlerts settings group instead. So thank you Smile
Here's the full method source if you want to look at the _uninstall() function with the reverse method.

function myalertsmore_install()
{
	global $db, $PL, $lang, $mybb;

	if (!file_exists(PLUGINLIBRARY))
	{
		flash_message("The selected plugin could not be installed because <a href=\"http://mods.mybb.com/view/pluginlibrary\">PluginLibrary</a> is missing.", "error");
		admin_redirect("index.php?module=config-plugins");
	}
	
	// check if a random myalerts setting exist - if false, then MyAlerts is not installed, warn the user and redirect him
	if(!$mybb->settings['myalerts_alert_rep'])
	{
		flash_message("The selected plugin could not be installed because <a href=\"http://mods.mybb.com/view/myalerts\">MyAlerts</a> is not installed yet.", "error");
		admin_redirect("index.php?module=config-plugins");
	}
	
	$PL or require_once PLUGINLIBRARY;
	
	
	// add an extra hook - needed because warnings_do_warn_start is positioned before many infos are being parsed - and we don't want to add extra queries, right? :}
	$PL->edit_core('myalertsmore', 'warnings.php',
               array('search' => '$db->update_query("users", $updated_user, "uid=\'{$user[\'uid\']}\'");',
                     'before' => '$plugins->run_hooks("warnings_do_warn_end");'),
               true);
	
	if (!$lang->myalertsmore)
	{
		$lang->load('myalertsmore');
	}
	
	// search for myalerts existing settings and add our custom ones
	$query = $db->simple_select("settinggroups", "gid", "name='myalerts'");
	$gid = intval($db->fetch_field($query, "gid"));
	
	$myalertsmore_settings_1 = array(
		"name" => "myalerts_alert_warn",
		"title" => $lang->setting_myalertsmore_alert_warn,
		"description" => $lang->setting_myalertsmore_alert_warn_desc,
		"optionscode" => "yesno",
		"value" => "1",
		"disporder" => "20",
		"gid" => $gid,
	);
	$db->insert_query("settings", $myalertsmore_settings_1);
	
	// rebuild settings
	rebuild_settings();

}

function myalertsmore_uninstall()
{
	global $db, $PL;
	
	if (!file_exists(PLUGINLIBRARY))
	{
		flash_message("The selected plugin could not be uninstalled because <a href=\"http://mods.mybb.com/view/pluginlibrary\">PluginLibrary</a> is missing.", "error");
		admin_redirect("index.php?module=config-plugins");
	}

	$PL or require_once PLUGINLIBRARY;
	
	// restore core edits we've done in installation process
	$PL->edit_core('myalertsmore', 'warnings.php',
               array(),
               true);
	
	// delete our custom settings we previously added - at the moment there is only one setting so it might be done with a single delete_query instead of write_query, but since we're gonna add a lot of other settings, we're anticipating the future here :) just add settings like 'myalerts_alert_warn', 'myalerts_alert_revokealert' and so on.
	$db->write_query("DELETE FROM ".TABLE_PREFIX."settings WHERE name IN('myalerts_alert_warn')");
	
	// rebuild settings
	rebuild_settings();

}

If I understood right, with the method you mentioned above I can make my custom arrangements effective for existing users am I right? If so, I will try to integrate it in my plugin to render it an automatic extension. Thank you.

I've developed my own method that works pretty well, without too many flips or key fills.

// Set our alerts on for all users by default, maintaining existing alerts values
	// Declare a data array containing all our alerts settings we'd like to add. To default them, the array must be associative and keys must be set to "on" (active) or 0 (not active)
    $possible_settings = array(
            'warn' => "on",
            'revokewarn' => "on",
            );
    
    $query = $db->simple_select('users', 'uid, myalerts_settings', '', array());
    
    while($settings = $db->fetch_array($query))
    {
		// decode existing alerts with corresponding key values. json_decode func returns an associative array by default, we don't need to edit it
        $alert_settings = json_decode($settings['myalerts_settings']);
        
		// merge our settings with existing ones...
        $my_settings = array_merge($possible_settings, (array) $alert_settings);
        
		// and update the table cell, encoding our modified array and paying attention to SQL inj (thanks Nathan!)
        $db->update_query('users', array('myalerts_settings' => $db->escape_string(json_encode($my_settings))), 'uid='.(int) $settings['uid']);
    } 

Edit: after some tests, I noticed that the method above only updates database infos, but alerts aren't displayed properly. Maybe euantor can tell us the exact method we should use.

Edit again: I changed something in the code and now it works again. Blush
(2012-12-12, 01:01 PM)Shade Wrote: [ -> ]Edit: after some tests, I noticed that the method above only updates database infos, but alerts aren't displayed properly. Maybe euantor can tell us the exact method we should use.

Edit again: I changed something in the code and now it works again. Blush

I get how it works man. I do the same thing: get something working then something else is a problem Big Grin When you have it figured out please post the code because I am sure that I am using too much code for such a simple thing, but in all honesty I am not that great at working with arrays in PHP other than simple usage and I still don't know what the hell json is :p

And I am not kidding either. Big Grin



On another note: I have been using the mention plugin with MyAlerts for two days on RC and a private forum that I run. Smile I am very happy to have it working and I also had to bugfix an issue with the Google SEO plugin's URLs so I came up with a way that works on a forum with or without Google SEO urls.
I edited the code I posted above, it works Smile

Here's my install function:

function myalertsmore_install()
{
	global $db, $PL, $lang, $mybb;

	if (!file_exists(PLUGINLIBRARY))
	{
		flash_message("The selected plugin could not be installed because <a href=\"http://mods.mybb.com/view/pluginlibrary\">PluginLibrary</a> is missing.", "error");
		admin_redirect("index.php?module=config-plugins");
	}
	
	// check if a random myalerts setting exist - if false, then MyAlerts is not installed, warn the user and redirect him
	if(!$mybb->settings['myalerts_alert_rep'])
	{
		flash_message("The selected plugin could not be installed because <a href=\"http://mods.mybb.com/view/myalerts\">MyAlerts</a> is not installed yet.", "error");
		admin_redirect("index.php?module=config-plugins");
	}
	
	$PL or require_once PLUGINLIBRARY;
	
	
	// add extra hooks - needed for some alerts
	$PL->edit_core('myalertsmore', 'warnings.php',
				array(
				// warn alert
					array('search' => '$db->update_query("users", $updated_user, "uid=\'{$user[\'uid\']}\'");',
                     	  'before' => '$plugins->run_hooks("warnings_do_warn_end");'),
				// revoke warn alert
					array('search' => 'redirect("warnings.php?action=view&wid={$warning[\'wid\']}", $lang->redirect_warning_revoked);',
                     	  'before' => '$plugins->run_hooks("warnings_do_revoke_end");'),
					 ),
               true);
			   
	$PL->edit_core('myalertsmore', 'moderation.php',
				array(
				// close multiple threads alert
					array('search' => '$moderation->close_threads($threads);',
                     	  'before' => '$plugins->run_hooks("moderation_multiclosethreads");'),
				// close single thread alert, merged in close multiple threads alert
					array('search' => '$redirect = $lang->redirect_closethread;',
                     	  'after' => '$plugins->run_hooks("moderation_closesinglethread");'),
				// open multiple threads alert
					array('search' => '$moderation->open_threads($threads);',
                     	  'before' => '$plugins->run_hooks("moderation_multiopenthreads");'),
				// open single thread alert, merged in open multiple threads alert
					array('search' => '$redirect = $lang->redirect_openthread;',
                     	  'after' => '$plugins->run_hooks("moderation_opensinglethread");'),
				// delete multiple threads alert
					array('search' => '$tid = intval($tid);',
                     	  'after' => '$plugins->run_hooks("moderation_multideletethreads");'),
					 ),
               true);
	
	if (!$lang->myalertsmore)
	{
		$lang->load('myalertsmore');
	}
	
	// search for myalerts existing settings and add our custom ones
	$query = $db->simple_select("settinggroups", "gid", "name='myalerts'");
	$gid = intval($db->fetch_field($query, "gid"));
	
	$myalertsmore_settings_1 = array(
		"name" => "myalerts_alert_warn",
		"title" => $lang->setting_myalertsmore_alert_warn,
		"description" => $lang->setting_myalertsmore_alert_warn_desc,
		"optionscode" => "yesno",
		"value" => "1",
		"disporder" => "20",
		"gid" => $gid,
	);
	$myalertsmore_settings_2 = array(
		"name" => "myalerts_alert_revokewarn",
		"title" => $lang->setting_myalertsmore_alert_revokewarn,
		"description" => $lang->setting_myalertsmore_alert_revokewarn_desc,
		"optionscode" => "yesno",
		"value" => "1",
		"disporder" => "21",
		"gid" => $gid,
	);
	$myalertsmore_settings_3 = array(
		"name" => "myalerts_alert_multideletethreads",
		"title" => $lang->setting_myalertsmore_alert_multideletethreads,
		"description" => $lang->setting_myalertsmore_alert_multideletethreads_desc,
		"optionscode" => "yesno",
		"value" => "1",
		"disporder" => "22",
		"gid" => $gid,
	);
	$myalertsmore_settings_4 = array(
		"name" => "myalerts_alert_multiclosethreads",
		"title" => $lang->setting_myalertsmore_alert_multiclosethreads,
		"description" => $lang->setting_myalertsmore_alert_multiclosethreads_desc,
		"optionscode" => "yesno",
		"value" => "1",
		"disporder" => "23",
		"gid" => $gid,
	);
	$myalertsmore_settings_5 = array(
		"name" => "myalerts_alert_multiopenthreads",
		"title" => $lang->setting_myalertsmore_alert_multiopenthreads,
		"description" => $lang->setting_myalertsmore_alert_multiopenthreads_desc,
		"optionscode" => "yesno",
		"value" => "1",
		"disporder" => "24",
		"gid" => $gid,
	);
	$db->insert_query("settings", $myalertsmore_settings_1);
	$db->insert_query("settings", $myalertsmore_settings_2);
	$db->insert_query("settings", $myalertsmore_settings_3);
	$db->insert_query("settings", $myalertsmore_settings_4);
	$db->insert_query("settings", $myalertsmore_settings_5);
	
	// Set our alerts on for all users by default, maintaining existing alerts values
    // Declare a data array containing all our alerts settings we'd like to add. To default them, the array must be associative and values must be set to "on" (active) or 0 (not active)
    $possible_settings = array(
            'warn' => "on",
            'revokewarn' => "on",
            'multideletethreads' => "on",
            'multiclosethreads' => "on",
            'multiopenthreads' => "on",
            );
    
    $query = $db->simple_select('users', 'uid, myalerts_settings', '', array());
    
    while($settings = $db->fetch_array($query))
    {
        // decode existing alerts with corresponding key values. json_decode func returns an associative array by default, we don't need to edit it
        $alert_settings = json_decode($settings['myalerts_settings']);
        
        // merge our settings with existing ones...
        $my_settings = array_merge($possible_settings, (array) $alert_settings);
        
        // and update the table cell, encoding our modified array and paying attention to SQL inj (thanks Nathan!)
        $db->update_query('users', array('myalerts_settings' => $db->escape_string(json_encode($my_settings))), 'uid='.(int) $settings['uid']);
    }
		
	// rebuild settings
	rebuild_settings();

}

I commented a lot of things just to be sure I'll remember what they mean in the future. As you can see, you firstly declare an associative array in which you set as "on" your custom alerts. Then, you retrieve the current users necessary data and for every user you merge his current alerts settings (decoded) with your custom ones, then you encode them again and update their settings in the database. Finally, you have to rebuild settings.php file (don't know why, but putting it before the database cell edit it doesn't work properly).

Don't care about core edits and such, they're necessary for my plugin to work Wink
Thanks Shade Smile

I have got your code working with my plugin which I am tentatively calling MentionMe

I also found some issues with my code if MyAlerts isn't installed and solved those it works with or without MyAlerts. My install code was relying on my custom MyAlerts settings for is_installed but if MyAlerts plugin isn't installed my plugin doesn't create a setting (and the MyAlerts settingsgroup doesn't exist) so I got around that by querying the adminlog and basing is_installed on actual activate/deactivate history.

I am getting closer. Big Grin
(2013-01-02, 10:16 AM)Solstice Wrote: [ -> ]Suggestion for next version: limit the mentions by post

In the plugin I use a preg_replace_callback() and I can easily limit the amount of attempts, but limiting the amount of mentions gets me confused :s

For instance, if this were posted:

Quote:@wild
@wilcerd
@wildy
@willy
@wooly
@wildcard

and the maximum attempts per post were set to five, @wildcard wouldn't show up even though it matches . . . that isn't acceptable, but I can't think of a way to handle it.

Any ideas?
Pages: 1 2 3