Presentación

Esta publicación tiene dos objetivos, uno personal y otro general. El objetivo personal es poder tener un apunte en limpio sobre el uso de la API del Banco de México (siebanxicor) con R, pues no suelo usar esta herramienta a menudo para mis propios análisis. El segundo objetivo, el general, es simplemente compartirlo con todo aquel que guste y tampoco esté familiarizado con el uso de APIs.

No asumo que mi código sea el más eficiente o esté libre de errores, así que cualquier corrección o comentario házmelo saber por este medio o a través de mi twitter ecodiegoale.

Recomiendo leer antes la información que el propio Banco de México tiene sobre su API en este enlace.

Además, nunca está de más revisar stackoverflow, github, rpubs, entre otros.

Aviso: Soy consciente que el uso de la API es más eficiente para el análisis de series financieras en tiempo real, pero yo no le daré ese uso, no es mi objetivo e interés por el momento. Si algún link no abre con click izquierdo, trata con el derecho y abrir en otra ventana o pestaña.

Contenido

En este blog se hará uso de la API del Banco de México de una manera muy sencilla utilizando las librerías de siebanxicor, tiidyverse y lubridate. Lo que haremos será calcular un indicador básico de suficiencia de reservas internacionales; para más información recomiendo revisar el libro Instrumentación de las operaciones monetarias, cambiarias y de administración de reservas del Banco de México publicado por el Banco de México y disponible en este enlace

Cómo comenzar a usar la API

Paso 1: instalación y token

Lo primero será instalar la librería siebanxicor.

#install.packages("siebanxicor")

Una vez que esté instalada correctamente hay que llamarla con el resto de librerías a usar:

rm(list = ls())#para borrar los objetos guardados de sesiones anteriores
library(siebanxicor)
library(tidyverse)
library(lubridate)

Después entraremos al siguiente enlace para poder generar un token con el que podremos tener acceso a las series económicas del Sistema de información económica del Banco de México.

Para generar el token abre este enlace.

Para revisar las series económicas de una manera más clara da click aquí.

Una vez hecho lo anterior basta con utilizar el token entre comillas como sigue:

setToken("28ec1a84ff716c5b1a8a305c32a6ba3e995fa7cc9eba0d30481b817babe3b5c0")

Paso 2: las series económicas y su identificador

Antes de usar la API debemos tener claro lo que queremos hacer. ¿Qué es lo que nos interesabe saber o qué pregunta queremos responder?

Para fines de este blog la pregunta es:

¿Son las reservas internacionales de México suficientes?

Como mencioné en la sección anterior, para conocer más sobre este tema recomiendo el libro ya citado.

En dicho libro nos ofrecen una respuesta, por ahora supondremos que esa respuesta satisface completamente a nuestra pregunta. La gráfica se presenta tal como se extrajo de la página 157 del ya citado libro.

Gráfico retomado de la pg.157 del libro ya citado De acuerdo con lo anterior, un país tiene suficientes reservas internacionales si estas representan el 10% de todo el agregado monetario M2.

Por lo tanto, requerimos conocer las series de las reservas internacionales, el agregado monetario M2 y el tipo de cambio (peso MXN a dólar).

Cada serie tiene un identificador único, para saber qué identificador tienen las series de interés podemos usar el catálago de series de la API en este link o visitando el Sistema de información económica del Banco de México (el link está en la sección anterior).

ID Serie Unidad
SF43718 Tipo de cambio FIX Millones de pesos
SF43707 Reservas internacionales Millones de dólares
SF311418 Agregado M2 Miles de pesos

Lo primero será crear un vector que contenga el ID de cada serie:

idSeries <- c("SF43718","SF43707","SF311418")

Es conveniente conocer las series empleadas, esto incluye su frecuencia, unidad y disponibilidad.

metadata <- getSeriesMetadata(idSeries)

Con la línea de código anterior, lo que hacemos es generar un objeto que contenga la información sobre nuestras series, una vez generados podemos ver el contenido

View(metadata)

Observamos las fechas de inicio de nuestras series, así como el final, su frecuencia, unidad y tipo de dato.

Paso 3: el procesamiento de las series

Con el objeto metadata observamos que la frecuencia de las series es diferente, además que abarcan distintos periodos. En este blog solo nos interesaremos por la suficiencia de las reservas internacionales a partir del año 2000 hasta la fecha disponible más reciente.

Primero, crearemos un objeto que indique que queremos la fecha disponible más reciente:

hoy <- Sys.Date()

Luego, con el comando getSeriesData() crearemos una lista que contenga las series de interés, partiendo de los ID y del periodo que nos importa:

series <- getSeriesData(idSeries, '2000-01-01', hoy)

Por último para este paso, partiendo de la lista anterior crearemos los data frames que contenga cada serie de manera independiente:

tc <- getSerieDataFrame(series,"SF43718")
ri <- getSerieDataFrame(series,"SF43707")
m2 <- getSerieDataFrame(series,"SF311418")

Paso 4: filtrar y limpiar las series

Preparación de M2

De acuerdo con el indicador, necesitamos al agregado monetario M2 en dólares, la serie de la que disponemos está en miles de pesos. Necesitamos una serie de M2 en dólares, además esta serie es mensual, necesitamos únicamente los saldos al 31 de diciembre desde el año 2000:

head(m2)
##         date      value
## 1 2000-12-01 1817196847
## 2 2001-01-01 1776421088
## 3 2001-02-01 1793737881
## 4 2001-03-01 1813184631
## 5 2001-04-01 1831650212
## 6 2001-05-01 1844982118

Para esto primero filtraré la serie, no me interesan los meses que no sean diciembre. Para esto primero filtramos la serie y luego la agrupamos por año:

m2 <- m2 %>% 
  filter(month(date) == 12) %>%
  group_by(year(date))

#Con el siguiente comando le cambié el nombre a la columna del dataframe que contiene el valor de la serie
names(m2)[2] <- "m2midp"
#m2midp=M2 miles de pesos

Preparación de las reservas internacionales

Como con M2, solo necesitamos el saldo al 31 de diciembre, el problema de esta serie es que su frecuencia es diaria y su último dato está para el año 2023, mientras que para M2 su último dato era mensual y para 2021 (el último dato de la serie es noviembre 2022, nosotros necesitamos saldos de diciembre).

Por lo anterior, necesitamos filtrar únicamente los saldos del 31 de diciembre para todos los años menores a 2022.

Primero, filtramos únicamente los meses de diciembre, posteriormente agrupamos por año. Luego, como queremos únicamenre los días 31 de cada diciembre, filtramos el último día disponible para cada diciembre. Te preguntarás ¿por qué no filtrar mejor los días 31? Antes de trabajar una serie conviene examinarla visualmente, al hacer esto, yo me di cuenta que no todos los diciembres de los años disponibles tienen los saldos exactamente al 31 de diciembre, algunos tienen al 28 o 29, por poner un ejemplo, por lo tanto, he decidido filtrar el último día de diciembre que esté disponible en la serie.

ri <- ri %>%
  filter(month(date) == 12) %>%
  group_by(year(date)) %>%
  filter(day(date) == max(day(date))) %>%
  filter(year(date) <= 2021)

names(ri)[2] <- "rimdd"
names(ri)[3] <- "year"
#rimdd=reservas internacionales en millones de dólares

Preparación del tipo de cambio

Para la serie del tipo de cambio, el problema es similar al de las reservas internacionales:

tc <- tc %>% 
  filter(month(date) == 12) %>%
  group_by(year(date)) %>%
  filter(day(date) == max(day(date)),
         year(date) <= 2021)

#tcfix=tipo de cambio FIX
names(tc)[2] <- "tcfix"

Paso 5: calcular el indicador

El indicador se calcula como sigue:

\(X_t= \frac{RI_t}{M2_t}\times 100\)

Creamos una pequeña base de datos donde se junten todas las series ya procesadas:

base <- data.frame(m2, ri, tc)
base <- base%>%
  dplyr::select(year, m2midp, rimdd, tcfix)
head(base)
##   year     m2midp   rimdd   tcfix
## 1 2000 1817196847 33554.9  9.6098
## 2 2001 2051445324 40091.2  9.1695
## 3 2002 2176465317 46098.7 10.4393
## 4 2003 2331594975 56085.7 11.2372
## 5 2004 2493275018 61496.3 11.1495
## 6 2005 2847571536 68668.9 10.6344

Posteriormente, calculamos el indicador. Primero, pasamos a millones de pesos el agregado M2, posteriormente lo convertimos a dólares, así tendremos la serie de M2 en millones de dólares (recuerda que las reservas internacionales están en millones de dólares). Finalmente, calculamos el indicador como indica la fórmula anterior.

base <- base%>%
  mutate(m2.mdp= m2midp/1000,
         m2.mdd=m2.mdp/tcfix,
         rim2  =rimdd/m2.mdd*100)
head(base)
##   year     m2midp   rimdd   tcfix  m2.mdp   m2.mdd     rim2
## 1 2000 1817196847 33554.9  9.6098 1817197 189098.3 17.74469
## 2 2001 2051445324 40091.2  9.1695 2051445 223724.9 17.91987
## 3 2002 2176465317 46098.7 10.4393 2176465 208487.7 22.11100
## 4 2003 2331594975 56085.7 11.2372 2331595 207489.0 27.03069
## 5 2004 2493275018 61496.3 11.1495 2493275 223622.1 27.50009
## 6 2005 2847571536 68668.9 10.6344 2847572 267769.8 25.64475

Paso 6: el más divertido

Ahora solo resta graficar. Si deseas saber más sobre cómo graficar usando ggplot2 te recomiendo revisar mis blogs:

  • Apuntes de ggplot2 pt.1 enlace
  • Apuntes de ggplot2 pt.2 enlace

No hay comando en esos apuntes que no se encuentre en sitios y foros como stackoverflow, repositorios de github, rpubs, los manuales de Wickham, The R graph gallery, etc.

plot.m2<-ggplot(data=base, aes(x=year, y=rim2))+
  geom_bar(stat="identity",color ="#14279B", fill="#14279B")+
  geom_hline(yintercept=10, linetype="dashed", color = "red", cex=1)+
  theme(plot.caption=element_text(hjust=0,size=9),
        plot.title=element_text(hjust=0.5, size=14,face="bold"),
        plot.subtitle =element_text(hjust=0.5, size=12,face="bold"),
        axis.text.x=element_text(angle =45,vjust =0.5, 
                                 hjust=0.5, colour = "black"),
        panel.background = element_rect(fill = "#E6E6E6"),
        panel.border = element_rect(colour = "black", fill=NA, size=1),
        axis.text.y = element_text(hjust = 0,
                                   colour = "black",
                                   size = 8))+
  labs(title="Razón de Reserva Internacional a M2",
       subtitle = "2000-2021",
       caption="Fuente: Elaboración propia con información del Banco de México.")+
  xlab(" ")+
  ylab("Porcentaje")
plot.m2

Con esto logramos contestar nuestra pregunta, de tal forma que podemos responder que desde el año 2000 México ha acumulado reservas internacionales más que suficientes. Si eso es bueno o malo, o las implicaciones económicas que esto conlleva no son objeto de este blog.