From ea267d8bf5008510ea3c45475bf821d1031d6dd3 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 16 Jan 2026 14:51:51 -0600 Subject: [PATCH 01/30] add function to write output files to adf --- tools/iter_dt_out.yaml | 31 ++++++++++++++++++++++++++++++- tools/script_template.py | 17 +++++++++++++++++ 2 files changed, 47 insertions(+), 1 deletion(-) diff --git a/tools/iter_dt_out.yaml b/tools/iter_dt_out.yaml index 5799aab..6224a5a 100644 --- a/tools/iter_dt_out.yaml +++ b/tools/iter_dt_out.yaml @@ -12,4 +12,33 @@ num_pulses : - 8 - 32 - 64 -flux_file : /filespace/a/asrajendra/research/activationDB/ref_flux_files/iter_dt_flux_2.0986E14 +flux_file : ../calc_dwell_dir/ref_flux_files/iter_dt_flux_2.0986E14 +run_dicts : + iter_dt_100_4y : + iter_dt_2p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_2p_100_4y_out + iter_dt_4p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_4p_100_4y_out + iter_dt_8p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_8p_100_4y_out + iter_dt_32p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_32p_100_4y_out + iter_dt_64p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_64p_100_4y_out + + iter_dt_90_4y : + iter_dt_2p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_2p_90_4y_out + iter_dt_4p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_4p_90_4y_out + iter_dt_8p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_8p_90_4y_out + iter_dt_32p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_32p_90_4y_out + iter_dt_64p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_64p_90_4y_out + + iter_dt_50_4y : + iter_dt_2p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_2p_50_4y_out + iter_dt_4p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_4p_50_4y_out + iter_dt_8p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_8p_50_4y_out + iter_dt_32p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_32p_50_4y_out + iter_dt_64p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_64p_50_4y_out + + iter_dt_25_4y : + iter_dt_2p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_2p_25_4y_out + iter_dt_4p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_4p_25_4y_out + iter_dt_8p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_8p_25_4y_out + iter_dt_32p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_32p_25_4y_out + iter_dt_64p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_64p_25_4y_out + diff --git a/tools/script_template.py b/tools/script_template.py index a2814b3..0f99590 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -2,6 +2,8 @@ import yaml import numpy as np import openmc +import pandas as pd +import alara_output_processing as aop def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): ''' @@ -59,6 +61,15 @@ def read_yaml(yaml_arg): inputs = yaml.safe_load(yaml_file) return inputs +def write_to_adf(run_dicts): + adf_data = [] + for run_dict in run_dicts: + lib = aop.DataLibrary() + adf = lib.make_entries(run_dicts[run_dict]) + adf_data.append(adf) + adf_data = pd.concat(adf_data) + return adf + def main(): args = parse_args() inputs = read_yaml(args.db_yaml) @@ -76,5 +87,11 @@ def main(): # normalize flux spectrum by the total flux in each interval norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) # 2D array of shape num_intervals x num_groups + run_dicts = inputs['run_dicts'] + + # for item in run_dicts: + # print(run_dicts[item]) + adf = write_to_adf(run_dicts) + if __name__ == "__main__": main() \ No newline at end of file From d8633504982ed992c3c9a9a16f68674350e58d3c Mon Sep 17 00:00:00 2001 From: anu1217 Date: Mon, 19 Jan 2026 14:54:21 -0600 Subject: [PATCH 02/30] fix write_to_adf() and make function to write to sqlite --- tools/script_template.py | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 0f99590..34e7ac6 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -68,7 +68,16 @@ def write_to_adf(run_dicts): adf = lib.make_entries(run_dicts[run_dict]) adf_data.append(adf) adf_data = pd.concat(adf_data) - return adf + return adf_data + +def write_to_sqlite(adf_data): + + #Remove some columns: + adf_data.drop(columns=['time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num'], inplace=True) + + #Rename some columns: + adf_data.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) + def main(): args = parse_args() @@ -88,10 +97,7 @@ def main(): norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) # 2D array of shape num_intervals x num_groups run_dicts = inputs['run_dicts'] - - # for item in run_dicts: - # print(run_dicts[item]) - adf = write_to_adf(run_dicts) + adf_data = write_to_adf(run_dicts) if __name__ == "__main__": main() \ No newline at end of file From daa624fa9818ad12c7092b939c21f700f52ee9b2 Mon Sep 17 00:00:00 2001 From: anu1217 Date: Mon, 19 Jan 2026 15:23:21 -0600 Subject: [PATCH 03/30] extend new function --- tools/iter_dt_out.yaml | 3 +-- tools/script_template.py | 35 +++++++++++++++++++++++++++-------- 2 files changed, 28 insertions(+), 10 deletions(-) diff --git a/tools/iter_dt_out.yaml b/tools/iter_dt_out.yaml index 6224a5a..327bbff 100644 --- a/tools/iter_dt_out.yaml +++ b/tools/iter_dt_out.yaml @@ -40,5 +40,4 @@ run_dicts : iter_dt_4p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_4p_25_4y_out iter_dt_8p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_8p_25_4y_out iter_dt_32p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_32p_25_4y_out - iter_dt_64p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_64p_25_4y_out - + iter_dt_64p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_64p_25_4y_out \ No newline at end of file diff --git a/tools/script_template.py b/tools/script_template.py index 34e7ac6..55a0b18 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -4,6 +4,7 @@ import openmc import pandas as pd import alara_output_processing as aop +import sqlite3 def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): ''' @@ -20,6 +21,7 @@ def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): rel_dwell_times = (1 - duty_cycle_list) / duty_cycle_list abs_dwell_times = np.outer(rel_dwell_times, pulse_lengths) t_irr_arr = active_burn_time + abs_dwell_times * (num_pulses - 1) + print(np.shape(t_irr_arr)) return pulse_lengths, abs_dwell_times, t_irr_arr def open_flux_file(flux_file): @@ -67,17 +69,31 @@ def write_to_adf(run_dicts): lib = aop.DataLibrary() adf = lib.make_entries(run_dicts[run_dict]) adf_data.append(adf) - adf_data = pd.concat(adf_data) - return adf_data + adf = pd.concat(adf_data) + return adf -def write_to_sqlite(adf_data): - +def modify_adf(adf): #Remove some columns: - adf_data.drop(columns=['time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num'], inplace=True) - + adf.drop(columns=['time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num'], inplace=True) #Rename some columns: - adf_data.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) + adf.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) + print(adf) + return adf + +def write_to_sqlite(adf): + sqlite_conn = sqlite3.connect('activation_results.db') + adf.to_sql('number_densities', sqlite_conn, if_exists='replace', method="multi") + try: + cursor = sqlite_conn.cursor() + sqlite_conn.commit() + result = cursor.fetchall() + cursor.close() + + if sqlite_conn: + sqlite_conn.close() + except sqlite3.OperationalError as error: + print(error) def main(): args = parse_args() @@ -97,7 +113,10 @@ def main(): norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) # 2D array of shape num_intervals x num_groups run_dicts = inputs['run_dicts'] - adf_data = write_to_adf(run_dicts) + + adf = write_to_adf(run_dicts) + adf = modify_adf(adf) + #write_to_sqlite(adf) if __name__ == "__main__": main() \ No newline at end of file From 5cae8184b41dafcce36adf75dd535e6ba8d95525 Mon Sep 17 00:00:00 2001 From: anu1217 Date: Mon, 19 Jan 2026 22:58:07 -0600 Subject: [PATCH 04/30] add flux spectrum shape and t_irr to db --- tools/script_template.py | 260 +++++++++++++++++++++------------------ 1 file changed, 139 insertions(+), 121 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 55a0b18..944881e 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -1,122 +1,140 @@ -import argparse -import yaml -import numpy as np -import openmc -import pandas as pd -import alara_output_processing as aop -import sqlite3 - -def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): - ''' - Uses provided pulsing information to determine dwell time and total irradiation time. - Assumes that the active irradiation time per pulse and dwell time between pulses both remain constant in any given simulation. - Iterates over the number of pulses, and for each number, calculates dwell time. - The duty cycle is defined as the pulse length / (pulse length + dwell time). - inputs: - active_burn_time : total active irradiation time (float) in any chosen unit - duty_cycle_list : list of chosen duty cycles (float) - num_pulses : list of number of pulses (int) that the active irradiation period is divided into - ''' - pulse_lengths = active_burn_time / num_pulses - rel_dwell_times = (1 - duty_cycle_list) / duty_cycle_list - abs_dwell_times = np.outer(rel_dwell_times, pulse_lengths) - t_irr_arr = active_burn_time + abs_dwell_times * (num_pulses - 1) - print(np.shape(t_irr_arr)) - return pulse_lengths, abs_dwell_times, t_irr_arr - -def open_flux_file(flux_file): - with open(flux_file, 'r') as flux_data: - flux_lines = flux_data.readlines() - return flux_lines - -def parse_flux_lines(flux_lines): - ''' - Uses provided list of flux lines and group structure applied to the run to create an array of flux entries, with: - # rows = # of intervals = total # flux entries / # group structure bins - # columns = # group structure bins - input : flux_lines (list of lines from ALARA flux file) - output : flux_array (numpy array of shape # intervals x number of energy groups) - ''' - energy_bins = openmc.mgxs.GROUP_STRUCTURES['VITAMIN-J-175'] - all_entries = np.array(' '.join(flux_lines).split(), dtype=float) - if len(all_entries) == 0: - raise Exception("The chosen flux file is empty.") - num_groups = len(energy_bins) - 1 - num_intervals = len(all_entries) // num_groups - if len(all_entries) % num_groups != 0: - raise Exception("The number of intervals must be an integer.") - flux_array = all_entries.reshape(num_intervals, num_groups) - return flux_array - -def parse_args(): - parser = argparse.ArgumentParser() - parser.add_argument('--db_yaml', default = "iter_dt_out.yaml", help="Path (str) to YAML containing inputs") - args = parser.parse_args() - return args - -def read_yaml(yaml_arg): - ''' - input: - yaml_arg : output of parse_args() corresponding to args.db_yaml - ''' - with open(yaml_arg, 'r') as yaml_file: - inputs = yaml.safe_load(yaml_file) - return inputs - -def write_to_adf(run_dicts): - adf_data = [] - for run_dict in run_dicts: - lib = aop.DataLibrary() - adf = lib.make_entries(run_dicts[run_dict]) - adf_data.append(adf) - adf = pd.concat(adf_data) - return adf - -def modify_adf(adf): - #Remove some columns: - adf.drop(columns=['time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num'], inplace=True) - #Rename some columns: - adf.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) - print(adf) - return adf - -def write_to_sqlite(adf): - sqlite_conn = sqlite3.connect('activation_results.db') - adf.to_sql('number_densities', sqlite_conn, if_exists='replace', method="multi") - - try: - cursor = sqlite_conn.cursor() - sqlite_conn.commit() - result = cursor.fetchall() - cursor.close() - - if sqlite_conn: - sqlite_conn.close() - except sqlite3.OperationalError as error: - print(error) - -def main(): - args = parse_args() - inputs = read_yaml(args.db_yaml) - - flux_file = inputs['flux_file'] - flux_lines = open_flux_file(flux_file) - flux_array = parse_flux_lines(flux_lines) - - active_burn_time = np.asarray(inputs['active_burn_time']) - duty_cycle_list = np.asarray(inputs['duty_cycles']) - num_pulses = np.asarray(inputs['num_pulses']) - pulse_lengths, abs_dwell_times, t_irr_arr = calc_time_params(active_burn_time, duty_cycle_list, num_pulses) - - total_flux = np.sum(flux_array, axis=1) # sum over the bin widths of flux array - # normalize flux spectrum by the total flux in each interval - norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) # 2D array of shape num_intervals x num_groups - - run_dicts = inputs['run_dicts'] - - adf = write_to_adf(run_dicts) - adf = modify_adf(adf) - #write_to_sqlite(adf) - -if __name__ == "__main__": +import argparse +import yaml +import numpy as np +import openmc +import pandas as pd +import alara_output_processing as aop +import sqlite3 + +def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): + ''' + Uses provided pulsing information to determine dwell time and total irradiation time. + Assumes that the active irradiation time per pulse and dwell time between pulses both remain constant in any given simulation. + Iterates over the number of pulses, and for each number, calculates dwell time. + The duty cycle is defined as the pulse length / (pulse length + dwell time). + inputs: + active_burn_time : total active irradiation time (float) in any chosen unit + duty_cycle_list : list of chosen duty cycles (float) + num_pulses : list of number of pulses (int) that the active irradiation period is divided into + ''' + pulse_lengths = active_burn_time / num_pulses + rel_dwell_times = (1 - duty_cycle_list) / duty_cycle_list + abs_dwell_times = np.outer(rel_dwell_times, pulse_lengths) + t_irr_arr = active_burn_time + abs_dwell_times * (num_pulses - 1) + return pulse_lengths, abs_dwell_times, t_irr_arr + +def open_flux_file(flux_file): + with open(flux_file, 'r') as flux_data: + flux_lines = flux_data.readlines() + return flux_lines + +def parse_flux_lines(flux_lines): + ''' + Uses provided list of flux lines and group structure applied to the run to create an array of flux entries, with: + # rows = # of intervals = total # flux entries / # group structure bins + # columns = # group structure bins + input : flux_lines (list of lines from ALARA flux file) + output : flux_array (numpy array of shape # intervals x number of energy groups) + ''' + energy_bins = openmc.mgxs.GROUP_STRUCTURES['VITAMIN-J-175'] + all_entries = np.array(' '.join(flux_lines).split(), dtype=float) + if len(all_entries) == 0: + raise Exception("The chosen flux file is empty.") + num_groups = len(energy_bins) - 1 + num_intervals = len(all_entries) // num_groups + if len(all_entries) % num_groups != 0: + raise Exception("The number of intervals must be an integer.") + flux_array = all_entries.reshape(num_intervals, num_groups) + return flux_array + +def parse_args(): + parser = argparse.ArgumentParser() + parser.add_argument('--db_yaml', default = "iter_dt_out.yaml", help="Path (str) to YAML containing inputs") + args = parser.parse_args() + return args + +def read_yaml(yaml_arg): + ''' + input: + yaml_arg : output of parse_args() corresponding to args.db_yaml + ''' + with open(yaml_arg, 'r') as yaml_file: + inputs = yaml.safe_load(yaml_file) + return inputs + +def write_to_adf(run_dicts): + adf_data = [] + for run_dict in run_dicts: + lib = aop.DataLibrary() + adf = lib.make_entries(run_dicts[run_dict]) + adf_data.append(adf) + adf = pd.concat(adf_data) + return adf + +def modify_adf(adf, norm_flux_arr, t_irr_arr, inputs): + #Remove some columns: + adf.drop(columns=['time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num'], inplace=True) + #Rename some columns: + adf.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) + block_names = adf['block_name'].unique() + flux_map = {block_name: flux_shape for block_name, flux_shape in zip(block_names, norm_flux_arr)} + # Normalized flux spectrum shape: + adf['flux_spec_shape'] = adf['block_name'].map(flux_map) + + num_pulses = inputs['num_pulses'] + duty_cycles = inputs['duty_cycles'] + + # Extract the number of pulses and duty cycles from the run label + pulse_num_dc = adf['run_lbl'].str.extract(r'_(\d+)p_(\d+)_').astype(int) + + # Map num_pulses and duty_cycles to an index + pulse_idx = pulse_num_dc[0].map({pulse_num: i for i, pulse_num in enumerate(num_pulses)}) + duty_cycle_idx = (pulse_num_dc[1]/100).map({duty_cycle: i for i, duty_cycle in enumerate(duty_cycles)}) + + # Add flattened irradiation time: + adf['t_irr_flat'] = t_irr_arr.T[pulse_idx.to_numpy(), duty_cycle_idx.to_numpy()] + adf['t_irr_flat'] = aop.convert_times(adf['t_irr_flat'], from_unit='y', to_unit='s') + + return adf + +def write_to_sqlite(adf): + sqlite_conn = sqlite3.connect('activation_results.db') + adf.to_sql('number_densities', sqlite_conn, if_exists='replace', method="multi") + + try: + cursor = sqlite_conn.cursor() + sqlite_conn.commit() + result = cursor.fetchall() + cursor.close() + + if sqlite_conn: + sqlite_conn.close() + except sqlite3.OperationalError as error: + print(error) + +def main(): + args = parse_args() + inputs = read_yaml(args.db_yaml) + + flux_file = inputs['flux_file'] + flux_lines = open_flux_file(flux_file) + flux_array = parse_flux_lines(flux_lines) + + active_burn_time = np.asarray(inputs['active_burn_time']) + duty_cycle_list = np.asarray(inputs['duty_cycles']) + num_pulses = np.asarray(inputs['num_pulses']) + pulse_lengths, abs_dwell_times, t_irr_arr = calc_time_params(active_burn_time, duty_cycle_list, num_pulses) + + total_flux = np.sum(flux_array, axis=1) # sum over the bin widths of flux array + # normalize flux spectrum by the total flux in each interval + norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) # 2D array of shape num_intervals x num_groups + + run_dicts = inputs['run_dicts'] + #run_dicts = inputs['iter_dt_100_4y'] + + adf = write_to_adf(run_dicts) + adf = modify_adf(adf, norm_flux_arr, t_irr_arr, inputs) + write_to_sqlite(adf) + +if __name__ == "__main__": main() \ No newline at end of file From 242c7071c5cc1d8e0217f41deaca44fb1b12c158 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra <113371601+anu1217@users.noreply.github.com> Date: Fri, 17 Apr 2026 11:23:39 -0500 Subject: [PATCH 05/30] Apply suggestions from code review Co-authored-by: Paul Wilson --- tools/script_template.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 944881e..9ff4c57 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -37,7 +37,7 @@ def parse_flux_lines(flux_lines): output : flux_array (numpy array of shape # intervals x number of energy groups) ''' energy_bins = openmc.mgxs.GROUP_STRUCTURES['VITAMIN-J-175'] - all_entries = np.array(' '.join(flux_lines).split(), dtype=float) + all_entries = np.array(flux_data.split(), dtype=float) if len(all_entries) == 0: raise Exception("The chosen flux file is empty.") num_groups = len(energy_bins) - 1 @@ -77,7 +77,7 @@ def modify_adf(adf, norm_flux_arr, t_irr_arr, inputs): #Rename some columns: adf.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) block_names = adf['block_name'].unique() - flux_map = {block_name: flux_shape for block_name, flux_shape in zip(block_names, norm_flux_arr)} + flux_map = dict(zip(block_names, norm_flux_arr)) # Normalized flux spectrum shape: adf['flux_spec_shape'] = adf['block_name'].map(flux_map) From 48fd7e4ae920181f2e8056d9538f1e27326a3e54 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 17 Apr 2026 11:24:12 -0500 Subject: [PATCH 06/30] switch to .read() instead of .readlines() --- tools/script_template.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/script_template.py b/tools/script_template.py index 944881e..9690b71 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -25,7 +25,7 @@ def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): def open_flux_file(flux_file): with open(flux_file, 'r') as flux_data: - flux_lines = flux_data.readlines() + flux_lines = flux_data.read() return flux_lines def parse_flux_lines(flux_lines): From cf8dd3aee7be644abfe1817d9a36b65372b3a495 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 17 Apr 2026 11:28:37 -0500 Subject: [PATCH 07/30] change variable names --- tools/script_template.py | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 79aec7a..5b29fae 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -25,19 +25,19 @@ def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): def open_flux_file(flux_file): with open(flux_file, 'r') as flux_data: - flux_lines = flux_data.read() - return flux_lines + flux_str = flux_data.read() + return flux_str -def parse_flux_lines(flux_lines): +def parse_flux_str(flux_str): ''' Uses provided list of flux lines and group structure applied to the run to create an array of flux entries, with: # rows = # of intervals = total # flux entries / # group structure bins # columns = # group structure bins - input : flux_lines (list of lines from ALARA flux file) + input : flux_str (data (str) from ALARA flux file) output : flux_array (numpy array of shape # intervals x number of energy groups) ''' energy_bins = openmc.mgxs.GROUP_STRUCTURES['VITAMIN-J-175'] - all_entries = np.array(flux_data.split(), dtype=float) + all_entries = np.array(flux_str.split(), dtype=float) if len(all_entries) == 0: raise Exception("The chosen flux file is empty.") num_groups = len(energy_bins) - 1 @@ -77,7 +77,8 @@ def modify_adf(adf, norm_flux_arr, t_irr_arr, inputs): #Rename some columns: adf.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) block_names = adf['block_name'].unique() - flux_map = dict(zip(block_names, norm_flux_arr)) + flux_map = dict(zip(block_names, norm_flux_arr)) + # Normalized flux spectrum shape: adf['flux_spec_shape'] = adf['block_name'].map(flux_map) @@ -117,8 +118,8 @@ def main(): inputs = read_yaml(args.db_yaml) flux_file = inputs['flux_file'] - flux_lines = open_flux_file(flux_file) - flux_array = parse_flux_lines(flux_lines) + flux_str = open_flux_file(flux_file) + flux_array = parse_flux_str(flux_str) active_burn_time = np.asarray(inputs['active_burn_time']) duty_cycle_list = np.asarray(inputs['duty_cycles']) From 972d346c26671c751af5bf0ea1780b69041f7479 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 17 Apr 2026 12:30:14 -0500 Subject: [PATCH 08/30] remove openmc dependency --- tools/script_template.py | 23 ++++++++++++++++++----- 1 file changed, 18 insertions(+), 5 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 5b29fae..6338c0f 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -1,7 +1,6 @@ import argparse import yaml import numpy as np -import openmc import pandas as pd import alara_output_processing as aop import sqlite3 @@ -28,7 +27,13 @@ def open_flux_file(flux_file): flux_str = flux_data.read() return flux_str -def parse_flux_str(flux_str): +def get_energy_bins(vit_j_file): + with open(vit_j_file, 'r') as vit_j: + energy_bins = vit_j.read() + energy_bins = np.fromstring(energy_bins, sep=' ') + return energy_bins + +def parse_flux_str(flux_str, energy_bins): ''' Uses provided list of flux lines and group structure applied to the run to create an array of flux entries, with: # rows = # of intervals = total # flux entries / # group structure bins @@ -36,7 +41,6 @@ def parse_flux_str(flux_str): input : flux_str (data (str) from ALARA flux file) output : flux_array (numpy array of shape # intervals x number of energy groups) ''' - energy_bins = openmc.mgxs.GROUP_STRUCTURES['VITAMIN-J-175'] all_entries = np.array(flux_str.split(), dtype=float) if len(all_entries) == 0: raise Exception("The chosen flux file is empty.") @@ -72,6 +76,13 @@ def write_to_adf(run_dicts): return adf def modify_adf(adf, norm_flux_arr, t_irr_arr, inputs): + adf = adf.filter_rows( + filter_dict= + { + "time": -1, + "variable" : adf.VARIABLE_ENUM["Number Density"] + } + ) #Remove some columns: adf.drop(columns=['time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num'], inplace=True) #Rename some columns: @@ -117,9 +128,11 @@ def main(): args = parse_args() inputs = read_yaml(args.db_yaml) - flux_file = inputs['flux_file'] + flux_file = inputs['flux_file'] + vit_j_file = inputs['vit_j_file'] flux_str = open_flux_file(flux_file) - flux_array = parse_flux_str(flux_str) + energy_bins = get_energy_bins(vit_j_file) + flux_array = parse_flux_str(flux_str, energy_bins) active_burn_time = np.asarray(inputs['active_burn_time']) duty_cycle_list = np.asarray(inputs['duty_cycles']) From 10997753ca419ea3a26e112756f9d53424e375b4 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 17 Apr 2026 12:31:23 -0500 Subject: [PATCH 09/30] store vit j data externally --- data/vit-j-175-bins.txt | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) create mode 100644 data/vit-j-175-bins.txt diff --git a/data/vit-j-175-bins.txt b/data/vit-j-175-bins.txt new file mode 100644 index 0000000..bc9831f --- /dev/null +++ b/data/vit-j-175-bins.txt @@ -0,0 +1,30 @@ + 1.0000e-05 1.0000e-01 4.1399e-01 5.3158e-01 6.8256e-01 8.7643e-01 + 1.1253e+00 1.4450e+00 1.8554e+00 2.3824e+00 3.0590e+00 3.9279e+00 + 5.0435e+00 6.4759e+00 8.3153e+00 1.0677e+01 1.3710e+01 1.7604e+01 + 2.2603e+01 2.9023e+01 3.7266e+01 4.7851e+01 6.1442e+01 7.8893e+01 + 1.0130e+02 1.3007e+02 1.6702e+02 2.1445e+02 2.7536e+02 3.5358e+02 + 4.5400e+02 5.8295e+02 7.4852e+02 9.6112e+02 1.2341e+03 1.5846e+03 + 2.0347e+03 2.2487e+03 2.4852e+03 2.6126e+03 2.7465e+03 3.0354e+03 + 3.3546e+03 3.7074e+03 4.3074e+03 5.5308e+03 7.1017e+03 9.1188e+03 + 1.0595e+04 1.1709e+04 1.5034e+04 1.9304e+04 2.1875e+04 2.3579e+04 + 2.4176e+04 2.4788e+04 2.6058e+04 2.7000e+04 2.8501e+04 3.1828e+04 + 3.4307e+04 4.0868e+04 4.6309e+04 5.2475e+04 5.6562e+04 6.7380e+04 + 7.2024e+04 7.9499e+04 8.2503e+04 8.6517e+04 9.8036e+04 1.1109e+05 + 1.1679e+05 1.2277e+05 1.2907e+05 1.3569e+05 1.4264e+05 1.4996e+05 + 1.5764e+05 1.6573e+05 1.7422e+05 1.8316e+05 1.9255e+05 2.0242e+05 + 2.1280e+05 2.2371e+05 2.3518e+05 2.4724e+05 2.7324e+05 2.8725e+05 + 2.9452e+05 2.9721e+05 2.9849e+05 3.0197e+05 3.3373e+05 3.6883e+05 + 3.8774e+05 4.0762e+05 4.5049e+05 4.9787e+05 5.2340e+05 5.5023e+05 + 5.7844e+05 6.0810e+05 6.3928e+05 6.7206e+05 7.0651e+05 7.4274e+05 + 7.8082e+05 8.2085e+05 8.6294e+05 9.0718e+05 9.6167e+05 1.0026e+06 + 1.1080e+06 1.1648e+06 1.2246e+06 1.2874e+06 1.3534e+06 1.4227e+06 + 1.4957e+06 1.5724e+06 1.6530e+06 1.7377e+06 1.8268e+06 1.9205e+06 + 2.0190e+06 2.1225e+06 2.2313e+06 2.3069e+06 2.3457e+06 2.3653e+06 + 2.3851e+06 2.4660e+06 2.5924e+06 2.7253e+06 2.8650e+06 3.0119e+06 + 3.1664e+06 3.3287e+06 3.6788e+06 4.0657e+06 4.4933e+06 4.7237e+06 + 4.9658e+06 5.2205e+06 5.4881e+06 5.7695e+06 6.0653e+06 6.3763e+06 + 6.5924e+06 6.7032e+06 7.0469e+06 7.4082e+06 7.7880e+06 8.1873e+06 + 8.6071e+06 9.0484e+06 9.5123e+06 1.0000e+07 1.0513e+07 1.1052e+07 + 1.1618e+07 1.2214e+07 1.2523e+07 1.2840e+07 1.3499e+07 1.3840e+07 + 1.4191e+07 1.4550e+07 1.4918e+07 1.5683e+07 1.6487e+07 1.6905e+07 + 1.7332e+07 1.9640e+07 \ No newline at end of file From dc1195609b2212b45aadb5df3f799fd58d400c61 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 17 Apr 2026 12:37:01 -0500 Subject: [PATCH 10/30] move empty flux file check, pass flux entries instead of flux_str --- tools/script_template.py | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 6338c0f..fa07fa8 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -25,7 +25,10 @@ def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): def open_flux_file(flux_file): with open(flux_file, 'r') as flux_data: flux_str = flux_data.read() - return flux_str + all_flux_entries = np.array(flux_str.split(), dtype=float) + if len(all_flux_entries) == 0: + raise Exception("The chosen flux file is empty.") + return all_flux_entries def get_energy_bins(vit_j_file): with open(vit_j_file, 'r') as vit_j: @@ -33,22 +36,19 @@ def get_energy_bins(vit_j_file): energy_bins = np.fromstring(energy_bins, sep=' ') return energy_bins -def parse_flux_str(flux_str, energy_bins): +def parse_flux_str(all_flux_entries, energy_bins): ''' Uses provided list of flux lines and group structure applied to the run to create an array of flux entries, with: # rows = # of intervals = total # flux entries / # group structure bins # columns = # group structure bins - input : flux_str (data (str) from ALARA flux file) + input : all_flux_entries (data (numpy array) from ALARA flux file) output : flux_array (numpy array of shape # intervals x number of energy groups) ''' - all_entries = np.array(flux_str.split(), dtype=float) - if len(all_entries) == 0: - raise Exception("The chosen flux file is empty.") num_groups = len(energy_bins) - 1 - num_intervals = len(all_entries) // num_groups - if len(all_entries) % num_groups != 0: + num_intervals = len(all_flux_entries) // num_groups + if len(all_flux_entries) % num_groups != 0: raise Exception("The number of intervals must be an integer.") - flux_array = all_entries.reshape(num_intervals, num_groups) + flux_array = all_flux_entries.reshape(num_intervals, num_groups) return flux_array def parse_args(): @@ -130,9 +130,9 @@ def main(): flux_file = inputs['flux_file'] vit_j_file = inputs['vit_j_file'] - flux_str = open_flux_file(flux_file) + all_flux_entries = open_flux_file(flux_file) energy_bins = get_energy_bins(vit_j_file) - flux_array = parse_flux_str(flux_str, energy_bins) + flux_array = parse_flux_str(all_flux_entries, energy_bins) active_burn_time = np.asarray(inputs['active_burn_time']) duty_cycle_list = np.asarray(inputs['duty_cycles']) From 56d610d4efaa68883a0d2b8d369d9d7f250965be Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 17 Apr 2026 12:40:07 -0500 Subject: [PATCH 11/30] remove write_to_adf() --- tools/iter_dt_out.yaml | 29 +---------------------------- tools/script_template.py | 18 +++--------------- 2 files changed, 4 insertions(+), 43 deletions(-) diff --git a/tools/iter_dt_out.yaml b/tools/iter_dt_out.yaml index 327bbff..71e9ae9 100644 --- a/tools/iter_dt_out.yaml +++ b/tools/iter_dt_out.yaml @@ -13,31 +13,4 @@ num_pulses : - 32 - 64 flux_file : ../calc_dwell_dir/ref_flux_files/iter_dt_flux_2.0986E14 -run_dicts : - iter_dt_100_4y : - iter_dt_2p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_2p_100_4y_out - iter_dt_4p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_4p_100_4y_out - iter_dt_8p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_8p_100_4y_out - iter_dt_32p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_32p_100_4y_out - iter_dt_64p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_64p_100_4y_out - - iter_dt_90_4y : - iter_dt_2p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_2p_90_4y_out - iter_dt_4p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_4p_90_4y_out - iter_dt_8p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_8p_90_4y_out - iter_dt_32p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_32p_90_4y_out - iter_dt_64p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_64p_90_4y_out - - iter_dt_50_4y : - iter_dt_2p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_2p_50_4y_out - iter_dt_4p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_4p_50_4y_out - iter_dt_8p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_8p_50_4y_out - iter_dt_32p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_32p_50_4y_out - iter_dt_64p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_64p_50_4y_out - - iter_dt_25_4y : - iter_dt_2p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_2p_25_4y_out - iter_dt_4p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_4p_25_4y_out - iter_dt_8p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_8p_25_4y_out - iter_dt_32p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_32p_25_4y_out - iter_dt_64p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_64p_25_4y_out \ No newline at end of file +vit_j_file : ../data/vit-j-175-bins.txt \ No newline at end of file diff --git a/tools/script_template.py b/tools/script_template.py index fa07fa8..58193cf 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -64,23 +64,14 @@ def read_yaml(yaml_arg): ''' with open(yaml_arg, 'r') as yaml_file: inputs = yaml.safe_load(yaml_file) - return inputs - -def write_to_adf(run_dicts): - adf_data = [] - for run_dict in run_dicts: - lib = aop.DataLibrary() - adf = lib.make_entries(run_dicts[run_dict]) - adf_data.append(adf) - adf = pd.concat(adf_data) - return adf + return inputs def modify_adf(adf, norm_flux_arr, t_irr_arr, inputs): adf = adf.filter_rows( filter_dict= { "time": -1, - "variable" : adf.VARIABLE_ENUM["Number Density"] + "variable" : adf.VARIABLE_ENUM["Number Density"] } ) #Remove some columns: @@ -143,10 +134,7 @@ def main(): # normalize flux spectrum by the total flux in each interval norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) # 2D array of shape num_intervals x num_groups - run_dicts = inputs['run_dicts'] - #run_dicts = inputs['iter_dt_100_4y'] - - adf = write_to_adf(run_dicts) + # Assume adf exists adf = modify_adf(adf, norm_flux_arr, t_irr_arr, inputs) write_to_sqlite(adf) From abbaf7cb39696a1b3b01794f79637657a11c4afd Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 28 Apr 2026 00:15:09 -0500 Subject: [PATCH 12/30] change script setup --- tools/script_template.py | 105 ++++++++---------------------- tools/test_script_template.py | 118 ++++++++++++++++++++++++++++++++++ 2 files changed, 146 insertions(+), 77 deletions(-) create mode 100644 tools/test_script_template.py diff --git a/tools/script_template.py b/tools/script_template.py index 58193cf..4c5c144 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -5,6 +5,7 @@ import alara_output_processing as aop import sqlite3 + def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): ''' Uses provided pulsing information to determine dwell time and total irradiation time. @@ -20,7 +21,7 @@ def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): rel_dwell_times = (1 - duty_cycle_list) / duty_cycle_list abs_dwell_times = np.outer(rel_dwell_times, pulse_lengths) t_irr_arr = active_burn_time + abs_dwell_times * (num_pulses - 1) - return pulse_lengths, abs_dwell_times, t_irr_arr + return t_irr_arr def open_flux_file(flux_file): with open(flux_file, 'r') as flux_data: @@ -30,82 +31,58 @@ def open_flux_file(flux_file): raise Exception("The chosen flux file is empty.") return all_flux_entries -def get_energy_bins(vit_j_file): - with open(vit_j_file, 'r') as vit_j: - energy_bins = vit_j.read() - energy_bins = np.fromstring(energy_bins, sep=' ') - return energy_bins -def parse_flux_str(all_flux_entries, energy_bins): +def parse_flux_str(all_flux_entries, num_groups): ''' Uses provided list of flux lines and group structure applied to the run to create an array of flux entries, with: # rows = # of intervals = total # flux entries / # group structure bins # columns = # group structure bins input : all_flux_entries (data (numpy array) from ALARA flux file) - output : flux_array (numpy array of shape # intervals x number of energy groups) + num_groups : total number (int) of energy groups from group structure + output : flux_array (numpy array of shape # intervals x # energy groups) ''' - num_groups = len(energy_bins) - 1 num_intervals = len(all_flux_entries) // num_groups if len(all_flux_entries) % num_groups != 0: raise Exception("The number of intervals must be an integer.") flux_array = all_flux_entries.reshape(num_intervals, num_groups) return flux_array -def parse_args(): - parser = argparse.ArgumentParser() - parser.add_argument('--db_yaml', default = "iter_dt_out.yaml", help="Path (str) to YAML containing inputs") - args = parser.parse_args() - return args -def read_yaml(yaml_arg): - ''' - input: - yaml_arg : output of parse_args() corresponding to args.db_yaml - ''' - with open(yaml_arg, 'r') as yaml_file: - inputs = yaml.safe_load(yaml_file) - return inputs - -def modify_adf(adf, norm_flux_arr, t_irr_arr, inputs): - adf = adf.filter_rows( - filter_dict= - { - "time": -1, - "variable" : adf.VARIABLE_ENUM["Number Density"] - } - ) +def modify_adf_columns(adf): + adf = adf.filter_rows(filter_dict={ + "time": -1, + "variable": adf.VARIABLE_ENUM["Number Density"] + }) #Remove some columns: - adf.drop(columns=['time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num'], inplace=True) + adf.drop(columns=[ + 'time', 'time_unit', 'variable', 'var_unit', 'block', 'block_num' + ], + inplace=True) #Rename some columns: - adf.rename(columns={'value':'num_dens_(atoms/cm3)'}, inplace=True) + adf.rename(columns={'value': 'num_dens_(atoms/cm3)'}, inplace=True) + + return adf + +def map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod): + block_names = adf['block_name'].unique() flux_map = dict(zip(block_names, norm_flux_arr)) # Normalized flux spectrum shape: adf['flux_spec_shape'] = adf['block_name'].map(flux_map) - - num_pulses = inputs['num_pulses'] - duty_cycles = inputs['duty_cycles'] - - # Extract the number of pulses and duty cycles from the run label - pulse_num_dc = adf['run_lbl'].str.extract(r'_(\d+)p_(\d+)_').astype(int) - - # Map num_pulses and duty_cycles to an index - pulse_idx = pulse_num_dc[0].map({pulse_num: i for i, pulse_num in enumerate(num_pulses)}) - duty_cycle_idx = (pulse_num_dc[1]/100).map({duty_cycle: i for i, duty_cycle in enumerate(duty_cycles)}) - - # Add flattened irradiation time: - adf['t_irr_flat'] = t_irr_arr.T[pulse_idx.to_numpy(), duty_cycle_idx.to_numpy()] - adf['t_irr_flat'] = aop.convert_times(adf['t_irr_flat'], from_unit='y', to_unit='s') - + adf['t_irr'] = t_irr_arr_mod return adf + def write_to_sqlite(adf): sqlite_conn = sqlite3.connect('activation_results.db') - adf.to_sql('number_densities', sqlite_conn, if_exists='replace', method="multi") + adf.to_sql('number_densities', + sqlite_conn, + if_exists='append', + method="multi") try: - cursor = sqlite_conn.cursor() + cursor = sqlite_conn.cursor() sqlite_conn.commit() result = cursor.fetchall() cursor.close() @@ -113,30 +90,4 @@ def write_to_sqlite(adf): if sqlite_conn: sqlite_conn.close() except sqlite3.OperationalError as error: - print(error) - -def main(): - args = parse_args() - inputs = read_yaml(args.db_yaml) - - flux_file = inputs['flux_file'] - vit_j_file = inputs['vit_j_file'] - all_flux_entries = open_flux_file(flux_file) - energy_bins = get_energy_bins(vit_j_file) - flux_array = parse_flux_str(all_flux_entries, energy_bins) - - active_burn_time = np.asarray(inputs['active_burn_time']) - duty_cycle_list = np.asarray(inputs['duty_cycles']) - num_pulses = np.asarray(inputs['num_pulses']) - pulse_lengths, abs_dwell_times, t_irr_arr = calc_time_params(active_burn_time, duty_cycle_list, num_pulses) - - total_flux = np.sum(flux_array, axis=1) # sum over the bin widths of flux array - # normalize flux spectrum by the total flux in each interval - norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) # 2D array of shape num_intervals x num_groups - - # Assume adf exists - adf = modify_adf(adf, norm_flux_arr, t_irr_arr, inputs) - write_to_sqlite(adf) - -if __name__ == "__main__": - main() \ No newline at end of file + print(error) diff --git a/tools/test_script_template.py b/tools/test_script_template.py new file mode 100644 index 0000000..288a7e6 --- /dev/null +++ b/tools/test_script_template.py @@ -0,0 +1,118 @@ +import argparse +import yaml +import numpy as np +import alara_output_processing as aop +import pandas as pd +import script_template as script_temp +import schedule_transforms as st +import sqlite3 + + +def write_to_adf(run_dicts): + adf_data = [] + for run_dict in run_dicts: + lib = aop.DataLibrary() + adf = lib.make_entries(run_dicts[run_dict]) + adf_data.append(adf) + adf = pd.concat(adf_data) + return adf + + +def test_modify_adf_columns(adf): + assert not any(col in adf for col in [ + "value", + "time", + "time_unit", + "variable", + "var_unit", + "block", + "block_num", + ]) + assert (any(col in adf + for col in ["num_dens_(atoms/cm3)", "half_life", "block_name"])) + + +def adf_map_flux_tirr(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles): + pulse_num_dc = adf["run_lbl"].str.extract(r"_(\d+)p_(\d+)_").astype(int) + # Map num_pulses and duty_cycles to an index + pulse_idx = pulse_num_dc[0].map( + {pulse_num: i + for i, pulse_num in enumerate(num_pulses)}) + duty_cycle_idx = (pulse_num_dc[1] / 100).map( + {duty_cycle: i + for i, duty_cycle in enumerate(duty_cycles)}) + t_irr_arr_mod = t_irr_arr.T[pulse_idx.to_numpy(), + duty_cycle_idx.to_numpy()] + script_temp.map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod) + adf["t_irr"] = aop.convert_times(adf["t_irr"], from_unit="y", to_unit="s") + return adf + + +def test_adf_map_flux_tirr(adf): + assert not ((adf["run_lbl"] == "iter_dt_2p_100_4y") + & (adf["t_irr"] != 4 * 365 * 24 * 60 * 60)).any() + assert not ((adf["run_lbl"] == "iter_dt_64p_25_4y") + & (adf["t_irr"] != 15.8125 * 365 * 24 * 60 * 60)).any() + + +def parse_args(): + parser = argparse.ArgumentParser() + parser.add_argument( + "--db_yaml", + default="iter_dt_out.yaml", + help="Path (str) to YAML containing inputs", + ) + args = parser.parse_args() + return args + + +def read_yaml(yaml_arg): + """ + input: + yaml_arg : output of parse_args() corresponding to args.db_yaml + """ + with open(yaml_arg, "r") as yaml_file: + inputs = yaml.safe_load(yaml_file) + return inputs + + +def main(): + args = parse_args() + inputs = read_yaml(args.db_yaml) + + num_energy_bins = inputs["num_energy_bins"] + + flux_file = inputs["flux_file"] + all_flux_entries = script_temp.open_flux_file(flux_file) + + flux_array = script_temp.parse_flux_str(all_flux_entries, num_energy_bins) + total_flux = np.sum(flux_array, + axis=1) # sum over the bin widths of flux array + # normalize flux spectrum by the total flux in each interval + norm_flux_arr = flux_array / total_flux.reshape( + len(total_flux), 1) # 2D array of shape num_intervals x num_groups + + active_burn_time = np.asarray(inputs["active_burn_time"]) + duty_cycle_list = np.asarray(inputs["duty_cycles"]) + num_pulses = np.asarray(inputs["num_pulses"]) + t_irr_arr = script_temp.calc_time_params(active_burn_time, duty_cycle_list, + num_pulses) + + run_dicts = inputs["run_dicts"] + adf = write_to_adf(run_dicts) + + num_pulses = inputs["num_pulses"] + duty_cycles = inputs["duty_cycles"] + adf = script_temp.modify_adf_columns(adf) + + test_modify_adf_columns(adf) + + adf = adf_map_flux_tirr(adf, norm_flux_arr, t_irr_arr, num_pulses, + duty_cycles) + test_adf_map_flux_tirr(adf) + + script_temp.write_to_sqlite(adf) + + +if __name__ == "__main__": + main() From 0596773995481d2e292f18e4c8216301b5dd1a98 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 28 Apr 2026 00:16:12 -0500 Subject: [PATCH 13/30] delete file with bins --- data/vit-j-175-bins.txt | 30 ------------------------------ tools/iter_dt_out.yaml | 31 ++++++++++++++++++++++++++++++- 2 files changed, 30 insertions(+), 31 deletions(-) delete mode 100644 data/vit-j-175-bins.txt diff --git a/data/vit-j-175-bins.txt b/data/vit-j-175-bins.txt deleted file mode 100644 index bc9831f..0000000 --- a/data/vit-j-175-bins.txt +++ /dev/null @@ -1,30 +0,0 @@ - 1.0000e-05 1.0000e-01 4.1399e-01 5.3158e-01 6.8256e-01 8.7643e-01 - 1.1253e+00 1.4450e+00 1.8554e+00 2.3824e+00 3.0590e+00 3.9279e+00 - 5.0435e+00 6.4759e+00 8.3153e+00 1.0677e+01 1.3710e+01 1.7604e+01 - 2.2603e+01 2.9023e+01 3.7266e+01 4.7851e+01 6.1442e+01 7.8893e+01 - 1.0130e+02 1.3007e+02 1.6702e+02 2.1445e+02 2.7536e+02 3.5358e+02 - 4.5400e+02 5.8295e+02 7.4852e+02 9.6112e+02 1.2341e+03 1.5846e+03 - 2.0347e+03 2.2487e+03 2.4852e+03 2.6126e+03 2.7465e+03 3.0354e+03 - 3.3546e+03 3.7074e+03 4.3074e+03 5.5308e+03 7.1017e+03 9.1188e+03 - 1.0595e+04 1.1709e+04 1.5034e+04 1.9304e+04 2.1875e+04 2.3579e+04 - 2.4176e+04 2.4788e+04 2.6058e+04 2.7000e+04 2.8501e+04 3.1828e+04 - 3.4307e+04 4.0868e+04 4.6309e+04 5.2475e+04 5.6562e+04 6.7380e+04 - 7.2024e+04 7.9499e+04 8.2503e+04 8.6517e+04 9.8036e+04 1.1109e+05 - 1.1679e+05 1.2277e+05 1.2907e+05 1.3569e+05 1.4264e+05 1.4996e+05 - 1.5764e+05 1.6573e+05 1.7422e+05 1.8316e+05 1.9255e+05 2.0242e+05 - 2.1280e+05 2.2371e+05 2.3518e+05 2.4724e+05 2.7324e+05 2.8725e+05 - 2.9452e+05 2.9721e+05 2.9849e+05 3.0197e+05 3.3373e+05 3.6883e+05 - 3.8774e+05 4.0762e+05 4.5049e+05 4.9787e+05 5.2340e+05 5.5023e+05 - 5.7844e+05 6.0810e+05 6.3928e+05 6.7206e+05 7.0651e+05 7.4274e+05 - 7.8082e+05 8.2085e+05 8.6294e+05 9.0718e+05 9.6167e+05 1.0026e+06 - 1.1080e+06 1.1648e+06 1.2246e+06 1.2874e+06 1.3534e+06 1.4227e+06 - 1.4957e+06 1.5724e+06 1.6530e+06 1.7377e+06 1.8268e+06 1.9205e+06 - 2.0190e+06 2.1225e+06 2.2313e+06 2.3069e+06 2.3457e+06 2.3653e+06 - 2.3851e+06 2.4660e+06 2.5924e+06 2.7253e+06 2.8650e+06 3.0119e+06 - 3.1664e+06 3.3287e+06 3.6788e+06 4.0657e+06 4.4933e+06 4.7237e+06 - 4.9658e+06 5.2205e+06 5.4881e+06 5.7695e+06 6.0653e+06 6.3763e+06 - 6.5924e+06 6.7032e+06 7.0469e+06 7.4082e+06 7.7880e+06 8.1873e+06 - 8.6071e+06 9.0484e+06 9.5123e+06 1.0000e+07 1.0513e+07 1.1052e+07 - 1.1618e+07 1.2214e+07 1.2523e+07 1.2840e+07 1.3499e+07 1.3840e+07 - 1.4191e+07 1.4550e+07 1.4918e+07 1.5683e+07 1.6487e+07 1.6905e+07 - 1.7332e+07 1.9640e+07 \ No newline at end of file diff --git a/tools/iter_dt_out.yaml b/tools/iter_dt_out.yaml index 71e9ae9..bf28b39 100644 --- a/tools/iter_dt_out.yaml +++ b/tools/iter_dt_out.yaml @@ -13,4 +13,33 @@ num_pulses : - 32 - 64 flux_file : ../calc_dwell_dir/ref_flux_files/iter_dt_flux_2.0986E14 -vit_j_file : ../data/vit-j-175-bins.txt \ No newline at end of file +num_energy_bins : 175 + +run_dicts : + iter_dt_100_4y : + iter_dt_2p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_2p_100_4y_out + iter_dt_4p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_4p_100_4y_out + iter_dt_8p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_8p_100_4y_out + iter_dt_32p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_32p_100_4y_out + iter_dt_64p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_64p_100_4y_out + + iter_dt_90_4y : + iter_dt_2p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_2p_90_4y_out + iter_dt_4p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_4p_90_4y_out + iter_dt_8p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_8p_90_4y_out + iter_dt_32p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_32p_90_4y_out + iter_dt_64p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_64p_90_4y_out + + iter_dt_50_4y : + iter_dt_2p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_2p_50_4y_out + iter_dt_4p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_4p_50_4y_out + iter_dt_8p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_8p_50_4y_out + iter_dt_32p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_32p_50_4y_out + iter_dt_64p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_64p_50_4y_out + + iter_dt_25_4y : + iter_dt_2p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_2p_25_4y_out + iter_dt_4p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_4p_25_4y_out + iter_dt_8p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_8p_25_4y_out + iter_dt_32p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_32p_25_4y_out + iter_dt_64p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_64p_25_4y_out \ No newline at end of file From c19b4446afcec13e3eaf7d167a2d75d349c825e9 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 28 Apr 2026 09:23:07 -0500 Subject: [PATCH 14/30] add docstrings --- tools/test_script_template.py | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 288a7e6..154d889 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -7,6 +7,11 @@ import schedule_transforms as st import sqlite3 +''' +Runs and tests the methods in script_template.py using a series of run dictionaries +with various pulse numbers and duty cycles. +''' + def write_to_adf(run_dicts): adf_data = [] @@ -19,6 +24,9 @@ def write_to_adf(run_dicts): def test_modify_adf_columns(adf): + ''' + Ensure that the expected columns exist in the adf. + ''' assert not any(col in adf for col in [ "value", "time", @@ -33,6 +41,11 @@ def test_modify_adf_columns(adf): def adf_map_flux_tirr(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles): + ''' + Maps each of the number of pulses and duty cycle values from the run label to an iterator, + from which the corresponding value of the irradiation time is identified. The irradiation + time is added to a new column in the adf. + ''' pulse_num_dc = adf["run_lbl"].str.extract(r"_(\d+)p_(\d+)_").astype(int) # Map num_pulses and duty_cycles to an index pulse_idx = pulse_num_dc[0].map( @@ -49,6 +62,9 @@ def adf_map_flux_tirr(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles): def test_adf_map_flux_tirr(adf): + ''' + Ensure that two of the run labels are associated with the correct irradiation time. + ''' assert not ((adf["run_lbl"] == "iter_dt_2p_100_4y") & (adf["t_irr"] != 4 * 365 * 24 * 60 * 60)).any() assert not ((adf["run_lbl"] == "iter_dt_64p_25_4y") From 6dd6dcef865c04874f47a1c92c1ec51dfb0c014f Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 28 Apr 2026 09:23:45 -0500 Subject: [PATCH 15/30] remove unused packages --- tools/script_template.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 4c5c144..5b24a23 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -1,5 +1,3 @@ -import argparse -import yaml import numpy as np import pandas as pd import alara_output_processing as aop From 2a99216ab4ebff7008025eccec9d32ea5b5c874f Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 28 Apr 2026 10:00:30 -0500 Subject: [PATCH 16/30] remove unused packages --- tools/test_script_template.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 154d889..f97e542 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -4,8 +4,6 @@ import alara_output_processing as aop import pandas as pd import script_template as script_temp -import schedule_transforms as st -import sqlite3 ''' Runs and tests the methods in script_template.py using a series of run dictionaries From 266530808a80cfcc21f9a92ac304ec7c35bb8703 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 28 Apr 2026 10:03:44 -0500 Subject: [PATCH 17/30] unindent line --- tools/test_script_template.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index f97e542..379fbb1 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -17,7 +17,7 @@ def write_to_adf(run_dicts): lib = aop.DataLibrary() adf = lib.make_entries(run_dicts[run_dict]) adf_data.append(adf) - adf = pd.concat(adf_data) + adf = pd.concat(adf_data) return adf From 0c618462e437e3aeee9826e073393aed312843d3 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 5 May 2026 14:06:17 -0500 Subject: [PATCH 18/30] modify function names, move integer interval check --- tools/script_template.py | 2 +- tools/test_script_template.py | 13 +++++++------ 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 5b24a23..1adf679 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -39,9 +39,9 @@ def parse_flux_str(all_flux_entries, num_groups): num_groups : total number (int) of energy groups from group structure output : flux_array (numpy array of shape # intervals x # energy groups) ''' - num_intervals = len(all_flux_entries) // num_groups if len(all_flux_entries) % num_groups != 0: raise Exception("The number of intervals must be an integer.") + num_intervals = len(all_flux_entries) // num_groups flux_array = all_flux_entries.reshape(num_intervals, num_groups) return flux_array diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 379fbb1..75bcf3f 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -38,11 +38,12 @@ def test_modify_adf_columns(adf): for col in ["num_dens_(atoms/cm3)", "half_life", "block_name"])) -def adf_map_flux_tirr(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles): +def make_use_tirr_mod(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles): ''' Maps each of the number of pulses and duty cycle values from the run label to an iterator, from which the corresponding value of the irradiation time is identified. The irradiation - time is added to a new column in the adf. + time array is added to a new column in the adf by running the map_adf_flux_tirr() method from + script_template.py. ''' pulse_num_dc = adf["run_lbl"].str.extract(r"_(\d+)p_(\d+)_").astype(int) # Map num_pulses and duty_cycles to an index @@ -54,12 +55,12 @@ def adf_map_flux_tirr(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles): for i, duty_cycle in enumerate(duty_cycles)}) t_irr_arr_mod = t_irr_arr.T[pulse_idx.to_numpy(), duty_cycle_idx.to_numpy()] - script_temp.map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod) + adf = script_temp.map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod) adf["t_irr"] = aop.convert_times(adf["t_irr"], from_unit="y", to_unit="s") return adf -def test_adf_map_flux_tirr(adf): +def test_make_use_tirr_mod(adf): ''' Ensure that two of the run labels are associated with the correct irradiation time. ''' @@ -121,9 +122,9 @@ def main(): test_modify_adf_columns(adf) - adf = adf_map_flux_tirr(adf, norm_flux_arr, t_irr_arr, num_pulses, + adf = make_use_tirr_mod(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles) - test_adf_map_flux_tirr(adf) + test_make_use_tirr_mod(adf) script_temp.write_to_sqlite(adf) From df144c73b6ba1d161f4ff88333b0920ccebd3bd1 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Thu, 7 May 2026 12:35:29 -0500 Subject: [PATCH 19/30] move functions around, create test df, add docstrings --- tools/script_template.py | 69 +++++++++-------- tools/test_script_template.py | 140 +++++++--------------------------- 2 files changed, 67 insertions(+), 142 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 1adf679..1c1f978 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -1,26 +1,7 @@ import numpy as np -import pandas as pd -import alara_output_processing as aop import sqlite3 -def calc_time_params(active_burn_time, duty_cycle_list, num_pulses): - ''' - Uses provided pulsing information to determine dwell time and total irradiation time. - Assumes that the active irradiation time per pulse and dwell time between pulses both remain constant in any given simulation. - Iterates over the number of pulses, and for each number, calculates dwell time. - The duty cycle is defined as the pulse length / (pulse length + dwell time). - inputs: - active_burn_time : total active irradiation time (float) in any chosen unit - duty_cycle_list : list of chosen duty cycles (float) - num_pulses : list of number of pulses (int) that the active irradiation period is divided into - ''' - pulse_lengths = active_burn_time / num_pulses - rel_dwell_times = (1 - duty_cycle_list) / duty_cycle_list - abs_dwell_times = np.outer(rel_dwell_times, pulse_lengths) - t_irr_arr = active_burn_time + abs_dwell_times * (num_pulses - 1) - return t_irr_arr - def open_flux_file(flux_file): with open(flux_file, 'r') as flux_data: flux_str = flux_data.read() @@ -47,6 +28,11 @@ def parse_flux_str(all_flux_entries, num_groups): def modify_adf_columns(adf): + ''' + Filters the adf for the pre-shutdown state and the number density. + Removes columns that do not add information required for the database. + :param: adf: ALARA DFrame object + ''' adf = adf.filter_rows(filter_dict={ "time": -1, "variable": adf.VARIABLE_ENUM["Number Density"] @@ -61,7 +47,15 @@ def modify_adf_columns(adf): return adf + def map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod): + ''' + Finds the unique block names in the adf and maps the correct flux spectrum + to the block. Assigns a column to store irradiation time. + :param: norm_flux_arr: numpy array of flux spectrum shape (# intervals x # energy groups) + :param: t_irr_arr_mod: numpy array of irradiation times where the total number of entries + is the number of rows in the adf + ''' block_names = adf['block_name'].unique() flux_map = dict(zip(block_names, norm_flux_arr)) @@ -72,20 +66,33 @@ def map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod): return adf -def write_to_sqlite(adf): - sqlite_conn = sqlite3.connect('activation_results.db') - adf.to_sql('number_densities', - sqlite_conn, - if_exists='append', - method="multi") - +def write_to_sqlite(adf, db_name="activation_results.db"): + ''' + Initialize a connection to a SQLite database, and write the adf + to it. Catches any errors produced during this process. + ''' try: - cursor = sqlite_conn.cursor() + sqlite_conn = sqlite3.connect(db_name) + adf.to_sql('number_densities', + sqlite_conn, + if_exists='append', + method="multi") sqlite_conn.commit() - result = cursor.fetchall() - cursor.close() + except sqlite3.OperationalError as error: + print(error) + return sqlite_conn.cursor() + - if sqlite_conn: - sqlite_conn.close() +def close_sqlite_conn(cursor): + ''' + Closes inidividual SQLite cursor objects, and the connection + to the database. To be executed after running write_to_sqlite() + or anytime a SQLite connection has been established. + :param: cursor: SQLite cursor object + ''' + try: + cursor.close() + if cursor.connection: + cursor.connection.close() except sqlite3.OperationalError as error: print(error) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 75bcf3f..c4b5880 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -1,30 +1,11 @@ -import argparse -import yaml -import numpy as np import alara_output_processing as aop -import pandas as pd import script_template as script_temp -''' -Runs and tests the methods in script_template.py using a series of run dictionaries -with various pulse numbers and duty cycles. -''' - - -def write_to_adf(run_dicts): - adf_data = [] - for run_dict in run_dicts: - lib = aop.DataLibrary() - adf = lib.make_entries(run_dicts[run_dict]) - adf_data.append(adf) - adf = pd.concat(adf_data) - return adf - - def test_modify_adf_columns(adf): ''' Ensure that the expected columns exist in the adf. ''' + adf = script_temp.modify_adf_columns(adf) assert not any(col in adf for col in [ "value", "time", @@ -34,100 +15,37 @@ def test_modify_adf_columns(adf): "block", "block_num", ]) - assert (any(col in adf + assert (all(col in adf for col in ["num_dens_(atoms/cm3)", "half_life", "block_name"])) - - -def make_use_tirr_mod(adf, norm_flux_arr, t_irr_arr, num_pulses, duty_cycles): - ''' - Maps each of the number of pulses and duty cycle values from the run label to an iterator, - from which the corresponding value of the irradiation time is identified. The irradiation - time array is added to a new column in the adf by running the map_adf_flux_tirr() method from - script_template.py. - ''' - pulse_num_dc = adf["run_lbl"].str.extract(r"_(\d+)p_(\d+)_").astype(int) - # Map num_pulses and duty_cycles to an index - pulse_idx = pulse_num_dc[0].map( - {pulse_num: i - for i, pulse_num in enumerate(num_pulses)}) - duty_cycle_idx = (pulse_num_dc[1] / 100).map( - {duty_cycle: i - for i, duty_cycle in enumerate(duty_cycles)}) - t_irr_arr_mod = t_irr_arr.T[pulse_idx.to_numpy(), - duty_cycle_idx.to_numpy()] - adf = script_temp.map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod) - adf["t_irr"] = aop.convert_times(adf["t_irr"], from_unit="y", to_unit="s") return adf - - -def test_make_use_tirr_mod(adf): - ''' - Ensure that two of the run labels are associated with the correct irradiation time. - ''' - assert not ((adf["run_lbl"] == "iter_dt_2p_100_4y") - & (adf["t_irr"] != 4 * 365 * 24 * 60 * 60)).any() - assert not ((adf["run_lbl"] == "iter_dt_64p_25_4y") - & (adf["t_irr"] != 15.8125 * 365 * 24 * 60 * 60)).any() - - -def parse_args(): - parser = argparse.ArgumentParser() - parser.add_argument( - "--db_yaml", - default="iter_dt_out.yaml", - help="Path (str) to YAML containing inputs", - ) - args = parser.parse_args() - return args - - -def read_yaml(yaml_arg): - """ - input: - yaml_arg : output of parse_args() corresponding to args.db_yaml - """ - with open(yaml_arg, "r") as yaml_file: - inputs = yaml.safe_load(yaml_file) - return inputs - + +def test_write_to_sqlite(adf): + cursor = script_temp.write_to_sqlite(adf, db_name = ":memory:") + cursor.execute("SELECT * FROM number_densities") + result = cursor.fetchall() + assert len(result) == len(adf["half_life"]) + assert len(result[0]) == 6 + return cursor + +def test_close_sqlite_conn(cursor): + script_temp.close_sqlite_conn(cursor) def main(): - args = parse_args() - inputs = read_yaml(args.db_yaml) - - num_energy_bins = inputs["num_energy_bins"] - - flux_file = inputs["flux_file"] - all_flux_entries = script_temp.open_flux_file(flux_file) - - flux_array = script_temp.parse_flux_str(all_flux_entries, num_energy_bins) - total_flux = np.sum(flux_array, - axis=1) # sum over the bin widths of flux array - # normalize flux spectrum by the total flux in each interval - norm_flux_arr = flux_array / total_flux.reshape( - len(total_flux), 1) # 2D array of shape num_intervals x num_groups - - active_burn_time = np.asarray(inputs["active_burn_time"]) - duty_cycle_list = np.asarray(inputs["duty_cycles"]) - num_pulses = np.asarray(inputs["num_pulses"]) - t_irr_arr = script_temp.calc_time_params(active_burn_time, duty_cycle_list, - num_pulses) - - run_dicts = inputs["run_dicts"] - adf = write_to_adf(run_dicts) - - num_pulses = inputs["num_pulses"] - duty_cycles = inputs["duty_cycles"] - adf = script_temp.modify_adf_columns(adf) - - test_modify_adf_columns(adf) - - adf = make_use_tirr_mod(adf, norm_flux_arr, t_irr_arr, num_pulses, - duty_cycles) - test_make_use_tirr_mod(adf) - - script_temp.write_to_sqlite(adf) - + adf = aop.ALARADFrame(data= + {"value": [5.678e-11]*2, + "time": [-1]*2, + "time_unit" : ["s"]*2, + "variable": [0]*2, + "var_unit": ["atoms/cm3"]*2, + "block" : [1,2], + "block_name": ["Be", "W"], + "block_num": [2]*2, + "nuclide": ["h-1"]*2, + "half_life": ["-1"]*2, + "run_lbl": ["test_case", "new_test_case"]}) + adf = test_modify_adf_columns(adf) + cursor = test_write_to_sqlite(adf) + test_close_sqlite_conn(cursor) if __name__ == "__main__": - main() + main() \ No newline at end of file From 7889b05b8123fae50c80fe0b374c605d43fbe8d5 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Thu, 7 May 2026 12:38:10 -0500 Subject: [PATCH 20/30] change function name --- tools/script_template.py | 2 +- tools/test_script_template.py | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 1c1f978..95d9785 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -27,7 +27,7 @@ def parse_flux_str(all_flux_entries, num_groups): return flux_array -def modify_adf_columns(adf): +def modify_adf_for_db(adf): ''' Filters the adf for the pre-shutdown state and the number density. Removes columns that do not add information required for the database. diff --git a/tools/test_script_template.py b/tools/test_script_template.py index c4b5880..5a9b430 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -1,11 +1,11 @@ import alara_output_processing as aop import script_template as script_temp -def test_modify_adf_columns(adf): +def test_modify_adf_for_db(adf): ''' Ensure that the expected columns exist in the adf. ''' - adf = script_temp.modify_adf_columns(adf) + adf = script_temp.modify_adf_for_db(adf) assert not any(col in adf for col in [ "value", "time", @@ -43,7 +43,7 @@ def main(): "nuclide": ["h-1"]*2, "half_life": ["-1"]*2, "run_lbl": ["test_case", "new_test_case"]}) - adf = test_modify_adf_columns(adf) + adf = test_modify_adf_for_db(adf) cursor = test_write_to_sqlite(adf) test_close_sqlite_conn(cursor) From 41595a8f00e3c1ca03e2aa2e3055b29668b70287 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 8 May 2026 11:14:15 -0500 Subject: [PATCH 21/30] normalize flux --- tools/script_template.py | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/tools/script_template.py b/tools/script_template.py index 95d9785..7f96f9a 100644 --- a/tools/script_template.py +++ b/tools/script_template.py @@ -16,9 +16,8 @@ def parse_flux_str(all_flux_entries, num_groups): Uses provided list of flux lines and group structure applied to the run to create an array of flux entries, with: # rows = # of intervals = total # flux entries / # group structure bins # columns = # group structure bins - input : all_flux_entries (data (numpy array) from ALARA flux file) - num_groups : total number (int) of energy groups from group structure - output : flux_array (numpy array of shape # intervals x # energy groups) + :param: all_flux_entries: (data (numpy array) from ALARA flux file) + :param: num_groups : total number (int) of energy groups from group structure ''' if len(all_flux_entries) % num_groups != 0: raise Exception("The number of intervals must be an integer.") @@ -26,6 +25,17 @@ def parse_flux_str(all_flux_entries, num_groups): flux_array = all_flux_entries.reshape(num_intervals, num_groups) return flux_array +def normalize_flux(flux_array): + ''' + Obtain the total flux by summing over the bin widths of the flux array, + then normalize the spectrum by the total flux in each interval. + :param: flux_array: (numpy array of shape # intervals x # energy groups) + ''' + total_flux = np.sum(flux_array, axis=1) + #norm_flux_arr = 2D array of shape num_intervals x num_groups + norm_flux_arr = flux_array / total_flux.reshape(len(total_flux), 1) + return norm_flux_arr + def modify_adf_for_db(adf): ''' From 7b48ffefb2b019e227d164f2746fdfff733377ac Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 8 May 2026 11:58:40 -0500 Subject: [PATCH 22/30] separate returned values from test for separation of concerns --- tools/test_script_template.py | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 5a9b430..806f56b 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -19,13 +19,11 @@ def test_modify_adf_for_db(adf): for col in ["num_dens_(atoms/cm3)", "half_life", "block_name"])) return adf -def test_write_to_sqlite(adf): - cursor = script_temp.write_to_sqlite(adf, db_name = ":memory:") +def test_write_to_sqlite(adf, cursor): cursor.execute("SELECT * FROM number_densities") result = cursor.fetchall() assert len(result) == len(adf["half_life"]) - assert len(result[0]) == 6 - return cursor + assert len(result[0]) == 6 def test_close_sqlite_conn(cursor): script_temp.close_sqlite_conn(cursor) @@ -44,7 +42,8 @@ def main(): "half_life": ["-1"]*2, "run_lbl": ["test_case", "new_test_case"]}) adf = test_modify_adf_for_db(adf) - cursor = test_write_to_sqlite(adf) + cursor = script_temp.write_to_sqlite(adf, db_name = ":memory:") + test_write_to_sqlite(adf, cursor) test_close_sqlite_conn(cursor) if __name__ == "__main__": From f23a8941b689f36e2cdcd9e19d8a6ea299a2eead Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 8 May 2026 12:05:58 -0500 Subject: [PATCH 23/30] remove redundant test --- tools/test_script_template.py | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 806f56b..3eb180d 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -23,10 +23,7 @@ def test_write_to_sqlite(adf, cursor): cursor.execute("SELECT * FROM number_densities") result = cursor.fetchall() assert len(result) == len(adf["half_life"]) - assert len(result[0]) == 6 - -def test_close_sqlite_conn(cursor): - script_temp.close_sqlite_conn(cursor) + assert len(result[0]) == 6 def main(): adf = aop.ALARADFrame(data= @@ -44,7 +41,7 @@ def main(): adf = test_modify_adf_for_db(adf) cursor = script_temp.write_to_sqlite(adf, db_name = ":memory:") test_write_to_sqlite(adf, cursor) - test_close_sqlite_conn(cursor) + script_temp.close_sqlite_conn(cursor) #this function has a built-in test in the form of catching any operational errors if __name__ == "__main__": main() \ No newline at end of file From 45323ad3196c8340a738f652ea816e50315d9581 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Fri, 8 May 2026 12:07:11 -0500 Subject: [PATCH 24/30] remove returned value from test --- tools/test_script_template.py | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 3eb180d..e8f314e 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -5,7 +5,6 @@ def test_modify_adf_for_db(adf): ''' Ensure that the expected columns exist in the adf. ''' - adf = script_temp.modify_adf_for_db(adf) assert not any(col in adf for col in [ "value", "time", @@ -17,7 +16,6 @@ def test_modify_adf_for_db(adf): ]) assert (all(col in adf for col in ["num_dens_(atoms/cm3)", "half_life", "block_name"])) - return adf def test_write_to_sqlite(adf, cursor): cursor.execute("SELECT * FROM number_densities") @@ -38,9 +36,13 @@ def main(): "nuclide": ["h-1"]*2, "half_life": ["-1"]*2, "run_lbl": ["test_case", "new_test_case"]}) - adf = test_modify_adf_for_db(adf) + + adf = script_temp.modify_adf_for_db(adf) + test_modify_adf_for_db(adf) + cursor = script_temp.write_to_sqlite(adf, db_name = ":memory:") test_write_to_sqlite(adf, cursor) + script_temp.close_sqlite_conn(cursor) #this function has a built-in test in the form of catching any operational errors if __name__ == "__main__": From 2fd5e55b8016df32071288034edd65ef9b41a3b7 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra <113371601+anu1217@users.noreply.github.com> Date: Fri, 8 May 2026 13:44:05 -0500 Subject: [PATCH 25/30] Delete unused file --- tools/iter_dt_out.yaml | 45 ------------------------------------------ 1 file changed, 45 deletions(-) delete mode 100644 tools/iter_dt_out.yaml diff --git a/tools/iter_dt_out.yaml b/tools/iter_dt_out.yaml deleted file mode 100644 index bf28b39..0000000 --- a/tools/iter_dt_out.yaml +++ /dev/null @@ -1,45 +0,0 @@ -# List of necessary inputs from 4FPY ITER DT simulations - -active_burn_time : 4 #years -duty_cycles : - - 1 - - 0.9 - - 0.5 - - 0.25 -num_pulses : - - 2 - - 4 - - 8 - - 32 - - 64 -flux_file : ../calc_dwell_dir/ref_flux_files/iter_dt_flux_2.0986E14 -num_energy_bins : 175 - -run_dicts : - iter_dt_100_4y : - iter_dt_2p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_2p_100_4y_out - iter_dt_4p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_4p_100_4y_out - iter_dt_8p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_8p_100_4y_out - iter_dt_32p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_32p_100_4y_out - iter_dt_64p_100_4y : ../calc_dwell_dir/iter/duty_cycle_100/output_100/iter_dt_64p_100_4y_out - - iter_dt_90_4y : - iter_dt_2p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_2p_90_4y_out - iter_dt_4p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_4p_90_4y_out - iter_dt_8p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_8p_90_4y_out - iter_dt_32p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_32p_90_4y_out - iter_dt_64p_90_4y : ../calc_dwell_dir/iter/duty_cycle_90/output_90/iter_dt_64p_90_4y_out - - iter_dt_50_4y : - iter_dt_2p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_2p_50_4y_out - iter_dt_4p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_4p_50_4y_out - iter_dt_8p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_8p_50_4y_out - iter_dt_32p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_32p_50_4y_out - iter_dt_64p_50_4y : ../calc_dwell_dir/iter/duty_cycle_50/output_50/iter_dt_64p_50_4y_out - - iter_dt_25_4y : - iter_dt_2p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_2p_25_4y_out - iter_dt_4p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_4p_25_4y_out - iter_dt_8p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_8p_25_4y_out - iter_dt_32p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_32p_25_4y_out - iter_dt_64p_25_4y : ../calc_dwell_dir/iter/duty_cycle_25/output_25/iter_dt_64p_25_4y_out \ No newline at end of file From 65ee23a39713c23a8f72069ebb44abbc36ffc70a Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 19 May 2026 12:55:35 -0500 Subject: [PATCH 26/30] make actual pytests --- tools/test_script_template.py | 60 +++++++++++++++++++++-------------- 1 file changed, 36 insertions(+), 24 deletions(-) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index e8f314e..0d91091 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -1,10 +1,29 @@ import alara_output_processing as aop import script_template as script_temp +import sqlite3 +import pytest + +@pytest.mark.parametrize( "adf", + [ + (aop.ALARADFrame(data= + {"value": [5.678e-11]*2, + "time": [-1]*2, + "time_unit" : ["s"]*2, + "variable": [0]*2, + "var_unit": ["atoms/cm3"]*2, + "block" : [1,2], + "block_name": ["Be", "W"], + "block_num": [2]*2, + "nuclide": ["h-1"]*2, + "half_life": ["-1"]*2, + "run_lbl": ["test_case", "new_test_case"]})) + ]) def test_modify_adf_for_db(adf): ''' Ensure that the expected columns exist in the adf. ''' + adf = script_temp.modify_adf_for_db(adf) assert not any(col in adf for col in [ "value", "time", @@ -16,34 +35,27 @@ def test_modify_adf_for_db(adf): ]) assert (all(col in adf for col in ["num_dens_(atoms/cm3)", "half_life", "block_name"])) - -def test_write_to_sqlite(adf, cursor): - cursor.execute("SELECT * FROM number_densities") - result = cursor.fetchall() - assert len(result) == len(adf["half_life"]) - assert len(result[0]) == 6 -def main(): - adf = aop.ALARADFrame(data= - {"value": [5.678e-11]*2, - "time": [-1]*2, - "time_unit" : ["s"]*2, - "variable": [0]*2, - "var_unit": ["atoms/cm3"]*2, - "block" : [1,2], +@pytest.mark.parametrize( "mod_adf", + [ + (aop.ALARADFrame(data= + {"num_dens_(atoms/cm3)": [5.678e-11]*2, "block_name": ["Be", "W"], - "block_num": [2]*2, "nuclide": ["h-1"]*2, "half_life": ["-1"]*2, - "run_lbl": ["test_case", "new_test_case"]}) + "run_lbl": ["test_case", "new_test_case"]})) + ]) - adf = script_temp.modify_adf_for_db(adf) - test_modify_adf_for_db(adf) - - cursor = script_temp.write_to_sqlite(adf, db_name = ":memory:") - test_write_to_sqlite(adf, cursor) +def test_write_to_sqlite(mod_adf): + cursor = script_temp.write_to_sqlite(mod_adf, db_name = ":memory:") + cursor.execute("SELECT * FROM number_densities") + result = cursor.fetchall() + assert len(result) == len(mod_adf["half_life"]) + assert len(result[0]) == 6 - script_temp.close_sqlite_conn(cursor) #this function has a built-in test in the form of catching any operational errors +@pytest.mark.parametrize( "test_cursor", + [sqlite3.connect(":memory").cursor()]) -if __name__ == "__main__": - main() \ No newline at end of file +def test_close_sqlite_conn(test_cursor): + # This function has a built-in test in the form of catching operational errors + script_temp.close_sqlite_conn(test_cursor) \ No newline at end of file From 191a9222671792289c71bae4f2118999f62a5dcf Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 19 May 2026 13:29:28 -0500 Subject: [PATCH 27/30] add tests for parse_flux_str and normalize_flux --- tools/test_script_template.py | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index 0d91091..e1474df 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -1,8 +1,29 @@ +import numpy as np import alara_output_processing as aop import script_template as script_temp import sqlite3 import pytest +@pytest.mark.parametrize( "all_flux_entries, num_groups, exp_flux_arr", + [(np.array([2,4,6,8,10,2,4,6,8,10]), 5, np.array([[2,4,6,8,10], [2,4,6,8,10]])) + ]) + +def test_parse_flux_str(all_flux_entries, num_groups, exp_flux_arr): + obs_flux_arr = script_temp.parse_flux_str(all_flux_entries, num_groups) + assert obs_flux_arr.all() == exp_flux_arr.all() + +@pytest.mark.parametrize( "flux_arr, exp_norm_flux_arr", + [ + (np.array([[2,4,6,8,10], [2,4,6,8,10]]), np.array([[num / 30 for num in [2,4,6,8,10]], + [num / 30 for num in [2,4,6,8,10]] + ]) + ) + ]) + +def test_normalize_flux(flux_arr, exp_norm_flux_arr): + obs_norm_flux_arr = script_temp.normalize_flux(flux_arr) + assert obs_norm_flux_arr.all() == exp_norm_flux_arr.all() + @pytest.mark.parametrize( "adf", [ (aop.ALARADFrame(data= From 53a81cab41a7215003808644e4b5d7f721044277 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 19 May 2026 14:40:52 -0500 Subject: [PATCH 28/30] add test for flux mapping --- tools/test_script_template.py | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) diff --git a/tools/test_script_template.py b/tools/test_script_template.py index e1474df..1b9aeea 100644 --- a/tools/test_script_template.py +++ b/tools/test_script_template.py @@ -1,4 +1,5 @@ import numpy as np +import pandas as pd import alara_output_processing as aop import script_template as script_temp import sqlite3 @@ -57,6 +58,35 @@ def test_modify_adf_for_db(adf): assert (all(col in adf for col in ["num_dens_(atoms/cm3)", "half_life", "block_name"])) +@pytest.mark.parametrize( "test_adf, norm_flux_arr, t_irr_arr_mod, exp_mod_adf", + [ + (aop.ALARADFrame(data= + {"num_dens_(atoms/cm3)": [5.678e-11]*2, + "block_name": ["Be", "W"], + "nuclide": ["h-1"]*2, + "half_life": ["-1"]*2, + "run_lbl": ["test_case", "new_test_case"]}), + np.array([[num / 25 for num in [1,3,5,7,9]], [num / 30 for num in [2,4,6,8,10]] + ]), + np.array([7.5]*2), + aop.ALARADFrame(data= + {"num_dens_(atoms/cm3)": [5.678e-11]*2, + "block_name": ["Be", "W"], + "nuclide": ["h-1"]*2, + "half_life": ["-1"]*2, + "run_lbl": ["test_case", "new_test_case"], + "flux_spec_shape" : [np.array([num / 25 for num in [1,3,5,7,9]]), + np.array([num / 30 for num in [2,4,6,8,10]])], + "t_irr" : [7.5]*2 + }) + ) + ]) + +def test_map_adf_flux_tirr(test_adf, norm_flux_arr, t_irr_arr_mod, exp_mod_adf): + obs_mod_adf = script_temp.map_adf_flux_tirr(test_adf, norm_flux_arr, t_irr_arr_mod) + assert pd.DataFrame(obs_mod_adf["flux_spec_shape"]).equals(pd.DataFrame(exp_mod_adf["flux_spec_shape"])) == True + assert all(obs_mod_adf["t_irr"]) == all(exp_mod_adf["t_irr"]) + @pytest.mark.parametrize( "mod_adf", [ (aop.ALARADFrame(data= From af6dd8f2e51c66768905117453df78667f3650ff Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 19 May 2026 14:44:31 -0500 Subject: [PATCH 29/30] rename scripts --- tools/{script_template.py => adf_to_sqlite.py} | 0 ...script_template.py => test_adf_to_sqlite.py} | 17 ++++++++--------- 2 files changed, 8 insertions(+), 9 deletions(-) rename tools/{script_template.py => adf_to_sqlite.py} (100%) rename tools/{test_script_template.py => test_adf_to_sqlite.py} (88%) diff --git a/tools/script_template.py b/tools/adf_to_sqlite.py similarity index 100% rename from tools/script_template.py rename to tools/adf_to_sqlite.py diff --git a/tools/test_script_template.py b/tools/test_adf_to_sqlite.py similarity index 88% rename from tools/test_script_template.py rename to tools/test_adf_to_sqlite.py index 1b9aeea..5dfc2e0 100644 --- a/tools/test_script_template.py +++ b/tools/test_adf_to_sqlite.py @@ -1,7 +1,6 @@ import numpy as np -import pandas as pd import alara_output_processing as aop -import script_template as script_temp +import adf_to_sqlite as ats import sqlite3 import pytest @@ -10,7 +9,7 @@ ]) def test_parse_flux_str(all_flux_entries, num_groups, exp_flux_arr): - obs_flux_arr = script_temp.parse_flux_str(all_flux_entries, num_groups) + obs_flux_arr = ats.parse_flux_str(all_flux_entries, num_groups) assert obs_flux_arr.all() == exp_flux_arr.all() @pytest.mark.parametrize( "flux_arr, exp_norm_flux_arr", @@ -22,7 +21,7 @@ def test_parse_flux_str(all_flux_entries, num_groups, exp_flux_arr): ]) def test_normalize_flux(flux_arr, exp_norm_flux_arr): - obs_norm_flux_arr = script_temp.normalize_flux(flux_arr) + obs_norm_flux_arr = ats.normalize_flux(flux_arr) assert obs_norm_flux_arr.all() == exp_norm_flux_arr.all() @pytest.mark.parametrize( "adf", @@ -45,7 +44,7 @@ def test_modify_adf_for_db(adf): ''' Ensure that the expected columns exist in the adf. ''' - adf = script_temp.modify_adf_for_db(adf) + adf = ats.modify_adf_for_db(adf) assert not any(col in adf for col in [ "value", "time", @@ -83,8 +82,8 @@ def test_modify_adf_for_db(adf): ]) def test_map_adf_flux_tirr(test_adf, norm_flux_arr, t_irr_arr_mod, exp_mod_adf): - obs_mod_adf = script_temp.map_adf_flux_tirr(test_adf, norm_flux_arr, t_irr_arr_mod) - assert pd.DataFrame(obs_mod_adf["flux_spec_shape"]).equals(pd.DataFrame(exp_mod_adf["flux_spec_shape"])) == True + obs_mod_adf = ats.map_adf_flux_tirr(test_adf, norm_flux_arr, t_irr_arr_mod) + assert obs_mod_adf["flux_spec_shape"].equals(exp_mod_adf["flux_spec_shape"]) == True assert all(obs_mod_adf["t_irr"]) == all(exp_mod_adf["t_irr"]) @pytest.mark.parametrize( "mod_adf", @@ -98,7 +97,7 @@ def test_map_adf_flux_tirr(test_adf, norm_flux_arr, t_irr_arr_mod, exp_mod_adf): ]) def test_write_to_sqlite(mod_adf): - cursor = script_temp.write_to_sqlite(mod_adf, db_name = ":memory:") + cursor = ats.write_to_sqlite(mod_adf, db_name = ":memory:") cursor.execute("SELECT * FROM number_densities") result = cursor.fetchall() assert len(result) == len(mod_adf["half_life"]) @@ -109,4 +108,4 @@ def test_write_to_sqlite(mod_adf): def test_close_sqlite_conn(test_cursor): # This function has a built-in test in the form of catching operational errors - script_temp.close_sqlite_conn(test_cursor) \ No newline at end of file + ats.close_sqlite_conn(test_cursor) \ No newline at end of file From 6a30a8d77137f326e807665b556847b9651bbd73 Mon Sep 17 00:00:00 2001 From: Anupama Rajendra Date: Tue, 19 May 2026 15:07:30 -0500 Subject: [PATCH 30/30] separate opening and closing of connection, don't record index in database --- tools/adf_to_sqlite.py | 7 +++---- tools/test_adf_to_sqlite.py | 6 +++--- 2 files changed, 6 insertions(+), 7 deletions(-) diff --git a/tools/adf_to_sqlite.py b/tools/adf_to_sqlite.py index 7f96f9a..717002b 100644 --- a/tools/adf_to_sqlite.py +++ b/tools/adf_to_sqlite.py @@ -75,18 +75,17 @@ def map_adf_flux_tirr(adf, norm_flux_arr, t_irr_arr_mod): adf['t_irr'] = t_irr_arr_mod return adf - -def write_to_sqlite(adf, db_name="activation_results.db"): +def write_to_sqlite(adf, sqlite_conn): ''' Initialize a connection to a SQLite database, and write the adf to it. Catches any errors produced during this process. ''' try: - sqlite_conn = sqlite3.connect(db_name) adf.to_sql('number_densities', sqlite_conn, if_exists='append', - method="multi") + method="multi", + index=False) sqlite_conn.commit() except sqlite3.OperationalError as error: print(error) diff --git a/tools/test_adf_to_sqlite.py b/tools/test_adf_to_sqlite.py index 5dfc2e0..3b49f6a 100644 --- a/tools/test_adf_to_sqlite.py +++ b/tools/test_adf_to_sqlite.py @@ -97,14 +97,14 @@ def test_map_adf_flux_tirr(test_adf, norm_flux_arr, t_irr_arr_mod, exp_mod_adf): ]) def test_write_to_sqlite(mod_adf): - cursor = ats.write_to_sqlite(mod_adf, db_name = ":memory:") + cursor = ats.write_to_sqlite(mod_adf, sqlite3.connect(":memory:")) cursor.execute("SELECT * FROM number_densities") result = cursor.fetchall() assert len(result) == len(mod_adf["half_life"]) - assert len(result[0]) == 6 + assert len(result[0]) == 5 @pytest.mark.parametrize( "test_cursor", - [sqlite3.connect(":memory").cursor()]) + [sqlite3.connect(":memory:").cursor()]) def test_close_sqlite_conn(test_cursor): # This function has a built-in test in the form of catching operational errors