View Issue Details
ID | Project | Category | View Status | Date Submitted | Last Update |
---|---|---|---|---|---|
0003790 | mantisbt | custom fields | public | 2004-04-29 14:32 | 2019-04-07 13:31 |
Reporter | RJelinek | Assigned To | |||
Priority | normal | Severity | feature | Reproducibility | always |
Status | acknowledged | Resolution | open | ||
Summary | 0003790: Additional Custom-Field-Type "users" | ||||
Description | It would be useful, to define a new custom-field-type that shows all users of a project or an access level of this project. I need this to specify - additional to a handler - a tester who reviews my changings to solve the problem. The user selected in this field also gets all information mails. | ||||
Tags | patch | ||||
Attached Files | cfdef_mantisuser.php (8,940 bytes)
<?php # Mantis - a php based bugtracking system # Copyright (C) 2000 - 2002 Kenzaburo Ito - kenito@300baud.org # Copyright (C) 2002 - 2009 Mantis Team - mantisbt-dev@lists.sourceforge.net # Mantis is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation, either version 2 of the License, or # (at your option) any later version. # # Mantis is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with Mantis. If not, see <http://www.gnu.org/licenses/>. /************************************************************ Adds a Custom Field type of 'Mantis User', including support for a minimum user level. Written by djcarr for Mantis 1.2.0a3. To Use: ------- 1. Go to 'Manage', 'Manage Custom Fields', and add a new Custom Field. 2. On the 'Edit custom field' page, select Type 'Mantis User' 3. Optionally, a minimum user level can be specified in the "Possible Values" property. This can be a known constant (DEVELOPER,UPDATER,MANAGER,etc) or a number (50,60,70). Only users at or above that user level will be available for this Custom Field. To Install: ----------- 1. Add this file ctdef_mantisuser.php to the [home]\core\cfdefs directory. 2. Add the following constant to [home]\custom_constant_inc.php: define( 'CUSTOM_FIELD_TYPE_MANTISUSER', 90 ); 3. Add the following to [home]\config_inc.php: $g_custom_field_types[CUSTOM_FIELD_TYPE_MANTISUSER] = 'mantisuser'; $g_custom_field_type_enum_string = $g_custom_field_type_enum_string.',90:mantis user'; 4. Add the following to [home]\custom_strings_inc.php: $s_custom_field_type_enum_string = '0:String,1:Numeric,2:Float,3:Enumeration,4:E-mail,5:Checkbox,6:List,7:Multiselection list,8:Date,9:Radio,90:Mantis User'; 5. Patch this new method into [home]\core\custom_field_api.php: function custom_field_string_value( $p_value, $p_type ) { global $g_custom_field_type_definition; if( isset( $g_custom_field_type_definition[$p_type]['#function_string_value'] ) ) { return call_user_func( $g_custom_field_type_definition[$p_type]['#function_string_value'], $p_value ); } return string_display_links( $p_value ); } 6. Patch these existing lines in [home]\core\filter_api.php: line #2930: $t_this_string = string_display( $t_current ); to: $t_this_string = string_display( custom_field_string_value( $t_current, $t_accessible_custom_fields_types[$i] ) ); line #3746: echo '>' . string_shorten( $t_item ) . '</option>' . "\n"; to: echo '>' . string_shorten( custom_field_string_value( $t_item, $t_accessible_custom_fields_types[$j] ) ) . '</option>' . "\n"; 7. Modify the value of $g_custom_field_mantisuser_filter_show_all below as desired. ************************************************************/ // if FALSE, uses the default custom field filter behaviour of only showing already selected values. // if TRUE, ALL users (satisfying the minimum level) are shown in the filter. $g_custom_field_mantisuser_filter_show_all = FALSE; $g_custom_field_type_definition[ CUSTOM_FIELD_TYPE_MANTISUSER ] = array ( '#display_possible_values' => TRUE, '#display_valid_regexp' => FALSE, '#display_length_min' => FALSE, '#display_length_max' => FALSE, '#display_default_value' => FALSE, '#function_return_distinct_values' => $g_custom_field_mantisuser_filter_show_all ? 'cfdef_prepare_mantisuser_all_values' : null, '#function_value_to_database' => null, '#function_database_to_value' => null, '#function_print_input' => 'cfdef_input_mantisuser', '#function_string_value' => 'cfdef_prepare_mantisuser_value', '#function_string_value_for_email' => 'cfdef_prepare_mantisuser_value', ); /** * Function to generate a combo box of Mantis Users. * Compatible with : $g_custom_field_type_definition['#function_print_input'] * This is used to generate the Custom Field on the Update Issue page. * @param array $p_field_def the Custom Field as defined in Mantis * @param array $t_custom_field_value contains the currently selected user id, if any * @access public */ function cfdef_input_mantisuser($p_field_def, $t_custom_field_value) { // generate list of valid users $t_users_array = array(); $t_project_id = helper_get_current_project(); $t_users_array = project_get_all_user_rows( $t_project_id, get_mantisuser_threshold( $p_field_def ) ); $t_users_array = sort_user_rows( $t_users_array ); // generate list of already selected user(s) $t_selected_values = explode( '|', $t_custom_field_value ); $t_list_size = 0; # for this the size is always 0 echo '<select ', helper_get_tab_index(), ' name="custom_field_' . $p_field_def['id'] . '" size="' . $t_list_size . '">'; // a blank option so an unselected field works properly echo '<option value="0"></option>'; foreach ($t_users_array as $t_user){ $t_user_id = $t_user['id']; $t_selected_substring = ''; if( in_array( $t_user_id, $t_selected_values, true ) ) { $t_selected_substring = ' selected="selected" '; } echo '<option value="'.$t_user_id.'"'.$t_selected_substring.'> '.cfdef_prepare_mantisuser_value($t_user_id).'</option>'; } echo '</select>'; } /** * Function to produce a printable string from a user ID * Compatible with : $g_custom_field_type_definition['#function_string_value'] * @param array $p_value a user ID * @access public */ function cfdef_prepare_mantisuser_value($p_value) { // convert a user id into the user's name if ( user_exists( $p_value ) ) { $t_show_real_names = config_get( 'show_realname' ) == ON; $t_user_realname = user_get_realname( $p_value ); if ($t_show_real_names && !is_blank( $t_user_realname ) ) { return $t_user_realname; } else { return user_get_name( $p_value ); } } else { return ''; } } /** * Function to retrieve an array of all valid user ids * Compatible with : $g_custom_field_type_definition['#function_return_distinct_values'] * This is used to generate the filter option. * @param array $p_field_def the Custom Field as defined in Mantis * @access public */ function cfdef_prepare_mantisuser_all_values($p_field_def) { $t_project_id = helper_get_current_project(); $t_users_array = array(); $t_users_array = project_get_all_user_rows( $t_project_id, get_mantisuser_threshold( $p_field_def ) ); $t_users_array = sort_user_rows( $t_users_array ); $t_return_arr = array(); foreach ($t_users_array as $t_user){ $t_user_id = $t_user['id']; array_push( $t_return_arr, $t_user_id ); } return $t_return_arr; } /** * Function to extract the minimum userlevel threshold from the Custom Field property 'Possible Values'. * This value can be entered as a constant (DEVELOPER,UPDATER,MANAGER,etc) or a number (50,60,70). * @param array $p_field_def the Custom Field as defined in Mantis * @return int representing the User Level threshold * @access public */ function get_mantisuser_threshold($p_field_def) { $t_threshold = ANYBODY; $t_possible_values = explode( '|', $p_field_def['possible_values'] ); // the first possible value is the minimum userlevel for the mantis user if ( count( $t_possible_values ) > 0 ) { $t_threshold = constant_replace( $t_possible_values[0] ); } return $t_threshold; } /** * Check if the passed string is a constant and return its value * Code pilfered from adm_config_set.php. * @access private */ function constant_replace( $p_name ) { $t_result = $p_name; if ( is_string( $p_name ) && defined( $p_name ) ) { // we have a constant $t_result = constant( $p_name ); } return $t_result; } /** * Sort the user rows returned by project_get_all_user_rows() * Code pilfered from print_user_option_list.php. * @access private */ function sort_user_rows( $p_user_rows ) { $t_users = $p_user_rows; $t_display = array(); $t_sort = array(); $t_show_realname = ( ON == config_get( 'show_realname' ) ); $t_sort_by_last_name = ( ON == config_get( 'sort_by_last_name' ) ); foreach( $t_users as $t_user ) { $t_user_name = string_attribute( $t_user['username'] ); $t_sort_name = strtolower( $t_user_name ); if( $t_show_realname && ( $t_user['realname'] <> "" ) ) { $t_user_name = string_attribute( $t_user['realname'] ); if( $t_sort_by_last_name ) { $t_sort_name_bits = split( ' ', strtolower( $t_user_name ), 2 ); $t_sort_name = ( isset( $t_sort_name_bits[1] ) ? $t_sort_name_bits[1] . ', ' : '' ) . $t_sort_name_bits[0]; } else { $t_sort_name = strtolower( $t_user_name ); } } $t_display[] = $t_user_name; $t_sort[] = $t_sort_name; } array_multisort( $t_sort, SORT_ASC, SORT_STRING, $t_users, $t_display ); return $t_users; } ?> customfield-mantisuser-patches-1.2.4.txt (4,674 bytes)
--- core/constant_inc.php Fri Jan 16 13:56:28 1970 +++ core/constant_inc.php Fri Jan 16 13:56:28 1970 @@ -414,6 +414,7 @@ define( 'CUSTOM_FIELD_TYPE_MULTILIST', 7 ); define( 'CUSTOM_FIELD_TYPE_DATE', 8 ); define( 'CUSTOM_FIELD_TYPE_RADIO', 9 ); +define( 'CUSTOM_FIELD_TYPE_MANTISUSER', 10 ); # Meta filter values define( 'META_FILTER_MYSELF', -1 ); --- core/custom_field_api.php Fri Jan 16 13:56:28 1970 +++ core/custom_field_api.php Fri Jan 16 13:56:28 1970 @@ -53,6 +53,7 @@ $g_custom_field_types[CUSTOM_FIELD_TYPE_LIST] = 'standard'; $g_custom_field_types[CUSTOM_FIELD_TYPE_MULTILIST] = 'standard'; $g_custom_field_types[CUSTOM_FIELD_TYPE_DATE] = 'standard'; +$g_custom_field_types[CUSTOM_FIELD_TYPE_MANTISUSER] = 'mantisuser'; foreach( $g_custom_field_types as $type ) { require_once( 'cfdefs' . DIRECTORY_SEPARATOR . 'cfdef_' . $type . '.php' ); @@ -1477,3 +1478,19 @@ } return $p_value; } + +/** + * Prepare a string containing a custom field value for use in filters + * NOTE: This probably belongs in the string_api.php + * @param string $p_value value of custom field + * @param int $p_type type of custom field + * @return string value ready for display in filters + * @access public + */ +function string_custom_field_value_for_filter( $p_value, $p_type ) { + global $g_custom_field_type_definition; + if( isset( $g_custom_field_type_definition[$p_type]['#function_string_value'] ) ) { + return call_user_func( $g_custom_field_type_definition[$p_type]['#function_string_value'], $p_value ); + } + return string_display_links( $p_value ); +} \ No newline at end of file --- core/filter_api.php Fri Jan 16 13:56:28 1970 +++ core/filter_api.php Fri Jan 16 13:56:28 1970 @@ -3160,7 +3160,7 @@ } else if( filter_field_is_none( $t_current ) ) { $t_this_string = lang_get( 'none' ); } else { - $t_this_string = string_display( $t_current ); + $t_this_string = string_display( string_custom_field_value_for_filter( $t_current, $t_accessible_custom_fields_types[$i] ) ); } if( $t_first_flag != true ) { @@ -4034,7 +4034,7 @@ if( isset( $t_filter['custom_fields'][$p_field_id] ) ) { check_selected( $t_filter['custom_fields'][$p_field_id], $t_item ); } - echo '>' . string_attribute( string_shorten( $t_item, $t_max_length ) ) . '</option>' . "\n"; + echo '>' . string_attribute( string_shorten( string_custom_field_value_for_filter( $t_item, $t_accessible_custom_fields_types[$j] ), $t_max_length ) ) . '</option>' . "\n"; } } } --- lang/strings_english.txt Fri Jan 16 13:56:28 1970 +++ lang/strings_english.txt Fri Jan 16 13:56:28 1970 @@ -1300,7 +1300,7 @@ $s_linked_projects = 'Linked Projects'; $s_custom_field_sequence = 'Sequence'; -$s_custom_field_type_enum_string = '0:String,1:Numeric,2:Float,3:Enumeration,4:E-mail,5:Checkbox,6:List,7:Multiselection list,8:Date,9:Radio'; +$s_custom_field_type_enum_string = '0:String,1:Numeric,2:Float,3:Enumeration,4:E-mail,5:Checkbox,6:List,7:Multiselection list,8:Date,9:Radio,10:Mantis User'; $s_confirm_used_custom_field_deletion = 'This field is currently linked to at least one project. If you continue all values for this field will be permanently deleted. This action cannot be undone. If you do not want to delete this field, hit the Back button in your browser. To proceed, click the button below'; $s_confirm_custom_field_deletion = 'Are you sure you want to delete this custom field and all associated values?'; --- config_defaults_inc.php Fri Jan 16 13:56:28 1970 +++ config_defaults_inc.php Fri Jan 16 13:56:28 1970 @@ -2985,8 +2985,8 @@ * * @global string $g_custom_field_type_enum_string */ - $g_custom_field_type_enum_string = '0:string,1:numeric,2:float,3:enum,4:email,5:checkbox,6:list,7:multiselection list,8:date,9:radio'; - + $g_custom_field_type_enum_string = '0:string,1:numeric,2:float,3:enum,4:email,5:checkbox,6:list,7:multiselection list,8:date,9:radio,10:mantis user'; + /********************************* * MantisBT Javascript Variables * *********************************/ @@ -3133,6 +3133,13 @@ */ $g_custom_field_edit_after_create = ON; + /** + * If TRUE, displays all users (above the minimum level if specified) in the filter. + * The default behaviour for custom field filters is to only show values that have been selected in issues. + * @global int $g_custom_field_mantisuser_filter_show_all + */ + $g_custom_field_mantisuser_filter_show_all = FALSE; + /**************** * Custom Menus * ****************/ patch-cfdef_mantisuser.txt (703 bytes)
Index: core/cfdefs/cfdef_mantisuser.php =================================================================== --- core/cfdefs/cfdef_mantisuser.php (révision 35921) +++ core/cfdefs/cfdef_mantisuser.php (révision 35968) @@ -130,7 +130,7 @@ */ function get_mantisuser_threshold($p_field_def) { $t_threshold = ANYBODY; - $t_possible_values = explode( '|', $p_field_def['possible_values'] ); + $t_possible_values = (strlen($p_field_def['possible_values']) > 0) ? explode( '|', $p_field_def['possible_values'] ) : array(); // the first possible value is the minimum userlevel for the mantis user if ( count( $t_possible_values ) > 0 ) { $t_threshold = constant_replace( $t_possible_values[0] ); patch2-cfdef_mantisuser.txt (912 bytes)
Index: core/cfdefs/cfdef_mantisuser.php =================================================================== --- core/cfdefs/cfdef_mantisuser.php (révision 35968) +++ core/cfdefs/cfdef_mantisuser.php (copie de travail) @@ -143,15 +143,16 @@ * Code pilfered from adm_config_set.php. * @access private */ -function constant_replace( $p_name ) { - $t_result = $p_name; - if ( is_string( $p_name ) && defined( $p_name ) ) { - // we have a constant - $t_result = constant( $p_name ); - } - return $t_result; +if (!function_exists('constant_replace')) { + function constant_replace( $p_name ) { + $t_result = $p_name; + if ( is_string( $p_name ) && defined( $p_name ) ) { + // we have a constant + $t_result = constant( $p_name ); + } + return $t_result; + } } - /** * Sort the user rows returned by project_get_all_user_rows() * Code pilfered from print_user_option_list.php. | ||||
Implemented new custom field "MantisUser" (and also TextArea) Add the below line to your config_inc.php Add the below line to your custom_strings_inc.php Change the below logic in the custom_field_api.php to include the mantis user list query. switch ($p_field_def['type']) { |
|
Some questions about the patch:
|
|
is it also possible to enter a name manually? |
|
Hi vboctor, Yep was a bit a quick and dirty fix. Here is something better. Used existing project api function as it makes sense for me to limit the user list to those involved in the project. Ordering was indeed not needed. Tied realname issue into existing config. Easy enough to add another customfield type to have multiselect mantis user custom field. Pluntke: Maybe vboctor could advise on the control to use to both have dropdown and input field. So patch is to update config_inc.php, custom_strings_inc.php and custom_constant_inc.php to add the new mantisuser constant. Change the below logic in the custom_field_api.php to include the mantis user list query. function print_custom_field_input( $p_field_def, $p_bug_id = null ) {
case CUSTOM_FIELD_TYPE_MANTISUSER: |
|
Hi, I have implemented a "Mantis User" Custom Field type for Mantis 1.2.0a3. Like the original request I wanted to implement a Tester custom field. I do want to thank qips for the initial implementations, however I started again from scratch as this version:
Have attached it as file cfdef_mantisuser.php. Inside the file are comments regarding the other files to edit or patch. Please follow the instructions carefully. If others can confirm that this is a reasonable implementation I'm willing to try and figure out how to provide a patch. |
|
Could you please provide some updates to the implemented solution for the latest version of Mantis? The line numbers referred to in the install instructions have changed. It would be helpful to indicate which function the patches go into. Thanks in advance. |
|
Hi Scott, I have reimplemented this feature against Mantis 1.2.4, this time as a full integration into the source rather than using the end-user customisation files. Attached file cfdef_mantisuser.php is now obsolete. To install:
Also attached is customfield-mantisuser-config.PNG which gives an example of a custom field of type 'Mantis User' being configured to record a Tester for an issue. Usage Notes:
Developer Notes:
|
|
Hi, Thank you for sharing the patch, I was able to add functionnality and it works like a charm on our 1.2.4 setup. I ran into trouble on view all bug page when selecting all projects (we currently have nearly 100 active projects), only two use the mantisuser custom field. Whe debugging I found that if the config field for possible values was left empty, the get_mantisuser_threshold function did not return its default value ANYBODY. I attached the patch to the ticket here (http://www.mantisbt.org/bugs/file_download.php?file_id=3310&type=bug). Regards, |
|
Hi Benoit, thanks for finding and patching that bug. I overlooked that explode() gotcha - if the string is empty, you get a 1 element array result. The PHP man page (http://php.net/manual/en/function.explode.php) suggests to wrap it in array_filter instead: $t_possible_values = array_filter( explode( '|', $p_field_def['possible_values'] ) ); Either way, the patch works. Thanks! |
|
Hi, I found another bug, when configuring custom fields type to display in view issue page columns (not only mantis user but classic enum also). Apparently, functions have been duplicated from adm_config_set.php (constant_replace) and print_user_option_list.php (sort_user_rows) This copy/paste could caused by includes issues, but I'm not sure. I've done a quick & dirty patch (but only constant_replace is safe) for our production environnement, but it must be cleaner solutions to this. |
|
The tasks plugin allows you to give another developer the assignement to carry out additional things like testing etcetera. |
|
Hi, |
|
Is there any chance this feature get's implemented some day? Would be nice to have an automatic choice and not a fixed manual list of users per project.... And I cannot use the patch: My Admin refuses to apply the patch because he doesn't want to apply the patch each time Mantis is updated. |
|
Actually, I needed a couple of days ago to add a custom field of type user (namely a 'Tester' field). I used the method explained in one of the comments, which consists in overriding the custom functions. I don't have access to my code right now, so I will share my exact solution tomorrow. But if I remember correctly I added the custom_function file in my config folder, where I declared the function custom_override_users or something like that (sorry I don't have the exact names), in which I basically copy-pasted the code to get a list of users (check what's done for the list of users in the edition page of a bug). Then I use the reference to that function in my custom field definition. |
|
OK, the explanation is in the ticket 0005180 and in the manual: http://www.mantisbt.org/manual/#admin.customize.customfields.dynamic. |
|
Hi again, so here are my settings in attachement. custom_functions_inc.php (2,283 bytes)
<?php # -------------------- # Construct an enumeration for all users for the current project. # The enumeration will be empty if current project is ALL PROJECTS. # Enumerations format is: "abc|lmn|xyz" # To use this in a custom field type "=users" in the possible values field. function custom_function_override_enum_users() { $t_users = project_get_all_user_rows( helper_get_current_project() ); $t_enum = array(); $t_show_realname = ( ON == config_get( 'show_realname' ) ); /* OLD: Unsorted list: foreach( $t_users as $t_user ) { $t_user_name = string_attribute( $t_user['username'] ); if( $t_show_realname && ( $t_user['realname'] <> '' ) ) { $t_user_name = string_attribute( $t_user['realname'] ); } $t_enum[] = $t_user_name; } */ $t_display = array(); $t_sort = array(); $t_sort_by_last_name = ( ON == config_get( 'sort_by_last_name' ) ); foreach( $t_users as $t_key => $t_user ) { $t_user_name = string_attribute( $t_user['username'] ); $t_sort_name = utf8_strtolower( $t_user_name ); if( $t_show_realname && ( $t_user['realname'] <> '' ) ) { $t_user_name = string_attribute( $t_user['realname'] ); if( $t_sort_by_last_name ) { $t_sort_name_bits = explode( ' ', utf8_strtolower( $t_user_name ), 2 ); $t_sort_name = ( isset( $t_sort_name_bits[1] ) ? $t_sort_name_bits[1] . ', ' : '' ) . $t_sort_name_bits[0]; } else { $t_sort_name = utf8_strtolower( $t_user_name ); } } $t_display[] = $t_user_name; $t_sort[] = $t_sort_name; } array_multisort( $t_sort, SORT_ASC, SORT_STRING, $t_users, $t_display ); unset( $t_sort ); $t_count = count( $t_users ); for( $i = 0;$i < $t_count;$i++ ) { $t_row = $t_users[$i]; $t_user_name = string_attribute( $t_row['username'] ); if( $t_show_realname && ( $t_row['realname'] <> '' ) ) { $t_user_name = string_attribute( $t_row['realname'] ); } $t_enum[] = $t_user_name; } $t_possible_values = implode( '|', $t_enum ); return $t_possible_values; } |
|
I'm doing some work on this in order to save on DB mantis_user_table.id. $t_enum[] = $t_user['id'] . <b> ':' </b> . $t_user['realname']; the several functions need to be changed to manage <b> : </b> as separator. I'm going to create a Pull Request during this week. |
|
here link to my pull request => https://github.com/mantisbt/mantisbt/pull/1273 |
|
Hi @djcarr @fman , i want to add this in v 2.15.0 , but the filter(core/filter_api.php) of 2.15.0. has changed compltely from 1.2.4 , do u guys have any plugin that woukd work for 2.15.0? |
|