public void Serialize() { var state = new RankingState1(); var avatarAddress = new PrivateKey().ToAddress(); state.UpdateRankingMap(avatarAddress); var serialized = state.Serialize(); var des = new RankingState1((Dictionary)serialized); Assert.Equal(Addresses.Ranking, des.address); Assert.Contains(des.RankingMap, m => m.Value.Contains(avatarAddress)); }
public void UpdateFromQuestRewardDeterministic() { var rankingState = new RankingState1(); Address avatarAddress = new PrivateKey().ToAddress(); Address agentAddress = new PrivateKey().ToAddress(); var avatarState = new AvatarState( avatarAddress, agentAddress, 0, _tableSheets.GetAvatarSheets(), new GameConfigState(), rankingState.UpdateRankingMap(avatarAddress)); var itemIds = avatarState.questList.OfType <ItemTypeCollectQuest>().First().ItemIds; var map = new Dictionary <int, int>() { [400000] = 1, [302002] = 1, [302003] = 1, [302001] = 1, [306023] = 1, [302000] = 1, }; var serialized = (Dictionary)avatarState.questList.OfType <WorldQuest>().First().Serialize(); serialized = serialized.SetItem("reward", new Nekoyume.Model.Quest.QuestReward(map).Serialize()); var quest = new WorldQuest(serialized); avatarState.UpdateFromQuestReward(quest, _tableSheets.MaterialItemSheet); Assert.Equal( avatarState.questList.OfType <ItemTypeCollectQuest>().First().ItemIds, new List <int>() { 302000, 302001, 302002, 302003, 306023, } ); }
public void Deterministic_Between_SerializeV1_And_SerializeV1_With_Deterministic_Problem() { var state = new RankingState1(); for (var i = 0; i < 1000; i++) { state.UpdateRankingMap(new PrivateKey().ToAddress()); } var serializedV1 = state.Serialize(); var serializedV1WithDeterministicProblem = SerializeV1_With_Deterministic_Problem(state); Assert.Equal(serializedV1WithDeterministicProblem, serializedV1); var deserialized = new RankingState1((Bencodex.Types.Dictionary)serializedV1); var deserializedV1 = new RankingState1((Bencodex.Types.Dictionary)serializedV1WithDeterministicProblem); serializedV1 = deserialized.Serialize(); serializedV1WithDeterministicProblem = deserializedV1.Serialize(); Assert.Equal(serializedV1WithDeterministicProblem, serializedV1); }
public override IAccountStateDelta Execute(IActionContext context) { IActionContext ctx = context; var states = ctx.PreviousStates; var avatarAddress = ctx.Signer.Derive( string.Format( CultureInfo.InvariantCulture, DeriveFormat, index ) ); var inventoryAddress = avatarAddress.Derive(LegacyInventoryKey); var worldInformationAddress = avatarAddress.Derive(LegacyWorldInformationKey); var questListAddress = avatarAddress.Derive(LegacyQuestListKey); if (ctx.Rehearsal) { states = states.SetState(ctx.Signer, MarkChanged); for (var i = 0; i < AvatarState.CombinationSlotCapacity; i++) { var slotAddress = avatarAddress.Derive( string.Format( CultureInfo.InvariantCulture, CombinationSlotState.DeriveFormat, i ) ); states = states.SetState(slotAddress, MarkChanged); } return(states .SetState(avatarAddress, MarkChanged) .SetState(Addresses.Ranking, MarkChanged) .SetState(inventoryAddress, MarkChanged) .SetState(worldInformationAddress, MarkChanged) .SetState(questListAddress, MarkChanged) .MarkBalanceChanged(GoldCurrencyMock, GoldCurrencyState.Address, context.Signer)); } var addressesHex = GetSignerAndOtherAddressesHex(context, avatarAddress); if (!Regex.IsMatch(name, GameConfig.AvatarNickNamePattern)) { throw new InvalidNamePatternException( $"{addressesHex}Aborted as the input name {name} does not follow the allowed name pattern."); } var sw = new Stopwatch(); sw.Start(); var started = DateTimeOffset.UtcNow; Log.Verbose("{AddressesHex}CreateAvatar exec started", addressesHex); AgentState existingAgentState = states.GetAgentState(ctx.Signer); var agentState = existingAgentState ?? new AgentState(ctx.Signer); var avatarState = states.GetAvatarState(avatarAddress); if (!(avatarState is null)) { throw new InvalidAddressException( $"{addressesHex}Aborted as there is already an avatar at {avatarAddress}."); } if (!(0 <= index && index < GameConfig.SlotCount)) { throw new AvatarIndexOutOfRangeException( $"{addressesHex}Aborted as the index is out of range #{index}."); } if (agentState.avatarAddresses.ContainsKey(index)) { throw new AvatarIndexAlreadyUsedException( $"{addressesHex}Aborted as the signer already has an avatar at index #{index}."); } sw.Stop(); Log.Verbose("{AddressesHex}CreateAvatar Get AgentAvatarStates: {Elapsed}", addressesHex, sw.Elapsed); sw.Restart(); Log.Verbose("{AddressesHex}Execute CreateAvatar; player: {AvatarAddress}", addressesHex, avatarAddress); agentState.avatarAddresses.Add(index, avatarAddress); // Avoid NullReferenceException in test var materialItemSheet = ctx.PreviousStates.GetSheet <MaterialItemSheet>(); RankingState1 rankingState = ctx.PreviousStates.GetRankingState1(); var rankingMapAddress = rankingState.UpdateRankingMap(avatarAddress); avatarState = CreateAvatar0.CreateAvatarState(name, avatarAddress, ctx, materialItemSheet, rankingMapAddress); if (hair < 0) { hair = 0; } if (lens < 0) { lens = 0; } if (ear < 0) { ear = 0; } if (tail < 0) { tail = 0; } avatarState.Customize(hair, lens, ear, tail); foreach (var address in avatarState.combinationSlotAddresses) { var slotState = new CombinationSlotState(address, GameConfig.RequireClearedStageLevel.CombinationEquipmentAction); states = states.SetState(address, slotState.Serialize()); } avatarState.UpdateQuestRewards(materialItemSheet); sw.Stop(); Log.Verbose("{AddressesHex}CreateAvatar CreateAvatarState: {Elapsed}", addressesHex, sw.Elapsed); var ended = DateTimeOffset.UtcNow; Log.Verbose("{AddressesHex}CreateAvatar Total Executed Time: {Elapsed}", addressesHex, ended - started); return(states .SetState(ctx.Signer, agentState.Serialize()) .SetState(Addresses.Ranking, rankingState.Serialize()) .SetState(inventoryAddress, avatarState.inventory.Serialize()) .SetState(worldInformationAddress, avatarState.worldInformation.Serialize()) .SetState(questListAddress, avatarState.questList.Serialize()) .SetState(avatarAddress, avatarState.SerializeV2())); }