|
1 |
| -import {createHash} from "node:crypto"; |
| 1 | +import { createHash } from 'node:crypto'; |
2 | 2 |
|
3 | 3 | // npx ts-node generate.ts
|
4 | 4 |
|
5 |
| -function hashAndEncode(jsonData: { precomputed: { response: any; }; }) { |
6 |
| - const salt = jsonData.precomputed.response.salt; |
7 |
| - const flags = jsonData.precomputed.response.flags; |
8 |
| - const bandits = jsonData.precomputed.response.bandits; |
9 |
| - // Process each flag |
10 |
| - for (const [flagKey, flag] of Object.entries(flags)) { |
11 |
| - // Hash flag key with salt |
12 |
| - const hashedKey = createHash('md5') |
13 |
| - .update(salt + flagKey) |
14 |
| - .digest('hex'); |
| 5 | +function hashAndEncode(jsonData: { precomputed: { response: any } }) { |
| 6 | + const salt = jsonData.precomputed.response.salt; |
| 7 | + const flags = jsonData.precomputed.response.flags; |
| 8 | + const bandits = jsonData.precomputed.response.bandits; |
| 9 | + // Process each flag |
| 10 | + for (const [flagKey, flag] of Object.entries(flags)) { |
| 11 | + // Hash flag key with salt |
| 12 | + const hashedKey = createHash('md5') |
| 13 | + .update(salt + flagKey) |
| 14 | + .digest('hex'); |
15 | 15 |
|
16 |
| - // Base64 encode specific fields |
17 |
| - // @ts-ignore |
18 |
| - flag.allocationKey = Buffer.from(flag.allocationKey).toString('base64'); |
19 |
| - // @ts-ignore |
20 |
| - flag.variationKey = Buffer.from(flag.variationKey).toString('base64'); |
21 |
| - // @ts-ignore |
22 |
| - flag.variationValue = Buffer.from(String(flag.variationValue)).toString('base64'); |
| 16 | + // Base64 encode specific fields |
| 17 | + // @ts-ignore |
| 18 | + flag.allocationKey = Buffer.from(flag.allocationKey).toString('base64'); |
| 19 | + // @ts-ignore |
| 20 | + flag.variationKey = Buffer.from(flag.variationKey).toString('base64'); |
| 21 | + // @ts-ignore |
| 22 | + flag.variationValue = Buffer.from(String(flag.variationValue)).toString( |
| 23 | + 'base64' |
| 24 | + ); |
23 | 25 |
|
24 |
| - // Process extraLogging if it has properties |
| 26 | + // Process extraLogging if it has properties |
| 27 | + // @ts-ignore |
| 28 | + if (flag.extraLogging && Object.keys(flag.extraLogging).length > 0) { |
| 29 | + const newExtraLogging = {}; |
| 30 | + // @ts-ignore |
| 31 | + for (const [key, value] of Object.entries(flag.extraLogging)) { |
| 32 | + const encodedKey = Buffer.from(key).toString('base64'); |
| 33 | + const encodedValue = Buffer.from(String(value)).toString('base64'); |
25 | 34 | // @ts-ignore
|
26 |
| - if (flag.extraLogging && Object.keys(flag.extraLogging).length > 0) { |
27 |
| - const newExtraLogging = {}; |
28 |
| - // @ts-ignore |
29 |
| - for (const [key, value] of Object.entries(flag.extraLogging)) { |
30 |
| - const encodedKey = Buffer.from(key).toString('base64'); |
31 |
| - const encodedValue = Buffer.from(String(value)).toString('base64'); |
32 |
| - // @ts-ignore |
33 |
| - newExtraLogging[encodedKey] = encodedValue; |
34 |
| - } |
35 |
| - // @ts-ignore |
36 |
| - flag.extraLogging = newExtraLogging; |
37 |
| - } |
38 |
| - |
39 |
| - // Replace the original flag key with hashed key |
40 |
| - flags[hashedKey] = flag; |
41 |
| - delete flags[flagKey]; |
| 35 | + newExtraLogging[encodedKey] = encodedValue; |
| 36 | + } |
| 37 | + // @ts-ignore |
| 38 | + flag.extraLogging = newExtraLogging; |
42 | 39 | }
|
43 | 40 |
|
44 |
| - // Process each bandit |
45 |
| - for (const [banditKey, bandit] of Object.entries(jsonData.precomputed.response.bandits)) { |
46 |
| - // Hash flag key with salt |
47 |
| - const hashedKey = createHash('md5') |
48 |
| - .update(salt + banditKey) |
49 |
| - .digest('hex'); |
| 41 | + // Replace the original flag key with hashed key |
| 42 | + flags[hashedKey] = flag; |
| 43 | + delete flags[flagKey]; |
| 44 | + } |
50 | 45 |
|
51 |
| - // Base64 encode specific fields |
52 |
| - // @ts-ignore |
53 |
| - bandit.banditKey = Buffer.from(bandit.banditKey).toString('base64'); |
54 |
| - // @ts-ignore |
55 |
| - bandit.action = Buffer.from(bandit.action).toString('base64'); |
56 |
| - // @ts-ignore |
57 |
| - bandit.modelVersion = Buffer.from(bandit.modelVersion).toString('base64'); |
58 |
| - |
59 |
| - // Process actionNumericAttributes |
| 46 | + // Process each bandit |
| 47 | + for (const [banditKey, bandit] of Object.entries( |
| 48 | + jsonData.precomputed.response.bandits |
| 49 | + )) { |
| 50 | + // Hash flag key with salt |
| 51 | + const hashedKey = createHash('md5') |
| 52 | + .update(salt + banditKey) |
| 53 | + .digest('hex'); |
| 54 | + |
| 55 | + // Base64 encode specific fields |
| 56 | + // @ts-ignore |
| 57 | + bandit.banditKey = Buffer.from(bandit.banditKey).toString('base64'); |
| 58 | + // @ts-ignore |
| 59 | + bandit.action = Buffer.from(bandit.action).toString('base64'); |
| 60 | + // @ts-ignore |
| 61 | + bandit.modelVersion = Buffer.from(bandit.modelVersion).toString('base64'); |
| 62 | + |
| 63 | + // Process actionNumericAttributes |
| 64 | + // @ts-ignore |
| 65 | + if ( |
| 66 | + bandit.actionNumericAttributes && |
| 67 | + Object.keys(bandit.actionNumericAttributes).length > 0 |
| 68 | + ) { |
| 69 | + const newNumericAttributes = {}; |
| 70 | + // @ts-ignore |
| 71 | + for (const [key, value] of Object.entries( |
| 72 | + bandit.actionNumericAttributes |
| 73 | + )) { |
| 74 | + const encodedKey = Buffer.from(key).toString('base64'); |
| 75 | + const encodedValue = Buffer.from(String(value)).toString('base64'); |
60 | 76 | // @ts-ignore
|
61 |
| - if (bandit.actionNumericAttributes && Object.keys(bandit.actionNumericAttributes).length > 0) { |
62 |
| - const newNumericAttributes = {}; |
63 |
| - // @ts-ignore |
64 |
| - for (const [key, value] of Object.entries(bandit.actionNumericAttributes)) { |
65 |
| - const encodedKey = Buffer.from(key).toString('base64'); |
66 |
| - const encodedValue = Buffer.from(String(value)).toString('base64'); |
67 |
| - // @ts-ignore |
68 |
| - newNumericAttributes[encodedKey] = encodedValue; |
69 |
| - } |
70 |
| - // @ts-ignore |
71 |
| - bandit.actionNumericAttributes = newNumericAttributes; |
72 |
| - } |
73 |
| - |
74 |
| - // Process actionCategoricalAttributes |
| 77 | + newNumericAttributes[encodedKey] = encodedValue; |
| 78 | + } |
| 79 | + // @ts-ignore |
| 80 | + bandit.actionNumericAttributes = newNumericAttributes; |
| 81 | + } |
| 82 | + |
| 83 | + // Process actionCategoricalAttributes |
| 84 | + // @ts-ignore |
| 85 | + if ( |
| 86 | + bandit.actionCategoricalAttributes && |
| 87 | + Object.keys(bandit.actionCategoricalAttributes).length > 0 |
| 88 | + ) { |
| 89 | + const newCategoricalAttributes = {}; |
| 90 | + // @ts-ignore |
| 91 | + for (const [key, value] of Object.entries( |
| 92 | + bandit.actionCategoricalAttributes |
| 93 | + )) { |
| 94 | + const encodedKey = Buffer.from(key).toString('base64'); |
| 95 | + const encodedValue = Buffer.from(String(value)).toString('base64'); |
75 | 96 | // @ts-ignore
|
76 |
| - if (bandit.actionCategoricalAttributes && Object.keys(bandit.actionCategoricalAttributes).length > 0) { |
77 |
| - const newCategoricalAttributes = {}; |
78 |
| - // @ts-ignore |
79 |
| - for (const [key, value] of Object.entries(bandit.actionCategoricalAttributes)) { |
80 |
| - const encodedKey = Buffer.from(key).toString('base64'); |
81 |
| - const encodedValue = Buffer.from(String(value)).toString('base64'); |
82 |
| - // @ts-ignore |
83 |
| - newCategoricalAttributes[encodedKey] = encodedValue; |
84 |
| - } |
85 |
| - // @ts-ignore |
86 |
| - bandit.actionCategoricalAttributes = newCategoricalAttributes; |
87 |
| - } |
88 |
| - |
89 |
| - // Replace the original bandit key with hashed key |
90 |
| - bandits[hashedKey] = bandit; |
91 |
| - delete bandits[banditKey]; |
| 97 | + newCategoricalAttributes[encodedKey] = encodedValue; |
| 98 | + } |
| 99 | + // @ts-ignore |
| 100 | + bandit.actionCategoricalAttributes = newCategoricalAttributes; |
92 | 101 | }
|
93 | 102 |
|
94 |
| - // Set obfuscated to true and stringify flags |
95 |
| - jsonData.precomputed.response.salt = salt; |
96 |
| - jsonData.precomputed.response.obfuscated = true; |
97 |
| - jsonData.precomputed.response = JSON.stringify(jsonData.precomputed.response); |
| 103 | + // Replace the original bandit key with hashed key |
| 104 | + bandits[hashedKey] = bandit; |
| 105 | + delete bandits[banditKey]; |
| 106 | + } |
| 107 | + |
| 108 | + // Set obfuscated to true and stringify flags |
| 109 | + jsonData.precomputed.response.salt = salt; |
| 110 | + jsonData.precomputed.response.obfuscated = true; |
| 111 | + jsonData.precomputed.response = JSON.stringify(jsonData.precomputed.response); |
98 | 112 |
|
99 |
| - return jsonData; |
| 113 | + return jsonData; |
100 | 114 | }
|
101 | 115 |
|
102 | 116 | const fs = require('fs');
|
103 | 117 | const inputFile = 'precomputed-v1-deobfuscated.json';
|
104 |
| -const outputFile ='precomputed-v1.json'; |
| 118 | +const outputFile = 'precomputed-v1.json'; |
105 | 119 |
|
106 | 120 | const jsonData = JSON.parse(fs.readFileSync(inputFile, 'utf8'));
|
107 | 121 | const encodedData = hashAndEncode(jsonData);
|
|
0 commit comments