Using the AnalyzeTimeSeries Class
This class contains a set of methods to create a database of data from KPF observations, as well as methods to ingest data, query the database, print data, and made plots of various types. The script ingest_kpf_ts_db.py can be used to ingest data from the command line.
The ingested data comes from PRIMARY header extensions of L0/2D/L1/L2 files, RV and CCF header extensions in L2 files, TELEMETRY extensions in L0 files.
An elaborate set of standard time series plots can be made over intervals of days/months/years/decades spanning a date range. Plots of the number of observations of a given type (e.g., flats) over time can also be produced in standardized ways.
This code is designed to be used in several ways. First, it can be run in ‘production’ mode on a central server to regularly generate a set of plots showing the state of KPF and its data products to inform observers and DRP developers. Within the KPF team, display of these plots is through the Jump web interface. The plotting methods offer a way for KPF afficianados to quickly diagnose hardware and software issues that are evident by comparing data from different observations and to assess remedies. This work can be done using a Jupyter Notebook or with production scripts running automatically. All of the standard Quality Control (QC) and Diagnostics outputs generated by the DRP are ingested automatically. Thus, users don’t need to scrape FITS headers for this information. The databases also offer a way to package derived KPF data products (e.g., RVs and metadata) into a single file for distribution and relatively easy access for analysis.
The AnalyzeTimeSeries class provides a front end to database methods inthe TSDB class. Under the hood, TSDB can use either a portable SQLite3 database stored in a file or a Postgresql database configured on a server. Distinctions between the SQLite3 and Postgresql implementations are discusssed on the related page titled “Database Details - SQLite and PostgreSQL”.
This tutorial describes the basics of data ingestion, querying and display of the database, and making standardized time series plots and histograms of the number of observations vs. time. For additional details about capabilities, the user is encouraged to read the code in KPF-Pipeline/database/modules/src/utils/tsdb.py and KPF-Pipeline/modules/quick_look/src/analyze_time_series.py.
To use AnalyzeTimeSeries methods, start by importing packages.
[1]:
from modules.quicklook.src.analyze_time_series import AnalyzeTimeSeries
import pandas as pd
import matplotlib.pyplot as plt
import os
import numpy as np
import time
import subprocess
import matplotlib.dates as mdates
from datetime import datetime
from astropy.table import Table
%matplotlib inline
Database Ingestion
The AnalyzeTimeSeries class is initiated as shown below. This example uses a SQLite3 database, which is fresh because the file kpf_ts.db didn’t exist. When running the database in another environment, the user may want to specify a different db_path.
[2]:
db_path = 'kpf_ts.db' # name of database file
myTS = AnalyzeTimeSeries(db_path=db_path)
INFO: Starting AnalyzeTimeSeries
INFO: Starting KPF_TSDB
INFO: Jupyter Notebook environment detected.
INFO: Base data directory: /data/L0
INFO: Backend: sqlite
INFO: Table prefix: tsdb_
INFO: Path of database file: /code/KPF-Pipeline/docs/source/tutorials/kpf_ts.db
INFO: Metadata table exists.
INFO: Metadata table read.
INFO: Data tables exist.
Drop the table if needed. This is needed if the database schema was updated since it was last run. Note that methods in myTS.db are part of the TSDB class, which is inherited by AnalyzeTS.
[3]:
myTS.db.drop_tables()
myTS = AnalyzeTimeSeries(db_path=db_path)
INFO: Dropped table: tsdb_base
INFO: Dropped table: tsdb_l0
INFO: Dropped table: tsdb_l0_cal
INFO: Dropped table: tsdb_l0_shutter
INFO: Dropped table: tsdb_2d
INFO: Dropped table: tsdb_2d_flux
INFO: Dropped table: tsdb_l1
INFO: Dropped table: tsdb_l1_flux
INFO: Dropped table: tsdb_l1_lines
INFO: Dropped table: tsdb_l1_medg
INFO: Dropped table: tsdb_l1_medr
INFO: Dropped table: tsdb_l1_stdg
INFO: Dropped table: tsdb_l1_stdr
INFO: Dropped table: tsdb_l2
INFO: Dropped table: tsdb_l0t
INFO: Dropped table: tsdb_l2rv
INFO: Dropped table: tsdb_l2ccf
INFO: Dropped table: tsdb_l2_bcv
INFO: Dropped table: tsdb_l2_bjd
INFO: Dropped table: tsdb_l2_ccfw
INFO: Dropped table: tsdb_l2_rv_sci1
INFO: Dropped table: tsdb_l2_rv_sci2
INFO: Dropped table: tsdb_l2_rv_sci3
INFO: Dropped table: tsdb_l2_rv_sci
INFO: Dropped table: tsdb_l2_rv_cal
INFO: Dropped table: tsdb_l2_rv_sky
INFO: Dropped table: tsdb_l2_erv_sci
INFO: Dropped table: tsdb_l2_erv_cal
INFO: Dropped table: tsdb_l2_erv_sky
INFO: Dropped table: tsdb_metadata
INFO: Starting AnalyzeTimeSeries
INFO: Starting KPF_TSDB
INFO: Jupyter Notebook environment detected.
INFO: Base data directory: /data/L0
INFO: Backend: sqlite
INFO: Table prefix: tsdb_
INFO: Path of database file: /code/KPF-Pipeline/docs/source/tutorials/kpf_ts.db
INFO: Metadata table does not exist. Attempting to create.
INFO: Metadata table created correctly with indexed columns.
INFO: Metadata table read.
INFO: Data tables do not exist. Attempting to create.
INFO: Data tables and indices created successfully.
Data can be ingested into the database using several methods. The first method is one observation at a time.
[4]:
myTS.db.ingest_one_observation('/data/L0/20241003/','KP.20241003.46386.23.fits')
myTS.db.print_db_status()
INFO: Ingested observation: KP.20241003.46386.23
INFO: Database Table Summary:
INFO: Table Columns Rows
INFO: -------------------------------------------------------
INFO: tsdb_base 23 1
INFO: tsdb_l0 54 1
INFO: tsdb_l0_cal 40 1
INFO: tsdb_l0_shutter 32 1
INFO: tsdb_2d 95 1
INFO: tsdb_2d_flux 96 1
INFO: tsdb_l1 37 1
INFO: tsdb_l1_flux 71 1
INFO: tsdb_l1_lines 31 1
INFO: tsdb_l1_medg 106 1
INFO: tsdb_l1_medr 97 1
INFO: tsdb_l1_stdg 106 1
INFO: tsdb_l1_stdr 97 1
INFO: tsdb_l2 29 1
INFO: tsdb_l0t 124 1
INFO: tsdb_l2rv 29 1
INFO: tsdb_l2ccf 7 1
INFO: tsdb_l2_bcv 68 1
INFO: tsdb_l2_bjd 68 1
INFO: tsdb_l2_ccfw 68 1
INFO: tsdb_l2_rv_sci1 68 1
INFO: tsdb_l2_rv_sci2 68 1
INFO: tsdb_l2_rv_sci3 68 1
INFO: tsdb_l2_rv_sci 68 1
INFO: tsdb_l2_rv_cal 68 1
INFO: tsdb_l2_rv_sky 68 1
INFO: tsdb_l2_erv_sci 68 1
INFO: tsdb_l2_erv_cal 68 1
INFO: tsdb_l2_erv_sky 68 1
INFO: Dates: 1 days from 20241003 to 20241003
INFO: Last update: 2025-12-18 22:30:41
Second, a list of observations can be downloaded with ObsIDs (e.g., ‘KP.20241215.16336.39’) in the first column of a csv file. Such files can be generated by, for example, the Jump website for those who work on the DRP development team. The command to ingest a list of these observations is is myTS.db.add_ObsID_list_to_db('filename.csv').
Third, data can be ingested over a range of dates. This command will take a few minutes to run, but rerunning it will take less time once the observations are ingested into the database.
[5]:
start_date = '20241001'
end_date = '20241006'
myTS = AnalyzeTimeSeries(db_path=db_path)
myTS.db.ingest_dates_to_db(start_date, end_date)
INFO: Starting AnalyzeTimeSeries
INFO: Starting KPF_TSDB
INFO: Jupyter Notebook environment detected.
INFO: Base data directory: /data/L0
INFO: Backend: sqlite
INFO: Table prefix: tsdb_
INFO: Path of database file: /code/KPF-Pipeline/docs/source/tutorials/kpf_ts.db
INFO: Metadata table exists.
INFO: Metadata table read.
INFO: Data tables exist.
INFO: Adding to database between 20241001 and 20241006
INFO: Files for 6 days ingested/checked
After ingestion is complete, a summary of the database tables is shown.
[6]:
myTS.db.print_db_status()
INFO: Database Table Summary:
INFO: Table Columns Rows
INFO: -------------------------------------------------------
INFO: tsdb_base 23 3345
INFO: tsdb_l0 54 3345
INFO: tsdb_l0_cal 40 3345
INFO: tsdb_l0_shutter 32 3345
INFO: tsdb_2d 95 3345
INFO: tsdb_2d_flux 96 3345
INFO: tsdb_l1 37 3345
INFO: tsdb_l1_flux 71 3345
INFO: tsdb_l1_lines 31 3345
INFO: tsdb_l1_medg 106 3345
INFO: tsdb_l1_medr 97 3345
INFO: tsdb_l1_stdg 106 3345
INFO: tsdb_l1_stdr 97 3345
INFO: tsdb_l2 29 3345
INFO: tsdb_l0t 124 3345
INFO: tsdb_l2rv 29 3345
INFO: tsdb_l2ccf 7 3345
INFO: tsdb_l2_bcv 68 3345
INFO: tsdb_l2_bjd 68 3345
INFO: tsdb_l2_ccfw 68 3345
INFO: tsdb_l2_rv_sci1 68 3345
INFO: tsdb_l2_rv_sci2 68 3345
INFO: tsdb_l2_rv_sci3 68 3345
INFO: tsdb_l2_rv_sci 68 3345
INFO: tsdb_l2_rv_cal 68 3345
INFO: tsdb_l2_rv_sky 68 3345
INFO: tsdb_l2_erv_sci 68 3345
INFO: tsdb_l2_erv_cal 68 3345
INFO: tsdb_l2_erv_sky 68 3345
INFO: Dates: 6 days from 20241001 to 20241006
INFO: Last update: 2025-12-18 22:32:42
The other ingestion methods (not shown) include ingesting based on the ObsIDs from a file (the method add_ObsID_list_to_db()) and using the commandline scripts KPF-Pipeline/scripts/ingest_dates_kpf_tsdb.py and KPF-Pipeline/scripts/ingest_watch_kpf_tsdb.py.
How the Database is Constructed
The time series database in built from the L0, 2D, L1, and L2 files associated with ObsIDs (e.g., KP.20241201.12345.67 is an ObsID for an observation on 12/01/2024). First, a set of “derived” keywords such as the full paths to the L0-L2 files are stored in the database. The rest of the infromation about an observation comes from reading the L0, 2D, L1, and L2 files. The keywords to be ingested are stored in a set of .csv files in KPF-Pipeline/static/tsdb_keywords/. A useful subset of
keywords from the primary headers of the L0, 2D, L1, and L2 files are ingested. Telemetry infromation is read from the TELEMETRY extension of L0 files and ingested. Keywords from the headers to the GREEN_CCF and RV extensions of L2 files are also ingested. Finally, the order-by-order RVs, CCF weights, and BJD times are read from the RV extension of L2 files and ingested. This full list of columns in the database, along with data types, units, descriptions, and notes about the sources of each
column can be read into a dataframe using the command df = myTS.metadata_table_to_df(). One can also print this database schema using the command myTS.print_metadata_table().
[7]:
df = myTS.db.metadata_table_to_df()
Database Querying and Display
The database can be queried to produce a dataframe for a certain set of data with other criteria applied. The docstring for this method and an example are shown below.
[8]:
help(myTS.db.dataframe_from_db)
Help on method dataframe_from_db in module database.modules.utils.tsdb:
dataframe_from_db(columns=None, start_date=None, end_date=None, only_object=None, only_source=None, object_like=None, on_sky=None, not_junk=None, qc_pass=None, qc_fail=None, qc_not_pass=None, qc_not_fail=None, extra_conditions=None, extra_conditions_logic='AND', verbose=False) method of database.modules.utils.tsdb.TSDB instance
Description:
Return a Pandas DataFrame containing specified columns from a
joined set of database tables, applying optional filters based on
object names, source types, date ranges, sky condition, and quality
checks.
Args:
columns (str or list of str, optional): Column name(s) to retrieve.
Defaults to None (fetches all columns).
start_date (str or datetime, optional): Starting date for filtering
observations (datetime object or YYYYMMDD or None). Defaults to
None.
end_date (str or datetime, optional): Ending date for filtering
observations (datetime object or YYYYMMDD or None). Defaults to
None.
only_object (str or list of str, optional): Exact object name(s) to
filter observations. Defaults to None.
E.g., only_object = ['autocal-dark', 'autocal-bias']
only_source (str or list of str, optional): Source type(s) to filter
observations. Defaults to None.
E.g., only_source = ['Dark', 'Bias']
object_like (str or list of str, optional): Partial object name(s)
for filtering observations using SQL LIKE conditions. Defaults
to None.
E.g., object_like = ['autocal-etalon', 'autocal-bias']
on_sky (bool, optional): Filter by on-sky (True) or calibration
(False) observations. Defaults to None.
qc_pass (str or list of str, optional): Column names where rows
must have True. Defaults to None.
qc_fail (str or list of str, optional): Column names where rows
must have False. Defaults to None.
qc_not_pass (str or list of str, optional): Column names where rows
are not True; allowable values are False and Null. A Null entry
can happen when an observation is ingested for which a QC test
has not been performed (e.g., because the QC was recently
developed). Defaults to None.
qc_not_fail (str or list of str, optional): Column names where rows
are not False; allowable values are True and Null. A Null entry
can happen when an observation is ingested for which a QC test
has not been performed (e.g., because the QC was recently
developed). Defaults to None.
not_junk (bool, optional): Filter by observations marked as not junk
(True) or junk (False). Defaults to None.
verbose (bool, optional): Enables detailed logging of SQL queries
and parameters. Defaults to False.
Returns:
The resulting dataframe.
[9]:
myTS = AnalyzeTimeSeries(db_path=db_path)
start_date = datetime(2024,10,1)
end_date = datetime(2024,10,6)
object_like = ['autocal-lfc-all-morn', 'autocal-lfc-all-eve']
columns_to_display = ['ObsID', 'OBJECT', 'DATE-MID', 'DRPTAGL1', 'DATAPRL0']
qc_not_fail = ['GOODREAD', 'FLXSTATS']
df = myTS.db.dataframe_from_db(object_like=object_like, columns=columns_to_display, start_date=start_date, end_date=end_date, qc_not_fail=qc_not_fail)
INFO: Starting AnalyzeTimeSeries
INFO: Starting KPF_TSDB
INFO: Jupyter Notebook environment detected.
INFO: Base data directory: /data/L0
INFO: Backend: sqlite
INFO: Table prefix: tsdb_
INFO: Path of database file: /code/KPF-Pipeline/docs/source/tutorials/kpf_ts.db
INFO: Metadata table exists.
INFO: Metadata table read.
INFO: Data tables exist.
The database can be displayed with a special method that includes links to the Jump webpage (or other websites if desired).
[10]:
myTS = AnalyzeTimeSeries(db_path=db_path)
start_date = datetime(2024,10,1)
end_date = datetime(2024,10,6)
object_like = ['autocal-lfc-all-morn', 'autocal-lfc-all-eve']
columns_to_display = ['ObsID', 'OBJECT', 'DATE-MID', 'DRPTAGL1', 'DATAPRL0']
qc_not_fail = ['GOODREAD', 'FLXSTATS']
myTS.db.display_data(object_like=object_like, columns=columns_to_display, start_date=start_date, end_date=end_date, qc_not_fail=qc_not_fail)
INFO: Starting AnalyzeTimeSeries
INFO: Starting KPF_TSDB
INFO: Jupyter Notebook environment detected.
INFO: Base data directory: /data/L0
INFO: Backend: sqlite
INFO: Table prefix: tsdb_
INFO: Path of database file: /code/KPF-Pipeline/docs/source/tutorials/kpf_ts.db
INFO: Metadata table exists.
INFO: Metadata table read.
INFO: Data tables exist.
| ObsID | OBJECT | DATE-MID | DRPTAGL1 | DATAPRL0 |
|---|---|---|---|---|
| KP.20241001.12022.36 | autocal-lfc-all-eve | 2024-10-01T03:20:52.370 | v2.11.1 | True |
| KP.20241001.12130.73 | autocal-lfc-all-eve | 2024-10-01T03:22:40.746 | v2.11.1 | True |
| KP.20241001.12239.12 | autocal-lfc-all-eve | 2024-10-01T03:24:29.129 | v2.11.1 | True |
| KP.20241001.12347.66 | autocal-lfc-all-eve | 2024-10-01T03:26:17.692 | v2.11.1 | True |
| KP.20241001.12456.17 | autocal-lfc-all-eve | 2024-10-01T03:28:06.179 | v2.11.1 | True |
| KP.20241001.12564.65 | autocal-lfc-all-eve | 2024-10-01T03:29:54.667 | v2.11.1 | True |
| KP.20241001.12673.01 | autocal-lfc-all-eve | 2024-10-01T03:31:43.048 | v2.11.1 | True |
| KP.20241001.12781.63 | autocal-lfc-all-eve | 2024-10-01T03:33:31.641 | v2.11.1 | True |
| KP.20241001.12889.98 | autocal-lfc-all-eve | 2024-10-01T03:35:20.018 | v2.11.1 | True |
| KP.20241001.12998.42 | autocal-lfc-all-eve | 2024-10-01T03:37:08.435 | v2.11.1 | True |
| KP.20241001.67440.59 | autocal-lfc-all-morn | 2024-10-01T18:44:30.601 | v2.11.1 | True |
| KP.20241001.67549.03 | autocal-lfc-all-morn | 2024-10-01T18:46:19.066 | v2.11.1 | True |
| KP.20241001.67657.43 | autocal-lfc-all-morn | 2024-10-01T18:48:07.447 | v2.11.1 | True |
| KP.20241001.67765.84 | autocal-lfc-all-morn | 2024-10-01T18:49:55.854 | v2.11.1 | True |
| KP.20241001.67874.24 | autocal-lfc-all-morn | 2024-10-01T18:51:44.284 | v2.11.1 | True |
| KP.20241001.67982.70 | autocal-lfc-all-morn | 2024-10-01T18:53:32.716 | v2.11.1 | True |
| KP.20241001.68091.05 | autocal-lfc-all-morn | 2024-10-01T18:55:21.088 | v2.11.1 | True |
| KP.20241001.68199.54 | autocal-lfc-all-morn | 2024-10-01T18:57:09.555 | v2.11.1 | True |
| KP.20241001.68308.29 | autocal-lfc-all-morn | 2024-10-01T18:58:58.303 | v2.11.1 | True |
| KP.20241001.68416.60 | autocal-lfc-all-morn | 2024-10-01T19:00:46.609 | v2.11.1 | True |
| KP.20241002.12025.87 | autocal-lfc-all-eve | 2024-10-02T03:20:55.881 | v2.11.1 | True |
| KP.20241002.12134.31 | autocal-lfc-all-eve | 2024-10-02T03:22:44.345 | v2.11.1 | True |
| KP.20241002.12242.68 | autocal-lfc-all-eve | 2024-10-02T03:24:32.694 | v2.11.1 | True |
| KP.20241002.12351.08 | autocal-lfc-all-eve | 2024-10-02T03:26:21.094 | v2.11.1 | True |
| KP.20241002.12459.58 | autocal-lfc-all-eve | 2024-10-02T03:28:09.612 | v2.11.1 | True |
| KP.20241002.12568.28 | autocal-lfc-all-eve | 2024-10-02T03:29:58.289 | v2.11.1 | True |
| KP.20241002.12676.72 | autocal-lfc-all-eve | 2024-10-02T03:31:46.733 | v2.11.1 | True |
| KP.20241002.12785.42 | autocal-lfc-all-eve | 2024-10-02T03:33:35.431 | v2.11.1 | True |
| KP.20241002.12894.03 | autocal-lfc-all-eve | 2024-10-02T03:35:24.074 | v2.11.1 | True |
| KP.20241002.13002.77 | autocal-lfc-all-eve | 2024-10-02T03:37:12.776 | v2.11.1 | True |
| KP.20241002.73814.41 | autocal-lfc-all-morn | 2024-10-02T20:30:44.420 | v2.11.1 | True |
| KP.20241002.73922.77 | autocal-lfc-all-morn | 2024-10-02T20:32:32.783 | v2.11.1 | True |
| KP.20241002.74031.20 | autocal-lfc-all-morn | 2024-10-02T20:34:21.207 | v2.11.1 | True |
| KP.20241002.74139.61 | autocal-lfc-all-morn | 2024-10-02T20:36:09.625 | v2.11.1 | True |
| KP.20241002.74247.96 | autocal-lfc-all-morn | 2024-10-02T20:37:57.969 | v2.11.1 | True |
| KP.20241002.74356.42 | autocal-lfc-all-morn | 2024-10-02T20:39:46.427 | v2.11.1 | True |
| KP.20241002.74465.12 | autocal-lfc-all-morn | 2024-10-02T20:41:35.130 | v2.11.1 | True |
| KP.20241002.74573.54 | autocal-lfc-all-morn | 2024-10-02T20:43:23.560 | v2.11.1 | True |
| KP.20241002.74681.89 | autocal-lfc-all-morn | 2024-10-02T20:45:11.902 | v2.11.1 | True |
| KP.20241002.74790.14 | autocal-lfc-all-morn | 2024-10-02T20:47:00.153 | v2.11.1 | True |
| KP.20241003.12026.87 | autocal-lfc-all-eve | 2024-10-03T03:20:56.875 | v2.11.1 | True |
| KP.20241003.12135.29 | autocal-lfc-all-eve | 2024-10-03T03:22:45.323 | v2.11.1 | True |
| KP.20241003.12243.94 | autocal-lfc-all-eve | 2024-10-03T03:24:33.945 | v2.11.1 | True |
| KP.20241003.12352.33 | autocal-lfc-all-eve | 2024-10-03T03:26:22.341 | v2.11.1 | True |
| KP.20241003.12460.78 | autocal-lfc-all-eve | 2024-10-03T03:28:10.791 | v2.11.1 | True |
| KP.20241003.12569.17 | autocal-lfc-all-eve | 2024-10-03T03:29:59.206 | v2.11.1 | True |
| KP.20241003.12677.54 | autocal-lfc-all-eve | 2024-10-03T03:31:47.550 | v2.11.1 | True |
| KP.20241003.12785.96 | autocal-lfc-all-eve | 2024-10-03T03:33:35.967 | v2.11.1 | True |
| KP.20241003.12894.35 | autocal-lfc-all-eve | 2024-10-03T03:35:24.364 | v2.11.1 | True |
| KP.20241003.13002.80 | autocal-lfc-all-eve | 2024-10-03T03:37:12.835 | v2.11.1 | True |
| KP.20241003.67446.46 | autocal-lfc-all-morn | 2024-10-03T18:44:36.469 | v2.11.1 | True |
| KP.20241003.67555.01 | autocal-lfc-all-morn | 2024-10-03T18:46:25.046 | v2.11.1 | True |
| KP.20241003.67663.61 | autocal-lfc-all-morn | 2024-10-03T18:48:13.618 | v2.11.1 | True |
| KP.20241003.67772.07 | autocal-lfc-all-morn | 2024-10-03T18:50:02.079 | v2.11.1 | True |
| KP.20241003.67880.39 | autocal-lfc-all-morn | 2024-10-03T18:51:50.400 | v2.11.1 | True |
| KP.20241003.67988.78 | autocal-lfc-all-morn | 2024-10-03T18:53:38.792 | v2.11.1 | True |
| KP.20241003.68097.19 | autocal-lfc-all-morn | 2024-10-03T18:55:27.199 | v2.11.1 | True |
| KP.20241003.68205.55 | autocal-lfc-all-morn | 2024-10-03T18:57:15.562 | v2.11.1 | True |
| KP.20241003.68313.96 | autocal-lfc-all-morn | 2024-10-03T18:59:03.970 | v2.11.1 | True |
| KP.20241003.68422.35 | autocal-lfc-all-morn | 2024-10-03T19:00:52.360 | v2.11.1 | True |
| KP.20241004.11972.20 | autocal-lfc-all-eve | 2024-10-04T03:20:02.209 | v2.11.1 | True |
| KP.20241004.12080.56 | autocal-lfc-all-eve | 2024-10-04T03:21:50.568 | v2.11.1 | True |
| KP.20241004.12188.95 | autocal-lfc-all-eve | 2024-10-04T03:23:38.957 | v2.11.1 | True |
| KP.20241004.12297.39 | autocal-lfc-all-eve | 2024-10-04T03:25:27.400 | v2.11.1 | True |
| KP.20241004.12405.85 | autocal-lfc-all-eve | 2024-10-04T03:27:15.857 | v2.11.1 | True |
| KP.20241004.12514.35 | autocal-lfc-all-eve | 2024-10-04T03:29:04.356 | v2.11.1 | True |
| KP.20241004.12622.91 | autocal-lfc-all-eve | 2024-10-04T03:30:52.920 | v2.11.1 | True |
| KP.20241004.12731.20 | autocal-lfc-all-eve | 2024-10-04T03:32:41.240 | v2.11.1 | True |
| KP.20241004.12839.91 | autocal-lfc-all-eve | 2024-10-04T03:34:29.917 | v2.11.1 | True |
| KP.20241004.12948.31 | autocal-lfc-all-eve | 2024-10-04T03:36:18.322 | v2.11.1 | True |
| KP.20241004.67505.95 | autocal-lfc-all-morn | 2024-10-04T18:45:35.956 | v2.11.1 | True |
| KP.20241004.67614.52 | autocal-lfc-all-morn | 2024-10-04T18:47:24.534 | v2.11.1 | True |
| KP.20241004.67723.08 | autocal-lfc-all-morn | 2024-10-04T18:49:13.093 | v2.11.1 | True |
| KP.20241004.67831.50 | autocal-lfc-all-morn | 2024-10-04T18:51:01.517 | v2.11.1 | True |
| KP.20241004.67939.88 | autocal-lfc-all-morn | 2024-10-04T18:52:49.898 | v2.11.1 | True |
| KP.20241004.68048.32 | autocal-lfc-all-morn | 2024-10-04T18:54:38.328 | v2.11.1 | True |
| KP.20241004.68156.87 | autocal-lfc-all-morn | 2024-10-04T18:56:26.880 | v2.11.1 | True |
| KP.20241004.68265.31 | autocal-lfc-all-morn | 2024-10-04T18:58:15.324 | v2.11.1 | True |
| KP.20241004.68373.75 | autocal-lfc-all-morn | 2024-10-04T19:00:03.762 | v2.11.1 | True |
| KP.20241004.68482.15 | autocal-lfc-all-morn | 2024-10-04T19:01:52.162 | v2.11.1 | True |
| KP.20241005.11964.18 | autocal-lfc-all-eve | 2024-10-05T03:19:54.193 | v2.11.1 | True |
| KP.20241005.12072.52 | autocal-lfc-all-eve | 2024-10-05T03:21:42.554 | v2.11.1 | True |
| KP.20241005.12180.98 | autocal-lfc-all-eve | 2024-10-05T03:23:30.997 | v2.11.1 | True |
| KP.20241005.12289.35 | autocal-lfc-all-eve | 2024-10-05T03:25:19.387 | v2.11.1 | True |
| KP.20241005.12398.04 | autocal-lfc-all-eve | 2024-10-05T03:27:08.079 | v2.11.1 | True |
| KP.20241005.12506.51 | autocal-lfc-all-eve | 2024-10-05T03:28:56.525 | v2.11.1 | True |
| KP.20241005.12614.88 | autocal-lfc-all-eve | 2024-10-05T03:30:44.891 | v2.11.1 | True |
| KP.20241005.12723.21 | autocal-lfc-all-eve | 2024-10-05T03:32:33.248 | v2.11.1 | True |
| KP.20241005.12831.67 | autocal-lfc-all-eve | 2024-10-05T03:34:21.676 | v2.11.1 | True |
| KP.20241005.12940.06 | autocal-lfc-all-eve | 2024-10-05T03:36:10.070 | v2.11.1 | True |
| KP.20241005.67440.79 | autocal-lfc-all-morn | 2024-10-05T18:44:30.804 | v2.11.1 | True |
| KP.20241005.67549.23 | autocal-lfc-all-morn | 2024-10-05T18:46:19.245 | v2.11.1 | True |
| KP.20241005.67657.62 | autocal-lfc-all-morn | 2024-10-05T18:48:07.635 | v2.11.1 | True |
| KP.20241005.67766.30 | autocal-lfc-all-morn | 2024-10-05T18:49:56.311 | v2.11.1 | True |
| KP.20241005.67874.69 | autocal-lfc-all-morn | 2024-10-05T18:51:44.705 | v2.11.1 | True |
| KP.20241005.67983.38 | autocal-lfc-all-morn | 2024-10-05T18:53:33.414 | v2.11.1 | True |
| KP.20241005.68092.04 | autocal-lfc-all-morn | 2024-10-05T18:55:22.071 | v2.11.1 | True |
| KP.20241005.68200.44 | autocal-lfc-all-morn | 2024-10-05T18:57:10.473 | v2.11.1 | True |
| KP.20241005.68308.81 | autocal-lfc-all-morn | 2024-10-05T18:58:58.836 | v2.11.1 | True |
| KP.20241005.68417.22 | autocal-lfc-all-morn | 2024-10-05T19:00:47.230 | v2.11.1 | True |
| KP.20241006.11966.70 | autocal-lfc-all-eve | 2024-10-06T03:19:56.712 | v2.11.1 | True |
| KP.20241006.12075.26 | autocal-lfc-all-eve | 2024-10-06T03:21:45.271 | v2.11.1 | True |
| KP.20241006.12183.70 | autocal-lfc-all-eve | 2024-10-06T03:23:33.713 | v2.11.1 | True |
| KP.20241006.12292.10 | autocal-lfc-all-eve | 2024-10-06T03:25:22.131 | v2.11.1 | True |
| KP.20241006.12400.47 | autocal-lfc-all-eve | 2024-10-06T03:27:10.479 | v2.11.1 | True |
| KP.20241006.12508.91 | autocal-lfc-all-eve | 2024-10-06T03:28:58.917 | v2.11.1 | True |
| KP.20241006.12617.40 | autocal-lfc-all-eve | 2024-10-06T03:30:47.416 | v2.11.1 | True |
| KP.20241006.12726.02 | autocal-lfc-all-eve | 2024-10-06T03:32:36.054 | v2.11.1 | True |
| KP.20241006.12834.53 | autocal-lfc-all-eve | 2024-10-06T03:34:24.538 | v2.11.1 | True |
| KP.20241006.12943.12 | autocal-lfc-all-eve | 2024-10-06T03:36:13.153 | v2.11.1 | True |
| KP.20241006.67444.26 | autocal-lfc-all-morn | 2024-10-06T18:44:34.300 | v2.11.1 | True |
| KP.20241006.67552.95 | autocal-lfc-all-morn | 2024-10-06T18:46:22.959 | v2.11.1 | True |
| KP.20241006.67661.66 | autocal-lfc-all-morn | 2024-10-06T18:48:11.666 | v2.11.1 | True |
| KP.20241006.67770.03 | autocal-lfc-all-morn | 2024-10-06T18:50:00.065 | v2.11.1 | True |
| KP.20241006.67878.74 | autocal-lfc-all-morn | 2024-10-06T18:51:48.750 | v2.11.1 | True |
| KP.20241006.67987.17 | autocal-lfc-all-morn | 2024-10-06T18:53:37.182 | v2.11.1 | True |
| KP.20241006.68095.90 | autocal-lfc-all-morn | 2024-10-06T18:55:25.915 | v2.11.1 | True |
| KP.20241006.68204.28 | autocal-lfc-all-morn | 2024-10-06T18:57:14.296 | v2.11.1 | True |
| KP.20241006.68312.66 | autocal-lfc-all-morn | 2024-10-06T18:59:02.667 | v2.11.1 | True |
| KP.20241006.68421.37 | autocal-lfc-all-morn | 2024-10-06T19:00:51.377 | v2.11.1 | True |
Or converted into a Pandas dataframe for manipulation or for making custom plots.
Plotting Dictionaries and YAML Files
The AnalyzeTimeSeries has a built-in plotting library that uses dictionaries to describe the elements of plots. An example is shown below. Note that start_date and end_date are formatted as datetime objects, not strings as above.
[11]:
start_date = datetime(2024, 10, 1)
end_date = datetime(2024, 10, 6)
dict1 = {'col': 'kpfmet.TEMP', 'plot_type': 'scatter', 'unit': 'K', 'plot_attr': {'label': 'Hallway', 'marker': '.', 'linewidth': 0.5}}
dict2 = {'col': 'kpfmet.GREEN_LN2_FLANGE', 'plot_type': 'scatter', 'unit': 'K', 'plot_attr': {'label': r'Green LN$_2$ Flng', 'marker': '.', 'linewidth': 0.5, 'color': 'darkgreen'}}
dict3 = {'col': 'kpfmet.RED_LN2_FLANGE', 'plot_type': 'scatter', 'unit': 'K', 'plot_attr': {'label': r'Red LN$_2$ Flng', 'marker': '.', 'linewidth': 0.5, 'color': 'darkred'}}
dict4 = {'col': 'kpfmet.CHAMBER_EXT_BOTTOM','plot_type': 'scatter', 'unit': 'K', 'plot_attr': {'label': r'Chamber Ext Bot', 'marker': '.', 'linewidth': 0.5}}
dict5 = {'col': 'kpfmet.CHAMBER_EXT_TOP', 'plot_type': 'plot', 'unit': 'K', 'plot_attr': {'label': r'Chamber Exterior Top', 'marker': '.', 'linewidth': 0.5}}
thispanelvars = [dict1]
thispaneldict = {'ylabel': 'Hallway\n' + r' Temperature ($^{\circ}$C)',
'legend_frac_size': 0.3}
halltemppanel = {'panelvars': thispanelvars,
'paneldict': thispaneldict}
thispanelvars2 = [dict2, dict3, dict4]
thispaneldict2 = {'ylabel': 'Exterior\n' + r' Temperatures ($^{\circ}$C)',
'legend_frac_size': 0.3}
halltemppanel2 = {'panelvars': thispanelvars2,
'paneldict': thispaneldict2}
thispanelvars3 = [dict2, dict3, dict4]
thispaneldict3 = {'ylabel': 'Exterior\n' + r'$\Delta$Temperature (K)',
'subtractmedian': 'true',
'legend_frac_size': 0.3}
halltemppanel3 = {'panelvars': thispanelvars3,
'paneldict': thispaneldict3}
panel_arr = [halltemppanel, halltemppanel2, halltemppanel3]
plotdict = {
"description": "Etalon RVs (autocal)",
"plot_type": "time_series_multipanel",
"panel_arr": panel_arr
}
myTS.plot_time_series_multipanel(plotdict, start_date=start_date, end_date=end_date, show_plot=True, clean=True)
The method plot_time_series_multipanel() above was written originally for use with dictionaries as shown above. However, it became easier to the plotting configuration in YAML files and convert to Python dictionaries when reading the configuration. An example of a configuration file is shown below.
[12]:
!cat /code/KPF-Pipeline/static/tsdb_plot_configs/QC/qc_lfc.yaml
description: QC - LFC Metrics
plot_type: time_series_multipanel
panel_arr:
- panelvars:
- col: LFCSAT
plot_type: state
plot_attr:
label: LFC Not Saturated
marker: .
paneldict:
ylabel: "LFC Not Saturated\n(LFCSAT)"
legend_frac_size: 0.15
only_object:
- autocal-lfc-all-morn
- autocal-lfc-all-eve
- autocal-lfc-all-night
- cal-LFC
- cal-LFC-morn
- cal-LFC-eve
- LFC_all
- lfc_all
- LFC
not_junk: true
qc_not_fail: 'GOODREAD, FLXSTATS, DATAPRL0, KWRDPRL0, TIMCHKL0'
- panelvars:
- col: LFC2DFOK
plot_type: state
plot_attr:
label: "2D LFC Flux Meets\nThreshold of 4000 Counts"
marker: .
paneldict:
ylabel: "2D LFC Flux Meets Threshold\nof 4000 Counts\n(LFC2DFOK)"
legend_frac_size: 0.15
only_object:
- autocal-lfc-all-morn
- autocal-lfc-all-eve
- autocal-lfc-all-night
- cal-LFC
- cal-LFC-morn
- cal-LFC-eve
- LFC_all
- lfc_all
- LFC
not_junk: true
qc_not_fail: 'GOODREAD, FLXSTATS, DATAPRL0, KWRDPRL0, TIMCHKL0'
- panelvars:
- col: LFCLINEP
plot_type: state
plot_attr:
label: "Number and dist of\nLFC lines sufficient\n(SCI orders 15-34, 1-31)"
marker: .
paneldict:
ylabel: "Number and dist of\nLFC lines sufficient\n(SCI orders 15-34, 1-31)\n(LFCLINEP)"
legend_frac_size: 0.15
only_object:
- autocal-lfc-all-morn
- autocal-lfc-all-eve
- autocal-lfc-all-night
- cal-LFC
- cal-LFC-morn
- cal-LFC-eve
- LFC_all
- lfc_all
- LFC
not_junk: true
qc_not_fail: 'GOODREAD, FLXSTATS, DATAPRL0, KWRDPRL0, TIMCHKL0'
- panelvars:
- col: LFCLINES
plot_type: state
plot_attr:
label: "Number and dist of\nLFC lines sufficient\n(SCI orders 2-34, 1-31)"
marker: .
paneldict:
ylabel: "Number and dist of\nLFC lines sufficient\n(SCI orders 2-34, 1-31)\n(LFCLINES)"
title: QC - LFC Metrics
legend_frac_size: 0.15
only_object:
- autocal-lfc-all-morn
- autocal-lfc-all-eve
- autocal-lfc-all-night
- cal-LFC
- cal-LFC-morn
- cal-LFC-eve
- LFC_all
- lfc_all
- LFC
not_junk: true
qc_not_fail: 'GOODREAD, FLXSTATS, DATAPRL0, KWRDPRL0, TIMCHKL0'
This simple example is equivalent to the dictionary plotdict below.
[13]:
dict1 = {'col': 'MONOTWLS',
'plot_type': 'state',
'plot_attr': {'label':'Montonic WLS','marker': '.'}}
thispanelvars = [dict1]
thispaneldict = {'ylabel': 'Montonic WLS',
'title': 'QC - Monotonic WLS in L1',
'legend_frac_size': 0.10}
lfcpanel = {'panelvars': thispanelvars,
'paneldict': thispaneldict}
panel_arr = [lfcpanel]
mydict = {
"description": "QC - Monotonic WLS in L1",
"plot_type": "time_series_multipanel",
"panel_arr": panel_arr
}
[14]:
myyaml = '''description: QC - Monotonic WLS in L1
plot_type: time_series_multipanel
panel_arr:
- panelvars:
- col: MONOTWLS
plot_type: state
plot_attr:
label: Montonic WLS
marker: .
paneldict:
ylabel: Monotonic WLS
title: QC - Monotonic WLS in L1
legend_frac_size: 0.10
'''
Below are plots of the dictionary and yaml representations.
[15]:
# Dictionary version
myTS.plot_time_series_multipanel(mydict, start_date=start_date, end_date=end_date, show_plot=True, clean=True)
# YAML version
myyaml_converted = myTS.yaml_to_dict(myyaml)
myTS.plot_time_series_multipanel(myyaml_converted, start_date=start_date, end_date=end_date, show_plot=True, clean=True)
Plotting Telemetry
Examples of two built-in standard telemetry plots are shown below.
[16]:
myTS.plot_time_series_multipanel('files_missing', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/DRP/files_missing.yaml
[17]:
myTS.plot_time_series_multipanel('ccd_temp', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/CCDs/ccd_temp.yaml
The examples above are all plots of float-type variables (e.g., temperatures) over time. The two below sho examples of state variables changing over time (the DRP version number used to process the data and the result of a quality control test).
[18]:
myTS.plot_time_series_multipanel('drptag', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/DRP/drptag.yaml
[19]:
myTS.plot_time_series_multipanel('qc_monotonic_wls', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/QC/qc_monotonic_wls.yaml
Plotting RVs
An example of plotting RVs (instead of telemetry) is shown below.
[20]:
myTS.plot_time_series_multipanel('autocal_etalon_rv', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/RV/autocal_etalon_rv.yaml
Here’s an example of plotting SoCal RV and spectral SNR time series.
[21]:
myTS.plot_time_series_multipanel('socal_rv', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
myTS.plot_time_series_multipanel('socal_snr', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/RV/socal_rv.yaml
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/SoCal/socal_snr.yaml
One can also plot information about on-sky conditions.
[22]:
myTS.plot_time_series_multipanel('seeing', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
myTS.plot_time_series_multipanel('sun_moon', start_date=start_date, end_date=end_date, show_plot=True, clean=True)
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/Observing/seeing.yaml
INFO: Plotting from config: /code/KPF-Pipeline/static/tsdb_plot_configs/Observing/sun_moon.yaml
Here’s the docstring describing the full set of options for AnalyzeTimeseries.plot_time_series_multipanel.
[23]:
myTS.plot_time_series_multipanel?
Signature:
myTS.plot_time_series_multipanel(
plotdict,
start_date=None,
end_date=None,
hatch_service_missions=True,
clean=False,
fig_path=None,
show_plot=False,
log_savefig_timing=False,
)
Docstring:
Generate a multi-panel time series plot from a KPF TSDB. Each subplot is configured
via a dict (or YAML file path), enabling control over filters, transforms, and style.
Parameters
----------
plotdict : str or dict
Path to a named YAML config or a dict with key 'panel_arr' (list of panel dicts).
start_date, end_date : datetime, optional
Query window (UT). Defaults if None: start=2020-01-01, end=2040-01-01. The code
may tighten to the data’s min/max timestamps.
hatch_service_missions : bool, default=True
Overlay hatched spans from self.get_service_mission_df() (UT_start_date, UT_end_date).
clean : bool, default=False
Apply self.db.clean_df() to remove outliers.
fig_path : str, optional
Full output path (PNG).
show_plot : bool, default=False
Show the figure interactively.
log_savefig_timing : bool, default=False
Log CPU time for savefig().
Plot Configuration (via panel_dict or YAML)
-------------------------------------------
plotdict['panel_arr'] : list[dict]
Each element defines one panel and includes:
- 'paneldict' : dict # panel-level behavior/filters
- 'only_object' : str | list[str] # exact OBJECT names
- 'object_like' : str | list[str] # LIKE patterns (nested lists ok)
- 'only_source' : str # passed to DB filter layer
- 'not_junk' : bool | {'true','false'} # filter on NOTJUNK
- 'qc_pass' : str | list[str] # columns that must be True
- 'qc_fail' : str | list[str] # columns that must be False
- 'qc_not_pass' : str | list[str] # columns that are not True (False/NaN)
- 'qc_not_fail' : str | list[str] # columns that are not False (True/NaN)
- 'on_sky' : bool | {'true','false'} # True→FIUMODE=='Observing', False→'Calibration'
- 'ylabel' : str # label for vertical axis
- 'ylim' : tuple | str # (ymin, ymax) or a string that evals to that
- 'ymin', 'ymax' : float # override parts of ylim
- 'yscale' : str # e.g., 'log'
- 'subtractmedian' : bool # subtract per-variable median before plotting
- 'nolegend' : bool # suppresses legend
- 'labelrms' : bool # add legend text like ""(0.001 C rms)"
- 'legend_frac_size' : float # legend anchor offset
- 'axhspan' : dict # {key: {'ymin','ymax','color','alpha'}}
- 'title' : str # title for a set of panels
- 'narrow_xlim_daily' : bool # shrink x-limits to data for day-scale plots
- 'panelvars' : list[dict] # variables drawn in this panel
- 'col' : str # main data column
- 'col_err' : str # symmetric error column (optional)
- 'col_subtract' : str # subtract this column from 'col'
- 'col_multiply' : float # scalar multiplier
- 'col_offset' : float # scalar offset
- 'normalize' : bool # divide by median after transforms
- 'plot_type' : { # determine plot type
'scatter', # scatter plot (default)
'errorbar', # errorbar plot; must include 'col_err'
'plot', # line plot
'step', # step plot
'state', # state value plot with distinct values, usually strings or booleans
'vlines' # plot with vertical lines; must include 'col_min' and 'col_max'
}
- 'plot_attr' : dict # matplotlib kwargs (marker, label, etc.)
- 'unit' : str # used when augmenting legend label with RMS
- 'col_min','col_max' : str # required for plot_type='vlines'
- 'vline_pt_color' : str # optional color for vline end points
Returns
-------
None
Saves to fig_path (if given), optionally shows, and logs as configured.
Notes
-----
- Time axis adapts to span:
* ~1 day: hours since start (UT/HST labels possible), optional “Night” shading
* <3 days or <32 days: days since start
* 28–31 days: month view (day numbers)
* ~1 year: month tick marks with MM-DD labels
* longer: calendar dates (YYYY-MM-DD)
- 'state' plots render categorical levels; {0,1,None}→{Fail,Pass,None}. If ylabel=='Junk Status',
{Pass,Fail}→{Not Junk,Junk}.
- Empty selections are annotated “No Data”.
- Labels may be augmented with “(X unit rms)” when legend shown and enough points exist.
- Data come from self.db.dataframe_from_db(...); DATE-MID parsed and sorted; clean_df() optional.
File: /code/KPF-Pipeline/modules/quicklook/src/analyze_time_series.py
Type: method
Making Histograms of the Number Observations Over Time
Make a plot of the number of observations for the whole time span that’s been ingested.
[24]:
myTS.plot_nobs_histogram(interval='year', date='20241002', show_plot=True, plot_source=True)
Show the observations by type for the that month and one day.
[25]:
myTS.plot_nobs_histogram(interval='month', date='20241002', plot_source=True, show_plot=True)
[26]:
myTS.plot_nobs_histogram(interval='day', date='20241002', plot_source=True, show_plot=True)
Show the number of observations of just one source over a month.
[27]:
myTS.plot_nobs_histogram(interval='month', date='20241002', plot_source=True, show_plot=True, only_sources=['Flat'])
Show the number of stell observations per UT night.
[28]:
myTS.plot_nobs_histogram(interval='month', date='20241002', plot_source=True, show_plot=True, only_sources=['Star'])
The Full Set of Standard Plots
There are also a number of standard plots based on YAML files in subdirectories of KPF-Pipeline/static/tsdb_plot_configs/. The full set is listed below.
[29]:
myTS.plot_all_quicklook(print_plot_names=True)
Plots available:
'ccd_controller': CCD Controller Temperatures
'ccd_dark_current': CCD Dark Current
'ccd_readnoise': CCD Read Noise
'ccd_readspeed': CCD Read Speed
'ccd_temp': CCD Temperatures
'ccd_noise_stats': CCD Read Noise Statistics
'xdisp_offset': CCD Cross Dispersion Offsets
'ccd_pressure': CCD Pressures
'saturated_etalon': Saturated Lines - Etalon
'saturated_thar': Saturated Lines - ThAr
'autocal-flat_flux_relative': autocal-flat-all Relative Flux Ratio
'autocal-flat_snr': autocal-flat-all SNR & Flux Ratio
'autocal-flat_snr_relative': autocal-flat-all Relative SNR Ratio
'good_orders_etalon': Good Orders - Etalon
'good_orders_lfc': Good Orders - LFC
'hcl': Hollow-Cathode Lamp Temperatures
'lamp_power': Power Meter Measurements of Lamp Brightness
'last_good_cal': Last Good LFC and Etalon Calibrations
'saturated_lfc': Saturated Lines - LFC
'lfc_freq': LFC Diagnostics
'autocal-etalon_snr': autocal-etalon and slewcal SNR
'lfc': LFC Diagnostics
'autocal-etalon_flux_ratio': autocal-etalon Flux Ratios
'saturated_une': Saturated Lines - Une
'chamber_temp': KPF Spectrometer Temperatures
'chamber_temp_detail': Chamber Temperature Detail
'hallway_temp': KPF Hallway Temperature
'spatial_gradients': KPF Spectrometer Spatial Temperature Gradients
'drphash': KPF-Pipeline Commit Hash
'drptag': KPF-Pipeline Version Number
'files_missing': 2D/L1/L2 Files Missing
'master_age': Ages of Master Files
'nobs_all_sources': All Sources - Number of Observations
'nobs_bias': Bias autocal - Number of Observations
'nobs_dark': Dark autocal - Number of Observations
'nobs_flat': Flat autocal - Number of Observations
'nobs_lfc': LFC autocal - Number of Observations
'nobs_sun': SoCal - Number of Observations
'nobs_all_good_sources': All Sources - Number of Observations
'nobs_star': Stars - Number of Observations
'bcvel': Barycentric Variations
'guider_images': Guider Images
'guiding': Guiding Errors & Bias
'observing_snr': Observing SNR & Flux Ratio for Stars
'seeing': Seeing
'sun_moon': Separation of Sun and Moon from Target
'junk_status': Junk Status and Smeared Readout Assessment
'qc_agitator': QC - Agitator Running
'qc_cals': QC - Flat SNR
'qc_ccd_temp': QC - CCD Temperature Set Points
'qc_data_kwds': QC - Data and Keywords Present
'qc_em': QC - Exposure Meter
'qc_etalon': QC - Etalon Metrics
'qc_flat': QC - Flat Metrics
'qc_guider': QC - Guider Performance
'qc_hk': QC - CaHK Shutter
'qc_kwds': QC - TARG Keywords
'qc_lfc': QC - LFC Metrics
'qc_low_flux': QC - Low Dark and Bias Flux
'qc_master_age': QC - Master File Ages
'qc_monotonic_wls': QC - Monotonic WLS in L1
'qc_ntp': QC - Network Time Protocol (NTP)
'qc_observing': QC - Observing
'qc_pos_2d_snr': QC - Not Negative 2D SNR
'qc_time_check': QC - L0 and L2 Times Consistent
'qc_wls': QC - Wavelength Solution Metrics
'autocal_etalon_rv': Etalon RVs (autocal)
'autocal_rv': LFC, ThAr, & Etalon RVs (autocal)
'socal_rv': SoCal RVs
'autocal_erv': LFC, ThAr, & Etalon ERVs (autocal)
'clearsky': Seeing
'socal_snr': SoCal SNR & Flux Ratio
'wls_median': WLS Median Difference
'wls_stdev': WLS Standard Deviation of (L1 - L1_ref)
'agitator': KPF Agitator
'fiber_temp': Fiber Temperatures
'hk_temp': Ca H&K Spectrometer Temperatures
'etalon': Etalon Temperatures
Generating All Standard Plots
One can also generate all plots from the plot_all_quicklook_daterange() method with a single call. It is in an if statement below so that be disabled because it generates a large number of plots (a few dozen) that may be more than are desired. Toggle if False: to if True: to show the output.
[30]:
if False:
myTS = AnalyzeTimeSeries(db_path=db_path)
myTS.plot_all_quicklook(datetime(2024, 10, 3), interval='day', show_plot=True, verbose=True)