|
1 | 1 | # NVDA add-on template SCONSTRUCT file |
2 | | -# Copyright (C) 2012-2021 Rui Batista, Noelia Martinez, Joseph Lee |
| 2 | +# Copyright (C) 2012-2023 Rui Batista, Noelia Martinez, Joseph Lee |
3 | 3 | # This file is covered by the GNU General Public License. |
4 | 4 | # See the file COPYING.txt for more details. |
5 | 5 |
|
@@ -75,8 +75,21 @@ def mdTool(env): |
75 | 75 | env['BUILDERS']['markdown'] = mdBuilder |
76 | 76 |
|
77 | 77 |
|
| 78 | +def validateVersionNumber(key, val, env): |
| 79 | + # Used to make sure version major.minor.patch are integers to comply with NV Access add-on store. |
| 80 | + # Ignore all this if version number is not specified, in which case json generator will validate this info. |
| 81 | + if val == "0.0.0": |
| 82 | + return |
| 83 | + versionNumber = val.split(".") |
| 84 | + if len(versionNumber) < 3: |
| 85 | + raise ValueError("versionNumber must have three parts (major.minor.patch)") |
| 86 | + if not all([part.isnumeric() for part in versionNumber]): |
| 87 | + raise ValueError("versionNumber (major.minor.patch) must be integers") |
| 88 | + |
| 89 | + |
78 | 90 | vars = Variables() |
79 | 91 | vars.Add("version", "The version of this build", buildVars.addon_info["addon_version"]) |
| 92 | +vars.Add("versionNumber", "Version number of the form major.minor.patch", "0.0.0", validateVersionNumber) |
80 | 93 | vars.Add(BoolVariable("dev", "Whether this is a daily development version", False)) |
81 | 94 | vars.Add("channel", "Update channel for this build", buildVars.addon_info["addon_updateChannel"]) |
82 | 95 |
|
@@ -155,9 +168,79 @@ def createAddonBundleFromPath(path, dest): |
155 | 168 | absPath = os.path.join(dir, filename) |
156 | 169 | if pathInBundle not in buildVars.excludedFiles: |
157 | 170 | z.write(absPath, pathInBundle) |
| 171 | + createAddonStoreJson(dest) |
158 | 172 | return dest |
159 | 173 |
|
160 | 174 |
|
| 175 | +def createAddonStoreJson(bundle): |
| 176 | + """Creates add-on store JSON file from an add-on package and manifest data.""" |
| 177 | + import json |
| 178 | + import hashlib |
| 179 | + # Set different json file names and version number properties based on version number parsing results. |
| 180 | + if env["versionNumber"] == "0.0.0": |
| 181 | + env["versionNumber"] = buildVars.addon_info["addon_version"] |
| 182 | + versionNumberParsed = env["versionNumber"].split(".") |
| 183 | + if all([part.isnumeric() for part in versionNumberParsed]): |
| 184 | + if len(versionNumberParsed) == 1: |
| 185 | + versionNumberParsed += ["0", "0"] |
| 186 | + elif len(versionNumberParsed) == 2: |
| 187 | + versionNumberParsed.append("0") |
| 188 | + else: |
| 189 | + versionNumberParsed = [] |
| 190 | + if len(versionNumberParsed): |
| 191 | + major, minor, patch = [int(part) for part in versionNumberParsed] |
| 192 | + jsonFilename = f'{buildVars.addon_info["addon_name"]}-{major}.{minor}.{patch}.json' |
| 193 | + else: |
| 194 | + jsonFilename = f'{buildVars.addon_info["addon_name"]}-{buildVars.addon_info["addon_version"]}.json' |
| 195 | + major, minor, patch = 0, 0, 0 |
| 196 | + print('Generating % s' % jsonFilename) |
| 197 | + sha256 = hashlib.sha256() |
| 198 | + with open(bundle, "rb") as f: |
| 199 | + for byte_block in iter(lambda: f.read(65536), b""): |
| 200 | + sha256.update(byte_block) |
| 201 | + hashValue = sha256.hexdigest() |
| 202 | + minimumNVDAVersion = buildVars.addon_info["addon_minimumNVDAVersion"].split(".") |
| 203 | + minMajor, minMinor = minimumNVDAVersion[:2] |
| 204 | + minPatch = minimumNVDAVersion[-1] if len(minimumNVDAVersion) == 3 else "0" |
| 205 | + lastTestedNVDAVersion = buildVars.addon_info["addon_lastTestedNVDAVersion"].split(".") |
| 206 | + lastTestedMajor, lastTestedMinor = lastTestedNVDAVersion[:2] |
| 207 | + lastTestedPatch = lastTestedNVDAVersion[-1] if len(lastTestedNVDAVersion) == 3 else "0" |
| 208 | + channel = buildVars.addon_info["addon_updateChannel"] |
| 209 | + if channel is None: |
| 210 | + channel = "stable" |
| 211 | + addonStoreEntry = { |
| 212 | + "addonId": buildVars.addon_info["addon_name"], |
| 213 | + "displayName": buildVars.addon_info["addon_summary"], |
| 214 | + "URL": "", |
| 215 | + "description": buildVars.addon_info["addon_description"], |
| 216 | + "sha256": hashValue, |
| 217 | + "homepage": buildVars.addon_info["addon_url"], |
| 218 | + "addonVersionName": buildVars.addon_info["addon_version"], |
| 219 | + "addonVersionNumber": { |
| 220 | + "major": major, |
| 221 | + "minor": minor, |
| 222 | + "patch": patch |
| 223 | + }, |
| 224 | + "minNVDAVersion": { |
| 225 | + "major": int(minMajor), |
| 226 | + "minor": int(minMinor), |
| 227 | + "patch": int(minPatch) |
| 228 | + }, |
| 229 | + "lastTestedVersion": { |
| 230 | + "major": int(lastTestedMajor), |
| 231 | + "minor": int(lastTestedMinor), |
| 232 | + "patch": int(lastTestedPatch) |
| 233 | + }, |
| 234 | + "channel": channel, |
| 235 | + "publisher": "", |
| 236 | + "sourceURL": buildVars.addon_info["addon_sourceURL"], |
| 237 | + "license": buildVars.addon_info["addon_license"], |
| 238 | + "licenseURL": buildVars.addon_info["addon_licenseURL"], |
| 239 | + } |
| 240 | + with open(jsonFilename, "w") as addonStoreJson: |
| 241 | + json.dump(addonStoreEntry, addonStoreJson, indent="\t") |
| 242 | + |
| 243 | + |
161 | 244 | def generateManifest(source, dest): |
162 | 245 | addon_info = buildVars.addon_info |
163 | 246 | with codecs.open(source, "r", "utf-8") as f: |
|
0 commit comments