def loadPreset(self): # load conf from session if available loaded = False if self.vars.action is not None: # press solve, load or save button if self.vars.action in ['Update', 'Create']: # store the changes in case the form won't be accepted presetDict = self.genJsonFromParams(self.vars) self.session.presets['presetDict'] = presetDict params = PresetLoader.factory(presetDict).params loaded = True elif self.vars.action in ['Load']: # nothing to load, we'll load the new params file with the load form code pass else: # no forms button pressed if self.session.presets['presetDict'] is not None: params = PresetLoader.factory( self.session.presets['presetDict']).params loaded = True if not loaded: presetPath = '{}/{}.json'.format( getPresetDir(self.session.presets['preset']), self.session.presets['preset']) params = PresetLoader.factory(presetPath).params return params
def presetWebService(self): # web service to get the content of the preset file if self.vars.preset == None: raiseHttp(400, "Missing parameter preset") preset = self.vars.preset if IS_ALPHANUMERIC()(preset)[1] is not None: raiseHttp(400, "Preset name must be alphanumeric") if IS_LENGTH(maxsize=32, minsize=1)(preset)[1] is not None: raiseHttp(400, "Preset name must be between 1 and 32 characters") print("presetWebService: preset={}".format(preset)) fullPath = '{}/{}.json'.format(getPresetDir(preset), preset) # check that the presets file exists if os.path.isfile(fullPath): # load it try: params = PresetLoader.factory(fullPath).params except Exception as e: raiseHttp(400, "Can't load the preset") params = json.dumps(params) return params else: raiseHttp(400, "Preset not found")
def loadPreset(self, presetFileName): presetLoader = PresetLoader.factory(presetFileName) presetLoader.load() self.smbm.createKnowsFunctions() if self.log.getEffectiveLevel() == logging.DEBUG: presetLoader.printToScreen()
def tryRemainingLocs(self): # use preset which knows every techniques to test the remaining locs to # find which technique could allow to continue the seed locations = self.majorLocations if self.majorsSplit == 'Full' else self.majorLocations + self.minorLocations # instanciate a new smbool manager to reset the cache self.smbm = SMBoolManager() presetFileName = os.path.expanduser('~/RandomMetroidSolver/standard_presets/solution.json') presetLoader = PresetLoader.factory(presetFileName) presetLoader.load() self.smbm.createKnowsFunctions() self.areaGraph.getAvailableLocations(locations, self.smbm, infinity, self.lastAP) return [loc for loc in locations if loc.difficulty.bool == True]
def getSkillLevelBarData(self, preset): result = {'name': preset} try: params = PresetLoader.factory('{}/{}.json'.format( getPresetDir(preset), preset)).params result['custom'] = (preset, params['score']) # add stats on the preset result['knowsKnown'] = len([ know for know in params['Knows'] if params['Knows'][know][0] == True ]) except: result['custom'] = (preset, 'N/A') result['knowsKnown'] = 'N/A' # get score of standard presets standardScores = self.cache.ram('standardScores', lambda: dict(), time_expire=None) if not standardScores: for preset in [ 'newbie', 'casual', 'regular', 'veteran', 'expert', 'master', 'samus' ]: score = PresetLoader.factory('{}/{}.json'.format( getPresetDir(preset), preset)).params['score'] standardScores[preset] = score result['standards'] = standardScores with DB() as db: result['lastAction'] = db.getPresetLastActionDate( result['custom'][0]) # TODO: normalize result (or not ?) return result
csvOut.write("Diff_preset;Item_set;ok;diff\n") print("*** " + name + " ***") for presetName, diffPreset in Settings.bossesDifficultyPresets[ name].items(): print("** Diff preset :" + presetName) Settings.bossesDifficulty[name] = diffPreset print(str(Settings.bossesDifficulty[name])) for setName, itemFunc in itemSets[name].items(): itemSet = itemFunc() print('* Item set ' + setName) print(str(itemSet)) sm.resetItems() sm.addItems(itemSet) d = diffFunction() print('---> ' + str(d) + "\n") csvOut.write(presetName + ";" + setName + ";" + str(d[0]) + ";" + str(d[1]) + "\n") print("\n") if __name__ == "__main__": if len(sys.argv) >= 2: params = sys.argv[1] PresetLoader.factory(params).load() h = Helpers(sm) boss('Kraid', h.enoughStuffsKraid) boss('Phantoon', h.enoughStuffsPhantoon) boss('Draygon', h.enoughStuffsDraygon) boss('Ridley', h.enoughStuffsRidley) boss('MotherBrain', h.enoughStuffsMotherbrain)
def skillPresetActionWebService(self): print("skillPresetActionWebService call") if self.session.presets is None: self.session.presets = {} # for create/update, not load (ok, msg) = self.validatePresetsParams(self.vars.action) if not ok: raiseHttp(400, json.dumps(msg)) else: self.session.presets['currentTab'] = self.vars.currenttab if self.vars.action == 'Create': preset = self.vars.presetCreate else: preset = self.vars.preset # check if the presets file already exists password = self.vars['password'] password = password.encode('utf-8') passwordSHA256 = hashlib.sha256(password).hexdigest() fullPath = '{}/{}.json'.format(getPresetDir(preset), preset) if os.path.isfile(fullPath): # load it end = False try: oldParams = PresetLoader.factory(fullPath).params except Exception as e: msg = "UC:Error loading the preset {}: {}".format(preset, e) end = True if end == True: raiseHttp(400, json.dumps(msg)) # check if password match if 'password' in oldParams and passwordSHA256 == oldParams[ 'password']: # update the presets file paramsDict = self.genJsonFromParams(self.vars) paramsDict['password'] = passwordSHA256 try: PresetLoader.factory(paramsDict).dump(fullPath) with DB() as db: db.addPresetAction(preset, 'update') self.updatePresetsSession() msg = "Preset {} updated".format(preset) return json.dumps(msg) except Exception as e: msg = "Error writing the preset {}: {}".format(preset, e) raiseHttp(400, json.dumps(msg)) else: msg = "Password mismatch with existing presets file {}".format( preset) raiseHttp(400, json.dumps(msg)) else: # prevent a malicious user from creating presets in a loop if not self.maxPresetsReach(): # write the presets file paramsDict = self.genJsonFromParams(self.vars) paramsDict['password'] = passwordSHA256 try: PresetLoader.factory(paramsDict).dump(fullPath) with DB() as db: db.addPresetAction(preset, 'create') self.updatePresetsSession() # add new preset in cache (stdPresets, tourPresets, comPresets) = loadPresetsList(self.cache) comPresets.append(preset) comPresets.sort(key=lambda v: v.upper()) msg = "Preset {} created".format(preset) return json.dumps(msg) except Exception as e: msg = "Error writing the preset {}: {}".format(preset, e) raiseHttp(400, json.dumps(msg)) redirect(URL(r=request, f='presets')) else: msg = "Sorry, maximum number of presets reached, can't add more" raiseHttp(400, json.dumps(msg))
def run(self): self.initPresetsSession() # use web2py builtin cache to avoid recomputing the hardrooms requirements hardRooms = self.cache.ram('hardRooms', lambda: dict(), time_expire=None) if len(hardRooms) == 0: self.computeHardRooms(hardRooms) hellRuns = self.cache.ram('hellRuns', lambda: dict(), time_expire=None) if len(hellRuns) == 0: self.computeHellruns(hellRuns) if self.vars.action is not None: (ok, msg) = self.validatePresetsParams(self.vars.action) if not ok: self.session.flash = msg redirect(URL(r=self.request, f='presets')) else: self.session.presets['currentTab'] = self.vars.currenttab preset = self.vars.preset # in web2py.js, in disableElement, remove 'working...' to have action with correct value if self.vars.action == 'Load': # check that the presets file exists fullPath = '{}/{}.json'.format(getPresetDir(preset), preset) if os.path.isfile(fullPath): # load it try: params = PresetLoader.factory(fullPath).params self.updatePresetsSession() self.session.presets["presetDict"] = None except Exception as e: self.session.flash = "L:Error loading the preset {}: {}".format( preset, e) else: self.session.flash = "Presets file not found: {}".format( fullPath) redirect(URL(r=self.request, f='presets')) # load conf from session if available error = False try: params = self.loadPreset() except Exception as e: self.session.presets['preset'] = 'regular' self.session.flash = "S:Error loading the preset: {}".format(e) error = True if error == True: redirect(URL(r=request, f='presets')) # load presets list (stdPresets, tourPresets, comPresets) = loadPresetsList(self.cache) # add missing knows/settings completePreset(params) # compute score for skill bar skillBarData = self.getSkillLevelBarData( self.session.presets['preset']) # send values to view return dict(desc=Knows.desc, difficulties=diff2text, categories=Knows.categories, settings=params['Settings'], knows=params['Knows'], easy=easy, medium=medium, hard=hard, harder=harder, hardcore=hardcore, mania=mania, controller=params['Controller'], stdPresets=stdPresets, tourPresets=tourPresets, comPresets=comPresets, skillBarData=skillBarData, hardRooms=hardRooms, hellRuns=hellRuns)
if argDict[arg] not in okValues: argDict[arg] = value forcedArgs[webArg if webArg != None else arg] = webValue if webValue != None else value print(msg) optErrMsgs.append(msg) # if rando preset given, load it first if args.randoPreset != None: preset = loadRandoPreset(args.randoPreset, args) # use the skill preset from the rando preset if preset is not None and args.paramsFileName is None: args.paramsFileName = '{}/{}/{}.json'.format(appDir, getPresetDir(preset), preset) # if diff preset given, load it if args.paramsFileName is not None: PresetLoader.factory(args.paramsFileName).load() preset = os.path.splitext(os.path.basename(args.paramsFileName))[0] if args.preset is not None: preset = args.preset else: preset = 'default' logger.debug("preset: {}".format(preset)) # if no seed given, choose one if args.seed == 0: seed = random.randrange(sys.maxsize) else: seed = args.seed logger.debug("seed: {}".format(seed))
return [ os.path.join(directory, f) for f in os.listdir(directory) if f != 'solution.json' ] if __name__ == "__main__": if len(sys.argv) != 2: sys.exit() presets = loadPresetsList(sys.argv[1]) for preset in presets: print(preset) loader = PresetLoader.factory(preset) # check # for know in ['GravLessLevel1', 'GravLessLevel3']: #['SuitlessOuterMaridia', 'SuitlessSandpit', 'GravLessLevel1', 'GravLessLevel3']: # if know in loader.params['Knows']: # print "{} in {}: {}".format(know, preset, loader.params['Knows'][know]) # else: # print "{} not in {}".format(know, preset) for know in ['GravLessLevel1', 'GravLessLevel3']: if know in loader.params['Knows']: del loader.params['Knows'][know] newNames = { 'SuitlessOuterMaridia': 'GravLessLevel1', 'SuitlessSandpit': 'GravLessLevel3'
def customWebService(self): print("customWebService") # check validity of all parameters switchs = [ 'itemsounds', 'spinjumprestart', 'rando_speed', 'elevators_speed', 'fast_doors', 'AimAnyButton', 'max_ammo_display', 'supermetroid_msu1', 'Infinite_Space_Jump', 'refill_before_save', 'customSpriteEnable', 'customItemsEnable', 'noSpinAttack', 'customShipEnable', 'remove_itemsounds', 'remove_elevators_speed', 'remove_fast_doors', 'remove_Infinite_Space_Jump', 'remove_rando_speed', 'remove_spinjumprestart', 'gamepadMapping', 'widescreen', 'hell', 'lava_acid_physics' ] others = [ 'colorsRandomization', 'suitsPalettes', 'beamsPalettes', 'tilesPalettes', 'enemiesPalettes', 'bossesPalettes', 'minDegree', 'maxDegree', 'invert', 'hellrun_rate', 'etanks' ] validateWebServiceParams(self.request, switchs, [], [], others, isJson=True) if self.vars.customSpriteEnable == 'on': if self.vars.customSprite == 'random': for sprite in self.vars.customSpriteMultiSelect.split(','): if sprite not in customSprites: raiseHttp(400, "Wrong value for customSpriteMultiSelect", True) elif self.vars.customSprite not in customSprites: raiseHttp(400, "Wrong value for customSprite", True) if self.vars.customShipEnable == 'on': if self.vars.customShip == 'random': for ship in self.vars.customShipMultiSelect.split(','): if ship not in customShips: raiseHttp(400, "Wrong value for customShipMultiSelect", True) elif self.vars.customShip not in customShips: raiseHttp(400, "Wrong value for customShip", True) if self.vars.music not in [ "Don't touch", "Disable", "Randomize", "Customize", "Restore" ]: raiseHttp(400, "Wrong value for music", True) if self.session.customizer == None: self.session.customizer = {} # update session self.session.customizer[ 'colorsRandomization'] = self.vars.colorsRandomization self.session.customizer['suitsPalettes'] = self.vars.suitsPalettes self.session.customizer['beamsPalettes'] = self.vars.beamsPalettes self.session.customizer['tilesPalettes'] = self.vars.tilesPalettes self.session.customizer['enemiesPalettes'] = self.vars.enemiesPalettes self.session.customizer['bossesPalettes'] = self.vars.bossesPalettes self.session.customizer['minDegree'] = self.vars.minDegree self.session.customizer['maxDegree'] = self.vars.maxDegree self.session.customizer['invert'] = self.vars.invert self.session.customizer['globalShift'] = self.vars.globalShift self.session.customizer[ 'customSpriteEnable'] = self.vars.customSpriteEnable self.session.customizer['customSprite'] = self.vars.customSprite if self.vars.customSprite == 'random': self.session.customizer[ 'customSpriteMultiSelect'] = self.vars.customSpriteMultiSelect.split( ',') self.session.customizer[ 'customItemsEnable'] = self.vars.customItemsEnable self.session.customizer['noSpinAttack'] = self.vars.noSpinAttack self.session.customizer[ 'customShipEnable'] = self.vars.customShipEnable self.session.customizer['customShip'] = self.vars.customShip if self.vars.customShip == 'random': self.session.customizer[ 'customShipMultiSelect'] = self.vars.customShipMultiSelect.split( ',') self.session.customizer['gamepadMapping'] = self.vars.gamepadMapping if self.session.customizer['gamepadMapping'] == "on": self.session.customizer['preset'] = self.vars.preset self.session.customizer['itemsounds'] = self.vars.itemsounds self.session.customizer['spinjumprestart'] = self.vars.spinjumprestart self.session.customizer['rando_speed'] = self.vars.rando_speed self.session.customizer['elevators_speed'] = self.vars.elevators_speed self.session.customizer['fast_doors'] = self.vars.fast_doors self.session.customizer[ 'Infinite_Space_Jump'] = self.vars.Infinite_Space_Jump self.session.customizer[ 'refill_before_save'] = self.vars.refill_before_save self.session.customizer['widescreen'] = self.vars.widescreen self.session.customizer['AimAnyButton'] = self.vars.AimAnyButton self.session.customizer[ 'max_ammo_display'] = self.vars.max_ammo_display self.session.customizer[ 'supermetroid_msu1'] = self.vars.supermetroid_msu1 self.session.customizer[ 'remove_itemsounds'] = self.vars.remove_itemsounds self.session.customizer[ 'remove_elevators_speed'] = self.vars.remove_elevators_speed self.session.customizer[ 'remove_fast_doors'] = self.vars.remove_fast_doors self.session.customizer[ 'remove_spinjumprestart'] = self.vars.remove_spinjumprestart self.session.customizer[ 'remove_Infinite_Space_Jump'] = self.vars.remove_Infinite_Space_Jump self.session.customizer[ 'remove_rando_speed'] = self.vars.remove_rando_speed self.session.customizer[ 'lava_acid_physics'] = self.vars.lava_acid_physics self.session.customizer['hell'] = self.vars.hell self.session.customizer['hellrun_rate'] = self.vars.hellrun_rate self.session.customizer['etanks'] = self.vars.etanks self.session.customizer['music'] = self.vars.music if self.vars.music == 'Customize': musics = self.loadMusics() for song, songId in musics["_list"]: self.session.customizer[songId] = self.vars[songId] # when beam doors patch is detected, don't randomize blue door palette no_blue_door_palette = self.vars.no_blue_door_palette # call the randomizer (fd, jsonFileName) = tempfile.mkstemp() params = [ getPythonExec(), os.path.expanduser("~/RandomMetroidSolver/randomizer.py"), '--output', jsonFileName, '--patchOnly' ] if self.vars.itemsounds == 'on': params += ['-c', 'itemsounds.ips'] if self.vars.elevators_speed == 'on': params += ['-c', 'elevators_speed.ips'] if self.vars.fast_doors == 'on': params += ['-c', 'fast_doors.ips'] if self.vars.spinjumprestart == 'on': params += ['-c', 'spinjumprestart.ips'] if self.vars.rando_speed == 'on': params += ['-c', 'rando_speed.ips'] if self.vars.AimAnyButton == 'on': params += ['-c', 'AimAnyButton.ips'] if self.vars.max_ammo_display == 'on': params += ['-c', 'max_ammo_display.ips'] if self.vars.supermetroid_msu1 == 'on': params += ['-c', 'supermetroid_msu1.ips'] if self.vars.Infinite_Space_Jump == 'on': params += ['-c', 'Infinite_Space_Jump'] if self.vars.refill_before_save == 'on': params += ['-c', 'refill_before_save.ips'] if self.vars.widescreen == 'on': params += ['-c', 'widescreen.ips'] if self.vars.remove_itemsounds == 'on': params += ['-c', 'remove_itemsounds.ips'] if self.vars.remove_elevators_speed == 'on': params += ['-c', 'remove_elevators_speed.ips'] if self.vars.remove_fast_doors == 'on': params += ['-c', 'remove_fast_doors.ips'] if self.vars.remove_rando_speed == 'on': params += ['-c', 'remove_rando_speed.ips'] if self.vars.remove_spinjumprestart == 'on': params += ['-c', 'remove_spinjumprestart.ips'] if self.vars.remove_Infinite_Space_Jump == 'on': params += ['-c', 'remove_Infinite_Space_Jump.ips'] if self.vars.music == 'Disable': params += ['-c', 'No_Music'] if self.vars.music == 'Randomize': params += ['-c', 'random_music.ips'] if self.vars.music == 'Restore': params += ['-c', 'vanilla_music.ips'] if self.vars.lava_acid_physics == 'on': params += ['-c', 'lava_acid_physics.ips'] if self.vars.hell == 'on': params += ['-c', 'hell.ips'] if self.vars.hellrun_rate != 'off': params += ['--hellrun', self.vars.hellrun_rate] if self.vars.etanks != 'off': params += ['--etanks', self.vars.etanks] if self.vars.colorsRandomization == 'on': params.append('--palette') if self.vars.suitsPalettes == 'off': params.append('--no_shift_suit_palettes') if self.vars.beamsPalettes == 'off': params.append('--no_shift_beam_palettes') if self.vars.tilesPalettes == 'off': params.append('--no_shift_tileset_palette') if self.vars.enemiesPalettes == 'off': params.append('--no_shift_enemy_palettes') if self.vars.bossesPalettes == 'off': params.append('--no_shift_boss_palettes') if self.vars.globalShift == 'off': params.append('--no_global_shift') params.append('--individual_suit_shift') params.append('--individual_tileset_shift') params.append('--no_match_ship_and_power') params += [ '--min_degree', self.vars.minDegree, '--max_degree', self.vars.maxDegree ] if self.vars.invert == 'on': params.append('--invert') if no_blue_door_palette == 'on': params.append('--no_blue_door_palette') if self.vars.customSpriteEnable == 'on': if self.vars.customSprite == 'random': sprite = random.choice( self.session.customizer['customSpriteMultiSelect']) else: sprite = self.vars.customSprite params += ['--sprite', "{}.ips".format(sprite)] with DB() as db: db.addSprite(sprite) if self.vars.customItemsEnable == 'on': params.append('--customItemNames') if self.vars.noSpinAttack == 'on': params.append('--no_spin_attack') if self.vars.customShipEnable == 'on': if self.vars.customShip == 'random': ship = random.choice( self.session.customizer['customShipMultiSelect']) else: ship = self.vars.customShip params += ['--ship', "{}.ips".format(ship)] with DB() as db: db.addShip(ship) if customShips[ship].get("hideSamus", False): params += ['-c', 'custom_ship.ips'] if customShips[ship].get("showSamusAtTakeoff", False): params += ['-c', 'Ship_Takeoff_Disable_Hide_Samus'] if self.vars.seedKey != None: with DB() as db: seedIpsInfo = db.getSeedIpsInfo(self.vars.seedKey) print("seedIpsInfo: {}".format(seedIpsInfo)) if seedIpsInfo == None or len(seedIpsInfo) == 0: raiseHttp(400, json.dumps("Can't get seed info")) (uploadStatus, fileName) = seedIpsInfo[0] if uploadStatus not in ['local', 'pending', 'uploaded']: raiseHttp(400, json.dumps("Seed is not available")) ipsFileName = os.path.join(localIpsDir, self.vars.seedKey, fileName.replace('sfc', 'ips')) params += ['--seedIps', ipsFileName] if self.vars.music == "Customize": musics = self.loadMusics() customMusic = { 'params': { "varia": self.vars.varia == "true", "area": self.vars.area == "true", "boss": self.vars.boss == "true" }, 'mapping': {} } for song, songId in musics["_list"]: newSong = self.vars[songId] if newSong not in musics: raiseHttp(400, "unknown song for {}".format(song)) if newSong != song: customMusic['mapping'][song] = newSong (fd2, jsonMusicFileName) = tempfile.mkstemp() with open(jsonMusicFileName, 'w') as musicFile: json.dump(customMusic, musicFile) params += ['--music', jsonMusicFileName] if self.vars.gamepadMapping == "on": preset = self.vars.preset fullPath = '{}/{}.json'.format(getPresetDir(preset), preset) controlMapping = PresetLoader.factory( fullPath).params['Controller'] (custom, controlParam) = getCustomMapping(controlMapping) if custom == True: print("apply custom gamepad mapping from preset: {}".format( self.vars.preset)) params += ['--controls', controlParam] if "Moonwalk" in controlMapping and controlMapping[ "Moonwalk"] == True: params.append('--moonwalk') print("before calling: {}".format(params)) start = datetime.now() ret = subprocess.call(params) end = datetime.now() duration = (end - start).total_seconds() print("ret: {}, duration: {}s".format(ret, duration)) if self.vars.music == "Customize": os.close(fd2) os.remove(jsonMusicFileName) if ret == 0: with open(jsonFileName) as jsonFile: data = json.load(jsonFile) os.close(fd) os.remove(jsonFileName) return json.dumps(data) else: # extract error from json try: with open(jsonFileName) as jsonFile: msg = json.load(jsonFile)['errorMsg'] except: msg = "customizerWebService: something wrong happened" os.close(fd) os.remove(jsonFileName) raiseHttp(400, json.dumps(msg))
def webService(self): # web service to compute a new random (returns json string) print("randomizerWebService") # check validity of all parameters switchs = ['suitsRestriction', 'hideItems', 'strictMinors', 'areaRandomization', 'areaLayout', 'lightAreaRandomization', 'doorsColorsRando', 'allowGreyDoors', 'escapeRando', 'removeEscapeEnemies', 'bossRandomization', 'minimizer', 'funCombat', 'funMovement', 'funSuits', 'layoutPatches', 'variaTweaks', 'nerfedCharge', 'itemsounds', 'elevators_speed', 'fast_doors', 'spinjumprestart', 'rando_speed', 'animals', 'No_Music', 'random_music', 'Infinite_Space_Jump', 'refill_before_save', 'hud', "scavRandomized"] quantities = ['missileQty', 'superQty', 'powerBombQty', 'minimizerQty', "scavNumLocs"] multis = ['majorsSplit', 'progressionSpeed', 'progressionDifficulty', 'morphPlacement', 'energyQty', 'startLocation', 'gravityBehaviour'] others = ['complexity', 'paramsFileTarget', 'seed', 'preset', 'maxDifficulty', 'objective', 'tourian'] validateWebServiceParams(self.request, switchs, quantities, multis, others, isJson=True) # randomize db = DB() id = db.initRando() # race mode useRace = False if self.vars.raceMode == 'on': magic = self.getMagic() useRace = True (fd1, presetFileName) = tempfile.mkstemp() presetFileName += '.json' (fd2, jsonFileName) = tempfile.mkstemp() (fd3, jsonRandoPreset) = tempfile.mkstemp() print("randomizerWebService, params validated") for var in self.vars: print("{}: {}".format(var, self.vars[var])) with open(presetFileName, 'w') as presetFile: presetFile.write(self.vars.paramsFileTarget) if self.vars.seed == '0': self.vars.seed = str(random.randrange(sys.maxsize)) preset = self.vars.preset params = [getPythonExec(), os.path.expanduser("~/RandomMetroidSolver/randomizer.py"), '--runtime', '20', '--output', jsonFileName, '--param', presetFileName, '--preset', preset] if useRace == True: params += ['--race', str(magic)] # load content of preset to get controller mapping try: controlMapping = PresetLoader.factory(presetFileName).params['Controller'] except Exception as e: os.close(fd1) os.remove(presetFileName) os.close(fd2) os.remove(jsonFileName) os.close(fd3) os.remove(jsonRandoPreset) return json.dumps({"status": "NOK", "errorMsg": "randomizerWebService: can't load the preset"}) (custom, controlParam) = getCustomMapping(controlMapping) if custom == True: params += ['--controls', controlParam] if "Moonwalk" in controlMapping and controlMapping["Moonwalk"] == True: params.append('--moonwalk') randoPresetDict = {var: self.vars[var] for var in self.vars if var != 'paramsFileTarget'} # set multi select as list as expected in a rando preset for var, value in randoPresetDict.items(): if 'MultiSelect' in var: randoPresetDict[var] = value.split(',') randoPresetDict['objective'] = self.vars.objective.split(',') with open(jsonRandoPreset, 'w') as randoPresetFile: json.dump(randoPresetDict, randoPresetFile) params += ['--randoPreset', jsonRandoPreset] db.addRandoParams(id, self.vars) print("before calling: {}".format(' '.join(params))) start = datetime.now() ret = subprocess.call(params) end = datetime.now() duration = (end - start).total_seconds() print("ret: {}, duration: {}s".format(ret, duration)) if ret == 0: with open(jsonFileName) as jsonFile: locsItems = json.load(jsonFile) # check if an info message has been returned msg = '' if len(locsItems['errorMsg']) > 0: msg = locsItems['errorMsg'] if msg[0] == '\n': msg = msg[1:] locsItems['errorMsg'] = msg.replace('\n', '<br/>') db.addRandoResult(id, ret, duration, msg) if "forcedArgs" in locsItems: db.updateRandoParams(id, locsItems["forcedArgs"]) # store ips in local directory guid = str(uuid.uuid4()) if self.storeLocalIps(guid, locsItems["fileName"], locsItems["ips"]): db.addRandoUploadResult(id, guid, locsItems["fileName"]) locsItems['seedKey'] = guid db.close() os.close(fd1) os.remove(presetFileName) os.close(fd2) os.remove(jsonFileName) os.close(fd3) os.remove(jsonRandoPreset) locsItems["status"] = "OK" return json.dumps(locsItems) else: # extract error from json try: with open(jsonFileName) as jsonFile: msg = json.load(jsonFile)['errorMsg'] if msg[0] == '\n': msg = msg[1:] msg = msg.replace('\n', '<br/>') except: msg = "randomizerWebService: something wrong happened" db.addRandoResult(id, ret, duration, msg) db.close() os.close(fd1) os.remove(presetFileName) os.close(fd2) os.remove(jsonFileName) os.close(fd3) os.remove(jsonRandoPreset) return json.dumps({"status": "NOK", "errorMsg": msg})
def run(self): self.initExtStatsSession() if self.vars.action == 'Load': (ok, msg) = self.validateExtStatsParams() if not ok: self.session.flash = msg redirect(URL(r=self.request, f='extStats')) self.updateExtStatsSession() skillPreset = self.vars.preset randoPreset = self.vars.randoPreset # load rando preset to get majors split fullPath = 'rando_presets/{}.json'.format(randoPreset) if not os.path.isfile(fullPath): raiseHttp(400, "Unknown rando preset: {}".format(e)) try: with open(fullPath) as jsonFile: randoPresetContent = json.load(jsonFile) except Exception as e: raiseHttp(400, "Can't load the rando preset: {}".format(e)) majorsSplit = randoPresetContent["majorsSplit"] # load skill preset fullPath = '{}/{}.json'.format(getPresetDir(skillPreset), skillPreset) try: skillPresetContent = PresetLoader.factory(fullPath).params completePreset(skillPresetContent) except Exception as e: raiseHttp(400, "Error loading the skill preset: {}".format(e)) with DB() as db: (itemsStats, techniquesStats, difficulties, solverStatsRaw) = db.getExtStat(skillPreset, randoPreset) solverStats = {} if "avgLocs" in solverStatsRaw: solverStats["avgLocs"] = transformStats( solverStatsRaw["avgLocs"]) solverStats["avgLocs"].insert( 0, ['Available locations', 'Percentage']) if "open14" in solverStatsRaw: open14 = transformStats(solverStatsRaw["open14"]) open24 = transformStats(solverStatsRaw["open24"]) open34 = transformStats(solverStatsRaw["open34"]) open44 = transformStats(solverStatsRaw["open44"]) solverStats["open"] = zipStats( [open14, open24, open34, open44]) solverStats["open"].insert(0, [ 'Collected items', '1/4 locations available', '2/4 locations available', '3/4 locations available', '4/4 locations available' ]) # check that all items are present in the stats: nbItems = 19 nbLocs = 109 if itemsStats and len(itemsStats) != nbItems: for i, item in enumerate([ 'Bomb', 'Charge', 'Grapple', 'Gravity', 'HiJump', 'Ice', 'Missile', 'Morph', 'Plasma', 'PowerBomb', 'ScrewAttack', 'SpaceJump', 'Spazer', 'SpeedBooster', 'SpringBall', 'Super', 'Varia', 'Wave', 'XRayScope' ]): if itemsStats[i][1] != item: itemsStats.insert(i, [itemsStats[0][0], item] + [0] * nbLocs) else: itemsStats = None techniquesStats = None difficulties = None solverStats = None skillPresetContent = None majorsSplit = None (randoPresets, tourRandoPresets) = loadRandoPresetsList(self.cache, filter=True) (stdPresets, tourPresets, comPresets) = loadPresetsList(self.cache) return dict(stdPresets=stdPresets, tourPresets=tourPresets, randoPresets=randoPresets, tourRandoPresets=tourRandoPresets, itemsStats=itemsStats, techniquesStats=techniquesStats, categories=Knows.categories, knowsDesc=Knows.desc, skillPresetContent=skillPresetContent, locations=locations, majorsSplit=majorsSplit, difficulties=difficulties, solverStats=solverStats)