test_secondaryCacheValidity.js (5367B)
1 /** 2 * Any copyright is dedicated to the Public Domain. 3 * http://creativecommons.org/publicdomain/zero/1.0/ 4 */ 5 6 const { FileUtils } = ChromeUtils.importESModule( 7 "resource://testing-common/dom/quota/test/modules/FileUtils.sys.mjs" 8 ); 9 const { PrincipalUtils } = ChromeUtils.importESModule( 10 "resource://testing-common/dom/quota/test/modules/PrincipalUtils.sys.mjs" 11 ); 12 const { QuotaUtils } = ChromeUtils.importESModule( 13 "resource://testing-common/dom/quota/test/modules/QuotaUtils.sys.mjs" 14 ); 15 16 /** 17 * This test is mainly to verify that L2 related cached usage information is 18 * stable across a forced metadata restoration and consists of these steps: 19 * - Install a packaged profile 20 * - Initialize storage and temporary storage 21 * - Get full origin metadata (cached in memory) 22 * - Shutdown storage 23 * - Remove the origin metadata file on disk (forces restoration) 24 * - Initialize storage and temporary storage 25 * - Get full origin metadata (cached in memory) 26 * - Compare cached usage information 27 * 28 * This test is intended to catch changes that would require bumping 29 * kCurrentQuotaVersion. 30 * 31 * If the comparison of cached usage information fails, it is very likely that 32 * kCurrentQuotaVersion needs to be bumped. 33 * 34 * See also the documentation for kCurrentQuotaVersion in Constants.h. 35 * 36 * Note: This test currently contains only the essential coverage for 37 * detecting L2 cache validity issues. In the future, the packaged profile 38 * could be generated using more comprehensive data creation methods, and a 39 * separate test could be added to leverage the conditioned profiles 40 * infrastructure. However, a custom test with its own pre-packaged profile 41 * will still be needed, since we do not have control over the contents of 42 * conditioned profiles. 43 */ 44 async function testSecondaryCacheValidity() { 45 const principal = PrincipalUtils.createPrincipal("http://example42.com"); 46 const metadata = FileUtils.getFile( 47 "storage/default/http+++example42.com/.metadata-v2" 48 ); 49 50 info("Clearing storage"); 51 52 { 53 const request = Services.qms.clear(); 54 await QuotaUtils.requestFinished(request); 55 } 56 57 info("Installing package"); 58 59 // The profile contains a single origin directory in the default repository 60 // populated with basic data for all quota clients. It was created locally 61 // using the make_secondaryCacheValidity.js script, which can be 62 // executed like this: 63 // mach xpcshell-test --interactive dom/quota/test/xpcshell/make_secondaryCacheValidity.js 64 // After running _execute_test() and quit(), additional manual steps are 65 // needed: 66 // 1. Remove the folder "storage/temporary". 67 // 2. Remove the file "storage/ls-archive.sqlite". 68 // 3. Remove the file "storage/default/http+++example42.com/cache/caches.sqlite-wal". 69 // 4. Remove the file "storage/default/http+++example42.com/idb/2320029346mByDIdnedxe.sqlite-wal". 70 installPackage("secondaryCacheValidity_profile"); 71 72 info("Initializing storage"); 73 74 { 75 const request = Services.qms.init(); 76 await QuotaUtils.requestFinished(request); 77 } 78 79 info("Initializing temporary storage"); 80 81 { 82 const request = Services.qms.initTemporaryStorage(); 83 await QuotaUtils.requestFinished(request); 84 } 85 86 info("Getting full origin metadata"); 87 88 { 89 const request = Services.qms.getFullOriginMetadata("default", principal); 90 await QuotaUtils.requestFinished(request); 91 } 92 93 info("Getting full origin metadata"); 94 95 const fullOriginMetadataBefore = await (async function () { 96 const request = Services.qms.getFullOriginMetadata("default", principal); 97 await QuotaUtils.requestFinished(request); 98 return request.result; 99 })(); 100 101 info("Shutting down storage"); 102 103 { 104 const request = Services.qms.reset(); 105 await QuotaUtils.requestFinished(request); 106 } 107 108 info("Removing origin metadata"); 109 110 metadata.remove(false); 111 112 info("Initializing storage"); 113 114 { 115 const request = Services.qms.init(); 116 await QuotaUtils.requestFinished(request); 117 } 118 119 info("Initializing temporary storage"); 120 121 { 122 const request = Services.qms.initTemporaryStorage(); 123 await QuotaUtils.requestFinished(request); 124 } 125 126 info("Getting full origin metadata"); 127 128 const fullOriginMetadataAfter = await (async function () { 129 const request = Services.qms.getFullOriginMetadata("default", principal); 130 await QuotaUtils.requestFinished(request); 131 return request.result; 132 })(); 133 134 info("Verifying full origin metadata"); 135 136 Assert.notEqual( 137 BigInt(fullOriginMetadataBefore.lastAccessTime), 138 BigInt(fullOriginMetadataAfter.lastAccessTime), 139 "Last access times are not the same" 140 ); 141 142 info("Client usages before: " + fullOriginMetadataBefore.clientUsages); 143 info("Client usages after: " + fullOriginMetadataAfter.clientUsages); 144 145 Assert.equal( 146 fullOriginMetadataBefore.clientUsages, 147 fullOriginMetadataAfter.clientUsages, 148 "Client usages are the same" 149 ); 150 151 info("Origin usgae before: " + fullOriginMetadataBefore.originUsage); 152 info("Origin usage after: " + fullOriginMetadataAfter.originUsage); 153 154 Assert.equal( 155 fullOriginMetadataBefore.originUsage, 156 fullOriginMetadataAfter.originUsage, 157 "Origin usage is the same" 158 ); 159 } 160 161 /* exported testSteps */ 162 async function testSteps() { 163 add_task( 164 { 165 pref_set: [["dom.quotaManager.loadQuotaFromCache", false]], 166 }, 167 testSecondaryCacheValidity 168 ); 169 }