# # # # profile_structure_util.cfv # # Restructures a report element so that the report element subnodes appear in a very specific order. # We require the specific order when we generate caching checksums for a report element. # The initial order in profile setup (where we don't really have a specific order) may be changed due # different operations, i.e. when we save report element data from un-ordered javascript objects. # This subroutine fixes it, it re-writes the entire report element node including subnodes such as graphs # and columns, all in a consistent order. # # # # rewrite_report_element_columns() # rewrite_report_element_items() # delete_report_element_items() # # restructure_report_element() # restructure_profile() # # # # # rewrite_report_element_columns() # # # subroutine(rewrite_report_element_columns( node source_columns, node target_columns), ( # Note, profile_setup uses report_field names in columns because this way they can easily be set via # a lpg format plug-in. Though the final profile (once profile setup is completed) uses numbers only # for column names! # We assume the source_columns to be in correct order, so no sorting is required at this point! debug_message("\n\n#### rewrite_report_element_columns() - START n"); node column; int column_count = 0; node new_column; bool show_column; bool show_percent_column; bool show_bar_column; bool show_graph; debug_message("#### rewrite_report_element_columns() - source_columns:\n" . node_as_string(source_columns) . "\n"); foreach column source_columns ( set_subnode_value(target_columns, column_count, ""); new_column = target_columns{column_count}; set_subnode_value(new_column, "report_field", @column{"report_field"}); show_column = @column{"show_column"}; set_subnode_value(new_column, "show_column", show_column); if (column?{"show_percent_column"}) then ( show_percent_column = @column{"show_percent_column"}; show_bar_column = @column{"show_bar_column"}; show_graph = @column{"show_graph"}; set_subnode_value(new_column, "show_percent_column", show_percent_column); set_subnode_value(new_column, "show_bar_column", show_bar_column); set_subnode_value(new_column, "show_graph", show_graph); ); column_count++; ); debug_message("#### rewrite_report_element_columns() - final columns to be saved on disk:\n" . node_as_string(target_columns) . "\n"); debug_message("#### rewrite_report_element_columns() - END n"); )); # # # # rewrite_report_element_items() # # # subroutine(rewrite_report_element_items( node report_element_structure, node temp_report_element, node report_element), ( node item; string item_name; foreach item report_element_structure ( item_name = node_name(item); # # We only add an item if it exists in temp_report_element # # debug_message("#### item_name: " . item_name . "\n"); if (temp_report_element?{item_name}) then ( if (num_subnodes(item) == 0) then ( # Write node value of original temp_report_element to report_element set_subnode_value(report_element, item_name, @temp_report_element{item_name}); ) else ( # This is an item with subnodes, add items recursively set_subnode_value(report_element, item_name, ""); rewrite_report_element_items(item, temp_report_element{item_name}, report_element{item_name}); ); ); ); )); # # # # delete_report_element_items() # # # subroutine(delete_report_element_items( node the_node), ( # Deletes any subnode of the given node node item; foreach item the_node ( delete_node(item); ); )); # # # # restructure_report_element() # # # subroutine(restructure_report_element( node report_element), ( debug_message("\n\n#### #### restructure_report_element() START \n"); # debug_message("\n report_element BEFORE:\n" . node_as_string(report_element) . "\n"); # # Clone report_element to a temp_report_element # delete_node("v.temp_report_element"); v.temp_report_element = ""; clone_node(report_element, "v.temp_report_element"); node temp_report_element = "v.temp_report_element"; # # Delete all subnodes in report_element # delete_report_element_items(report_element); # # Start rewriting the report element # node report_element_structure = "templates.util.profile_structure.report_element_structure"; rewrite_report_element_items(report_element_structure, temp_report_element, report_element); # # Handle the columns node, if any # if (temp_report_element?{"columns"}) then ( set_subnode_value(report_element, "columns", ""); rewrite_report_element_columns(temp_report_element{"columns"}, report_element{"columns"}); ); # debug_message("\n report_element AFTER:\n" . node_as_string(report_element) . "\n"); # debug_message("\n#### #### restructure_report_element() END \n"); )); # # # # restructure_profile() # # # subroutine(restructure_profile( node profile), ( # Restructures all report elements of a profile. # This subroutine does not save the profile, hence save the profile in the callee. node reports = profile . ".statistics.reports"; node report; node report_elements; node report_element; foreach report reports ( # Make sure the report has a valid label if (@report{"label"} eq "") then ( # No report label exists, use the node name as label @report{"label"} = node_name(report); ); report_elements = report{"report_elements"}; foreach report_element report_elements ( restructure_report_element(report_element); ); ); ));