Initial commit
commit
6c4de34920
|
@ -0,0 +1,364 @@
|
||||||
|
## Ignore Visual Studio temporary files, build results, and
|
||||||
|
## files generated by popular Visual Studio add-ons.
|
||||||
|
##
|
||||||
|
## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
|
||||||
|
|
||||||
|
# User-specific files
|
||||||
|
*.rsuser
|
||||||
|
*.suo
|
||||||
|
*.user
|
||||||
|
*.userosscache
|
||||||
|
*.sln.docstates
|
||||||
|
|
||||||
|
# User-specific files (MonoDevelop/Xamarin Studio)
|
||||||
|
*.userprefs
|
||||||
|
|
||||||
|
# Mono auto generated files
|
||||||
|
mono_crash.*
|
||||||
|
|
||||||
|
# Build results
|
||||||
|
[Dd]ebug/
|
||||||
|
[Dd]ebugPublic/
|
||||||
|
[Rr]elease/
|
||||||
|
[Rr]eleases/
|
||||||
|
x64/
|
||||||
|
x86/
|
||||||
|
[Ww][Ii][Nn]32/
|
||||||
|
[Aa][Rr][Mm]/
|
||||||
|
[Aa][Rr][Mm]64/
|
||||||
|
bld/
|
||||||
|
[Bb]in/
|
||||||
|
[Oo]bj/
|
||||||
|
[Ll]og/
|
||||||
|
[Ll]ogs/
|
||||||
|
|
||||||
|
# Visual Studio 2015/2017 cache/options directory
|
||||||
|
.vs/
|
||||||
|
# Uncomment if you have tasks that create the project's static files in wwwroot
|
||||||
|
#wwwroot/
|
||||||
|
|
||||||
|
# Visual Studio 2017 auto generated files
|
||||||
|
Generated\ Files/
|
||||||
|
|
||||||
|
# MSTest test Results
|
||||||
|
[Tt]est[Rr]esult*/
|
||||||
|
[Bb]uild[Ll]og.*
|
||||||
|
|
||||||
|
# NUnit
|
||||||
|
*.VisualState.xml
|
||||||
|
TestResult.xml
|
||||||
|
nunit-*.xml
|
||||||
|
|
||||||
|
# Build Results of an ATL Project
|
||||||
|
[Dd]ebugPS/
|
||||||
|
[Rr]eleasePS/
|
||||||
|
dlldata.c
|
||||||
|
|
||||||
|
# Benchmark Results
|
||||||
|
BenchmarkDotNet.Artifacts/
|
||||||
|
|
||||||
|
# .NET Core
|
||||||
|
project.lock.json
|
||||||
|
project.fragment.lock.json
|
||||||
|
artifacts/
|
||||||
|
|
||||||
|
# ASP.NET Scaffolding
|
||||||
|
ScaffoldingReadMe.txt
|
||||||
|
|
||||||
|
# StyleCop
|
||||||
|
StyleCopReport.xml
|
||||||
|
|
||||||
|
# Files built by Visual Studio
|
||||||
|
*_i.c
|
||||||
|
*_p.c
|
||||||
|
*_h.h
|
||||||
|
*.ilk
|
||||||
|
*.meta
|
||||||
|
*.obj
|
||||||
|
*.iobj
|
||||||
|
*.pch
|
||||||
|
*.pdb
|
||||||
|
*.ipdb
|
||||||
|
*.pgc
|
||||||
|
*.pgd
|
||||||
|
*.rsp
|
||||||
|
*.sbr
|
||||||
|
*.tlb
|
||||||
|
*.tli
|
||||||
|
*.tlh
|
||||||
|
*.tmp
|
||||||
|
*.tmp_proj
|
||||||
|
*_wpftmp.csproj
|
||||||
|
*.log
|
||||||
|
*.vspscc
|
||||||
|
*.vssscc
|
||||||
|
.builds
|
||||||
|
*.pidb
|
||||||
|
*.svclog
|
||||||
|
*.scc
|
||||||
|
|
||||||
|
# Chutzpah Test files
|
||||||
|
_Chutzpah*
|
||||||
|
|
||||||
|
# Visual C++ cache files
|
||||||
|
ipch/
|
||||||
|
*.aps
|
||||||
|
*.ncb
|
||||||
|
*.opendb
|
||||||
|
*.opensdf
|
||||||
|
*.sdf
|
||||||
|
*.cachefile
|
||||||
|
*.VC.db
|
||||||
|
*.VC.VC.opendb
|
||||||
|
|
||||||
|
# Visual Studio profiler
|
||||||
|
*.psess
|
||||||
|
*.vsp
|
||||||
|
*.vspx
|
||||||
|
*.sap
|
||||||
|
|
||||||
|
# Visual Studio Trace Files
|
||||||
|
*.e2e
|
||||||
|
|
||||||
|
# TFS 2012 Local Workspace
|
||||||
|
$tf/
|
||||||
|
|
||||||
|
# Guidance Automation Toolkit
|
||||||
|
*.gpState
|
||||||
|
|
||||||
|
# ReSharper is a .NET coding add-in
|
||||||
|
_ReSharper*/
|
||||||
|
*.[Rr]e[Ss]harper
|
||||||
|
*.DotSettings.user
|
||||||
|
|
||||||
|
# TeamCity is a build add-in
|
||||||
|
_TeamCity*
|
||||||
|
|
||||||
|
# DotCover is a Code Coverage Tool
|
||||||
|
*.dotCover
|
||||||
|
|
||||||
|
# AxoCover is a Code Coverage Tool
|
||||||
|
.axoCover/*
|
||||||
|
!.axoCover/settings.json
|
||||||
|
|
||||||
|
# Coverlet is a free, cross platform Code Coverage Tool
|
||||||
|
coverage*.json
|
||||||
|
coverage*.xml
|
||||||
|
coverage*.info
|
||||||
|
|
||||||
|
# Visual Studio code coverage results
|
||||||
|
*.coverage
|
||||||
|
*.coveragexml
|
||||||
|
|
||||||
|
# NCrunch
|
||||||
|
_NCrunch_*
|
||||||
|
.*crunch*.local.xml
|
||||||
|
nCrunchTemp_*
|
||||||
|
|
||||||
|
# MightyMoose
|
||||||
|
*.mm.*
|
||||||
|
AutoTest.Net/
|
||||||
|
|
||||||
|
# Web workbench (sass)
|
||||||
|
.sass-cache/
|
||||||
|
|
||||||
|
# Installshield output folder
|
||||||
|
[Ee]xpress/
|
||||||
|
|
||||||
|
# DocProject is a documentation generator add-in
|
||||||
|
DocProject/buildhelp/
|
||||||
|
DocProject/Help/*.HxT
|
||||||
|
DocProject/Help/*.HxC
|
||||||
|
DocProject/Help/*.hhc
|
||||||
|
DocProject/Help/*.hhk
|
||||||
|
DocProject/Help/*.hhp
|
||||||
|
DocProject/Help/Html2
|
||||||
|
DocProject/Help/html
|
||||||
|
|
||||||
|
# Click-Once directory
|
||||||
|
publish/
|
||||||
|
|
||||||
|
# Publish Web Output
|
||||||
|
*.[Pp]ublish.xml
|
||||||
|
*.azurePubxml
|
||||||
|
# Note: Comment the next line if you want to checkin your web deploy settings,
|
||||||
|
# but database connection strings (with potential passwords) will be unencrypted
|
||||||
|
*.pubxml
|
||||||
|
*.publishproj
|
||||||
|
|
||||||
|
# Microsoft Azure Web App publish settings. Comment the next line if you want to
|
||||||
|
# checkin your Azure Web App publish settings, but sensitive information contained
|
||||||
|
# in these scripts will be unencrypted
|
||||||
|
PublishScripts/
|
||||||
|
|
||||||
|
# NuGet Packages
|
||||||
|
*.nupkg
|
||||||
|
# NuGet Symbol Packages
|
||||||
|
*.snupkg
|
||||||
|
# The packages folder can be ignored because of Package Restore
|
||||||
|
**/[Pp]ackages/*
|
||||||
|
# except build/, which is used as an MSBuild target.
|
||||||
|
!**/[Pp]ackages/build/
|
||||||
|
# Uncomment if necessary however generally it will be regenerated when needed
|
||||||
|
#!**/[Pp]ackages/repositories.config
|
||||||
|
# NuGet v3's project.json files produces more ignorable files
|
||||||
|
*.nuget.props
|
||||||
|
*.nuget.targets
|
||||||
|
|
||||||
|
# Microsoft Azure Build Output
|
||||||
|
csx/
|
||||||
|
*.build.csdef
|
||||||
|
|
||||||
|
# Microsoft Azure Emulator
|
||||||
|
ecf/
|
||||||
|
rcf/
|
||||||
|
|
||||||
|
# Windows Store app package directories and files
|
||||||
|
AppPackages/
|
||||||
|
BundleArtifacts/
|
||||||
|
Package.StoreAssociation.xml
|
||||||
|
_pkginfo.txt
|
||||||
|
*.appx
|
||||||
|
*.appxbundle
|
||||||
|
*.appxupload
|
||||||
|
|
||||||
|
# Visual Studio cache files
|
||||||
|
# files ending in .cache can be ignored
|
||||||
|
*.[Cc]ache
|
||||||
|
# but keep track of directories ending in .cache
|
||||||
|
!?*.[Cc]ache/
|
||||||
|
|
||||||
|
# Others
|
||||||
|
ClientBin/
|
||||||
|
~$*
|
||||||
|
*~
|
||||||
|
*.dbmdl
|
||||||
|
*.dbproj.schemaview
|
||||||
|
*.jfm
|
||||||
|
*.pfx
|
||||||
|
*.publishsettings
|
||||||
|
orleans.codegen.cs
|
||||||
|
|
||||||
|
# Including strong name files can present a security risk
|
||||||
|
# (https://github.com/github/gitignore/pull/2483#issue-259490424)
|
||||||
|
#*.snk
|
||||||
|
|
||||||
|
# Since there are multiple workflows, uncomment next line to ignore bower_components
|
||||||
|
# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
|
||||||
|
#bower_components/
|
||||||
|
|
||||||
|
# RIA/Silverlight projects
|
||||||
|
Generated_Code/
|
||||||
|
|
||||||
|
# Backup & report files from converting an old project file
|
||||||
|
# to a newer Visual Studio version. Backup files are not needed,
|
||||||
|
# because we have git ;-)
|
||||||
|
_UpgradeReport_Files/
|
||||||
|
Backup*/
|
||||||
|
UpgradeLog*.XML
|
||||||
|
UpgradeLog*.htm
|
||||||
|
ServiceFabricBackup/
|
||||||
|
*.rptproj.bak
|
||||||
|
|
||||||
|
# SQL Server files
|
||||||
|
*.mdf
|
||||||
|
*.ldf
|
||||||
|
*.ndf
|
||||||
|
|
||||||
|
# Business Intelligence projects
|
||||||
|
*.rdl.data
|
||||||
|
*.bim.layout
|
||||||
|
*.bim_*.settings
|
||||||
|
*.rptproj.rsuser
|
||||||
|
*- [Bb]ackup.rdl
|
||||||
|
*- [Bb]ackup ([0-9]).rdl
|
||||||
|
*- [Bb]ackup ([0-9][0-9]).rdl
|
||||||
|
|
||||||
|
# Microsoft Fakes
|
||||||
|
FakesAssemblies/
|
||||||
|
|
||||||
|
# GhostDoc plugin setting file
|
||||||
|
*.GhostDoc.xml
|
||||||
|
|
||||||
|
# Node.js Tools for Visual Studio
|
||||||
|
.ntvs_analysis.dat
|
||||||
|
node_modules/
|
||||||
|
|
||||||
|
# Visual Studio 6 build log
|
||||||
|
*.plg
|
||||||
|
|
||||||
|
# Visual Studio 6 workspace options file
|
||||||
|
*.opt
|
||||||
|
|
||||||
|
# Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
|
||||||
|
*.vbw
|
||||||
|
|
||||||
|
# Visual Studio LightSwitch build output
|
||||||
|
**/*.HTMLClient/GeneratedArtifacts
|
||||||
|
**/*.DesktopClient/GeneratedArtifacts
|
||||||
|
**/*.DesktopClient/ModelManifest.xml
|
||||||
|
**/*.Server/GeneratedArtifacts
|
||||||
|
**/*.Server/ModelManifest.xml
|
||||||
|
_Pvt_Extensions
|
||||||
|
|
||||||
|
# Paket dependency manager
|
||||||
|
.paket/paket.exe
|
||||||
|
paket-files/
|
||||||
|
|
||||||
|
# FAKE - F# Make
|
||||||
|
.fake/
|
||||||
|
|
||||||
|
# CodeRush personal settings
|
||||||
|
.cr/personal
|
||||||
|
|
||||||
|
# Python Tools for Visual Studio (PTVS)
|
||||||
|
__pycache__/
|
||||||
|
*.pyc
|
||||||
|
|
||||||
|
# Cake - Uncomment if you are using it
|
||||||
|
# tools/**
|
||||||
|
# !tools/packages.config
|
||||||
|
|
||||||
|
# Tabs Studio
|
||||||
|
*.tss
|
||||||
|
|
||||||
|
# Telerik's JustMock configuration file
|
||||||
|
*.jmconfig
|
||||||
|
|
||||||
|
# BizTalk build output
|
||||||
|
*.btp.cs
|
||||||
|
*.btm.cs
|
||||||
|
*.odx.cs
|
||||||
|
*.xsd.cs
|
||||||
|
|
||||||
|
# OpenCover UI analysis results
|
||||||
|
OpenCover/
|
||||||
|
|
||||||
|
# Azure Stream Analytics local run output
|
||||||
|
ASALocalRun/
|
||||||
|
|
||||||
|
# MSBuild Binary and Structured Log
|
||||||
|
*.binlog
|
||||||
|
|
||||||
|
# NVidia Nsight GPU debugger configuration file
|
||||||
|
*.nvuser
|
||||||
|
|
||||||
|
# MFractors (Xamarin productivity tool) working folder
|
||||||
|
.mfractor/
|
||||||
|
|
||||||
|
# Local History for Visual Studio
|
||||||
|
.localhistory/
|
||||||
|
|
||||||
|
# BeatPulse healthcheck temp database
|
||||||
|
healthchecksdb
|
||||||
|
|
||||||
|
# Backup folder for Package Reference Convert tool in Visual Studio 2017
|
||||||
|
MigrationBackup/
|
||||||
|
|
||||||
|
# Ionide (cross platform F# VS Code tools) working folder
|
||||||
|
.ionide/
|
||||||
|
|
||||||
|
# Fody - auto-generated XML schema
|
||||||
|
FodyWeavers.xsd
|
||||||
|
|
||||||
|
.idea/
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages;
|
||||||
|
|
||||||
|
public interface IMessageHandler
|
||||||
|
{
|
||||||
|
Task TryHandleAsync(GameSession session, ClientMessage request);
|
||||||
|
}
|
|
@ -0,0 +1,28 @@
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
using Tiger.Communication.Messages.Outgoing.Handshake;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Incoming.Handshake;
|
||||||
|
|
||||||
|
public class InfoRetrieveEvent : IMessageEvent
|
||||||
|
{
|
||||||
|
private readonly IGameSessionManager _gameSessionManager;
|
||||||
|
|
||||||
|
public InfoRetrieveEvent(IGameSessionManager gameSessionManager)
|
||||||
|
{
|
||||||
|
_gameSessionManager = gameSessionManager;
|
||||||
|
}
|
||||||
|
|
||||||
|
public IncomingHeaders Header => IncomingHeaders.InfoRetrieveEvent;
|
||||||
|
public async Task HandleAsync(GameSession gameSession, ClientMessage request)
|
||||||
|
{
|
||||||
|
if (gameSession.Habbo == null)
|
||||||
|
{
|
||||||
|
await _gameSessionManager.CloseAsync("Not logged in", gameSession);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
await gameSession.SendComposerAsync(new UserObjectMessageComposer(gameSession.Habbo));
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,52 @@
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
using Tiger.Communication.Messages.Outgoing.Generic.Alerts;
|
||||||
|
using Tiger.Communication.Messages.Outgoing.Handshake;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Game.Habbos;
|
||||||
|
using Tiger.Game.Settings;
|
||||||
|
using Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Incoming.Handshake;
|
||||||
|
|
||||||
|
public class SsoTicketEvent : IMessageEvent
|
||||||
|
{
|
||||||
|
private readonly IHabboDao _habboDao;
|
||||||
|
private readonly IGameSessionManager _gameSessionManager;
|
||||||
|
private readonly ISettingsManager _settingsManager;
|
||||||
|
|
||||||
|
public SsoTicketEvent(IHabboDao habboDao, IGameSessionManager gameSessionManager, ISettingsManager settingsManager)
|
||||||
|
{
|
||||||
|
_habboDao = habboDao;
|
||||||
|
_gameSessionManager = gameSessionManager;
|
||||||
|
_settingsManager = settingsManager;
|
||||||
|
}
|
||||||
|
|
||||||
|
public IncomingHeaders Header => IncomingHeaders.SSoTicketEvent;
|
||||||
|
|
||||||
|
public async Task HandleAsync(GameSession gameSession, ClientMessage request)
|
||||||
|
{
|
||||||
|
var sso = request.ReadString();
|
||||||
|
|
||||||
|
if (sso == null)
|
||||||
|
{
|
||||||
|
await _gameSessionManager.CloseAsync("Malformed packet", gameSession);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
var habbo = await _habboDao.GetHabboBySsoAsync(sso);
|
||||||
|
|
||||||
|
if (habbo == null)
|
||||||
|
{
|
||||||
|
await _gameSessionManager.CloseAsync("User not found", gameSession);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
gameSession.Habbo = habbo;
|
||||||
|
|
||||||
|
await gameSession.SendComposerAsync(new AuthenticationOkMessageComposer());
|
||||||
|
await gameSession.SendComposerAsync(new HabboBroadcastMessageComposer(
|
||||||
|
_settingsManager.GetSetting<string>("welcome.message")
|
||||||
|
.Replace("{user}", gameSession.Habbo.Username)
|
||||||
|
));
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,491 @@
|
||||||
|
namespace Tiger.Communication.Messages.Incoming;
|
||||||
|
|
||||||
|
public enum IncomingHeaders : short
|
||||||
|
{
|
||||||
|
AcceptFriendEvent = 137,
|
||||||
|
AcceptTradingEvent = 3863,
|
||||||
|
AddAdminRightsToMemberEvent = 2894,
|
||||||
|
AddFavouriteRoomEvent = 3817,
|
||||||
|
AddItemToTradeEvent = 3107,
|
||||||
|
AddItemsToTradeEvent = 1263,
|
||||||
|
AddJukeboxDiskEvent = 753,
|
||||||
|
AddSpamWallPostItEvent = 3283,
|
||||||
|
AmbassadorAlertEvent = 2996,
|
||||||
|
AnswerPollEvent = 3505,
|
||||||
|
ApplySnapshotEvent = 3373,
|
||||||
|
ApproveMembershipRequestEvent = 3386,
|
||||||
|
ApproveNameEvent = 2109,
|
||||||
|
AssignRightsEvent = 808,
|
||||||
|
AvatarEffectActivatedEvent = 2959,
|
||||||
|
AvatarEffectSelectedEvent = 1752,
|
||||||
|
AvatarExpressionEvent = 2456,
|
||||||
|
BanUserWithDurationEvent = 1477,
|
||||||
|
BreedPetsEvent = 1638,
|
||||||
|
BuildersClubPlaceWallItemEvent = 2462,
|
||||||
|
BuildersClubQueryFurniCountEvent = 2529,
|
||||||
|
BuyMarketplaceOfferEvent = 1603,
|
||||||
|
CallForHelpEvent = 1691,
|
||||||
|
CallForHelpFromForumMessageEvent = 1412,
|
||||||
|
CallForHelpFromForumThreadEvent = 534,
|
||||||
|
CallForHelpFromImEvent = 2950,
|
||||||
|
CallForHelpFromPhotoEvent = 2492,
|
||||||
|
CanCreateRoomEvent = 2128,
|
||||||
|
CancelMarketplaceOfferEvent = 434,
|
||||||
|
CancelPetBreedingEvent = 2713,
|
||||||
|
CancelTypingEvent = 1474,
|
||||||
|
ChangeMottoEvent = 2228,
|
||||||
|
ChangePostureEvent = 2235,
|
||||||
|
ChangeUserNameEvent = 2977,
|
||||||
|
ChatEvent = 1314,
|
||||||
|
ChatReviewGuideDecidesOnOfferEvent = 3365,
|
||||||
|
ChatReviewGuideDetachedEvent = 2501,
|
||||||
|
ChatReviewGuideVoteEvent = 3961,
|
||||||
|
ChatReviewSessionCreateEvent = 3060,
|
||||||
|
CheckUserNameEvent = 3950,
|
||||||
|
ClientHelloEvent = 4000,
|
||||||
|
CloseIssueDefaultActionEvent = 2717,
|
||||||
|
CloseIssuesEvent = 2067,
|
||||||
|
CloseTradingEvent = 2551,
|
||||||
|
CommandBotEvent = 2624,
|
||||||
|
CompleteDiffieHandshakeEvent = 773,
|
||||||
|
CompostPlantEvent = 3835,
|
||||||
|
ConfirmAcceptTradingEvent = 2760,
|
||||||
|
ConfirmDeclineTradingEvent = 2341,
|
||||||
|
ConfirmPetBreedingEvent = 3382,
|
||||||
|
ControlYoutubeDisplayPlaybackEvent = 3005,
|
||||||
|
CraftEvent = 3591,
|
||||||
|
CraftSecretEvent = 1251,
|
||||||
|
CreateFlatEvent = 2752,
|
||||||
|
CreateGuildEvent = 230,
|
||||||
|
CreditFurniRedeemEvent = 3115,
|
||||||
|
CustomizeAvatarWithFurniEvent = 3374,
|
||||||
|
CustomizePetWithFurniEvent = 1328,
|
||||||
|
DanceEvent = 2080,
|
||||||
|
DeactivateGuildEvent = 1134,
|
||||||
|
DeclineFriendEvent = 2890,
|
||||||
|
DeleteFavouriteRoomEvent = 309,
|
||||||
|
DeleteRoomEvent = 532,
|
||||||
|
DeselectFavouriteHabboGroupEvent = 1820,
|
||||||
|
DiceOffEvent = 1533,
|
||||||
|
DropCarryItemEvent = 2814,
|
||||||
|
EditEventEvent = 3991,
|
||||||
|
EnterOneWayDoorEvent = 2765,
|
||||||
|
EventLogEvent = 3457,
|
||||||
|
FindNewFriendsEvent = 516,
|
||||||
|
FollowFriendEvent = 2970,
|
||||||
|
ForwardToSomeRoomEvent = 1703,
|
||||||
|
FriendFurniConfirmLockEvent = 3775,
|
||||||
|
Game2GetAccountGameStatusEvent = 11,
|
||||||
|
GameUnloadedEvent = 3207,
|
||||||
|
GetAchievementsEvent = 219,
|
||||||
|
GetBadgePointLimitsEvent = 1371,
|
||||||
|
GetBadgesEvent = 2769,
|
||||||
|
GetBannedUsersFromRoomEvent = 2267,
|
||||||
|
GetBonusRareInfoEvent = 957,
|
||||||
|
GetBotCommandConfigurationDataEvent = 1986,
|
||||||
|
GetBotInventoryEvent = 3848,
|
||||||
|
GetBundleDiscountRulesetEvent = 223,
|
||||||
|
GetCatalogIndexEvent = 1195,
|
||||||
|
GetCatalogPageEvent = 412,
|
||||||
|
GetCfhChatlogEvent = 211,
|
||||||
|
GetCfhStatusEvent = 2746,
|
||||||
|
GetClubGiftInfo = 487,
|
||||||
|
GetClubOffersEvent = 3285,
|
||||||
|
GetCraftableProductsEvent = 633,
|
||||||
|
GetCraftingRecipeEvent = 1173,
|
||||||
|
GetCraftingRecipesAvailableEvent = 3086,
|
||||||
|
GetCreditsInfoEvent = 273,
|
||||||
|
GetCurrentTimingCodeEvent = 2912,
|
||||||
|
GetCustomRoomFilterEvent = 1911,
|
||||||
|
GetExtendedProfileEvent = 3265,
|
||||||
|
GetFlatControllersEvent = 3385,
|
||||||
|
GetForumStatsEvent = 3149,
|
||||||
|
GetForumsListEvent = 873,
|
||||||
|
GetFriendRequestsEvent = 2448,
|
||||||
|
GetFurnitureAliasesEvent = 3898,
|
||||||
|
GetGameListEvent = 741,
|
||||||
|
GetGameStatusEvent = 3171,
|
||||||
|
GetGiftWrappingConfigurationEvent = 418,
|
||||||
|
GetGuestRoomEvent = 2230,
|
||||||
|
GetGuideReportingStatusEvent = 3786,
|
||||||
|
GetGuildCreationInfoEvent = 798,
|
||||||
|
GetGuildEditInfoEvent = 1004,
|
||||||
|
GetGuildEditorDataEvent = 813,
|
||||||
|
GetGuildFurniContextMenuInfoEvent = 2651,
|
||||||
|
GetGuildMembersEvent = 312,
|
||||||
|
GetGuildMembershipsEvent = 367,
|
||||||
|
GetHabboGroupBadgesEvent = 21,
|
||||||
|
GetHabboGroupDetailsEvent = 2991,
|
||||||
|
GetIgnoredUsersEvent = 3878,
|
||||||
|
GetItemDataEvent = 3964,
|
||||||
|
GetJukeboxPlayListEvent = 1435,
|
||||||
|
GetLimitedOfferAppearingNextEvent = 410,
|
||||||
|
GetMotdEvent = 1523,
|
||||||
|
GetMarketplaceCanMakeOfferEvent = 848,
|
||||||
|
GetMarketplaceConfigurationEvent = 2597,
|
||||||
|
GetMarketplaceItemStatsEvent = 3288,
|
||||||
|
GetMarketplaceOffersEvent = 2407,
|
||||||
|
GetMarketplaceOwnOffersEvent = 2105,
|
||||||
|
GetMemberGuildItemCountEvent = 3593,
|
||||||
|
GetMessagesEvent = 232,
|
||||||
|
GetModeratorRoomInfoEvent = 707,
|
||||||
|
GetModeratorUserInfoEvent = 3295,
|
||||||
|
GetNowPlayingEvent = 1325,
|
||||||
|
GetOccupiedTilesEvent = 1687,
|
||||||
|
GetOfficialSongIdEvent = 3189,
|
||||||
|
GetPendingCallsForHelpEvent = 3267,
|
||||||
|
GetPetCommandsEvent = 2161,
|
||||||
|
GetPetInfoEvent = 2934,
|
||||||
|
GetPetInventoryEvent = 3095,
|
||||||
|
GetPopularRoomTagsEvent = 826,
|
||||||
|
GetProductOfferEvent = 2594,
|
||||||
|
GetPromoArticlesEvent = 1827,
|
||||||
|
GetRecyclerPrizesEvent = 398,
|
||||||
|
GetRecyclerStatusEvent = 1342,
|
||||||
|
GetRelationshipStatusInfoEvent = 2138,
|
||||||
|
GetResolutionAchievementsEvent = 359,
|
||||||
|
GetRoomAdPurchaseInfoEvent = 1075,
|
||||||
|
GetRoomChatlogEvent = 2587,
|
||||||
|
GetRoomEntryDataEvent = 2300,
|
||||||
|
GetRoomEntryTileEvent = 3559,
|
||||||
|
GetRoomSettingsEvent = 3129,
|
||||||
|
GetRoomVisitsEvent = 3526,
|
||||||
|
GetSelectedBadgesEvent = 2091,
|
||||||
|
GetSellablePetPalettesEvent = 1756,
|
||||||
|
GetSongInfoEvent = 3082,
|
||||||
|
GetSoundSettingsEvent = 2388,
|
||||||
|
GetTalentTrackEvent = 196,
|
||||||
|
GetTalentTrackLevelEvent = 2127,
|
||||||
|
GetThreadsEvent = 436,
|
||||||
|
GetUnreadForumsCountEvent = 2908,
|
||||||
|
GetUserChatlogEvent = 1391,
|
||||||
|
GetUserEventCatsEvent = 1782,
|
||||||
|
GetUserFlatCatsEvent = 3027,
|
||||||
|
GetUserTagsEvent = 17,
|
||||||
|
GetWardrobeEvent = 2742,
|
||||||
|
GetWeeklyGameRewardEvent = 2914,
|
||||||
|
GetWeeklyGameRewardWinnersEvent = 1054,
|
||||||
|
GetYoutubeDisplayStatusEvent = 336,
|
||||||
|
GuideSessionCreateEvent = 3338,
|
||||||
|
GuideSessionFeedbackEvent = 477,
|
||||||
|
GuideSessionGetRequesterRoomEvent = 1052,
|
||||||
|
GuideSessionGuideDecidesEvent = 1424,
|
||||||
|
GuideSessionInviteRequesterEvent = 234,
|
||||||
|
GuideSessionIsTypingEvent = 519,
|
||||||
|
GuideSessionMessageEvent = 3899,
|
||||||
|
GuideSessionOnDutyUpdateEvent = 1922,
|
||||||
|
GuideSessionReportEvent = 3969,
|
||||||
|
GuideSessionRequesterCancelsEvent = 291,
|
||||||
|
GuideSessionResolvedEvent = 887,
|
||||||
|
HabboSearchEvent = 1210,
|
||||||
|
// HotelViewClaimBadgeRewardEvent = -1,
|
||||||
|
HotelViewRequestBadgeRewardEvent = 2318,
|
||||||
|
HotelViewRequestSecondsUntilEvent = 271,
|
||||||
|
IgnoreUserEvent = 1117,
|
||||||
|
InfoRetrieveEvent = 357,
|
||||||
|
InitDiffieHandshakeEvent = 3110,
|
||||||
|
JoinHabboGroupEvent = 998,
|
||||||
|
JoinQueueEvent = 1458,
|
||||||
|
JukeBoxEventOne = 2304,
|
||||||
|
KickMemberEvent = 593,
|
||||||
|
LatencyPingRequestEvent = 295,
|
||||||
|
LetUserInEvent = 1644,
|
||||||
|
LookToEvent = 3301,
|
||||||
|
MakeOfferEvent = 3447,
|
||||||
|
MessengerInitEvent = 2781,
|
||||||
|
ModAlertEvent = 229,
|
||||||
|
ModBanEvent = 2766,
|
||||||
|
ModKickEvent = 2582,
|
||||||
|
ModMessageEvent = 1840,
|
||||||
|
ModMuteEvent = 1945,
|
||||||
|
// ModToolRequestRoomUserChatlogEvent = -1,
|
||||||
|
ModToolSanctionEvent = 1392,
|
||||||
|
// ModToolWarnEvent = -1,
|
||||||
|
ModTradingLockEvent = 3742,
|
||||||
|
ModerateMessageEvent = 286,
|
||||||
|
ModerateRoomEvent = 3260,
|
||||||
|
ModerateThreadEvent = 1397,
|
||||||
|
ModeratorActionEvent = 3842,
|
||||||
|
MountPetEvent = 1036,
|
||||||
|
MoveAvatarEvent = 3320,
|
||||||
|
MoveObjectEvent = 248,
|
||||||
|
MovePetEvent = 3449,
|
||||||
|
MoveWallItemEvent = 168,
|
||||||
|
MuteAllInRoomEvent = 3637,
|
||||||
|
MyFavouriteRoomsSearchEvent = 2578,
|
||||||
|
MyFriendsRoomsSearchEvent = 2266,
|
||||||
|
MyGuildBasesSearchEvent = 39,
|
||||||
|
MyRoomHistorySearchEvent = 2264,
|
||||||
|
MyRoomRightsSearchEvent = 272,
|
||||||
|
MyRoomsSearchEvent = 2277,
|
||||||
|
NavigatorAddCollapsedCategoryEvent = 1834,
|
||||||
|
NavigatorAddSavedSearchEvent = 2226,
|
||||||
|
NavigatorDeleteSavedSearchEvent = 1954,
|
||||||
|
NavigatorRemoveCollapsedCategoryEvent = 637,
|
||||||
|
NavigatorSetSearchCodeViewModeEvent = 1202,
|
||||||
|
NewNavigatorInitEvent = 2110,
|
||||||
|
NewNavigatorSearchEvent = 249,
|
||||||
|
NewUserExperienceGetGiftsEvent = 1822,
|
||||||
|
NewUserExperienceScriptProceedEvent = 1299,
|
||||||
|
OpenCampaignCalendarDoorEvent = 8809,
|
||||||
|
OpenCampaignCalendarDoorAsStaffEvent = 2507,
|
||||||
|
OpenFlatConnectionEvent = 2312,
|
||||||
|
OpenPetPackageEvent = 3698,
|
||||||
|
OpenTradingEvent = 1481,
|
||||||
|
PassCarryItemEvent = 2941,
|
||||||
|
PickIssuesEvent = 15,
|
||||||
|
PickupObjectEvent = 3456,
|
||||||
|
PlaceBotEvent = 1592,
|
||||||
|
PlaceObjectEvent = 1258,
|
||||||
|
PlacePetEvent = 2647,
|
||||||
|
PlacePostItEvent = 2248,
|
||||||
|
PollRejectEvent = 1773,
|
||||||
|
PollStartEvent = 109,
|
||||||
|
PongEvent = 2596,
|
||||||
|
PopularRoomsSearchEvent = 2758,
|
||||||
|
PostMessageEvent = 3529,
|
||||||
|
PresentOpenEvent = 3558,
|
||||||
|
PublishPhotoEvent = 2068,
|
||||||
|
PurchaseFromCatalogAsGiftEvent = 1411,
|
||||||
|
PurchaseFromCatalogEvent = 3492,
|
||||||
|
PurchasePhotoEvent = 2408,
|
||||||
|
PurchaseRoomAdEvent = 777,
|
||||||
|
PurchaseTargetedOfferEvent = 1826,
|
||||||
|
PurchaseVipMembershipExtensionEvent = 3407,
|
||||||
|
QuitEvent = 105,
|
||||||
|
RateFlatEvent = 3582,
|
||||||
|
RecycleItemsEvent = 2771,
|
||||||
|
RedeemMarketplaceOfferCreditsEvent = 2650,
|
||||||
|
RedeemVoucherEvent = 339,
|
||||||
|
RejectMembershipRequestEvent = 1894,
|
||||||
|
ReleaseIssuesEvent = 1572,
|
||||||
|
RemoveAdminRightsFromMemberEvent = 722,
|
||||||
|
RemoveAllRightsEvent = 2683,
|
||||||
|
RemoveBotFromFlatEvent = 3323,
|
||||||
|
RemoveFriendEvent = 1689,
|
||||||
|
RemoveItemEvent = 3336,
|
||||||
|
RemoveItemFromTradeEvent = 3845,
|
||||||
|
RemoveJukeboxDiskEvent = 3050,
|
||||||
|
RemoveOwnRoomRightsRoomEvent = 3182,
|
||||||
|
RemovePetFromFlatEvent = 1581,
|
||||||
|
RemoveRightsEvent = 2064,
|
||||||
|
RemoveSaddleFromPetEvent = 186,
|
||||||
|
RenderRoomEvent = 3226,
|
||||||
|
RenderRoomThumbnailEvent = 1982,
|
||||||
|
RentableSpaceCancelRentEvent = 1667,
|
||||||
|
RentableSpaceRentEvent = 2946,
|
||||||
|
// RequestAchievementConfigurationEvent = -1,
|
||||||
|
RequestCameraConfigurationEvent = 796,
|
||||||
|
RequestFriendEvent = 3157,
|
||||||
|
RequestFurniInventoryEvent = 3150,
|
||||||
|
RequestFurniInventoryWhenNotInRoomEvent = 3500,
|
||||||
|
RequestRoomPropertySet = 711,
|
||||||
|
RespectPetEvent = 3202,
|
||||||
|
RespectUserEvent = 2694,
|
||||||
|
RoomDimmerChangeStateEvent = 2296,
|
||||||
|
RoomDimmerGetPresetsEvent = 2813,
|
||||||
|
RoomDimmerSavePresetEvent = 1648,
|
||||||
|
RoomTextSearchEvent = 3943,
|
||||||
|
RoomUserKickEvent = 1320,
|
||||||
|
RoomUserMuteEvent = 3485,
|
||||||
|
RoomsWhereMyFriendsAreSearchEvent = 1786,
|
||||||
|
RoomsWithHighestScoreSearchEvent = 2939,
|
||||||
|
SSoTicketEvent = 2419,
|
||||||
|
SaveRoomSettingsEvent = 1969,
|
||||||
|
SaveWardrobeOutfitEvent = 800,
|
||||||
|
ScrGetKickbackInfoEvent = 869,
|
||||||
|
ScrGetUserInfoEvent = 3166,
|
||||||
|
// SearchRoomsByTagEvent = -1,
|
||||||
|
SelectClubGiftEvent = 2276,
|
||||||
|
SelectFavouriteHabboGroupEvent = 3549,
|
||||||
|
SendMsgEvent = 3567,
|
||||||
|
SendRoomInviteEvent = 1276,
|
||||||
|
SetActivatedBadgesEvent = 644,
|
||||||
|
SetChatPreferencesEvent = 1262,
|
||||||
|
SetChatStylePreferenceEvent = 1030,
|
||||||
|
SetClothingChangeDataEvent = 924,
|
||||||
|
SetCustomStackingHeightEvent = 3839,
|
||||||
|
SetIgnoreRoomInvitesEvent = 1086,
|
||||||
|
SetItemDataEvent = 3666,
|
||||||
|
SetMannequinFigureEvent = 2209,
|
||||||
|
SetMannequinNameEvent = 2850,
|
||||||
|
SetNewNavigatorWindowPreferencesEvent = 3159,
|
||||||
|
SetObjectDataEvent = 3608,
|
||||||
|
SetRandomStateEvent = 3617,
|
||||||
|
SetRelationshipStatusEvent = 3768,
|
||||||
|
SetRoomBackgroundColorDataEvent = 2880,
|
||||||
|
SetRoomCameraPreferencesEvent = 1461,
|
||||||
|
SetSoundSettingsEvent = 1367,
|
||||||
|
SetTargetedOfferStateEvent = 2041,
|
||||||
|
SetYoutubeDisplayPlaylistEvent = 2069,
|
||||||
|
ShoutEvent = 2085,
|
||||||
|
SignEvent = 1975,
|
||||||
|
SpinWheelOfFortuneEvent = 2144,
|
||||||
|
StartTypingEvent = 1597,
|
||||||
|
SubmitRoomToCompetitionEvent = 2595,
|
||||||
|
ThrowDiceEvent = 1990,
|
||||||
|
TogglePetBreedingPermissionEvent = 3379,
|
||||||
|
TogglePetRidingPermissionEvent = 1472,
|
||||||
|
ToggleStaffPickEvent = 1918,
|
||||||
|
UnacceptTradingEvent = 1444,
|
||||||
|
UnbanUserFromRoomEvent = 992,
|
||||||
|
UnignoreUserEvent = 2061,
|
||||||
|
UniqueIdEvent = 2490,
|
||||||
|
UpdateActionEvent = 2281,
|
||||||
|
UpdateConditionEvent = 3203,
|
||||||
|
UpdateFigureDataEvent = 2730,
|
||||||
|
UpdateFloorPropertiesEvent = 875,
|
||||||
|
UpdateForumSettingsEvent = 2214,
|
||||||
|
UpdateGuildBadgeEvent = 1991,
|
||||||
|
UpdateGuildColorsEvent = 1764,
|
||||||
|
UpdateGuildIdentityEvent = 3137,
|
||||||
|
UpdateGuildSettingsEvent = 3435,
|
||||||
|
UpdateHomeRoomEvent = 1740,
|
||||||
|
UpdateRoomFilterEvent = 3001,
|
||||||
|
UpdateThreadEvent = 3045,
|
||||||
|
UpdateTriggerEvent = 1520,
|
||||||
|
UpdateUiFlagsEvent = 2313,
|
||||||
|
UseFurnitureEvent = 99,
|
||||||
|
UseWallItemEvent = 210,
|
||||||
|
VisitUserEvent = 3997,
|
||||||
|
WhisperEvent = 1543,
|
||||||
|
AcceptGameInviteEvent = 3802,
|
||||||
|
AcceptQuestEvent = 3604,
|
||||||
|
ApproveAllMembershipRequestsEvent = 882,
|
||||||
|
BuildersClubPlaceRoomItemEvent = 1051,
|
||||||
|
BuyMarketplaceTokensEvent = 1866,
|
||||||
|
CallForHelpFromSelfieEvent = 2755,
|
||||||
|
CancelEventEvent = 2725,
|
||||||
|
CancelQuestEvent = 3133,
|
||||||
|
ChangeEmailEvent = 3965,
|
||||||
|
ChangeQueueEvent = 3093,
|
||||||
|
CommunityGoalVoteEvent = 3536,
|
||||||
|
CompetitionRoomsSearchEvent = 433,
|
||||||
|
DeletePendingCallsForHelpEvent = 3605,
|
||||||
|
DisconnectEvent = 2445,
|
||||||
|
ExtendRentOrBuyoutFurniEvent = 1071,
|
||||||
|
ExtendRentOrBuyoutStripItemEvent = 2115,
|
||||||
|
ForwardToACompetitionRoomEvent = 172,
|
||||||
|
ForwardToARandomPromotedRoomEvent = 10,
|
||||||
|
ForwardToRandomCompetitionRoomEvent = 865,
|
||||||
|
FriendListUpdateEvent = 1419,
|
||||||
|
FriendRequestQuestCompleteEvent = 1148,
|
||||||
|
Game2CheckGameDirectoryStatusEvent = 3259,
|
||||||
|
Game2ExitGameEvent = 1445,
|
||||||
|
Game2GameChatEvent = 2502,
|
||||||
|
Game2GetWeeklyFriendsLeaderboardEvent = 1232,
|
||||||
|
Game2GetWeeklyLeaderboardEvent = 2565,
|
||||||
|
Game2LoadStageReadyEvent = 2415,
|
||||||
|
Game2PlayAgainEvent = 3196,
|
||||||
|
Game2RequestFullStatusUpdateEvent = 1598,
|
||||||
|
GetCatalogPageExpirationEvent = 742,
|
||||||
|
GetCatalogPageWithEarliestExpiryEvent = 3135,
|
||||||
|
GetCategoriesWithUserCountEvent = 3782,
|
||||||
|
GetCommunityGoalEarnedPrizesEvent = 2688,
|
||||||
|
GetCommunityGoalHallOfFameEvent = 2167,
|
||||||
|
GetCommunityGoalProgressEvent = 1145,
|
||||||
|
GetConcurrentUsersGoalProgressEvent = 1343,
|
||||||
|
GetConcurrentUsersRewardEvent = 3872,
|
||||||
|
GetDailyQuestEvent = 2486,
|
||||||
|
GetDirectClubBuyAvailableEvent = 801,
|
||||||
|
GetEmailStatusEvent = 2557,
|
||||||
|
GetExtendedProfileByNameEvent = 2249,
|
||||||
|
GetFaqCategoryEvent = 3445,
|
||||||
|
GetFaqTextEvent = 1849,
|
||||||
|
GetGameAchievementsEvent = 2399,
|
||||||
|
GetHabboBasicMembershipExtendOfferEvent = 603,
|
||||||
|
GetInterstitialEvent = 2519,
|
||||||
|
GetIsBadgeRequestFulfilledEvent = 1364,
|
||||||
|
GetIsOfferGiftableEvent = 1347,
|
||||||
|
GetIsUserPartOfCompetitionEvent = 2077,
|
||||||
|
GetNextTargetedOfferEvent = 2487,
|
||||||
|
GetOfficialRoomsEvent = 1229,
|
||||||
|
GetQuestsEvent = 3333,
|
||||||
|
GetQuizQuestionsEvent = 1296,
|
||||||
|
GetSeasonalCalendarDailyOfferEvent = 3257,
|
||||||
|
GetSeasonalQuestsOnlyEvent = 1190,
|
||||||
|
GetSoundMachinePlayListEvent = 3498,
|
||||||
|
GetTargetedOfferEvent = 596,
|
||||||
|
GetThreadEvent = 3900,
|
||||||
|
GetUserGameAchievementsEvent = 389,
|
||||||
|
GiveSupplementToPetEvent = 749,
|
||||||
|
GoToFlatEvent = 685,
|
||||||
|
GuideAdvertisementReadEvent = 2455,
|
||||||
|
GuildBaseSearchEvent = 2930,
|
||||||
|
HarvestPetEvent = 1521,
|
||||||
|
IgnoreUserIdEvent = 3314,
|
||||||
|
InterstitialShownEvent = 1109,
|
||||||
|
LagWarningReportEvent = 3847,
|
||||||
|
LatencyPingReportEvent = 96,
|
||||||
|
LeaveQueueEvent = 2384,
|
||||||
|
ModToolPreferencesEvent = 31,
|
||||||
|
MyFrequentRoomHistorySearchEvent = 1002,
|
||||||
|
MyRecommendedRoomsEvent = 2537,
|
||||||
|
MysteryBoxWaitingCanceledEvent = 2012,
|
||||||
|
OpenMysteryTrophyEvent = 3074,
|
||||||
|
OpenQuestTrackerEvent = 2750,
|
||||||
|
OpenWelcomeGiftEvent = 2638,
|
||||||
|
PassCarryItemToPetEvent = 2768,
|
||||||
|
PeerUsersClassificationEvent = 1160,
|
||||||
|
PerformanceLogEvent = 3230,
|
||||||
|
PetSelectedEvent = 549,
|
||||||
|
PhotoCompetitionEvent = 3959,
|
||||||
|
PostQuizAnswersEvent = 3720,
|
||||||
|
PurchaseBasicMembershipExtensionEvent = 2735,
|
||||||
|
RedeemCommunityGoalPrizeEvent = 90,
|
||||||
|
RejectQuestEvent = 2397,
|
||||||
|
RentableSpaceStatusEvent = 872,
|
||||||
|
RequestABadgeEvent = 3077,
|
||||||
|
ResetPhoneNumberStateEvent = 2741,
|
||||||
|
ResetResolutionAchievementEvent = 3144,
|
||||||
|
ResetUnseenItemIdsEvent = 3493,
|
||||||
|
ResetUnseenItemsEvent = 2343,
|
||||||
|
RoomAdEventTabAdClickedEvent = 2412,
|
||||||
|
RoomAdEventTabViewedEvent = 2668,
|
||||||
|
RoomAdPurchaseInitiatedEvent = 2283,
|
||||||
|
RoomAdSearchEvent = 2809,
|
||||||
|
RoomCompetitionInitEvent = 1334,
|
||||||
|
RoomNetworkOpenConnectionEvent = 3736,
|
||||||
|
RoomUsersClassificationEvent = 2285,
|
||||||
|
SearchFaqsEvent = 2031,
|
||||||
|
SetPhoneNumberVerificationStatusEvent = 1379,
|
||||||
|
SetRoomSessionTagsEvent = 3305,
|
||||||
|
ShopTargetedOfferViewedEvent = 3483,
|
||||||
|
StartCampaignEvent = 1697,
|
||||||
|
TryPhoneNumberEvent = 790,
|
||||||
|
UnblockGroupMemberEvent = 2864,
|
||||||
|
UpdateForumReadMarkerEvent = 1855,
|
||||||
|
UpdateRoomCategoryAndTradeSettingsEvent = 1265,
|
||||||
|
UpdateRoomThumbnailEvent = 2468,
|
||||||
|
VerifyCodeEvent = 2721,
|
||||||
|
VersionCheckEvent = 1053,
|
||||||
|
VoteForRoomEvent = 143,
|
||||||
|
WelcomeGiftChangeEmailEvent = 66,
|
||||||
|
UnknownSnowStormEvent6000 = 6000,
|
||||||
|
UnknownSnowStormEvent6001 = 6001,
|
||||||
|
UnknownSnowStormEvent6002 = 6002,
|
||||||
|
UnknownSnowStormEvent6003 = 6003,
|
||||||
|
UnknownSnowStormEvent6004 = 6004,
|
||||||
|
UnknownSnowStormEvent6005 = 6005,
|
||||||
|
UnknownSnowStormEvent6006 = 6006,
|
||||||
|
UnknownSnowStormEvent6007 = 6007,
|
||||||
|
UnknownSnowStormEvent6008 = 6008,
|
||||||
|
UnknownSnowStormEvent6009 = 6009,
|
||||||
|
UnknownSnowStormEvent6010 = 6010,
|
||||||
|
UnknownSnowStormEvent6011 = 6011,
|
||||||
|
SnowStormJoinQueueEvent = 6012,
|
||||||
|
UnknownSnowStormEvent6013 = 6013,
|
||||||
|
UnknownSnowStormEvent6014 = 6014,
|
||||||
|
UnknownSnowStormEvent6015 = 6015,
|
||||||
|
UnknownSnowStormEvent6016 = 6016,
|
||||||
|
UnknownSnowStormEvent6017 = 6017,
|
||||||
|
UnknownSnowStormEvent6018 = 6018,
|
||||||
|
UnknownSnowStormEvent6019 = 6019,
|
||||||
|
UnknownSnowStormEvent6020 = 6020,
|
||||||
|
UnknownSnowStormEvent6021 = 6021,
|
||||||
|
UnknownSnowStormEvent6022 = 6022,
|
||||||
|
UnknownSnowStormEvent6023 = 6023,
|
||||||
|
UnknownSnowStormEvent6024 = 6024,
|
||||||
|
UnknownSnowStormEvent6025 = 6025,
|
||||||
|
SnowStormUserPickSnowballEvent = 6026,
|
||||||
|
}
|
|
@ -0,0 +1,10 @@
|
||||||
|
using Tiger.Communication.Messages.Outgoing;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Interfaces;
|
||||||
|
|
||||||
|
public interface IMessageComposer
|
||||||
|
{
|
||||||
|
OutgoingHeaders Header { get; }
|
||||||
|
void Compose(ServerMessage message);
|
||||||
|
}
|
|
@ -0,0 +1,11 @@
|
||||||
|
using Tiger.Communication.Messages.Incoming;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Interfaces;
|
||||||
|
|
||||||
|
public interface IMessageEvent
|
||||||
|
{
|
||||||
|
IncomingHeaders Header { get; }
|
||||||
|
Task HandleAsync(GameSession gameSession, ClientMessage request);
|
||||||
|
}
|
|
@ -0,0 +1,46 @@
|
||||||
|
using Microsoft.Extensions.Logging;
|
||||||
|
using Tiger.Communication.Messages.Incoming;
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages;
|
||||||
|
|
||||||
|
public class MessageHandler : IMessageHandler
|
||||||
|
{
|
||||||
|
private readonly ILogger<MessageHandler> _logger;
|
||||||
|
private readonly IDictionary<short, IMessageEvent> _messageEvents;
|
||||||
|
private readonly IDictionary<short, string> _messageNames;
|
||||||
|
|
||||||
|
public MessageHandler(ILogger<MessageHandler> logger, IEnumerable<IMessageEvent> messageEvents)
|
||||||
|
{
|
||||||
|
_logger = logger;
|
||||||
|
_messageEvents = messageEvents.ToDictionary(messageEvent => (short)messageEvent.Header);
|
||||||
|
|
||||||
|
_messageNames = new Dictionary<short, string>();
|
||||||
|
|
||||||
|
foreach (var name in Enum.GetNames(typeof(IncomingHeaders)))
|
||||||
|
{
|
||||||
|
_messageNames.Add((short)Enum.Parse(typeof(IncomingHeaders), name), name);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task TryHandleAsync(GameSession session, ClientMessage request)
|
||||||
|
{
|
||||||
|
if (request.Header == null)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_messageEvents.TryGetValue(request.Header.Value, out var messageEvent))
|
||||||
|
{
|
||||||
|
_logger.LogInformation("Handling header ID {Header} on class {Class}", request.Header.Value, messageEvent.GetType());
|
||||||
|
|
||||||
|
await messageEvent.HandleAsync(session, request);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
_logger.LogWarning("Unregistered header {Header} {Name}", request.Header.Value, _messageNames.TryGetValue(request.Header.Value, out var messageName) ? messageName : string.Empty);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,20 @@
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Outgoing.Generic.Alerts;
|
||||||
|
|
||||||
|
public class HabboBroadcastMessageComposer : IMessageComposer
|
||||||
|
{
|
||||||
|
private readonly string _welcomeMessage;
|
||||||
|
|
||||||
|
public HabboBroadcastMessageComposer(string welcomeMessage)
|
||||||
|
{
|
||||||
|
_welcomeMessage = welcomeMessage;
|
||||||
|
}
|
||||||
|
|
||||||
|
public OutgoingHeaders Header => OutgoingHeaders.HabboBroadcastMessageComposer;
|
||||||
|
public void Compose(ServerMessage message)
|
||||||
|
{
|
||||||
|
message.AppendString(_welcomeMessage);
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,13 @@
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Outgoing.Handshake;
|
||||||
|
|
||||||
|
public class AuthenticationOkMessageComposer : IMessageComposer
|
||||||
|
{
|
||||||
|
public OutgoingHeaders Header => OutgoingHeaders.AuthenticationOkMessageComposer;
|
||||||
|
|
||||||
|
public void Compose(ServerMessage message)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,35 @@
|
||||||
|
using System.Globalization;
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Game.Habbos;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Outgoing.Handshake;
|
||||||
|
|
||||||
|
public class UserObjectMessageComposer : IMessageComposer
|
||||||
|
{
|
||||||
|
private readonly Habbo _habbo;
|
||||||
|
|
||||||
|
public UserObjectMessageComposer(Habbo habbo)
|
||||||
|
{
|
||||||
|
_habbo = habbo;
|
||||||
|
}
|
||||||
|
|
||||||
|
public OutgoingHeaders Header => OutgoingHeaders.UserObjectComposer;
|
||||||
|
public void Compose(ServerMessage message)
|
||||||
|
{
|
||||||
|
message.AppendUInt32(_habbo.Id);
|
||||||
|
message.AppendString(_habbo.Username);
|
||||||
|
message.AppendString(_habbo.Figure);
|
||||||
|
message.AppendString(_habbo.Gender);
|
||||||
|
message.AppendString(_habbo.Motto);
|
||||||
|
message.AppendString(string.Empty);
|
||||||
|
message.AppendBoolean(false);
|
||||||
|
message.AppendInt32(0); // respect received
|
||||||
|
message.AppendInt32(0); // respect points to give
|
||||||
|
message.AppendInt32(0); // scratch to give
|
||||||
|
message.AppendBoolean(false);
|
||||||
|
message.AppendString(_habbo.LastLogin.ToString(CultureInfo.CurrentCulture));
|
||||||
|
message.AppendBoolean(false); // can change name
|
||||||
|
message.AppendBoolean(false); // safety locked
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,507 @@
|
||||||
|
namespace Tiger.Communication.Messages.Outgoing;
|
||||||
|
|
||||||
|
public enum OutgoingHeaders
|
||||||
|
{
|
||||||
|
AcceptFriendResultComposer = 896,
|
||||||
|
AccountPreferencesComposer = 513,
|
||||||
|
AccountSafetyLockStatusChangeMessageComposer = 1243,
|
||||||
|
AchievementComposer = 2107,
|
||||||
|
AchievementResolutionCompletedMessageComposer = 740,
|
||||||
|
AchievementResolutionProgressMessageComposer = 3370,
|
||||||
|
AchievementResolutionsMessageComposer = 66,
|
||||||
|
AchievementsComposer = 305,
|
||||||
|
AchievementsScoreComposer = 1968,
|
||||||
|
ActivityPointsMessageComposer = 2018,
|
||||||
|
ApproveNameMessageComposer = 1503,
|
||||||
|
AuthenticationOkMessageComposer = 2491,
|
||||||
|
AvailabilityStatusMessageComposer = 2033,
|
||||||
|
AvailabilityTimeMessageComposer = 600,
|
||||||
|
AvatarEffectActivatedMessageComposer = 1959,
|
||||||
|
AvatarEffectAddedMessageComposer = 2867,
|
||||||
|
AvatarEffectExpiredMessageComposer = 2228,
|
||||||
|
AvatarEffectMessageComposer = 1167,
|
||||||
|
AvatarEffectSelectedMessageComposer = 3473,
|
||||||
|
AvatarEffectsMessageComposer = 340,
|
||||||
|
BadgePointLimitsComposer = 2501,
|
||||||
|
BadgeReceivedComposer = 2493,
|
||||||
|
BadgesComposer = 717,
|
||||||
|
BannedUsersFromRoomComposer = 1869,
|
||||||
|
BonusRareInfoMessageComposer = 1533,
|
||||||
|
BotAddedToInventoryComposer = 1352,
|
||||||
|
BotCommandConfigurationComposer = 1618,
|
||||||
|
BotErrorComposer = 639,
|
||||||
|
BotForceOpenContextMenuComposer = 296,
|
||||||
|
BotInventoryComposer = 3086,
|
||||||
|
BotReceivedMessageComposer = 3684,
|
||||||
|
BotRemovedFromInventoryComposer = 233,
|
||||||
|
BotSkillListUpdateComposer = 69,
|
||||||
|
BuildersClubFurniCountMessageComposer = 3828,
|
||||||
|
BuildersClubSubscriptionStatusMessageComposer = 1452,
|
||||||
|
BundleDiscountRulesetMessageComposer = 2347,
|
||||||
|
CallForHelpDisabledNotifyMessageComposer = 1651,
|
||||||
|
CallForHelpPendingCallsDeletedMessageComposer = 77,
|
||||||
|
CallForHelpPendingCallsMessageComposer = 1121,
|
||||||
|
CallForHelpReplyMessageComposer = 3796,
|
||||||
|
CallForHelpResultMessageComposer = 3635,
|
||||||
|
CameraPublishStatusMessageComposer = 2057,
|
||||||
|
CameraPurchaseOkMessageComposer = 2783,
|
||||||
|
CameraSnapshotMessageComposer = 463,
|
||||||
|
CameraStorageUrlMessageComposer = 3696,
|
||||||
|
CampaignCalendarDataMessageComposer = 2531,
|
||||||
|
CampaignCalendarDoorOpenedMessageComposer = 2551,
|
||||||
|
CanCreateRoomComposer = 378,
|
||||||
|
CanCreateRoomEventComposer = 2599,
|
||||||
|
CantConnectMessageComposer = 899,
|
||||||
|
CarryObjectMessageComposer = 1474,
|
||||||
|
CatalogPageExpirationComposer = 2668,
|
||||||
|
CatalogPageMessageComposer = 804,
|
||||||
|
CatalogPagesListComposer = 1032,
|
||||||
|
CatalogPageWithEarliestExpiryMessageComposer = 2515,
|
||||||
|
CatalogPublishedMessageComposer = 1866,
|
||||||
|
CategoriesWithVisitorCountComposer = 1455,
|
||||||
|
CfhChatlogComposer = 607,
|
||||||
|
CfhSanctionMessageComposer = 2782,
|
||||||
|
CfhTopicsInitComposer = 325,
|
||||||
|
ChangeEmailResultComposer = 1815,
|
||||||
|
ChangeUserNameResultMessageEvent = 118,
|
||||||
|
ChatMessageComposer = 1446,
|
||||||
|
ChatReviewSessionDetachedMessageComposer = 30,
|
||||||
|
ChatReviewSessionOfferedToGuideMessageComposer = 735,
|
||||||
|
ChatReviewSessionResultsMessageComposer = 3276,
|
||||||
|
ChatReviewSessionStartedMessageComposer = 143,
|
||||||
|
ChatReviewSessionVotingStatusMessageComposer = 1829,
|
||||||
|
CheckUserNameResultMessageComposer = 563,
|
||||||
|
CitizenshipVipOfferPromoEnabledComposer = 2278,
|
||||||
|
CloseConnectionMessageComposer = 122,
|
||||||
|
ClubGiftInfoComposer = 619,
|
||||||
|
ClubGiftNotificationComposer = 2188,
|
||||||
|
ClubGiftSelectedComposer = 659,
|
||||||
|
CollapsedCategoriesComposer = 1543,
|
||||||
|
CommunityGoalEarnedPrizesMessageComposer = 3319,
|
||||||
|
CommunityGoalHallOfFameMessageComposer = 3005,
|
||||||
|
CommunityGoalProgressMessageComposer = 2525,
|
||||||
|
CommunityGoalVoteMessageComposer = 1435,
|
||||||
|
CompetitionEntrySubmitResultComposer = 1177,
|
||||||
|
CompetitionRoomsDataMessageComposer = 3954,
|
||||||
|
CompetitionStatusMessageComposer = 133,
|
||||||
|
CompetitionVotingInfoMessageComposer = 3506,
|
||||||
|
CompleteDiffieHandshakeComposer = 3885,
|
||||||
|
ConcurrentUsersGoalProgressMessageComposer = 2737,
|
||||||
|
ConfirmBreedingRequestComposer = 634,
|
||||||
|
ConfirmBreedingResultComposer = 1625,
|
||||||
|
ConvertedRoomIdComposer = 1331,
|
||||||
|
CraftableProductsComposer = 1000,
|
||||||
|
CraftingRecipeComposer = 2774,
|
||||||
|
CraftingRecipesAvailableComposer = 2124,
|
||||||
|
CraftingResultComposer = 618,
|
||||||
|
CreditBalanceComposer = 3475,
|
||||||
|
CurrentTimingCodeMessageComposer = 1745,
|
||||||
|
CustomUserNotificationMessageComposer = 909,
|
||||||
|
DanceMessageComposer = 2233,
|
||||||
|
DiceValueMessageComposer = 3431,
|
||||||
|
DirectSmsClubBuyAvailableMessageComposer = 195,
|
||||||
|
DisconnectReasonComposer = 4000,
|
||||||
|
DoorbellMessageComposer = 2309,
|
||||||
|
ElementPointerMessageComposer = 1787,
|
||||||
|
EmailStatusResultComposer = 612,
|
||||||
|
EpicPopupMessageComposer = 3945,
|
||||||
|
ErrorReportComposer = 1004,
|
||||||
|
ExpressionMessageComposer = 1631,
|
||||||
|
ExtendedProfileChangedMessageComposer = 876,
|
||||||
|
ExtendedProfileMessageComposer = 3898,
|
||||||
|
FaqCategoriesMessageComposer = 2756,
|
||||||
|
FaqCategoryMessageComposer = 2819,
|
||||||
|
FaqClientFaqsMessageComposer = 2492,
|
||||||
|
FaqSearchResultsMessageComposer = 1551,
|
||||||
|
FaqTextMessageComposer = 3292,
|
||||||
|
FavoriteMembershipUpdateMessageComposer = 3403,
|
||||||
|
FavouriteChangedComposer = 2524,
|
||||||
|
FavouritesComposer = 151,
|
||||||
|
FigureSetIdsComposer = 1450,
|
||||||
|
FigureUpdateComposer = 2429,
|
||||||
|
FindFriendsProcessResultComposer = 1210,
|
||||||
|
FlatAccessDeniedMessageComposer = 878,
|
||||||
|
FlatAccessibleMessageComposer = 3783,
|
||||||
|
FlatControllerAddedComposer = 2088,
|
||||||
|
FlatControllerRemovedComposer = 1327,
|
||||||
|
FlatControllersComposer = 1284,
|
||||||
|
FlatCreatedComposer = 1304,
|
||||||
|
FloodControlMessageComposer = 566,
|
||||||
|
FloorHeightMapComposer = 1301,
|
||||||
|
FollowFriendFailedComposer = 3048,
|
||||||
|
ForumDataMessageComposer = 3011,
|
||||||
|
ForumsListMessageComposer = 3001,
|
||||||
|
FriendFurniCancelLockMessageComposer = 770,
|
||||||
|
FriendFurniOtherLockConfirmedMessageComposer = 382,
|
||||||
|
FriendFurniStartConfirmationMessageComposer = 3753,
|
||||||
|
FriendListFragmentMessageComposer = 3130,
|
||||||
|
FriendListUpdateComposer = 2800,
|
||||||
|
FriendNotificationComposer = 3082,
|
||||||
|
FriendRequestsComposer = 280,
|
||||||
|
FurniListAddOrUpdateComposer = 104,
|
||||||
|
FurniListComposer = 994,
|
||||||
|
FurniListInvalidateComposer = 3151,
|
||||||
|
FurniListRemoveComposer = 159,
|
||||||
|
FurniRentOrBuyoutOfferMessageComposer = 35,
|
||||||
|
FurnitureAliasesMessageComposer = 1723,
|
||||||
|
Game2AccountGameStatusMessageComposer = 2893,
|
||||||
|
Game2GameDirectoryStatusMessageComposer = 2246,
|
||||||
|
Game2InArenaQueueMessageComposer = 872,
|
||||||
|
Game2JoiningGameFailedMessageComposer = 1730,
|
||||||
|
Game2StopCounterMessageComposer = 2233,
|
||||||
|
Game2UserLeftGameMessageComposer = 2383,
|
||||||
|
Game2WeeklyFriendsLeaderboardComposer = 2270,
|
||||||
|
Game2WeeklyLeaderboardComposer = 2196,
|
||||||
|
GameAchievementsMessageComposer = 1689,
|
||||||
|
GameInviteMessageComposer = 904,
|
||||||
|
GameListMessageComposer = 222,
|
||||||
|
GamePlayerValueMessageComposer = 2324,
|
||||||
|
GameStatusMessageComposer = 3805,
|
||||||
|
GenericErrorComposer = 1600,
|
||||||
|
GetGuestRoomResultComposer = 687,
|
||||||
|
GiftReceiverNotFoundComposer = 1517,
|
||||||
|
GiftWrappingConfigurationComposer = 2234,
|
||||||
|
GotMysteryBoxPrizeMessageComposer = 3712,
|
||||||
|
GoToBreedingNestFailureComposer = 2621,
|
||||||
|
GroupDetailsChangedMessageComposer = 1459,
|
||||||
|
GroupMembershipRequestedMessageComposer = 1180,
|
||||||
|
GuestRoomSearchResultComposer = 52,
|
||||||
|
GuideOnDutyStatusMessageComposer = 1548,
|
||||||
|
GuideReportingStatusMessageComposer = 3463,
|
||||||
|
GuideSessionAttachedMessageComposer = 1591,
|
||||||
|
GuideSessionDetachedMessageComposer = 138,
|
||||||
|
GuideSessionEndedMessageComposer = 1456,
|
||||||
|
GuideSessionErrorMessageComposer = 673,
|
||||||
|
GuideSessionInvitedToGuideRoomMessageComposer = 219,
|
||||||
|
GuideSessionMessageMessageComposer = 841,
|
||||||
|
GuideSessionPartnerIsTypingComposer = 1016,
|
||||||
|
GuideSessionRequesterRoomMessageComposer = 1847,
|
||||||
|
GuideSessionStartedComposer = 3209,
|
||||||
|
GuideTicketCreationResultMessageComposer = 3285,
|
||||||
|
GuideTicketResolutionMessageComposer = 2674,
|
||||||
|
GuildCreatedMessageComposer = 2808,
|
||||||
|
GuildCreationInfoMessageComposer = 2159,
|
||||||
|
GuildEditFailedMessageComposer = 3988,
|
||||||
|
GuildEditInfoMessageComposer = 3965,
|
||||||
|
GuildEditorDataMessageComposer = 2238,
|
||||||
|
GuildForumThreadsComposer = 1073,
|
||||||
|
GuildFurniContextMenuInfoMessageComposer = 3293,
|
||||||
|
GuildMemberFurniCountInHqMessageComposer = 1876,
|
||||||
|
GuildMemberMgmtFailedMessageComposer = 818,
|
||||||
|
GuildMembersComposer = 1200,
|
||||||
|
GuildMembershipRejectedMessageComposer = 2445,
|
||||||
|
GuildMembershipsMessageComposer = 420,
|
||||||
|
GuildMembershipUpdatedMessageComposer = 265,
|
||||||
|
HabboAchievementNotificationMessageComposer = 806,
|
||||||
|
HabboActivityPointNotificationMessageComposer = 2275,
|
||||||
|
HabboBroadcastMessageComposer = 3801,
|
||||||
|
HabboClubExtendOfferMessageComposer = 3964,
|
||||||
|
HabboClubOffersMessageComposer = 2405,
|
||||||
|
HabboGroupBadgesMessageComposer = 2402,
|
||||||
|
HabboGroupDeactivatedMessageComposer = 3129,
|
||||||
|
HabboGroupDetailsMessageComposer = 1702,
|
||||||
|
HabboGroupJoinFailedMessageComposer = 762,
|
||||||
|
HabboSearchResultComposer = 973,
|
||||||
|
HabboWayQuizComposer1 = 3379,
|
||||||
|
HandItemReceivedMessageComposer = 354,
|
||||||
|
HeightMapComposer = 2753,
|
||||||
|
HeightMapUpdateMessageComposer = 558,
|
||||||
|
HotelClosedAndOpensComposer = 3728,
|
||||||
|
HotelClosesAndWillOpenAtComposer = 2771,
|
||||||
|
HotelMergeNameChangeComposer = 1663,
|
||||||
|
HotelViewCatalogPageExpiringComposer = 690,
|
||||||
|
HotelViewCustomTimerComposer = -1,
|
||||||
|
HotelWillCloseInMinutesComposer = 1050,
|
||||||
|
IdentityAccountsComposer = 3523,
|
||||||
|
IgnoredUsersMessageComposer = 126,
|
||||||
|
IgnoreResultMessageComposer = 207,
|
||||||
|
InClientLinkMessageComposer = 2023,
|
||||||
|
InfoFeedEnableMessageComposer = 3284,
|
||||||
|
InitCameraMessageComposer = 3878,
|
||||||
|
InitDiffieHandshakeComposer = 1347,
|
||||||
|
InstantMessageErrorComposer = 3359,
|
||||||
|
InterstitialMessageComposer = 1808,
|
||||||
|
IsBadgeRequestFulfilledComposer = 2998,
|
||||||
|
IsFirstLoginOfDayComposer = 793,
|
||||||
|
IsOfferGiftableMessageComposer = 761,
|
||||||
|
IssueCloseNotificationMessageComposer = 934,
|
||||||
|
IssueDeletedMessageComposer = 3192,
|
||||||
|
IssueInfoMessageComposer = 3609,
|
||||||
|
IssuePickFailedMessageComposer = 3150,
|
||||||
|
IsUserPartOfCompetitionMessageComposer = 3841,
|
||||||
|
ItemAddMessageComposer = 2187,
|
||||||
|
ItemDataUpdateMessageComposer = 2202,
|
||||||
|
ItemRemoveMessageComposer = 3208,
|
||||||
|
ItemsComposer = 1369,
|
||||||
|
ItemUpdateMessageComposer = 2009,
|
||||||
|
JoinedQueueMessageComposer = 2260,
|
||||||
|
JoiningQueueFailedMessageComposer = 3035,
|
||||||
|
JukeBoxPlaylistFullMessageComposer = 105,
|
||||||
|
JukeboxSongDisksMessageComposer = 34,
|
||||||
|
LatencyPingResponseMessageComposer = 10,
|
||||||
|
LeftQueueMessageComposer = 1477,
|
||||||
|
LimitedEditionSoldOutComposer = 377,
|
||||||
|
LimitedOfferAppearingNextMessageComposer = 44,
|
||||||
|
LoadGameMessageComposer = 3654,
|
||||||
|
LoadGameUrlMessageComposer = 2624,
|
||||||
|
MaintenanceStatusMessageComposer = 1350,
|
||||||
|
MarketplaceBuyOfferResultComposer = 2032,
|
||||||
|
MarketplaceCancelOfferResultComposer = 3264,
|
||||||
|
MarketplaceCanMakeOfferResult = 54,
|
||||||
|
MarketplaceConfigurationComposer = 1823,
|
||||||
|
MarketplaceItemStatsComposer = 725,
|
||||||
|
MarketplaceMakeOfferResult = 1359,
|
||||||
|
MarketplaceOffersComposer = 680,
|
||||||
|
MarketPlaceOwnOffersComposer = 3884,
|
||||||
|
MessengerErrorComposer = 892,
|
||||||
|
MessengerInitComposer = 1605,
|
||||||
|
MiniMailNewMessageComposer = 1911,
|
||||||
|
MiniMailUnreadCountComposer = 2803,
|
||||||
|
ModeratorActionResultMessageComposer = 2335,
|
||||||
|
ModeratorCautionComposer = 1890,
|
||||||
|
ModeratorInitMessageComposer = 2696,
|
||||||
|
ModeratorMessageComposer = 2030,
|
||||||
|
ModeratorRoomInfoComposer = 1333,
|
||||||
|
ModeratorToolPreferencesComposer = 1576,
|
||||||
|
ModeratorUserInfoComposer = 2866,
|
||||||
|
MOtdNotificationComposer = 2035,
|
||||||
|
MuteAllInRoomComposer = 2533,
|
||||||
|
MysteryBoxClosingComposer = 596,
|
||||||
|
MysteryBoxKeysMessageComposer = 2833,
|
||||||
|
MysteryBoxStartComposer = 3201,
|
||||||
|
NavigatorLiftedRoomsComposer = 3104,
|
||||||
|
NavigatorMetaDataComposer = 3052,
|
||||||
|
NavigatorSavedSearchesComposer = 3984,
|
||||||
|
NavigatorSearchResultBlocksComposer = 2690,
|
||||||
|
NavigatorSettingsComposer = 2875,
|
||||||
|
NestBreedingSuccessComposer = 2527,
|
||||||
|
NewConsoleMessageComposer = 1587,
|
||||||
|
NewFriendRequestComposer = 2219,
|
||||||
|
NewNavigatorPreferencesComposer = 518,
|
||||||
|
NewUserExperienceGiftOfferComposer = 3575,
|
||||||
|
NewUserExperienceNotCompleteComposer = 3639,
|
||||||
|
NoobnessLevelMessageComposer = 3738,
|
||||||
|
NoOwnedRoomsAlertMessageComposer = 2064,
|
||||||
|
NoSuchFlatComposer = 84,
|
||||||
|
NotEnoughBalanceMessageComposer = 3914,
|
||||||
|
NotificationDialogMessageComposer = 1992,
|
||||||
|
NowPlayingMessageComposer = 469,
|
||||||
|
ObjectAddMessageComposer = 1534,
|
||||||
|
ObjectDataUpdateMessageComposer = 2547,
|
||||||
|
ObjectRemoveMessageComposer = 2703,
|
||||||
|
ObjectsDataUpdateMessageComposer = 1453,
|
||||||
|
ObjectsMessageComposer = 1778,
|
||||||
|
ObjectUpdateMessageComposer = 3776,
|
||||||
|
OfferRewardDeliveredMessageComposer = 2125,
|
||||||
|
OfficialRoomsComposer = 2726,
|
||||||
|
OfficialSongIdMessageComposer = 1381,
|
||||||
|
OneWayDoorStatusMessageComposer = 2376,
|
||||||
|
OpenComposer = 1830,
|
||||||
|
OpenConnectionMessageComposer = 758,
|
||||||
|
OpenPetPackageRequestedMessageComposer = 2380,
|
||||||
|
OpenPetPackageResultMessageComposer = 546,
|
||||||
|
PerkAllowancesComposer = 2586,
|
||||||
|
PetAddedToInventoryComposer = 2101,
|
||||||
|
PetBreedingComposer = 1746,
|
||||||
|
PetBreedingResultComposer = 1553,
|
||||||
|
PetExperienceComposer = 2156,
|
||||||
|
PetFigureUpdateComposer = 1924,
|
||||||
|
PetInfoMessageComposer = 2901,
|
||||||
|
PetInventoryComposer = 3522,
|
||||||
|
PetLevelNotificationComposer = 859,
|
||||||
|
PetLevelUpdateComposer = 2824,
|
||||||
|
PetPlacingErrorComposer = 2913,
|
||||||
|
PetReceivedMessageComposer = 1111,
|
||||||
|
PetRemovedFromInventoryComposer = 3253,
|
||||||
|
PetRespectFailedComposer = 1130,
|
||||||
|
PetRespectNotificationComposer = 2788,
|
||||||
|
PetStatusUpdateComposer = 1907,
|
||||||
|
PetSupplementedNotificationComposer = 3441,
|
||||||
|
PetTrainingPanelComposer = 1164,
|
||||||
|
PhoneCollectionStateMessageComposer = 2890,
|
||||||
|
PingMessageComposer = 3928,
|
||||||
|
PlayListMessageComposer = 1748,
|
||||||
|
PlayListSongAddedMessageComposer = 1140,
|
||||||
|
PollContentsComposer = 2997,
|
||||||
|
PollErrorComposer = 662,
|
||||||
|
PollOfferComposer = 3785,
|
||||||
|
PopularRoomTagsResultComposer = 2012,
|
||||||
|
PostItPlacedComposer = 1501,
|
||||||
|
PostMessageMessageComposer = 2049,
|
||||||
|
PostThreadMessageComposer = 1862,
|
||||||
|
PresentOpenedMessageComposer = 56,
|
||||||
|
ProductOfferComposer = 3388,
|
||||||
|
PromoArticlesMessageComposer = 286,
|
||||||
|
PurchaseErrorMessageComposer = 1404,
|
||||||
|
PurchaseNotAllowedMessageComposer = 3770,
|
||||||
|
PurchaseOkMessageComposer = 869,
|
||||||
|
QuestCancelledMessageComposer = 3027,
|
||||||
|
QuestCompletedMessageComposer = 949,
|
||||||
|
QuestDailyMessageComposer = 1878,
|
||||||
|
QuestionAnsweredComposer = 2589,
|
||||||
|
QuestionComposer = 2665,
|
||||||
|
QuestionFinishedComposer = 1066,
|
||||||
|
QuestionInfoComposer = -1,
|
||||||
|
QuestMessageComposer = 230,
|
||||||
|
QuestsMessageComposer = 3625,
|
||||||
|
QuizDataMessageComposer = 2927,
|
||||||
|
QuizResultsMessageComposer = 2772,
|
||||||
|
RecyclerFinishedComposer = 468,
|
||||||
|
RecyclerPrizesComposer = 3164,
|
||||||
|
RecyclerStatusComposer = 3433,
|
||||||
|
RelationshipStatusInfoComposer = 2016,
|
||||||
|
RemainingMutePeriodComposer = 826,
|
||||||
|
RentableSpaceRentFailedMessageComposer = 1868,
|
||||||
|
RentableSpaceRentOkMessageComposer = 2046,
|
||||||
|
RentableSpaceStatusMessageComposer = 3559,
|
||||||
|
RequestSpamWallPostItMessageComposer = 2366,
|
||||||
|
RestoreClientMessageComposer = 426,
|
||||||
|
RoomAdErrorComposer = 1759,
|
||||||
|
RoomAdPurchaseInfoComposer = 2468,
|
||||||
|
RoomChatlogComposer = 3434,
|
||||||
|
RoomChatSettingsMessageComposer = 1191,
|
||||||
|
RoomDimmerPresetsComposer = 2710,
|
||||||
|
RoomEntryInfoComposer = -1,
|
||||||
|
RoomEntryInfoMessageComposer = 749,
|
||||||
|
RoomEntryTileMessageComposer = 1664,
|
||||||
|
RoomEventCancelComposer = 3479,
|
||||||
|
RoomEventComposer = 1840,
|
||||||
|
RoomFilterSettingsMessageComposer = 2937,
|
||||||
|
RoomFloorThicknessUpdatedComposer = 3786,
|
||||||
|
RoomForwardMessageComposer = 160,
|
||||||
|
RoomInfoUpdatedComposer = 3297,
|
||||||
|
RoomInviteComposer = 3870,
|
||||||
|
RoomInviteErrorComposer = 462,
|
||||||
|
RoomMessageNotificationMessageComposer = 1634,
|
||||||
|
RoomOccupiedTilesMessageComposer = 3990,
|
||||||
|
RoomPropertyMessageComposer = 2454,
|
||||||
|
RoomQueueStatusMessageComposer = 2208,
|
||||||
|
RoomRatingComposer = 482,
|
||||||
|
RoomReadyMessageComposer = 2031,
|
||||||
|
RoomSettingsDataComposer = 1498,
|
||||||
|
RoomSettingsErrorComposer = 2897,
|
||||||
|
RoomSettingsSavedComposer = 948,
|
||||||
|
RoomSettingsSaveErrorComposer = 1555,
|
||||||
|
RoomThumbnailUpdateResultComposer = 1927,
|
||||||
|
RoomUserQuestionAnsweredComposer = -1,
|
||||||
|
RoomUserRespectComposer = 2815,
|
||||||
|
RoomVisitsComposer = 1752,
|
||||||
|
RoomVisualizationSettingsComposer = 3547,
|
||||||
|
SanctionStatusComposer = 2221,
|
||||||
|
ScrSendKickbackInfoMessageComposer = 3277,
|
||||||
|
ScrSendUserInfoComposer = 954,
|
||||||
|
SeasonalCalendarDailyOfferMessageComposer = 1889,
|
||||||
|
SeasonalQuestsMessageComposer = 1122,
|
||||||
|
SecondsUntilMessageComposer = 3926,
|
||||||
|
SellablePetPalettesMessageComposer = 3331,
|
||||||
|
ShoutMessageComposer = 1036,
|
||||||
|
ShowEnforceRoomCategoryDialogComposer = 3896,
|
||||||
|
SleepMessageComposer = 1797,
|
||||||
|
SlideObjectBundleMessageComposer = 3207,
|
||||||
|
Str16258Composer = 1660,
|
||||||
|
Str16667Composer = 3099,
|
||||||
|
Str17054Composer = 416,
|
||||||
|
TalentLevelUpComposer = 638,
|
||||||
|
TalentTrackLevelMessageEvent = 1203,
|
||||||
|
TalentTrackMessageComposer = 3406,
|
||||||
|
TargetedOfferComposer = 119,
|
||||||
|
TargetedOfferNotFoundComposer = 1237,
|
||||||
|
ThreadMessagesMessageComposer = 509,
|
||||||
|
ThumbnailStatusMessageComposer = 3595,
|
||||||
|
TradeCloseWindowComposer = 1001,
|
||||||
|
TradeCompleteComposer = 2369,
|
||||||
|
TradingAcceptComposer = 2568,
|
||||||
|
TradingCloseComposer = 1373,
|
||||||
|
TradingConfirmationComposer = 2720,
|
||||||
|
TradingItemListComposer = 2024,
|
||||||
|
TradingNoSuchItemComposer = 2873,
|
||||||
|
TradingNotOpenComposer = 3128,
|
||||||
|
TradingOpenComposer = 2505,
|
||||||
|
TradingOpenFailedComposer = 217,
|
||||||
|
TradingOtherNotAllowedComposer = 1254,
|
||||||
|
TradingYouAreNotAllowedComposer = 3058,
|
||||||
|
TraxSongInfoMessageComposer = 3365,
|
||||||
|
TryPhoneNumberResultMessageComposer = 800,
|
||||||
|
TryVerificationCodeResultMessageComposer = 91,
|
||||||
|
UniqueMachineIdComposer = 1488,
|
||||||
|
Unknowncomposer1188 = 1437,
|
||||||
|
UnloadGameMessageComposer = 1715,
|
||||||
|
UnreadForumsCountMessageComposer = 2379,
|
||||||
|
UnseenItemsComposer = 2103,
|
||||||
|
UpdateMessageMessageComposer = 324,
|
||||||
|
UpdateStackHeightTileHeightComposer = 2816,
|
||||||
|
UpdateThreadMessageComposer = 2528,
|
||||||
|
UseObjectMessageComposer = 1774,
|
||||||
|
UserBadgesComposer = 1087,
|
||||||
|
UserBannedMessageComposer = 1683,
|
||||||
|
UserBcLimitsComposer = -1,
|
||||||
|
UserChangeMessageComposer = 3920,
|
||||||
|
UserChatlogComposer = 3377,
|
||||||
|
UserClassificationMessageComposer = 966,
|
||||||
|
UserEventCatsComposer = 3244,
|
||||||
|
UserFlatCatsComposer = 1562,
|
||||||
|
UserGameAchievementsMessageComposer = 2265,
|
||||||
|
UserNameChangedMessageComposer = 2182,
|
||||||
|
UserObjectComposer = 2725,
|
||||||
|
UserRemoveMessageComposer = 2661,
|
||||||
|
UserRightsMessageComposer = 411,
|
||||||
|
UsersComposer = 374,
|
||||||
|
UserSongDisksInventoryMessageComposer = 2602,
|
||||||
|
UserTagsMessageComposer = 1255,
|
||||||
|
UserTypingMessageComposer = 1717,
|
||||||
|
UserUnbannedFromRoomComposer = 3429,
|
||||||
|
UserUpdateComposer = 1640,
|
||||||
|
VoucherRedeemErrorMessageComposer = 714,
|
||||||
|
VoucherRedeemOkMessageComposer = 3336,
|
||||||
|
WardrobeMessageComposer = 3315,
|
||||||
|
WeeklyCompetitiveFriendsLeaderboardComposer = 3560,
|
||||||
|
WeeklyCompetitiveLeaderboardComposer = 3512,
|
||||||
|
WeeklyGameRewardComposer = 2641,
|
||||||
|
WeeklyGameRewardWinnersComposer = 3097,
|
||||||
|
WelcomeGiftChangeEmailResultComposer = 2293,
|
||||||
|
WelcomeGiftStatusComposer = 2707,
|
||||||
|
WhisperMessageComposer = 2704,
|
||||||
|
WiredConditionDataComposer = 1108,
|
||||||
|
WiredEffectDataComposer = 1434,
|
||||||
|
WiredRewardResultMessageComposer = 178,
|
||||||
|
WiredSavedComposer = 1155,
|
||||||
|
WiredTriggerDataComposer = 383,
|
||||||
|
WiredValidationErrorComposer = 156,
|
||||||
|
YouAreControllerMessageComposer = 780,
|
||||||
|
YouAreNotControllerMessageComposer = 2392,
|
||||||
|
YouAreOwnerMessageComposer = 339,
|
||||||
|
YouArePlayingGameMessageComposer = 448,
|
||||||
|
YouAreSpectatorMessageEvent = 1033,
|
||||||
|
YoutubeControlVideoMessageComposer = 1554,
|
||||||
|
YoutubeDisplayPlaylistsComposer = 1112,
|
||||||
|
YoutubeDisplayVideoMessageComposer = 1411,
|
||||||
|
SnowStormGameStartedComposer = 5000,
|
||||||
|
SnowStormQuePositionComposer = 5001,
|
||||||
|
SnowStormStartBlockTickerComposer = 5002,
|
||||||
|
SnowStormStartLobbyCounterComposer = 5003,
|
||||||
|
SnowStormUnusedAlertGenericComposer = 5004,
|
||||||
|
SnowStormLongDataComposer = 5005,
|
||||||
|
SnowStormGameEndedComposer = 5006,
|
||||||
|
SnowStormQuePlayerAddedComposer = 5008,
|
||||||
|
SnowStormPlayAgainComposer = 5009,
|
||||||
|
SnowStormGamesLeftComposer = 5010,
|
||||||
|
SnowStormQuePlayerRemovedComposer = 5011,
|
||||||
|
SnowStormGamesInformationComposer = 5012,
|
||||||
|
SnowStormLongData2Composer = 5013,
|
||||||
|
UnusedSnowstorm5014 = 5014,
|
||||||
|
SnowStormGameStatusComposer = 5015,
|
||||||
|
SnowStormFullGameStatusComposer = 5016,
|
||||||
|
SnowStormOnStageStartComposer = 5017,
|
||||||
|
SnowStormIntializeGameArenaViewComposer = 5018,
|
||||||
|
SnowStormRejoinPreviousRoomComposer = 5019,
|
||||||
|
UnknownSnowstorm5020 = 5020,
|
||||||
|
SnowStormLevelDataComposer = 5021,
|
||||||
|
SnowStormOnGameEndingComposer = 5022,
|
||||||
|
SnowStormUserChatMessageComposer = 5023,
|
||||||
|
SnowStormOnStageRunningComposer = 5024,
|
||||||
|
SnowStormOnStageEndingComposer = 5025,
|
||||||
|
SnowStormIntializedPlayersComposer = 5026,
|
||||||
|
SnowStormOnPlayerExitedArenaComposer = 5027,
|
||||||
|
SnowStormGenericErrorComposer = 5028,
|
||||||
|
SnowStormUserRematchedComposer = 5029
|
||||||
|
}
|
|
@ -0,0 +1,70 @@
|
||||||
|
using System.Text;
|
||||||
|
using Tiger.Utils;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Types;
|
||||||
|
|
||||||
|
public class ClientMessage
|
||||||
|
{
|
||||||
|
private readonly byte[] _packet;
|
||||||
|
private int _readerIndex;
|
||||||
|
|
||||||
|
public short? Header { get; }
|
||||||
|
|
||||||
|
public ClientMessage(byte[] packet)
|
||||||
|
{
|
||||||
|
_packet = packet;
|
||||||
|
_readerIndex = 0;
|
||||||
|
Header = ReadInt16();
|
||||||
|
}
|
||||||
|
|
||||||
|
public short? ReadInt16()
|
||||||
|
{
|
||||||
|
var raw = ReadBytes(2);
|
||||||
|
|
||||||
|
if (raw.Length != 2) return null;
|
||||||
|
|
||||||
|
return ByteUtils.GetInt16(raw);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int? ReadInt32()
|
||||||
|
{
|
||||||
|
var raw = ReadBytes(4);
|
||||||
|
|
||||||
|
if (raw.Length != 4) return null;
|
||||||
|
|
||||||
|
return ByteUtils.GetInt32(raw);
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool? ReadBoolean()
|
||||||
|
{
|
||||||
|
if (_packet.Length - _readerIndex == 0) return null;
|
||||||
|
|
||||||
|
var result = _packet[_readerIndex];
|
||||||
|
_readerIndex++;
|
||||||
|
return result == 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
public string? ReadString()
|
||||||
|
{
|
||||||
|
var strlen = ReadInt16();
|
||||||
|
|
||||||
|
if (strlen == null) return null;
|
||||||
|
|
||||||
|
var raw = ReadBytes(strlen.Value);
|
||||||
|
|
||||||
|
return raw.Length != strlen ? null : Encoding.UTF8.GetString(raw);
|
||||||
|
}
|
||||||
|
|
||||||
|
private byte[] ReadBytes(int amount)
|
||||||
|
{
|
||||||
|
if (_packet.Length - _readerIndex < amount)
|
||||||
|
{
|
||||||
|
return Array.Empty<byte>();
|
||||||
|
}
|
||||||
|
|
||||||
|
var data = new byte[amount];
|
||||||
|
Array.Copy(_packet, _readerIndex, data, 0, amount);
|
||||||
|
_readerIndex += amount;
|
||||||
|
return data;
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,48 @@
|
||||||
|
using System.Text;
|
||||||
|
using Tiger.Utils;
|
||||||
|
|
||||||
|
namespace Tiger.Communication.Messages.Types;
|
||||||
|
|
||||||
|
public class ServerMessage
|
||||||
|
{
|
||||||
|
private readonly List<byte> _packet = new();
|
||||||
|
|
||||||
|
public ServerMessage(short header)
|
||||||
|
{
|
||||||
|
AppendInt16(header);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void AppendInt16(short value)
|
||||||
|
{
|
||||||
|
_packet.AddRange(ByteUtils.Int16ToArray(value));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void AppendInt32(int value)
|
||||||
|
{
|
||||||
|
_packet.AddRange(ByteUtils.Int32ToArray(value));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void AppendUInt32(uint value)
|
||||||
|
{
|
||||||
|
_packet.AddRange(ByteUtils.UInt32ToArray(value));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void AppendBoolean(bool value)
|
||||||
|
{
|
||||||
|
_packet.Add((byte)(value ? 1 : 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void AppendString(string value)
|
||||||
|
{
|
||||||
|
AppendInt16((short)value.Length);
|
||||||
|
_packet.AddRange(Encoding.UTF8.GetBytes(value));
|
||||||
|
}
|
||||||
|
|
||||||
|
public byte[] ToArray()
|
||||||
|
{
|
||||||
|
var finalizedPacket = new List<byte>();
|
||||||
|
finalizedPacket.AddRange(ByteUtils.Int32ToArray(_packet.Count));
|
||||||
|
finalizedPacket.AddRange(_packet);
|
||||||
|
return finalizedPacket.ToArray();
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,39 @@
|
||||||
|
using MySqlConnector;
|
||||||
|
|
||||||
|
namespace Tiger.Game.Habbos;
|
||||||
|
|
||||||
|
public class Habbo
|
||||||
|
{
|
||||||
|
public uint Id { get; }
|
||||||
|
public string Username { get; }
|
||||||
|
public string Email { get; }
|
||||||
|
public DateTime AccountCreated { get; }
|
||||||
|
public DateTime LastLogin { get; }
|
||||||
|
public string Motto { get; set; }
|
||||||
|
public string Figure { get; set; }
|
||||||
|
public string Gender { get; set; }
|
||||||
|
public byte Rank { get; set; }
|
||||||
|
public uint Credits { get; set; }
|
||||||
|
public bool Online { get; set; }
|
||||||
|
public uint HomeRoom { get; set; }
|
||||||
|
public uint AchievementScore { get; set; }
|
||||||
|
public uint GroupId { get; set; }
|
||||||
|
|
||||||
|
public Habbo(MySqlDataReader reader)
|
||||||
|
{
|
||||||
|
Id = reader.GetUInt32("id");
|
||||||
|
Username = reader.GetString("username");
|
||||||
|
Email = reader.GetString("email");
|
||||||
|
AccountCreated = reader.GetDateTime("account_created");
|
||||||
|
LastLogin = reader.GetDateTime("last_login");
|
||||||
|
Motto = reader.GetString("motto");
|
||||||
|
Figure = reader.GetString("figure");
|
||||||
|
Gender = reader.GetString("gender");
|
||||||
|
Rank = reader.GetByte("rank");
|
||||||
|
Credits = reader.GetUInt32("credits");
|
||||||
|
Online = reader.GetBoolean("online");
|
||||||
|
HomeRoom = reader.GetUInt32("home_room");
|
||||||
|
AchievementScore = reader.GetUInt32("achievement_score");
|
||||||
|
GroupId = reader.GetUInt32("group_id");
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,26 @@
|
||||||
|
using Tiger.Storage;
|
||||||
|
|
||||||
|
namespace Tiger.Game.Habbos;
|
||||||
|
|
||||||
|
public class HabboDao : IHabboDao
|
||||||
|
{
|
||||||
|
private readonly IDatabaseHelper _databaseHelper;
|
||||||
|
|
||||||
|
public HabboDao(IDatabaseHelper databaseHelper)
|
||||||
|
{
|
||||||
|
_databaseHelper = databaseHelper;
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task<Habbo?> GetHabboBySsoAsync(string sso)
|
||||||
|
{
|
||||||
|
await using var dbConnection = _databaseHelper.GetConnection();
|
||||||
|
var resultSet =
|
||||||
|
await dbConnection.GetResultSet("SELECT * FROM habbos WHERE sso_ticket = @sso LIMIT 1", ("@sso", sso));
|
||||||
|
if (await resultSet.ReadAsync())
|
||||||
|
{
|
||||||
|
return new Habbo(resultSet);
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
namespace Tiger.Game.Habbos;
|
||||||
|
|
||||||
|
public interface IHabboDao
|
||||||
|
{
|
||||||
|
Task<Habbo?> GetHabboBySsoAsync(string sso);
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
namespace Tiger.Game.Settings;
|
||||||
|
|
||||||
|
public interface ISettingsDao
|
||||||
|
{
|
||||||
|
Task<IReadOnlyDictionary<string, object>> GetSettingsAsync();
|
||||||
|
}
|
|
@ -0,0 +1,7 @@
|
||||||
|
namespace Tiger.Game.Settings;
|
||||||
|
|
||||||
|
public interface ISettingsManager
|
||||||
|
{
|
||||||
|
Task ReloadSettingsAsync();
|
||||||
|
T GetSetting<T>(string key);
|
||||||
|
}
|
|
@ -0,0 +1,27 @@
|
||||||
|
using System.Collections.ObjectModel;
|
||||||
|
using Tiger.Storage;
|
||||||
|
|
||||||
|
namespace Tiger.Game.Settings;
|
||||||
|
|
||||||
|
public class SettingsDao : ISettingsDao
|
||||||
|
{
|
||||||
|
private readonly IDatabaseHelper _databaseHelper;
|
||||||
|
|
||||||
|
public SettingsDao(IDatabaseHelper databaseHelper)
|
||||||
|
{
|
||||||
|
_databaseHelper = databaseHelper;
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task<IReadOnlyDictionary<string, object>> GetSettingsAsync()
|
||||||
|
{
|
||||||
|
var settings = new Dictionary<string, object>();
|
||||||
|
await using var dbConnection = _databaseHelper.GetConnection();
|
||||||
|
await using var resultSet = await dbConnection.GetResultSet("SELECT * FROM settings");
|
||||||
|
while (await resultSet.ReadAsync())
|
||||||
|
{
|
||||||
|
settings.Add(resultSet.GetString("skey"), resultSet.GetValue(resultSet.GetOrdinal("value")));
|
||||||
|
}
|
||||||
|
|
||||||
|
return new ReadOnlyDictionary<string, object>(settings);
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,35 @@
|
||||||
|
using Microsoft.Extensions.Logging;
|
||||||
|
|
||||||
|
namespace Tiger.Game.Settings;
|
||||||
|
|
||||||
|
public class SettingsManager : ISettingsManager
|
||||||
|
{
|
||||||
|
private IReadOnlyDictionary<string, object> _settings;
|
||||||
|
private readonly ISettingsDao _settingsDao;
|
||||||
|
private readonly ILogger<ISettingsManager> _logger;
|
||||||
|
|
||||||
|
public SettingsManager(ISettingsDao settingsDao, ILogger<ISettingsManager> logger)
|
||||||
|
{
|
||||||
|
_settingsDao = settingsDao;
|
||||||
|
_logger = logger;
|
||||||
|
_settings = new Dictionary<string, object>();
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task ReloadSettingsAsync()
|
||||||
|
{
|
||||||
|
_settings = await _settingsDao.GetSettingsAsync();
|
||||||
|
|
||||||
|
_logger.LogInformation("Loaded {Count} settings", _settings.Count);
|
||||||
|
}
|
||||||
|
|
||||||
|
public T GetSetting<T>(string key)
|
||||||
|
{
|
||||||
|
if (!_settings.TryGetValue(key, out var value))
|
||||||
|
throw new KeyNotFoundException($"No setting found with key '{key}'");
|
||||||
|
|
||||||
|
if (value is T castedValue)
|
||||||
|
return castedValue;
|
||||||
|
|
||||||
|
throw new InvalidCastException($"Setting '{key}' is not of type '{typeof(T)}'");
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
namespace Tiger.Networking.Game;
|
||||||
|
|
||||||
|
public interface IWebSocketServer
|
||||||
|
{
|
||||||
|
Task Start(string uriPrefix);
|
||||||
|
}
|
|
@ -0,0 +1,28 @@
|
||||||
|
using System.Net.WebSockets;
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Game.Habbos;
|
||||||
|
|
||||||
|
namespace Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
public class GameSession
|
||||||
|
{
|
||||||
|
public WebSocket WebSocket { get; }
|
||||||
|
public string SessionId { get; }
|
||||||
|
public Habbo? Habbo { get; set; }
|
||||||
|
|
||||||
|
public GameSession(WebSocket webSocket, string sessionId)
|
||||||
|
{
|
||||||
|
WebSocket = webSocket;
|
||||||
|
SessionId = sessionId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task SendComposerAsync(IMessageComposer composer)
|
||||||
|
{
|
||||||
|
var message = new ServerMessage((short)composer.Header);
|
||||||
|
composer.Compose(message);
|
||||||
|
var bytes = message.ToArray();
|
||||||
|
await WebSocket.SendAsync(new ArraySegment<byte>(bytes), WebSocketMessageType.Binary, true,
|
||||||
|
CancellationToken.None);
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,56 @@
|
||||||
|
using System.Collections.Concurrent;
|
||||||
|
using System.Net.WebSockets;
|
||||||
|
|
||||||
|
namespace Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
public class GameSessionManager : IGameSessionManager
|
||||||
|
{
|
||||||
|
private readonly ConcurrentDictionary<string, GameSession> _sessions = new();
|
||||||
|
|
||||||
|
public GameSession AddSession(WebSocket webSocket)
|
||||||
|
{
|
||||||
|
var sessionId = Guid.NewGuid().ToString();
|
||||||
|
var gameSession = new GameSession(webSocket, sessionId);
|
||||||
|
_sessions.TryAdd(sessionId, gameSession);
|
||||||
|
return gameSession;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void RemoveSession(WebSocket webSocket)
|
||||||
|
{
|
||||||
|
var session = GetSession(webSocket);
|
||||||
|
if (session != null)
|
||||||
|
{
|
||||||
|
_sessions.TryRemove(session.SessionId, out _);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void CloseAll()
|
||||||
|
{
|
||||||
|
foreach (var session in _sessions.Values)
|
||||||
|
{
|
||||||
|
session.WebSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, "Server shutdown", CancellationToken.None);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public GameSession? GetSession(WebSocket webSocket)
|
||||||
|
{
|
||||||
|
return (from session in _sessions where session.Value.WebSocket == webSocket select session.Value).FirstOrDefault();
|
||||||
|
}
|
||||||
|
|
||||||
|
public GameSession? GetSession(string sessionId)
|
||||||
|
{
|
||||||
|
return _sessions.TryGetValue(sessionId, out var gameSession) ? gameSession : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task CloseAsync(string reason, GameSession session)
|
||||||
|
{
|
||||||
|
if (_sessions.TryGetValue(session.SessionId, out var gameSession))
|
||||||
|
{
|
||||||
|
if (gameSession.WebSocket.State == WebSocketState.Open)
|
||||||
|
{
|
||||||
|
await gameSession.WebSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, reason, CancellationToken.None);
|
||||||
|
}
|
||||||
|
_sessions.TryRemove(session.SessionId, out _);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,13 @@
|
||||||
|
using System.Net.WebSockets;
|
||||||
|
|
||||||
|
namespace Tiger.Networking.Game.Sessions;
|
||||||
|
|
||||||
|
public interface IGameSessionManager
|
||||||
|
{
|
||||||
|
GameSession AddSession(WebSocket webSocket);
|
||||||
|
void RemoveSession(WebSocket webSocket);
|
||||||
|
void CloseAll();
|
||||||
|
GameSession? GetSession(WebSocket webSocket);
|
||||||
|
GameSession? GetSession(string sessionId);
|
||||||
|
Task CloseAsync(string reason, GameSession gameSession);
|
||||||
|
}
|
|
@ -0,0 +1,104 @@
|
||||||
|
using System.Net;
|
||||||
|
using System.Net.WebSockets;
|
||||||
|
using Tiger.Communication.Messages;
|
||||||
|
using Tiger.Communication.Messages.Types;
|
||||||
|
using Tiger.Networking.Game.Sessions;
|
||||||
|
using Tiger.Utils;
|
||||||
|
|
||||||
|
namespace Tiger.Networking.Game;
|
||||||
|
|
||||||
|
public class WebSocketServer : IWebSocketServer
|
||||||
|
{
|
||||||
|
private readonly HttpListener _httpListener = new();
|
||||||
|
private readonly IGameSessionManager _gameSessionManager;
|
||||||
|
private readonly IMessageHandler _messageHandler;
|
||||||
|
|
||||||
|
public WebSocketServer(IGameSessionManager gameSessionManager, IMessageHandler messageHandler)
|
||||||
|
{
|
||||||
|
_gameSessionManager = gameSessionManager;
|
||||||
|
_messageHandler = messageHandler;
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task Start(string uriPrefix)
|
||||||
|
{
|
||||||
|
_httpListener.Prefixes.Add(uriPrefix);
|
||||||
|
_httpListener.Start();
|
||||||
|
|
||||||
|
Console.WriteLine($"Listening on {uriPrefix}...");
|
||||||
|
|
||||||
|
while (true)
|
||||||
|
{
|
||||||
|
var context = await _httpListener.GetContextAsync();
|
||||||
|
|
||||||
|
if (context.Request.IsWebSocketRequest)
|
||||||
|
{
|
||||||
|
ProcessRequestAsync(context);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
context.Response.StatusCode = 400;
|
||||||
|
context.Response.Close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private async void ProcessRequestAsync(HttpListenerContext context)
|
||||||
|
{
|
||||||
|
WebSocket? webSocket = null;
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
var webSocketContext = await context.AcceptWebSocketAsync(null);
|
||||||
|
webSocket = webSocketContext.WebSocket;
|
||||||
|
|
||||||
|
var session = _gameSessionManager.AddSession(webSocket);
|
||||||
|
Console.WriteLine($"WebSocket Session {session.SessionId} has connected.");
|
||||||
|
|
||||||
|
await ReceiveMessageAsync(session.SessionId);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
Console.WriteLine($"WebSocket Session Error: {e.Message}");
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
if (webSocket != null)
|
||||||
|
{
|
||||||
|
_gameSessionManager.RemoveSession(webSocket);
|
||||||
|
webSocket.Dispose();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private async Task ReceiveMessageAsync(string sessionId)
|
||||||
|
{
|
||||||
|
var buffer = new byte[1024 * 4];
|
||||||
|
while (_gameSessionManager.GetSession(sessionId) is { WebSocket.State: WebSocketState.Open } gameSession)
|
||||||
|
{
|
||||||
|
var result = await gameSession.WebSocket.ReceiveAsync(new ArraySegment<byte>(buffer), CancellationToken.None);
|
||||||
|
var offset = 0;
|
||||||
|
|
||||||
|
while (result.MessageType == WebSocketMessageType.Binary && offset + 4 <= result.Count)
|
||||||
|
{
|
||||||
|
var length = ByteUtils.GetInt32(new[]
|
||||||
|
{
|
||||||
|
buffer[offset], buffer[offset + 1], buffer[offset + 2], buffer[offset + 3]
|
||||||
|
});
|
||||||
|
offset += 4;
|
||||||
|
|
||||||
|
if (offset + length > result.Count) break;
|
||||||
|
|
||||||
|
var packet = new byte[result.Count];
|
||||||
|
Array.Copy(buffer, offset, packet, 0, length);
|
||||||
|
offset += length;
|
||||||
|
|
||||||
|
_messageHandler.TryHandleAsync(gameSession, new ClientMessage(packet));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (result.MessageType == WebSocketMessageType.Close)
|
||||||
|
{
|
||||||
|
await gameSession.WebSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, "", CancellationToken.None);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,44 @@
|
||||||
|
using Microsoft.Extensions.Configuration;
|
||||||
|
using Microsoft.Extensions.Configuration.Yaml;
|
||||||
|
using Microsoft.Extensions.DependencyInjection;
|
||||||
|
using Microsoft.Extensions.Logging;
|
||||||
|
using Tiger.Communication.Messages;
|
||||||
|
using Tiger.Game.Habbos;
|
||||||
|
using Tiger.Game.Settings;
|
||||||
|
using Tiger.Networking.Game;
|
||||||
|
using Tiger.Networking.Game.Sessions;
|
||||||
|
using Tiger.Storage;
|
||||||
|
using Tiger.Utils;
|
||||||
|
|
||||||
|
var quitEvent = new ManualResetEvent(false);
|
||||||
|
|
||||||
|
Console.CancelKeyPress += (sender, e) =>
|
||||||
|
{
|
||||||
|
quitEvent.Set();
|
||||||
|
e.Cancel = true;
|
||||||
|
};
|
||||||
|
|
||||||
|
var configuration = new ConfigurationBuilder()
|
||||||
|
.SetBasePath(Directory.GetCurrentDirectory())
|
||||||
|
.AddYamlFile("appsettings.yaml")
|
||||||
|
.Build();
|
||||||
|
|
||||||
|
var collection = new ServiceCollection();
|
||||||
|
collection.AddLogging(builder => builder.AddConsole());
|
||||||
|
collection.AddSingleton<IConfiguration>(configuration);
|
||||||
|
collection.AddSingleton<IWebSocketServer, WebSocketServer>();
|
||||||
|
collection.AddSingleton<IGameSessionManager, GameSessionManager>();
|
||||||
|
collection.AddSingleton<IMessageHandler, MessageHandler>();
|
||||||
|
collection.AddSingleton<IDatabaseHelper, DatabaseHelper>();
|
||||||
|
collection.AddSingleton<ISettingsDao, SettingsDao>();
|
||||||
|
collection.AddSingleton<ISettingsManager, SettingsManager>();
|
||||||
|
collection.AddSingleton<IHabboDao, HabboDao>();
|
||||||
|
collection.RegisterMessageEvents();
|
||||||
|
|
||||||
|
var provider = collection.BuildServiceProvider();
|
||||||
|
|
||||||
|
await provider.GetRequiredService<ISettingsManager>().ReloadSettingsAsync();
|
||||||
|
|
||||||
|
provider.GetRequiredService<IWebSocketServer>().Start($"http://{configuration["Network:Game:Ip"]}:{configuration["Network:Game:Port"]}/");
|
||||||
|
|
||||||
|
quitEvent.WaitOne();
|
|
@ -0,0 +1,38 @@
|
||||||
|
using MySqlConnector;
|
||||||
|
|
||||||
|
namespace Tiger.Storage;
|
||||||
|
|
||||||
|
public class DatabaseConnection : IAsyncDisposable
|
||||||
|
{
|
||||||
|
private readonly MySqlConnection _connection;
|
||||||
|
private readonly MySqlCommand _command;
|
||||||
|
|
||||||
|
public DatabaseConnection(MySqlConnection connection)
|
||||||
|
{
|
||||||
|
_connection = connection;
|
||||||
|
_command = connection.CreateCommand();
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task<MySqlDataReader> GetResultSet(string query, params (string, object)[] mysqlParams)
|
||||||
|
{
|
||||||
|
await _connection.OpenAsync();
|
||||||
|
|
||||||
|
_command.CommandText = query;
|
||||||
|
|
||||||
|
foreach (var mysqlParam in mysqlParams)
|
||||||
|
{
|
||||||
|
_command.Parameters.AddWithValue(mysqlParam.Item1, mysqlParam.Item2);
|
||||||
|
}
|
||||||
|
|
||||||
|
var reader = await _command.ExecuteReaderAsync();
|
||||||
|
_command.Parameters.Clear();
|
||||||
|
return reader;
|
||||||
|
}
|
||||||
|
|
||||||
|
public async ValueTask DisposeAsync()
|
||||||
|
{
|
||||||
|
await _connection.DisposeAsync();
|
||||||
|
await _command.DisposeAsync();
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,31 @@
|
||||||
|
using Microsoft.Extensions.Configuration;
|
||||||
|
using MySqlConnector;
|
||||||
|
|
||||||
|
namespace Tiger.Storage;
|
||||||
|
|
||||||
|
public class DatabaseHelper : IDatabaseHelper
|
||||||
|
{
|
||||||
|
private readonly string _connectionString;
|
||||||
|
|
||||||
|
public DatabaseHelper(IConfiguration configuration)
|
||||||
|
{
|
||||||
|
var stringBuilder = new MySqlConnectionStringBuilder
|
||||||
|
{
|
||||||
|
Server = configuration["Database:Host"],
|
||||||
|
Port = uint.Parse(configuration["Database:Port"] ?? "3306"),
|
||||||
|
UserID = configuration["Database:Username"],
|
||||||
|
Password = configuration["Database:Password"],
|
||||||
|
Database = configuration["Database:Database"],
|
||||||
|
Pooling = true,
|
||||||
|
MinimumPoolSize = uint.Parse(configuration["Database:MinPool"] ?? "5"),
|
||||||
|
MaximumPoolSize = uint.Parse(configuration["Database:MaxPool"] ?? "15")
|
||||||
|
};
|
||||||
|
|
||||||
|
_connectionString = stringBuilder.ToString();
|
||||||
|
}
|
||||||
|
|
||||||
|
public DatabaseConnection GetConnection()
|
||||||
|
{
|
||||||
|
return new DatabaseConnection(new MySqlConnection(_connectionString));
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
namespace Tiger.Storage;
|
||||||
|
|
||||||
|
public interface IDatabaseHelper
|
||||||
|
{
|
||||||
|
DatabaseConnection GetConnection();
|
||||||
|
}
|
|
@ -0,0 +1,27 @@
|
||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<OutputType>Exe</OutputType>
|
||||||
|
<TargetFramework>net7.0</TargetFramework>
|
||||||
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
|
<Nullable>enable</Nullable>
|
||||||
|
<RootNamespace>Tiger</RootNamespace>
|
||||||
|
<LangVersion>11</LangVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="Microsoft.Extensions.Configuration" Version="8.0.0-rc.1.23419.4" />
|
||||||
|
<PackageReference Include="Microsoft.Extensions.Configuration.FileExtensions" Version="8.0.0-rc.1.23419.4" />
|
||||||
|
<PackageReference Include="Microsoft.Extensions.Configuration.Yaml" Version="2.0.0-preview2" />
|
||||||
|
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="8.0.0-rc.1.23419.4" />
|
||||||
|
<PackageReference Include="Microsoft.Extensions.Logging.Console" Version="8.0.0-rc.1.23419.4" />
|
||||||
|
<PackageReference Include="MySqlConnector" Version="2.3.0-beta.3" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<None Update="appsettings.yaml">
|
||||||
|
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||||
|
</None>
|
||||||
|
</ItemGroup>
|
||||||
|
</Project>
|
|
@ -0,0 +1,29 @@
|
||||||
|
namespace Tiger.Utils;
|
||||||
|
|
||||||
|
public static class ByteUtils
|
||||||
|
{
|
||||||
|
public static int GetInt32(byte[] array)
|
||||||
|
{
|
||||||
|
return (array[0] << 24) | (array[1] << 16) | (array[2] << 8) | array[3];
|
||||||
|
}
|
||||||
|
|
||||||
|
public static short GetInt16(byte[] array)
|
||||||
|
{
|
||||||
|
return (short)((array[0] << 8) | array[1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static IEnumerable<byte> UInt32ToArray(uint value)
|
||||||
|
{
|
||||||
|
return new[] { (byte)(value >> 24), (byte)(value >> 16), (byte)(value >> 8), (byte)value };
|
||||||
|
}
|
||||||
|
|
||||||
|
public static IEnumerable<byte> Int32ToArray(int value)
|
||||||
|
{
|
||||||
|
return new[] { (byte)(value >> 24), (byte)(value >> 16), (byte)(value >> 8), (byte)value };
|
||||||
|
}
|
||||||
|
|
||||||
|
public static IEnumerable<byte> Int16ToArray(short value)
|
||||||
|
{
|
||||||
|
return new[] { (byte)(value >> 8), (byte)value };
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,25 @@
|
||||||
|
using System.Reflection;
|
||||||
|
using Microsoft.Extensions.DependencyInjection;
|
||||||
|
using Tiger.Communication.Messages.Interfaces;
|
||||||
|
|
||||||
|
namespace Tiger.Utils;
|
||||||
|
|
||||||
|
public static class DependencyInjectionExtensions
|
||||||
|
{
|
||||||
|
public static void RegisterMessageEvents(this IServiceCollection services)
|
||||||
|
{
|
||||||
|
// Get the assembly you are interested in (this could be any Assembly)
|
||||||
|
var assembly = Assembly.GetExecutingAssembly();
|
||||||
|
|
||||||
|
// Get all types that implement IMessageEvent and are not abstract
|
||||||
|
var messageEventTypes = assembly.GetTypes()
|
||||||
|
.Where(t => t.GetInterfaces().Contains(typeof(IMessageEvent)) && !t.IsAbstract);
|
||||||
|
|
||||||
|
// Register each type with AddSingleton
|
||||||
|
foreach (var type in messageEventTypes)
|
||||||
|
{
|
||||||
|
services.AddSingleton(typeof(IMessageEvent), type);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,12 @@
|
||||||
|
Database:
|
||||||
|
Host: 127.0.0.1
|
||||||
|
Port: 3306
|
||||||
|
Username: root
|
||||||
|
Password: 123
|
||||||
|
Database: tiger_db
|
||||||
|
MinPool: 5
|
||||||
|
MaxPool: 15
|
||||||
|
Network:
|
||||||
|
Game:
|
||||||
|
Ip: 127.0.0.1
|
||||||
|
Port: 2096
|
Loading…
Reference in New Issue