78 lines
4.2 KiB
Python
78 lines
4.2 KiB
Python
"""Execute the additive rest-fire migration and the production context policy."""
|
|
from pathlib import Path
|
|
import sqlite3
|
|
import subprocess
|
|
import tempfile
|
|
|
|
root = Path(__file__).resolve().parents[2]
|
|
sql = (root / 'sql/custom/world/2026_10_27_01_adventure_rest_fire.sql').read_text()
|
|
sql = sql.replace('INSERT IGNORE', 'INSERT OR IGNORE')
|
|
db = sqlite3.connect(':memory:')
|
|
db.executescript('''
|
|
CREATE TABLE vcore_adventure_action (
|
|
action_key TEXT PRIMARY KEY,kind TEXT,min_seconds INTEGER,max_seconds INTEGER,requirement TEXT,emote_id INTEGER);
|
|
CREATE TABLE vcore_adventure_action_intent (
|
|
action_key TEXT,intent TEXT,weight REAL,PRIMARY KEY(action_key,intent));
|
|
INSERT INTO vcore_adventure_action VALUES ('social_fire','social',25,50,'fire',0);
|
|
INSERT INTO vcore_adventure_action_intent VALUES ('social_fire','social',1);
|
|
''')
|
|
db.executescript(sql)
|
|
assert db.execute("SELECT kind,min_seconds,max_seconds,requirement FROM vcore_adventure_action WHERE action_key='rest_fire'").fetchone() == ('social',45,75,'fire')
|
|
assert db.execute("SELECT intent,weight FROM vcore_adventure_action_intent WHERE action_key='rest_fire'").fetchall() == [('rest',3.0)]
|
|
db.execute("UPDATE vcore_adventure_action_intent SET weight=7 WHERE action_key='rest_fire'")
|
|
db.executescript(sql)
|
|
assert db.execute("SELECT weight FROM vcore_adventure_action_intent WHERE action_key='rest_fire'").fetchone() == (7.0,)
|
|
assert db.execute("SELECT max_seconds FROM vcore_adventure_action WHERE action_key='social_fire'").fetchone() == (50,)
|
|
source = (root / 'src/server/game/World/AdventureBehaviorMgr.cpp').read_text()
|
|
a = source.index('AdventureSocialContext AdventureBehaviorMgr::SocialContext(')
|
|
b = source.index('\nbool AdventureBehaviorMgr::UpdateSocial(', a)
|
|
method = source[a:b]
|
|
code = r'''
|
|
#include "AdventureProfessionPolicy.h"
|
|
#include <cassert>
|
|
#include "AdventureEconomyPolicy.h"
|
|
#include <cstdint>
|
|
#include <deque>
|
|
#include <functional>
|
|
#include <random>
|
|
#include <string>
|
|
using uint32=uint32_t;
|
|
struct Position{};
|
|
struct Guid{uint32 GetCounter(){return 26;}};
|
|
struct Player{Guid GetGUID(){return {};}};
|
|
struct Profile{AdventureProfessionPolicy::Professions PrimaryProfessions;std::string Locale="deDE";}profile;
|
|
struct Lua{Profile* GetAdventureProfile(uint32){return &profile;}}lua;
|
|
auto sClientlessLuaEngine=&lua;
|
|
struct Location{struct{std::string Category;}Point;}location;
|
|
struct Locations{bool present=true;Location* Find(std::string const&){return present?&location:nullptr;}}locations;
|
|
auto sAdventureLocationMgr=&locations;
|
|
struct AdventureSocialContext{
|
|
Position Anchor;uint32 MapId;bool Festival;std::string Locale,Intent;
|
|
std::mt19937& Random;std::deque<std::string>& TargetHistory;std::deque<std::string>& VariantHistory;
|
|
std::function<bool(Position const&,float)> Move;bool AllowCreateFire=true;std::string ServiceKind,LocationCategory;AdventureProfessionPolicy::Professions PrimaryProfessions;
|
|
};
|
|
class AdventureBehaviorMgr{public:
|
|
struct Record{Position Anchor;uint32 AnchorMap=0;std::string Location,Intent;std::mt19937 Random;std::deque<std::string> TargetHistory,VariantHistory;};
|
|
bool LocalMove(Player*,Record&,Position const&,float){return true;}
|
|
AdventureSocialContext SocialContext(Player*,Record&);
|
|
};
|
|
'''
|
|
code += method + r'''
|
|
int main(){
|
|
Player p;AdventureBehaviorMgr mgr;AdventureBehaviorMgr::Record r;r.Intent="rest";
|
|
for(auto category:{"tavern","settlement","rest_seat","rest_sleep"}){
|
|
location.Point.Category=category;assert(!mgr.SocialContext(&p,r).AllowCreateFire);
|
|
}
|
|
location.Point.Category="rest_ground";assert(mgr.SocialContext(&p,r).AllowCreateFire);
|
|
locations.present=false;assert(!mgr.SocialContext(&p,r).AllowCreateFire);locations.present=true;
|
|
location.Point.Category="tavern";r.Intent="social";assert(mgr.SocialContext(&p,r).AllowCreateFire);
|
|
r.Intent="adventure";assert(mgr.SocialContext(&p,r).AllowCreateFire);
|
|
}
|
|
'''
|
|
with tempfile.TemporaryDirectory(prefix='vcore-rest-fire-policy-') as folder:
|
|
cpp, binary = Path(folder)/'test.cpp', Path(folder)/'test'
|
|
cpp.write_text(code)
|
|
subprocess.run(['c++','-std=c++17','-I',str(root/'src/server/game/World'),str(cpp),'-o',str(binary)],check=True)
|
|
subprocess.run([str(binary)],check=True)
|
|
print('Rest fire: shared scene mapping, additive migration, preserved weights and authored creation-place policy passed.')
|