Thursday, July 9, 2026

Crude oil shares at Cushing, Oklahoma


A really brief publish at present. Throughout the world gas disaster referring to the battle in Iran, I’ve been monitoring this chart, each Thursday morning my time:

It exhibits the quantity of crude oil within the Cushing facility in Oklahoma and is among the most well timed and steadily updating (each Wednesday) indicators of the general well being of the crude oil market within the USA. Because the chart says, under 20 million barrels is extensively cited as problematic, “tank backside”, or the “operational flooring”. Beneath this stage is predicted to trigger dangers to grease high quality, to the flexibility of infrastructure to maneuver oil round, and to service the commodities markets that depend on this facility for precise supply.

We’ve been below 20 million for a number of weeks now and but the oil markets within the USA haven’t blown up or floor to a halt (select your metaphor), so clearly there’s a little bit of slack constructed into that “minimal”. Maybe the true minimal is eighteen million, 17 million, who is aware of? However it could’t be far under the present stage and that is clearly value monitoring.

There’s in fact an internet web page the place you possibly can verify the info immediately, however naturally I needed to attract my very own polished chart and label it appropriately. The code under runs a whole pipeline to obtain the info, course of it (together with getting ready some sensible uncluttered computerized labelling of factors) and drawing the plot.

library(tidyverse)
library(scales)
library(readxl)
library(ggrepel)
library(glue)

# Obtain knowledge
obtain.file("https://www.eia.gov/dnav/pet/hist_xls/W_EPC0_SAX_YCUOK_MBBLw.xls", 
              mode = "wb", destfile = "cushing.xls")

# Import and course of knowledge
cushing <- read_excel("cushing.xls", sheet = "Knowledge 1", skip = 2) |> 
      rename(worth = `Weekly Cushing, OK Ending Shares excluding SPR of Crude Oil  (Thousand Barrels)`,
             end_date = Date) |> 
      # we wish a label for a degree solely whether it is not less than 500 completely different from
      # the following level (that is to keep away from litter when the road is
      # principally horizontal)
      mutate(label = ifelse(is.na(lead(worth)) | 
                            abs(worth - lead(worth)) > 500, 
                            comma(worth), ""),
      # We additionally need the label to vanish if the worth is basically near
      # 20,000, which goes to be a clearly labelled line anyway so would
      # simply be pointless litter.
             label = ifelse(abs(worth - 20000) < 200, "", label))

# Draw chart
cushing |> 
    filter(end_date > as.Date("2025-12-31")) |>
    # authentic knowledge was in 1000's nevertheless it's higher to have it in millioms
    # visually:
    ggplot(aes(x = end_date, y = worth / 1000)) +
    geom_hline(yintercept = 20, color = "darkred") +
    geom_line(color = "steelblue") +
    geom_point(color = "steelblue") +
    geom_text(knowledge = filter(cushing, end_date > as.Date("2026-05-01")), 
              aes(label = label, x = end_date + 150000), 
              dimension = 2.8, hjust = 0) +
    annotate("textual content", x = as.Date("2026-03-02"), y = 20.500, 
             label = "Broadly cited minimal working stage - 20 million barrels", 
             color = "darkred") +
    scale_x_date(date_breaks = "1 month", date_labels = "%b") + 
    scale_y_continuous(label = comma) +
    theme(panel.grid.minor = element_blank()) +
    labs(x = "Month (2026)",
         y = "Million barrels",
         title = "Shares of crude oil at Cushing, Oklahoma",
         subtitle = "Cushing is the principle US crude oil storage and pipeline hub, and the supply level for the West Texas Middleman (WTI) oil benchmark.",
         caption = glue("Supply: US Power Info Administration (EIA) https://www.eia.gov/dnav/pet/hist/LeafHandler.ashx?n=PET&s=W_EPC0_SAX_YCUOK_MBBL&f=W. Accessed {Sys.Date()}."))



Related Articles

Latest Articles