ECCU’s High-Income Paradox: Wealth Doesn’t Always Mean Resilience
Author
Martina
Photo: Wikipedia
Introduction
The World Bank creates a yearly income classification for all countries with a population of over 30,000. This classification divides countries into four income groups: low, lower-middle, upper-middle, and high income. These groups are based on Gross National Income (GNI) per capita, measured in US dollars. The classification is used for analytical purposes and to determine eligibility for World Bank loans and other support programs. This classification stays the same throughout the fiscal year (from July 1 to June 30).
According to Table 1, income group definitions fall into the following categories for 2024 Fiscal Year:
Low-income countries: GNI per capita of $1,145 or less.
Lower-middle-income countries: GNI per capita between $1,146 and $4,515.
Upper-middle-income countries: GNI per capita between $4,516 and $14,005.
High-income countries: GNI per capita of $14,006 or more.
Code
library(gt)library(dplyr)library(tidyverse)# Create the data frameincome_thresholds<-tibble::tibble( ` ` =c("July 1, 2024 - for FY25 (new)", "July 1, 2023 - for FY24 (previous)"), `Low Income` =c("≤ 1,145", "≤ 1,135"), `Lower-middle Income` =c("1,146 - 4,515", "1,136 - 4,465"), `Upper-middle Income` =c("4,516 - 14,005", "4,466 - 13,845"), `High Income` =c("> 14,005", "> 13,845"))# Create the gt tableincome_thresholds_table<-income_thresholds%>%gt()%>%# Add a title (optional)# tab_header(# title = "World Bank Income Classifications (Gross National Income per capita, US$)"# ) %>%# Style the headercols_align("center")%>%cols_width(` `~px(200),everything()~px(150))%>%# Add color to the cellstab_style( style =cell_fill(color ="aliceblue"), # Light blue locations =cells_body( columns =`Low Income`))%>%tab_style( style =cell_fill(color ="skyblue"), # Plum locations =cells_body( columns =`Lower-middle Income`))%>%tab_style( style =cell_fill(color ="#90EE90"), # Light green locations =cells_body( columns =`Upper-middle Income`))%>%tab_style( style =cell_fill(color ="#3CB371"), # Medium sea green locations =cells_body( columns =`High Income`))%>%# Add a source note (optional)# tab_source_note(# source_note = "Source: World Bank"# )opt_table_font( font ="Arial")income_thresholds_table
Table 1: Classification
Low Income
Lower-middle Income
Upper-middle Income
High Income
July 1, 2024 - for FY25 (new)
≤ 1,145
1,146 - 4,515
4,516 - 14,005
> 14,005
July 1, 2023 - for FY24 (previous)
≤ 1,135
1,136 - 4,465
4,466 - 13,845
> 13,845
Methodology
According to the World Bank, to keep income classification thresholds fixed in real terms, they are adjusted annually for inflation using the Special Drawing Rights (SDR) deflator, a weighted average of the GDP deflators of China, Japan, the United Kingdom, the United States, and the Euro Area.
Code
library(ggplot2)library(plotly)library(dplyr)library(scales)# Create the data frameincome_data<-tibble::tibble( income_group =factor(c("Low Income", "Lower Middle", "Upper Middle", "High Income"), levels =c("Low Income", "Lower Middle", "Upper Middle", "High Income")), lower_bound =c(0, 1146, 4516, 14006), upper_bound =c(1145, 4515, 14005, Inf), midpoint =c(572.5, 2830.5, 9260.5, 20000), # Approximate midpoints for visualization color_group =c("Low Income", "Lower Middle", "Upper Middle", "High Income")# For consistent coloring)%>%mutate(income_range_label =case_when(upper_bound==Inf~paste0(">", format(lower_bound-1, big.mark =",")),TRUE~paste0("$", format(lower_bound, big.mark =","), "-$", format(upper_bound, big.mark =","))))# Define colors to match the imageincome_colors<-c("Low Income"="#FFB347", # Light orange"Lower Middle"="#0099f9", # Light blue"Upper Middle"="#00124D", # dark blue"High Income"="#007E33")# Dark green# Create the ggplotincome_plot<-ggplot(income_data, aes(x =income_group, y =midpoint, fill =color_group, text =paste("Income Group:", income_group, "<br>","Range:", income_range_label)))+geom_bar(stat ="identity", width =0.6)+geom_text(aes(label =income_range_label, y =midpoint+(max(midpoint)*0.05)), # Adjust y for spacing vjust ="bottom", hjust ="center", size =3.5)+# Adjust appearancescale_fill_manual(values =income_colors)+scale_y_continuous(labels =scales::comma, expand =c(0, 0), limits =c(0, max(income_data$midpoint)*1.2))+# Adjust limitslabs(title ="Figure 1: Income Groups in 2025", subtitle ="Annual GNI per capita (US$)", x =NULL, y ="Approximate Midpoint (US$)", fill ="Income Group")+theme_minimal()+theme(axis.text.x =element_text(size =10), axis.title.y =element_text(size =10), plot.title =element_text(size =14, face ="bold", hjust =0.5), plot.subtitle =element_text(size =12, hjust =0.5), legend.position ="none")# Remove legend as colors are self-explanatory# Convert to plotlyincome_plotly<-ggplotly(income_plot, tooltip ="text")# Display the plotly chartincome_plotly
Globally, the share of low-income countries has declined significantly, dropping from 30.7% in 2000 to just 11.9% today.
China transitioned out of low-income status in 1999 and, by 2010, had achieved upper-middle-income status, a position it holds today.
Similarly, India, which was classified as a low-income country two decades ago, has experienced rapid growth driven by infrastructure investments, economic reforms, and the expansion of its services sector.
Figure 2: Tree map
The World Bank also highlighted the following trends
100% of South Asian countries were classified as low-income countries in 1987, whereas this share has fallen to just 13% in
In the Middle East and North Africa there is a higher share of low-income countries in 2023 (10%) than in 1987, when no countries were classified to this category.
In Latin America and the Caribbean, the share of high-income countries has climbed from 9% in 1987 to 44% in 2023.
Europe and Central Asia has a slightly lower share of high-income countries in 2023 (69%) than it did in 1987 (71%).
The ECCU
The Eastern Caribbean Currency Union (ECCU) has a combination of both high-income and upper-middle-income economies (Figure 3). This reflects the diverse economic conditions across the member countries. Factors like tourism, financial services, and in some cases, citizenship-by-investment programs, contribute to the GNI per capita, which determines these classifications. However, these economies are also vulnerable to external shocks, such as natural disasters and fluctuations in the global economy, which can impact their economic stability and potentially shift their income group status.
Code
library(ggplot2)library(dplyr)library(wbstats)library(tidyr)# Define the countries and yearscountries<-c("VC", "KN", "LC", "GD", "DM", "AG")# Country codesyears<-c(2022, 2023, 2024)indicator_code<-"NY.GNP.PCAP.CD"# GNI per capita (Atlas method, current US$)# Fetch the data from the World Bankgni_data<-wb_data( indicator =indicator_code, country =countries, start_date =min(years), end_date =max(years))%>%# Select relevant columnsselect(country, date, iso2c, iso3c, NY.GNP.PCAP.CD)%>%# Filter for the desired yearsfilter(date%in%years)%>%# Rename columns for clarityrename(Country =country, Year =date, GNI_per_capita =NY.GNP.PCAP.CD)%>%# Get income groupmutate(Income_Group =rep(c("High Income","Upper Middle", "Upper Middle", "High Income", "Upper Middle","Upper Middle"), each =3))#Made up, change as neededgni_data_filtered<-gni_data%>%group_by(Year)%>%filter(!all(is.na(GNI_per_capita)))%>%ungroup()# Create the horizontal bar chart with reversed ordergni_chart<-gni_data_filtered%>%arrange(desc(GNI_per_capita))%>%# Arrange the data by value in descending ordermutate(Country =factor(Country, levels =rev(c("St. Kitts and Nevis", "Antigua and Barbuda", "St. Lucia", "Grenada", "St. Vincent and the Grenadines", "Dominica"))))%>%ggplot(aes(x =Country, y =GNI_per_capita, fill =Income_Group))+geom_bar(stat ="identity", position ="dodge")+scale_y_continuous(labels =function(x)paste0(x/1000, "k"))+facet_wrap(~Year, scales ="free_y")+coord_flip()+scale_fill_manual(values =c("Low Income"="cornflowerblue","Lower Middle"="#AEEA00","Upper Middle"="#00124D","High Income"="#FCB001"))+labs( title ="Figure 3: GNI per Capita by Country and Year", x ="Country", y ="GNI per Capita (US$)", fill ="Income Group")+theme_minimal()+theme(plot.title =element_text(size =14, face ="bold", hjust =0.5), axis.text.x =element_text(hjust =1), legend.title =element_blank(), legend.key.size =unit(0.5, "lines"), legend.position ="bottom")# Display the chartprint(gni_chart)
Figure 3: Classification and GNI per capita for ECCU Independent Countries
The reliance on specific sectors and inherent vulnerabilities present both opportunities and challenges for the ECCU. While the high and upper-middle-income statuses indicate a degree of economic development, these countries are vulnerable to shocks. For instance, countries like Antigua and Barbuda, despite facing significant vulnerabilities to economic and environmental shocks due to their small size and reliance on sectors like tourism, often find it difficult to secure IDA loans. This is because the International Development Association (IDA), the World Bank’s concessional lending arm, primarily allocates resources based on a country’s Gross National Income (GNI) per capita, which places Antigua and Barbuda and St Kitts and Nevis in the high-income category. While this income level suggests a degree of economic development, it does not fully account for the unique challenges these nations face, where a single hurricane or a global recession can have devastating and long-lasting impacts, creating a mismatch between their actual needs and their eligibility for concessional financing.
ECCU member countries must therefore pursue sustainable and diversified growth strategies. This includes building resilience to climate change, promoting inclusive economic policies, and addressing issues like high public debt. By doing so, ECCU countries can aim to maintain or even improve their income group status, leading to greater prosperity and improved living standards for their citizens.