1.枚举提供类型安全
2.匿名token
作用:防止被人恶意刷接口。
情景:当应用,在非登录状态下也可以使用的情况下,需要匿名token。
解决:要去服务器请求一个匿名token
3微信分享没有回调
.wxapi.WXEntryActivity必须在包名下面。
微信分享没有回调问题
4android中网络请求中页面关闭了会怎么样?
问题:android中网络请求中页面关闭了会怎么样
以activity为例子,
1.可以在onDestroy里cancel掉所有网络请求。
2.也可以采用虚引用的方式
虚引用 :不能单独使用,主要是用于追踪对象被垃圾回收的状态。通过PhantomReference类和引用队列ReferenceQueue类联合使用实现
可以每个请求的时候标志一个tag(一个页面一个 bject tag = new Object();不能采用当前activity.this,因为你的回调是个内部匿名类会默认持有当前activity,内部匿名类不是消失,activity得不到释放),tag的hashcode值和应用队列建立一个虚引用,需引用里又个list<call>,后台开启一个常驻线程,检测。当Gc时,就能得到ReferenceQueue得到PhantomReference,把所有没执行的call都cancel
* 为每个 NetCall 建立一个与 Tag(Object) 的引用. 当 Tag 被 JVM 回收后,自动关闭 NetCall. * */
public class BJNetResourceManager {
private Object mDefaultObject = new Object();
private ReferenceQueue<Object> mReferenceQueue = new ReferenceQueue<>();
private Map<Integer, ResourceReference> mResourceRefMap = new ConcurrentHashMap<>();
private ResourceCheckThread mResourceCheckThread = new ResourceCheckThread();
public BJNetResourceManager() { mResourceCheckThread.start();
}
public void release() { }
public void addNetCall(Object tag, BJNetCall call) { int key = mDefaultObject.hashCode(); if (tag != null) { key = tag.hashCode(); } if (mResourceRefMap.containsKey(key)) { ResourceReference reference = mResourceRefMap.get(key); reference.add(call); } else { ResourceReference reference = new ResourceReference(tag == null ? mDefaultObject : tag, mReferenceQueue); reference.add(call); mResourceRefMap.put(key, reference); } } public void removeNetCall(Object tag, BJNetCall call) { int key = mDefaultObject.hashCode(); if (tag != null) { key = tag.hashCode(); } if (mResourceRefMap.containsKey(key)) { ResourceReference reference = mResourceRefMap.get(key); reference.remove(call); } else { } } public void removeAll(Object tag) { int key = mDefaultObject.hashCode(); if (tag != null) { key = tag.hashCode(); } if (mResourceRefMap.containsKey(key)) { ResourceReference reference = mResourceRefMap.get(key); reference.cancelAll(); mResourceRefMap.remove(key); } } private static class ResourceReference extends PhantomReference<Object> { private int tagId; private String tagName; private List<BJNetCall> list; /** * Constructs a new phantom reference and registers it with the given * reference queue. The reference queue may be {@code null}, but this case * does not make any sense, since the reference will never be enqueued, and * the {@link #get()} method always returns {@code null}. * * @param r the referent to track * @param q the queue to register the phantom reference object with */ public ResourceReference(Object r, ReferenceQueue<? super Object> q) { super(r, q); this.tagId = r.hashCode(); this.tagName = r.getClass().getSimpleName(); this.list = Collections.synchronizedList(new LinkedList<BJNetCall>()); } public int getTagId() { return tagId; } public String getTagName() { return tagName; } public void add(BJNetCall call) { list.add(call); } public void remove(BJNetCall call) { list.remove(call); } public void cancelAll() { for (BJNetCall call : list) { try { call.cancel(); } catch (Exception e) { e.printStackTrace(); } } list.clear(); } } private class ResourceCheckThread extends Thread { public ResourceCheckThread() { super("NetResourceCheckThread"); setPriority(Thread.MAX_PRIORITY); setDaemon(true); } @Override public void run() { ResourceReference reference = null; while (! interrupted()) { if (reference != null) { reference.cancelAll(); reference.clear(); mResourceRefMap.remove(reference.getTagId()); Log.i("BJNetResource", "["+reference.getTagName() +"("+reference.getTagId()+")"+" is released and cancel calls auto.]"); } // default tag 域中可能有已经执行完成了的 call. 将其回收掉 ResourceReference defaultReference = mResourceRefMap.get(mDefaultObject.hashCode()); if (defaultReference != null) { Iterator<BJNetCall> iterator = defaultReference.list.listIterator(); while (iterator.hasNext()) { if (! iterator.next().isExecuted()) { iterator.remove(); Log.i("BJNetResource", "["+defaultReference.getTagName() +"("+defaultReference.getTagId()+")"+" is cleanup and cancel calls auto.]"); } } } try { // remove() 会 wait 住线程 reference = (ResourceReference) mReferenceQueue.remove(1000); } catch (Exception e) { e.printStackTrace(); } } } }}