Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Check and plot the ACIS FP safety planning limit, support the new ACIS FP model #50

Merged
merged 9 commits into from
May 19, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 36 additions & 10 deletions acis_thermal_check/apps/acisfp_check.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,9 @@ def __init__(self):
"planning.data_quality.high.acisi": "acis_i",
"planning.data_quality.high.aciss": "acis_s",
"planning.data_quality.high.aciss_hot": "acis_hot",
"planning.data_quality.high.cold_ecs": "cold_ecs"
"planning.data_quality.high.cold_ecs": "cold_ecs",
"planning.warning.high": "planning_hi",
"safety.caution.high": "yellow_hi"
}
super(ACISFPCheck, self).__init__("fptemp", "acisfp", valid_limits,
hist_limit,
Expand Down Expand Up @@ -99,8 +101,11 @@ def _calc_model_supp(self, model, state_times, states, ephem, state0):

# Input ephemeris explicitly for calculating Earth heating
for axis in "xyz":
name = 'orbitephem0_{}'.format(axis)
name = f'orbitephem0_{axis}'
model.comp[name].set_data(ephem[name], model.times)
name = f'solarephem0_{axis}'
if name in model.comp:
model.comp[name].set_data(ephem[name], model.times)

# Set some initial values. You do this because some
# of these values may not be set at the actual start time.
Expand Down Expand Up @@ -149,7 +154,7 @@ def make_prediction_plots(self, outdir, states, temps, load_start):
w1 = None
# Make plots of FPTEMP and pitch vs time, looping over
# three different temperature ranges
ylim = [(-120, -90), (-120, -119), (-120.0, -107.5)]
ylim = [(-120, -79), (-120, -119), (-120.0, -107.5)]
ypos = [-110.0, -119.35, -116]
capwidth = [2.0, 0.1, 0.4]
textypos = [-108.0, -119.3, -115.7]
Expand All @@ -173,6 +178,10 @@ def make_prediction_plots(self, outdir, states, temps, load_start):
plots[name].add_limit_line(self.limits["acis_s"], "ACIS-S", ls='--')
# Draw a horizontal line showing the hot ACIS-S cutoff
plots[name].add_limit_line(self.limits["acis_hot"], "Hot ACIS-S", ls='--')
# Draw a horizontal line showing the planning warning limit
plots[name].add_limit_line(self.limits["planning_hi"], "Planning", ls='-')
# Draw a horizontal line showing the safety caution limit
plots[name].add_limit_line(self.limits["yellow_hi"], "Yellow", ls='-')
# Get the width of this plot to make the widths of all the
# prediction plots the same
if i == 0:
Expand Down Expand Up @@ -200,7 +209,7 @@ def make_prediction_plots(self, outdir, states, temps, load_start):

# Make the legend on the temperature plot
plots[name].ax.legend(bbox_to_anchor=(0.15, 0.99),
loc='lower left', ncol=4, fontsize=14)
loc='lower left', ncol=4, fontsize=12)

# Build the file name
filename = f'{self.msid.lower()}' \
Expand Down Expand Up @@ -271,16 +280,29 @@ def make_prediction_viols(self, temps, states, load_start):

temp = temps[self.name]

# ------------------------------------------------------------
# ACIS-I - Collect any -112 C violations of any non-ECS ACIS-I
# science run. These are load killers
# ------------------------------------------------------------
#
# ---------------------------------------------------------------
# Planning - Collect any -84 C violations. These are load killers
# ---------------------------------------------------------------

hi_viols = self._make_prediction_viols(
times, temp, load_start, self.limits["planning_hi"].value,
"planning", "max")
viols = {"hi":
{"name": f"Planning High ({self.limits['planning_hi'].value} C)",
"type": "Max",
"values": hi_viols}
}

acis_i_limit = self.limits["acis_i"].value
acis_s_limit = self.limits["acis_s"].value
acis_hot_limit = self.limits["acis_hot"].value
cold_ecs_limit = self.limits["cold_ecs"].value

# ------------------------------------------------------------
# ACIS-I - Collect any -112 C violations of any non-ECS ACIS-I
# science run. These are load killers
# ------------------------------------------------------------

mylog.info(f'ACIS-I Science ({acis_i_limit} C) violations')

# Create the violation data structure.
Expand All @@ -295,7 +317,7 @@ def make_prediction_viols(self, temps, states, load_start):
# ACIS-S - Collect any -111 C violations of any non-ECS ACIS-S
# science run. These are load killers
# ------------------------------------------------------------
#

mylog.info(f'ACIS-S Science ({acis_s_limit} C) violations')

acis_s_viols = self.search_obsids_for_viols("ACIS-S",
Expand Down Expand Up @@ -450,18 +472,21 @@ def draw_obsids(obs_list, plots, msid, ypos, endcapstart, endcapstop,
obs_stop,
linestyle='-',
color=color,
zorder=2,
linewidth=2.0)

# Plot vertical end caps for each obsid to visually show start/stop
plots[msid].ax.vlines(obs_start,
endcapstart,
endcapstop,
color=color,
zorder=2,
linewidth=2.0)
plots[msid].ax.vlines(obs_stop,
endcapstart,
endcapstop,
color=color,
zorder=2,
linewidth=2.0)

# Now print the obsid in the middle of the time span,
Expand All @@ -477,6 +502,7 @@ def draw_obsids(obs_list, plots, msid, ypos, endcapstart, endcapstop,
va='bottom',
ma='left',
rotation=90,
zorder=2,
fontsize=fontsize)


Expand Down
35 changes: 18 additions & 17 deletions acis_thermal_check/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -935,24 +935,25 @@ def make_validation_plots(self, tlm, model_spec, outdir):
scale = scales.get(msid, 1.0)
ticklocs, fig, ax = plot_cxctime(
model.times, pred[msid] / scale, label='Model',
fig=fig, ls='-', lw=4, color=thermal_red)
fig=fig, ls='-', lw=4, color=thermal_red, zorder=9)
ticklocs, fig, ax = plot_cxctime(
model.times, tlm[msid] / scale, label='Data',
fig=fig, ls='-', lw=2, color=thermal_blue)
fig=fig, ls='-', lw=2, color=thermal_blue, zorder=10)
if np.any(~good_mask):
ticklocs, fig, ax = plot_cxctime(model.times[~good_mask],
tlm[msid][~good_mask] / scale,
fig=fig, fmt='.c')
fig=fig, fmt='.c', zorder=10)
ax.set_title(msid.upper() + ' validation', loc='left', pad=10)
ax.set_xlabel("Date")
ax.set_ylabel(labels[msid])
ax.grid()
ax.set_axisbelow(True)
# add lines for perigee passages
for rz in rzs:
ptimes = cxctime2plotdate([rz.tstart, rz.tstop])
for ptime in ptimes:
ax.axvline(ptime, ls='--', color='C2',
linewidth=2, zorder=-10)
linewidth=2, zorder=2)
# Add horizontal lines for the planning and caution limits
# or the limits for the focal plane model. Make sure we can
# see all of the limits.
Expand All @@ -962,34 +963,34 @@ def make_validation_plots(self, tlm, model_spec, outdir):
ax.axhline(self.limits["cold_ecs"].value,
linestyle='--', label='Cold ECS',
color=self.limits["cold_ecs"].color,
zorder=-8, linewidth=2)
zorder=2, linewidth=2)
ax.axhline(self.limits["acis_i"].value,
linestyle='--', label='ACIS-I',
color=self.limits["acis_i"].color,
zorder=-8, linewidth=2)
zorder=2, linewidth=2)
ax.axhline(self.limits["acis_s"].value,
linestyle='--', label='ACIS-S',
color=self.limits["acis_s"].color,
zorder=-8, linewidth=2)
zorder=2, linewidth=2)
ax.axhline(self.limits["acis_hot"].value,
linestyle='--', label='Hot ACIS',
color=self.limits["acis_hot"].color,
zorder=-8, linewidth=2)
zorder=2, linewidth=2)
ymax = max(self.limits["acis_hot"].value+1, ymax)
else:
ax.axhline(self.limits["yellow_hi"].value,
linestyle='-', linewidth=2, zorder=-8,
linestyle='-', linewidth=2, zorder=2,
color=self.limits["yellow_hi"].color)
ax.axhline(self.limits["planning_hi"].value,
linestyle='-', linewidth=2, zorder=-8,
linestyle='-', linewidth=2, zorder=2,
color=self.limits["planning_hi"].color)
ymax = max(self.limits["yellow_hi"].value+1, ymax)
if self.flag_cold_viols:
ax.axhline(self.limits["yellow_lo"].value,
linestyle='-', linewidth=2, zorder=-8,
linestyle='-', linewidth=2, zorder=2,
color=self.limits["yellow_lo"].color)
ax.axhline(self.limits["planning_lo"].value,
linestyle='-', linewidth=2, zorder=-8,
linestyle='-', linewidth=2, zorder=2,
color=self.limits["planning_lo"].color)
ymin = min(self.limits["yellow_lo"].value-1, ymin)
ax.set_ylim(ymin, ymax)
Expand Down Expand Up @@ -1042,9 +1043,9 @@ def make_validation_plots(self, tlm, model_spec, outdir):
fig = plt.figure(10+fig_id, figsize=(12, 6))
fig.clf()
ticklocs, fig, ax = plot_cxctime(model.times, model.comp['ccd_count'].dvals,
fig=fig, ls='-', lw=2, color=thermal_blue)
fig=fig, ls='-', lw=2, color=thermal_blue, zorder=10)
ticklocs, fig, ax = plot_cxctime(model.times, model.comp['fep_count'].dvals,
fig=fig, ls='--', lw=2, color=thermal_blue)
fig=fig, ls='--', lw=2, color=thermal_blue, zorder=10)
ax.set_ylim(0, 6.5)
ax.set_title("ACIS CCD/FEPs")
ax.set_xlabel("Date")
Expand All @@ -1058,7 +1059,7 @@ def make_validation_plots(self, tlm, model_spec, outdir):
ptimes = cxctime2plotdate([rz.tstart, rz.tstop])
for ptime in ptimes:
ax.axvline(ptime, ls='--', color='C2',
linewidth=2, zorder=-10)
linewidth=2, zorder=2)
ax.legend(fancybox=True, framealpha=0.5, loc=2)
plots["ccd_count"] = {
"lines": {"fig": fig,
Expand All @@ -1073,7 +1074,7 @@ def make_validation_plots(self, tlm, model_spec, outdir):
fig = plt.figure(10 + fig_id, figsize=(12, 6))
fig.clf()
ticklocs, fig, ax = plot_cxctime(model.times, model.comp['earthheat__fptemp'].dvals,
fig=fig, ls='-', lw=2, color=thermal_blue)
fig=fig, ls='-', lw=2, color=thermal_blue, zorder=10)
ax.set_title("Earth Solid Angle in Rad FOV")
ax.set_xlabel("Date")
ax.set_ylabel("Earth Solid Angle (sr)")
Expand All @@ -1086,7 +1087,7 @@ def make_validation_plots(self, tlm, model_spec, outdir):
ptimes = cxctime2plotdate([rz.tstart, rz.tstop])
for ptime in ptimes:
ax.axvline(ptime, ls='--', color='C2',
linewidth=2, zorder=-10)
linewidth=2, zorder=2)

plots["earthheat__fptemp"] = {
"lines": {"fig": fig,
Expand Down
2 changes: 1 addition & 1 deletion acis_thermal_check/templates/index_template.rst
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ ADDITIONAL PLOTS
Additional plots of FPTEMP vs TIME for different temperature ranges

.. image:: fptempM120toM119.png
.. image:: fptempM120toM90.png
.. image:: fptempM120toM79.png

{% endif %}

Expand Down
66 changes: 66 additions & 0 deletions acis_thermal_check/tests/acisfp/answers/MAY0922A_viol.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
{
"run_start": "2022:251:23:10:06.816",
"limits": {
"planning_hi": -97.0
},
"datestarts": [
"2022:128:08:49:58.816",
"2022:131:00:09:18.816",
"2022:133:15:55:58.816",
"2022:130:07:12:30.816",
"2022:132:22:31:50.816",
"2022:134:10:03:50.816",
"2022:134:21:54:30.816",
"2022:129:04:19:50.816",
"2022:132:11:03:02.816",
"2022:135:18:19:02.816"
],
"datestops": [
"2022:128:10:06:30.816",
"2022:131:01:47:42.816",
"2022:133:16:28:46.816",
"2022:130:09:07:18.816",
"2022:133:00:21:10.816",
"2022:134:12:04:06.816",
"2022:134:22:43:42.816",
"2022:129:05:58:14.816",
"2022:132:22:15:26.816",
"2022:135:19:57:26.816"
],
"duration": [
"4.59",
"5.90",
"1.97",
"6.89",
"6.56",
"7.22",
"2.95",
"5.90",
"40.34",
"5.90"
],
"temps": [
"-90.27",
"-88.14",
"-94.38",
"-111.44",
"-111.02",
"-111.42",
"-111.87",
"-110.62",
"-109.93",
"-110.44"
],
"obsids": [
"",
"",
"",
"23816",
"26364",
"26081",
"26418",
"23827",
"23867",
"26033"
]
}
6 changes: 6 additions & 0 deletions acis_thermal_check/tests/acisfp/test_acisfp_viols.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,3 +22,9 @@ def test_JUN1421A_viols(answer_store, test_root):
fp_rt = RegressionTester(ACISFPCheck, test_root=test_root, sub_dir='viols')
fp_rt.check_violation_reporting("JUN1421A", answer_data,
answer_store=answer_store)

def test_MAY0922A_viols(answer_store, test_root):
answer_data = tests_path / "acisfp/answers/MAY0922A_viol.json"
fp_rt = RegressionTester(ACISFPCheck, test_root=test_root, sub_dir='viols')
fp_rt.check_violation_reporting("MAY0922A", answer_data,
answer_store=answer_store)
8 changes: 6 additions & 2 deletions acis_thermal_check/tests/regression_testing.py
Original file line number Diff line number Diff line change
Expand Up @@ -397,8 +397,12 @@ def check_violation_reporting(self, load_week, viol_json,
viol_data["datestops"].append(words[1])
viol_data["duration"].append(words[2])
viol_data["temps"].append(words[3])
if self.msid == "fptemp":
viol_data["obsids"].append(words[4])
if self.msid == "fptemp":
if len(words) > 4:
obsid = words[4]
else:
obsid = ""
viol_data["obsids"].append(obsid)
else:
try:
assert viol_data["datestarts"][i] in line
Expand Down
11 changes: 6 additions & 5 deletions acis_thermal_check/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ def __init__(self, fig_id, x, y, x2=None, y2=None, yy=None,
ax = fig.add_subplot(1, 1, 1)
# Plot left y-axis
ax.plot(xt, y, linestyle='-', linewidth=2,
color=self._color)
color=self._color, zorder=10)
if yy is not None:
ax.plot(xt, yy, linestyle='--', linewidth=2,
color=self._color2)
Expand All @@ -179,7 +179,9 @@ def __init__(self, fig_id, x, y, x2=None, y2=None, yy=None,
ax.set_ylabel(ylabel)
ax.set_title(title)
ax.grid()

ax.set_zorder(10)
ax.set_axisbelow(True)

# Plot right y-axis

if x2 is not None and y2 is not None:
Expand All @@ -197,7 +199,7 @@ def __init__(self, fig_id, x, y, x2=None, y2=None, yy=None,

if load_start is not None:
# Add a vertical line to mark the start time of the load
ax.axvline(load_start, linestyle='-', color='g', linewidth=2.0)
ax.axvline(load_start, linestyle='-', color='g', zorder=2, linewidth=2.0)

Ska.Matplotlib.set_time_ticks(ax)
for label in ax.xaxis.get_ticklabels():
Expand All @@ -217,7 +219,6 @@ def __init__(self, fig_id, x, y, x2=None, y2=None, yy=None,
rm = fig.subplotpars.right * width / w2
fig.subplots_adjust(left=lm, right=rm)

ax.set_zorder(10)
ax.patch.set_visible(False)

self.fig = fig
Expand All @@ -240,7 +241,7 @@ def add_limit_line(self, limit, label, ls='-'):
The line style for the limit line. Default: "-"
"""
self.ax.axhline(limit.value, linestyle=ls, linewidth=2.0,
color=limit.color, label=label, zorder=-8)
color=limit.color, label=label, zorder=2.0)


class PredictPlot(PlotDate):
Expand Down