Flare List Demo#

How to search, combine and explore STIX L3 flare list products.

This example uses STIXClient (a Fido client) to find three months of L3 flare list files, loads each one as a FlareList product, concatenates them into a single catalogue, plots the peak count time series, then filters for X-class flares close to the Earth-facing solar limb and plots their locations.

Imports

import matplotlib.pyplot as plt
import numpy as np

from sunpy.net import attrs as a

from stixpy.net.client import STIXClient
from stixpy.product import Product

Search three months of flare list data.

The flare list test products are currently hosted on a separate URL from the rest of the STIX archive, so we instantiate STIXClient with that source.

client = STIXClient(source="https://pub099.cs.technik.fhnw.ch/testing/p311_comp_test")

results = client.search(
    a.Time("2024-09-01T01:00:00", "2024-11-30T23:59"),
    a.Instrument.stix,
    a.stix.DataType.flarelist,
)
print(results)
       Start Time               End Time        Instrument Level  DataType   DataProduct    Ver Request ID
----------------------- ----------------------- ---------- ----- --------- ---------------- --- ----------
2024-09-01T00:00:00.000 2024-10-01T00:47:10.000       STIX    L3 FLARELIST flarelist-sdcloc V02          -
2024-10-01T00:00:00.000 2024-11-01T00:05:46.000       STIX    L3 FLARELIST flarelist-sdcloc V02          -
2024-11-01T00:00:00.000 2024-11-30T23:48:24.000       STIX    L3 FLARELIST flarelist-sdcloc V02          -

Download the matching files and load each one as a FlareList product

paths = client.fetch(results)
products = [Product(p) for p in paths]
Files Downloaded:   0%|          | 0/3 [00:00<?, ?file/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:   0%|          | 0.00/1.22M [00:00<?, ?B/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:   0%|          | 0.00/1.44M [00:00<?, ?B/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:   0%|          | 0.00/1.35M [00:00<?, ?B/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:   0%|          | 1.02k/1.44M [00:00<02:44, 8.72kB/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:   0%|          | 1.02k/1.22M [00:00<02:22, 8.54kB/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:   0%|          | 1.02k/1.35M [00:00<02:35, 8.70kB/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:   1%|          | 8.94k/1.22M [00:00<00:26, 44.9kB/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:   1%|          | 8.94k/1.44M [00:00<00:31, 44.9kB/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:   1%|          | 8.94k/1.35M [00:00<00:30, 44.4kB/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:   3%|▎         | 40.9k/1.22M [00:00<00:07, 160kB/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:   3%|▎         | 40.9k/1.44M [00:00<00:08, 157kB/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:   3%|▎         | 40.9k/1.35M [00:00<00:08, 160kB/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:  11%|█         | 129k/1.22M [00:00<00:02, 420kB/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:   9%|▉         | 129k/1.44M [00:00<00:03, 419kB/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:  10%|▉         | 129k/1.35M [00:00<00:02, 420kB/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:  26%|██▌       | 313k/1.22M [00:00<00:01, 885kB/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:  23%|██▎       | 337k/1.44M [00:00<00:01, 962kB/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:  25%|██▍       | 337k/1.35M [00:00<00:01, 963kB/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:  52%|█████▏    | 629k/1.22M [00:00<00:00, 1.58MB/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:  47%|████▋     | 672k/1.44M [00:00<00:00, 1.69MB/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:  48%|████▊     | 655k/1.35M [00:00<00:00, 1.64MB/s]



solo_L3_stix-flarelist-sdcloc_20241101T000000-20241130T234824_V02.fits:  87%|████████▋ | 1.06M/1.22M [00:00<00:00, 2.37MB/s]


solo_L3_stix-flarelist-sdcloc_20241001T000000-20241101T000546_V02.fits:  77%|███████▋  | 1.11M/1.44M [00:00<00:00, 2.47MB/s]

solo_L3_stix-flarelist-sdcloc_20240901T000000-20241001T004710_V02.fits:  79%|███████▉  | 1.07M/1.35M [00:00<00:00, 2.36MB/s]




Files Downloaded:  33%|███▎      | 1/3 [00:01<00:02,  1.14s/file]





Files Downloaded: 100%|██████████| 3/3 [00:01<00:00,  2.61file/s]

Concatenate the monthly products into a single FlareList covering Sep–Nov 2024

flares = products[0].concatenate(products[1:])
print(flares)
FlareList
       <sunpy.time.timerange.TimeRange object at 0x7125fd895c40>
    Start: 2024-09-01 00:06:44
    End:   2024-11-30 23:48:24
    Center:2024-10-16 11:57:34
    Duration:90.98726238425925 days or
           2183.6942972222223 hours or
           131021.65783333333 minutes or
           7861299.47 seconds

    7025 flares

Inspect the available columns. flares.data is an QTable — each column carries its own unit and a short description loaded from the FITS header.

print(f"{'Column':<26s}  {'Unit':<10s}  Description")
print("-" * 90)
for name in flares.data.colnames:
    info = flares.data[name].info
    unit = "" if info.unit is None else str(info.unit)
    desc = info.description or ""
    print(f"{name:<26s}  {unit:<10s}  {desc}")
Column                      Unit        Description
------------------------------------------------------------------------------------------
flare_id                                unique flare id for flarelist SDCFlareListManager
start_UTC                               start time of flare
duration                    s           duration of flare
end_UTC                                 end time of flare
peak_UTC                                flare peak time
att_in                                  was attenuator in during flare
bkg_baseline                ct          background baseline at 4-10 keV
GOES_class                              GOES class of the GOES XRS data at time of flare - not derived from STIX data.  Do not use when flare isn't visible to Earth
goes_min_class_est                      min GOES class estimate derived from STIX data
goes_max_class_est                      max GOES class estimate derived from STIX data
goes_mean_class_est                     mean GOES class estimate derived from STIX data
GOES_flux                   W / m2      GOES flux of the GOES XRS data at time of flare- not derived from STIX data. Do not use when the flare isn't visible to Earth
goes_min_flux_est           W / m2      min GOES flux estimate derived from STIX data
goes_max_flux_est           W / m2      max GOES flux estimate derived from STIX data
goes_mean_flux_est          W / m2      mean GOES flux estimate derived from STIX data
lc_peak                     ct          counts in 4s peak window from quicklook lightcurve
lc_bgk_peak                 ct          background counts in 4s peak windowfrom quicklook lightcurve
energy_index                            energy band index
soop_encoded_type                       campaign ID
soop_id                                 SOOP ID
soop_type                               name of the SOOP campaign
anc_ephemeris_path                      Path to the daily ancillary ephemeris file
cpd_path                                Path to the CPD file used for flare location estimation
_position_status                        Status of the flare position calculation
_position_message                       Message describing the status of the flare position calculation
location_icrs               deg,deg,km  Flare location in ICRS coordinates at 'location_time_UTC'
solo_location_icrs          deg,deg,km  Solar Orbiter location in ICRS coordinates at 'location_time_UTC'
sidelobes_ratio                         Ratio of sidelobes in the STIX image used to assess imaging quality
rcr_at_peak                             max rcr level at flare location estimation time range, > 0 attenuator in place
visible_from_earth                      Whether the flare location is visible from Earth (not occulted by the Sun)
location_time_UTC                       time center used for flare location estimation in UTC
location_duration           s           duration of the flare location estimation time range
time_shift                  s           Time(Sun to Earth) - Time(Sun to S/C)
sun_disc_size               arcsec      Apparent photospheric solar radius
location_hgs                deg,deg,km  Flare location in Heliographic Stonyhurst coordinates at 'location_time_UTC'
solo_location_hgs           deg,deg,km  Solar Orbiter location in Heliographic Stonyhurst coordinates at 'location_time_UTC'

Plot the timeline of peak counts per energy band across all three months

flares.plot_timeseries()
plt.title(f"STIX peak counts — {len(flares)} flares (Sep–Nov 2024)")
plt.tight_layout()
STIX peak counts — 7025 flares (Sep–Nov 2024)

Filter the catalogue for M- and X-class flares close to the Earth-facing limb.

Seen from Earth the solar limb maps to HGS longitude ±90°. We keep flares whose absolute HGS longitude exceeds 70° and whose GOES classification starts with "M" or "X".

lon = flares.flare_location_hgs.lon.deg
is_strong = np.array([str(g).strip().upper().startswith(("M", "X")) for g in flares.goes_class])
near_limb = np.isfinite(lon) & (np.abs(lon) > 70)
mask = is_strong & near_limb
print(f"Selected {mask.sum()} M/X-class limb flares of {len(flares)} total.")
Selected 185 M/X-class limb flares of 7025 total.

A boolean mask can be applied directly to the FlareList; the result is a new FlareList with the matching rows. Plot the filtered locations from Earth’s point of view.

filtered = flares[mask]
print(filtered)

filtered.plot_timeseries()
plt.title(f"Peak counts — {len(filtered)} M/X-class limb flares")
plt.tight_layout()

filtered.plot_locations(observer="earth")
plt.tight_layout()
  • Peak counts — 185 M/X-class limb flares
  • Flare locations (n=185) — earth
FlareList
       <sunpy.time.timerange.TimeRange object at 0x7125fd760f80>
    Start: 2024-09-01 07:56:24
    End:   2024-11-25 17:22:01
    Center:2024-10-14 00:39:13
    Duration:85.39278921296297 days or
           2049.4269411111113 hours or
           122965.61646666667 minutes or
           7377936.988 seconds

    185 flares

Masking is non-destructive: flares is the full catalogue, so we can apply a completely independent filter to the same object — here, strong flares within ±30° of disk centre as seen from Earth.

near_disk = np.isfinite(lon) & (np.abs(lon) < 30)
disk_flares = flares[is_strong & near_disk]
print(f"Selected {len(disk_flares)} M/X-class on-disk flares of {len(flares)} total.")

disk_flares.plot_timeseries()
plt.title(f"Peak counts — {len(disk_flares)} M/X-class on-disk flares")
plt.tight_layout()

disk_flares.plot_locations(observer="earth")
plt.tight_layout()
  • Peak counts — 77 M/X-class on-disk flares
  • Flare locations (n=77) — earth
Selected 77 M/X-class on-disk flares of 7025 total.

Plotting a catalogue that spans many weeks onto a single Earth-view Sun disc is misleading: solar rotation moves features ~13°/day, so a persistent active region smears into a horizontal streak across the disc and individual flares are no longer comparable in position.

A rotation-fixed view solves this. observer="carrington" plots heliographic Carrington longitude (0–360°) vs latitude — the Carrington prime meridian rotates with the Sun, so an active region keeps the same longitude across many days. Each flare’s own Solar Orbiter position is used as the HGC observer, matching how STIX actually saw the event.

flares.plot_locations(observer="carrington")
plt.title(f"Carrington view — {len(flares)} flares (Sep–Nov 2024)")
plt.tight_layout()
plt.show()
Carrington view — 7025 flares (Sep–Nov 2024)

Total running time of the script: (3 minutes 40.258 seconds)

Gallery generated by Sphinx-Gallery