Kingfisher es una biblioteca para cargar y almacenar en caché imágenes en iOS, macOS y watchOS, escrita en Swift puro. Según el repositorio oficial, la biblioteca proporciona soporte completo para Swift Concurrency, Combine y SwiftUI, así como almacenamiento en caché automático de dos niveles. Kingfisher es conocida por su API type-safe y su fácil integración con proyectos en Swift.
Puntos clave
Kingfisher es una biblioteca para la carga asíncrona y el almacenamiento en caché de imágenes en plataformas Apple, escrita completamente en Swift. El autor de la biblioteca es Wei Wang (onevcat). Kingfisher proporciona un conjunto de herramientas para cargar imágenes desde la red con caché automática, transformaciones y soporte para tecnologías modernas de Swift: async/await, Combine, Sendable.
La biblioteca tiene más de 23.000 estrellas en GitHub y se utiliza en aplicaciones como Telegram, Snapchat y Dropbox. Kingfisher admite GIF, APNG, HEIF y todos los formatos de imagen estándar. Cada solicitud devuelve un Result
La arquitectura de Kingfisher se basa en tres componentes principales: Manager (gestor de descargas), Cache (caché de dos niveles) y Processor (transformaciones). Estos componentes están conectados a través de protocolos, lo que permite reemplazar cualquier parte sin cambiar las dependencias.
KingfisherManager es la clase central que coordina la carga, el almacenamiento en caché y el procesamiento de imágenes. Contiene referencias a ImageCache e ImageDownloader y proporciona un método único retrieveImage que devuelve la imagen lista después de pasar por todas las etapas.
Al llamar a retrieveImage, el Manager primero verifica Memory Cache — un NSCache con UIImage, donde la clave se forma a partir de la URL de origen y CacheSerializer. Si se encuentra la imagen, se devuelve inmediatamente. En caso de fallo, se verifica Disk Cache: lectura del sistema de archivos con descifrado a través del serializador. Si el caché de disco está vacío, se realiza una solicitud de red a través de ImageDownloader, el resultado se decodifica, transforma y guarda en ambos niveles de caché.
A partir de la versión 7.0, Kingfisher es totalmente compatible con async/await. El método retrieveImage está disponible como una función asíncrona que devuelve Result directamente sin bloques de finalización. Esto permite usar la biblioteca en arquitecturas Swift modernas con Structured Concurrency.
Kingfisher está dividida en varios módulos, cada uno resolviendo su propia tarea. Esta separación simplifica las pruebas y el reemplazo de componentes.
KingfisherManager es una fachada que combina carga, caché y procesadores. Por defecto se usa el singleton KingfisherManager.shared, pero se puede crear una instancia separada con configuraciones personalizadas para escenarios aislados (por ejemplo, para pruebas unitarias).
ImageCache es un caché de dos niveles con configuraciones separadas para memoria y disco. Memory Cache no tiene límite en la cantidad de objetos, pero el sistema lo limpia cuando falta memoria. Disk Cache almacena archivos en un directorio con TTL configurable (por defecto 7 días), límite de tamaño (por defecto 0 — sin límite) y limpieza automática.
ImageProcessor es un protocolo con un único método process(item:options:) que devuelve la imagen procesada. Implementaciones integradas: ResizingImageProcessor (cambio de tamaño), RoundCornerImageProcessor (redondeo), BlurImageProcessor (desenfoque gaussiano), OverlayImageProcessor (superposición de color). Los procesadores se pueden combinar mediante el operador |>.
La arquitectura de caché de Kingfisher se basa en el principio de write-through: los datos se escriben en ambos niveles simultáneamente y la lectura comienza desde el nivel más rápido: la memoria. La clave de caché es la URL absoluta de la imagen después de eliminar los parámetros de consulta.
| Parámetro | Memory Cache | Disk Cache |
|---|---|---|
| Almacenamiento | NSCache (RAM) | Sistema de archivos (SSD) |
| Formato | UIImage (decodificado) | Data (comprimido, mediante serializador) |
| Limpieza | UIApplication.didReceiveMemoryWarningNotification | TTL + superación del límite |
| Serialización | No requerida | CacheSerializer (por defecto PNG/JPEG) |
| Seguridad de hilos | Sí (acceso sincronizado) | Sí (cola IO + barreras) |
Para gestionar el tamaño de Disk Cache, se calcula el tamaño total de los archivos ordenándolos por fecha de último acceso. Cuando se supera el límite, se eliminan los archivos con la fecha de acceso más antigua hasta que el tamaño sea inferior al 50% del límite. La limpieza TTL ocurre durante la inicialización del caché y en cada llamada a cleanExpired.
Kingfisher proporciona varias interfaces para cargar imágenes: una extensión en UIImageView, un gestor separado y una View de SwiftUI.
kf es una propiedad namespace en UIImageView que proporciona los métodos setImage, cancelDownload e indicadores de carga. El método setImage acepta URLSource y los parámetros opcionales Options y completionHandler.
import Kingfisher
imageView.kf.setImage(
with: URL(string: "https://example.com/image.jpg"),
placeholder: UIImage(named: "placeholder"),
options: [
.processor(RoundCornerImageProcessor(radius: .point(12))),
.transition(.fade(0.3)),
.cacheMemoryOnly
],
progressBlock: { receivedSize, totalSize in
print("Cargado \(receivedSize) / \(totalSize)")
}
)
El método devuelve un DownloadTask que admite la cancelación mediante cancel y el seguimiento del progreso. Internamente, setImage llama a KingfisherManager.shared.retrieveImage con detección automática de ImageView como Target.
A partir de Kingfisher 7.0, el método setImage está disponible en versión asíncrona. Esto permite integrar la carga de imágenes en Swift Structured Concurrency sin callbacks.
func loadAvatar() async {
do {
let result = try await imageView.kf.setImage(
with: url,
options: [.processor(ResizingImageProcessor(
targetSize: CGSize(width: 100, height: 100)
))]
)
// result.image contiene UIImage
} catch {
print("Falló: \(error)")
}
}
KFImage es una View de SwiftUI, similar a AsyncImage de iOS 15, pero con soporte completo de caché de Kingfisher. La View usa automáticamente KingfisherManager.shared, pero admite un gestor personalizado mediante el modificador .configure.
struct AvatarView: View {
let url: URL
var body: some View {
KFImage(url)
.placeholder { ProgressView() }
.resizable()
.fade(duration: 0.25)
.forceTransition()
.frame(width: 80, height: 80)
.cornerRadius(40)
}
}
Kingfisher proporciona un sistema de indicadores integrado para mostrar el progreso de la carga de imágenes. IndicatorType es una enumeración con tres opciones: .activity (UIActivityIndicatorView), .progress (UIProgressView) y .custom (implementación personalizada del protocolo Indicator). El indicador aparece automáticamente sobre el ImageView durante la carga y se oculta al finalizar.
Para un indicador personalizado, es necesario implementar el protocolo Indicator con los métodos startAnimatingView() y stopAnimatingView(). Esto permite soluciones híbridas: un esqueleto con animación shimmer, una imagen de placeholder con aparición gradual o un logotipo con animación de opacidad. Kingfisher también admite la configuración global del indicador a través de KingfisherManager.shared.defaultOptions.
En la plataforma iOS, Kingfisher y SDWebImage son las dos bibliotecas dominantes para la carga de imágenes. La elección entre ellas depende del lenguaje del proyecto, los requisitos de rendimiento y el ecosistema.
| Criterio | Kingfisher | SDWebImage |
|---|---|---|
| Lenguaje | Swift (100%) | Objective-C + Swift |
| Async/Await | Soporte nativo | Mediante envoltorio |
| Combine | Publisher incorporado | No |
| Sendable | Compatible | Limitado |
| Type Safety | Completo (tipo Result) | Mediante Any? |
| ImageProcessor | Compuesto mediante |> | Transformer mediante && |
| Tamaño | ~900 KB | ~1.2 MB |
| Estrellas GitHub | 23.000+ | 25.000+ |
La ventaja clave de Kingfisher es su arquitectura Swift-first: soporte completo de async/await, Combine Publishers, Sendable y tipos Result. SDWebImage mantiene el liderazgo gracias a su ecosistema más amplio de complementos (WebP, SVG, MapKit) y soporte para Objective-C.
Kingfisher se instala mediante Swift Package Manager, CocoaPods o Carthage. Después de la instalación, basta con importar el módulo y llamar a cualquier método de carga: la biblioteca está lista para usar sin configuración adicional.
// Swift Package Manager (Package.swift)
dependencies: [
.package(
url: "https://github.com/onevcat/Kingfisher.git",
from: "7.12.0"
)
]
// CocoaPods (Podfile)
pod 'Kingfisher', '~> 7.12'
Para personalizar la configuración global, se utiliza KingfisherManager.shared. Se puede cambiar el tiempo de espera del descargador, la estrategia de caché y los procesadores predeterminados. A continuación se muestra un ejemplo de configuración de un caché de 500 MB con TTL de 14 días.
let cache = ImageCache(name: "custom")
cache.memoryStorage.config.totalCostLimit = 100 * 1024 * 1024
cache.diskStorage.config.sizeLimit = 500 * 1024 * 1024
cache.diskStorage.config.expiration = .days(14)
KingfisherManager.shared.cache = cache
ImageDownloader también se configura a través del gestor: se puede establecer una URLSessionConfiguration personalizada con tiempos de espera, encabezados y políticas de caché. Para el monitoreo del progreso, está disponible el módulo KFIndicator con soporte para ActivityIndicator, ProgressView e indicadores personalizados.
Preguntas frecuentes
Kingfisher es una biblioteca para cargar imágenes en iOS, escrita en Swift puro. Se utiliza para la carga asíncrona, el almacenamiento en caché y la transformación de imágenes desde la red con integración completa en SwiftUI, UIKit y las tecnologías modernas de Swift.
Agregue el paquete https://github.com/onevcat/Kingfisher.git con la versión desde 7.12.0 en Xcode mediante File → Add Packages. O especifique la dependencia en Package.swift con el parámetro from: "7.12.0". Después de la instalación, importe el módulo Kingfisher.
Kingfisher admite JPEG, PNG, GIF, APNG, HEIF y WebP. Todos los formatos se decodifican a través de los frameworks del sistema (ImageIO, CoreGraphics). GIF se admite mediante CGImageSource con carga progresiva y animación.
Kingfisher está escrito en Swift puro y es totalmente compatible con async/await, Combine y Sendable. Proporciona una API Result type-safe y una arquitectura modular mediante protocolos, lo que simplifica el reemplazo de componentes y las pruebas.
Para limpiar Memory Cache, llame a KingfisherManager.shared.cache.clearMemoryCache(). Para Disk Cache, use clearDiskCache(). Para eliminar solo los archivos caducados — cleanExpiredDiskCache(). El tamaño del caché se puede verificar mediante cache.calculateDiskStorageSize().
Resumen
Desarrollaremos una aplicación móvil llave en mano
IT Sectr crea aplicaciones para iOS y Android para startups y empresas desde 2017. Le asesoraremos y le propondremos la mejor solución.
Lea también