Glide使用探索(二)——磁盘缓存无效化
2017-03-02 15:50
417 查看
原文地址:https://github.com/bumptech/glide/wiki/Caching-and-Cache-Invalidation
一、缓存Keys:
Glide中的缓存keys由四部分构成:
1.DataFetcher的getId()方法返回的字串。一般DataFetchers只是返回数据模型的toString()方法的返回值,例如:如果你提供的是URL则返回URL的路径,如果提供的是文件则返回文件路径
2.override(int, int)方法中传入的高、宽值(如果调用了此方法),默认返回Target的getSize()方法提供的高、宽值
3.各个用于加载、缓存图片的编、解码器中的getId()方法返回的字串。只有当编、解码器影响到检索数据时才能包含id。例如:一个编码器只是简单地将byte数组写入磁盘,则此编码器是没有id值的,因为它没有对数据造成任何影响
4.每次加载时用到的一个可选的签名。
这些keys将以特定的顺序hash化,以用来创建唯一且安全的文件名用来将特定的图片缓存到磁盘。
二、缓存无效化:
由于缓存图片的文件名都是hash后的值,因此没有一个好的方式用来删除给定url或文件路径对应的磁盘上的全部缓存文件。因为Glide会同时缓存预览图、各种转码后的图片,每一种图片都会在缓存中创建一个新的文件,因此追踪并删除一个图片的所有缓存文件是很困难的。因此清楚缓存最好的方式是在内容改变时(url、uri、file path等)改变标识符。
三、自定义缓存无效化:
基于改变标识符的困难性,Glide提供了signature()方法用来将可控制的附加数据(签名)加入缓存key中。签名在存储多媒体资源时效果很好,同样,缓存其他内容时也可以在其中保留一些元数据。
1.缓存多媒体资源:可以使用Glide的MediaStoreSignature作为签名。MediaStoreSignature允许你将修改时间、mimeType、多媒体的定位这三种信息混入缓存key。
2.文件:可以使用StringSignature来混入文件的修改时。。
3.Urls:最好地清除urls缓存的方式是服务端改变url并在url改变时在客户端进行更新。不过,同样可以使用StringSignature混入任意元数据(例如版本号)的方式来取代。
传入string signatures:
Glide.with(yourFragment)
.load(yourFileDataModel)
.signature(new StringSignature(yourVersionMetadata))
.into(yourImageView);
多媒体签名:
Glide.with(fragment)
.load(mediaStoreUri)
.signature(new MediaStoreSignature(mimeType, dateModified, orientation))
.into(view);
通过实现Key接口可以自定义签名(确保实现equals()、hashCode()以及updateDiskCacheKey()方法):
public class IntegerVersionSignature implements Key {
}
public class CustomFileSignature implements Key {
}
注意:为了不影响性能,最好在后台加载元数据
也可以使用diskCacheStrategy()以及DiskCacheStrategy.NONE的方式来彻底禁用磁盘缓存。
Glide.with(context).load(imageUrl).diskCacheStrategy(DiskCacheStrategy.NONE).into(view);
一、缓存Keys:
Glide中的缓存keys由四部分构成:
1.DataFetcher的getId()方法返回的字串。一般DataFetchers只是返回数据模型的toString()方法的返回值,例如:如果你提供的是URL则返回URL的路径,如果提供的是文件则返回文件路径
2.override(int, int)方法中传入的高、宽值(如果调用了此方法),默认返回Target的getSize()方法提供的高、宽值
3.各个用于加载、缓存图片的编、解码器中的getId()方法返回的字串。只有当编、解码器影响到检索数据时才能包含id。例如:一个编码器只是简单地将byte数组写入磁盘,则此编码器是没有id值的,因为它没有对数据造成任何影响
4.每次加载时用到的一个可选的签名。
这些keys将以特定的顺序hash化,以用来创建唯一且安全的文件名用来将特定的图片缓存到磁盘。
二、缓存无效化:
由于缓存图片的文件名都是hash后的值,因此没有一个好的方式用来删除给定url或文件路径对应的磁盘上的全部缓存文件。因为Glide会同时缓存预览图、各种转码后的图片,每一种图片都会在缓存中创建一个新的文件,因此追踪并删除一个图片的所有缓存文件是很困难的。因此清楚缓存最好的方式是在内容改变时(url、uri、file path等)改变标识符。
三、自定义缓存无效化:
基于改变标识符的困难性,Glide提供了signature()方法用来将可控制的附加数据(签名)加入缓存key中。签名在存储多媒体资源时效果很好,同样,缓存其他内容时也可以在其中保留一些元数据。
1.缓存多媒体资源:可以使用Glide的MediaStoreSignature作为签名。MediaStoreSignature允许你将修改时间、mimeType、多媒体的定位这三种信息混入缓存key。
2.文件:可以使用StringSignature来混入文件的修改时。。
3.Urls:最好地清除urls缓存的方式是服务端改变url并在url改变时在客户端进行更新。不过,同样可以使用StringSignature混入任意元数据(例如版本号)的方式来取代。
传入string signatures:
Glide.with(yourFragment)
.load(yourFileDataModel)
.signature(new StringSignature(yourVersionMetadata))
.into(yourImageView);
多媒体签名:
Glide.with(fragment)
.load(mediaStoreUri)
.signature(new MediaStoreSignature(mimeType, dateModified, orientation))
.into(view);
通过实现Key接口可以自定义签名(确保实现equals()、hashCode()以及updateDiskCacheKey()方法):
public class IntegerVersionSignature implements Key {
private int currentVersion; public IntegerVersionSignature(int currentVersion) { this.currentVersion = currentVersion; } @Override public boolean equals(Object o) { if (o instanceof IntegerVersionSignature) { IntegerVersionSignature other = (IntegerVersionSignature) o; return currentVersion == other.currentVersion; } return false; } @Override public int hashCode() { return currentVersion; } @Override public void updateDiskCacheKey(MessageDigest messageDigest) { messageDigest.update(ByteBuffer.allocate(Integer.SIZE).putInt(currentVersion).array()); }
}
public class CustomFileSignature implements Key {
private final String fileName; private final long dateModified; private final String filePath; public CustomFileSignature(String fileName, long dateModified, String filePath) { this.fileName = fileName; this.dateModified = dateModified; this.filePath = filePath; } @Override public boolean equals(Object o) { if (this == o) { return true; } if (o == null || getClass() != o.getClass()) { return false; } CustomFileSignature that = (CustomFileSignature) o; if (fileName != null ? !fileName.equals(that.fileName) : that.fileName != null) { return false; } if (dateModified != that.dateModified) { return false; } if (filePath != null ? !filePath.equals(that.filePath) : that.filePath != null) { return false; } return true; } @Override public int hashCode() { int result = fileName != null ? fileName.hashCode() : 0; // dateModified >>> 32 ——> dateModified / ((int) Math.pow(2, 32)) result = 31 * result + (int) (dateModified ^ (dateModified >>> 32)); result = 31 * result + (filePath != null ? filePath.hashCode() : 0); return result; } @Override public void updateDiskCacheKey(MessageDigest messageDigest) throws UnsupportedEncodingException { byte[] data = ByteBuffer.allocate(12) .putLong(dateModified) .array(); messageDigest.update(data); messageDigest.update(fileName.getBytes(STRING_CHARSET_NAME)); messageDigest.update(filePath.getBytes(STRING_CHARSET_NAME)); }
}
注意:为了不影响性能,最好在后台加载元数据
也可以使用diskCacheStrategy()以及DiskCacheStrategy.NONE的方式来彻底禁用磁盘缓存。
Glide.with(context).load(imageUrl).diskCacheStrategy(DiskCacheStrategy.NONE).into(view);
相关文章推荐
- Glide使用探索(四)——自定义显示控件
- Glide使用探索(一)
- Glide使用探索(三)——配置
- 探索 SOA 体系结构和服务的基本原则,第 1 部分: 使用体系结构和抽象级别来创建更好的 SOA
- 2005-3-29+ 探索ASP.NET Forum(2)控件的使用
- 探索 SOA 体系结构和服务的基本原则,第 1 部分: 使用体系结构和抽象级别来创建更好的 SOA
- 用WinDbg探索CLR世界 [8] InternalCall 的使用与实现
- 使用Word中的CheckBox,探索属性/方法
- 用WinDbg探索CLR世界 [8] InternalCall 的使用与实现
- LINQ下使用三层架构的探索(二)建立一个LTS层,并在表示层中查询数据
- LINQ下使用三层架构的探索(三)建立一个LTS层,并在表示层中插入数据
- PFC的使用与探索(一)
- LINQ下使用三层架构的探索(六)逻辑访问层中的数据统计以及一个主从报表。
- [Ext]2.0探索(七)Grid使用介绍
- LINQ下使用三层架构的探索(五)逻辑访问层中的带参查询、插入、更新以及删除。
- 深入探索SOAP1.1--使用SAAJ1.2.1
- 深入探索SOAP1.1--使用SAAJ1.2.1
- 使用Word中的CheckBox,探索属性/方法
- Visual Studio .NET使用技巧手册读书笔记之探索编译器
- PFC的使用与探索(一)