EvEmu  0.8.4
11 September 2021
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
CorporationService.cpp
Go to the documentation of this file.
1 /*
2  ------------------------------------------------------------------------------------
3  LICENSE:
4  ------------------------------------------------------------------------------------
5  This file is part of EVEmu: EVE Online Server Emulator
6  Copyright 2006 - 2021 The EVEmu Team
7  For the latest information visit https://evemu.dev
8  ------------------------------------------------------------------------------------
9  This program is free software; you can redistribute it and/or modify it under
10  the terms of the GNU Lesser General Public License as published by the Free Software
11  Foundation; either version 2 of the License, or (at your option) any later
12  version.
13 
14  This program is distributed in the hope that it will be useful, but WITHOUT
15  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16  FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
17 
18  You should have received a copy of the GNU Lesser General Public License along with
19  this program; if not, write to the Free Software Foundation, Inc., 59 Temple
20  Place - Suite 330, Boston, MA 02111-1307, USA, or go to
21  http://www.gnu.org/copyleft/lesser.txt.
22  ------------------------------------------------------------------------------------
23  Author: Zhur
24 */
25 
26 #include "eve-server.h"
27 
28 #include "PyServiceCD.h"
29 #include "StaticDataMgr.h"
30 #include "account/AccountService.h"
32 #include "station/StationDataMgr.h"
33 
35 
37 : PyService(mgr, "corporationSvc"),
38  m_dispatch(new Dispatcher(this))
39 {
40  _SetCallDispatcher(m_dispatch);
41 
42  PyCallable_REG_CALL(CorporationService, GetFactionInfo);
44  PyCallable_REG_CALL(CorporationService, GetNPCDivisions);
45  PyCallable_REG_CALL(CorporationService, GetEmploymentRecord);
46  PyCallable_REG_CALL(CorporationService, GetRecruitmentAdsByCriteria);
47  PyCallable_REG_CALL(CorporationService, GetRecruitmentAdRegistryData);
48  PyCallable_REG_CALL(CorporationService, GetRecruitmentAdsForCorporation);
49 
50  PyCallable_REG_CALL(CorporationService, GetMedalsReceived);
51  PyCallable_REG_CALL(CorporationService, GetMedalDetails);
52  PyCallable_REG_CALL(CorporationService, GetAllCorpMedals);
54  PyCallable_REG_CALL(CorporationService, GiveMedalToCharacters);
55  PyCallable_REG_CALL(CorporationService, SetMedalStatus);
56  PyCallable_REG_CALL(CorporationService, GetMedalStatuses);
57  PyCallable_REG_CALL(CorporationService, GetRecipientsOfMedal);
58 }
59 
60 
62  delete m_dispatch;
63 }
64 
65 /*
66  * CORP__ERROR
67  * CORP__WARNING
68  * CORP__INFO
69  * CORP__MESSAGE
70  * CORP__TRACE
71  * CORP__CALL
72  * CORP__CALL_DUMP
73  * CORP__RSP_DUMP
74  * CORP__DB_ERROR
75  * CORP__DB_WARNING
76  * CORP__DB_INFO
77  * CORP__DB_MESSAGE
78  */
79 
80 PyResult CorporationService::Handle_GetNPCDivisions(PyCallArgs &call)
81 {
82  return sDataMgr.GetNPCDivisions();
83 }
84 
85 PyResult CorporationService::Handle_GetEmploymentRecord(PyCallArgs &call) {
86  Call_SingleIntegerArg args;
87  if (!args.Decode(&call.tuple)) {
88  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
89  return nullptr;
90  }
91 
92  return m_db.GetEmploymentRecord(args.arg);
93 }
94 
95 PyResult CorporationService::Handle_GetFactionInfo(PyCallArgs &call) {
96  /*self.factionIDbyNPCCorpID, self.factionRegions, self.factionConstellations, self.factionSolarSystems,
97  * self.factionRaces, self.factionStationCount, self.factionSolarSystemCount, self.npcCorpInfo = sm.RemoteSvc('corporationSvc').GetFactionInfo()
98  * for corpID, factionID in self.factionIDbyNPCCorpID.iteritems():
99  * if factionID not in self.corpsByFactionID:
100  * self.corpsByFactionID[factionID] = []
101  * if corpID not in self.corpsByFactionID[factionID]:
102  * self.corpsByFactionID[factionID].append(corpID)
103  *
104  * owners = {}
105  * for k, v in self.factionIDbyNPCCorpID.iteritems():
106  * owners[k] = 0
107  * owners[v] = 0
108  */
109 
110  return sDataMgr.GetFactionInfo();
111 }
112 
113 // this wants corp market info
114 PyResult CorporationService::Handle_GetCorpInfo(PyCallArgs &call)
115 {
116  //corpmktinfo = sm.RemoteSvc('corporationSvc').GetCorpInfo(itemID)
117  Call_SingleIntegerArg args;
118  if (!args.Decode(&call.tuple)) {
119  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
120  return nullptr;
121  }
122 
123  return m_db.GetMktInfo(args.arg);
124 }
125 
126 PyResult CorporationService::Handle_GetRecruitmentAdRegistryData( PyCallArgs& call )
127 { // working
128  _log(CORP__CALL, "CorporationService::Handle_GetRecruitmentAdRegistryData()");
129  call.Dump(CORP__CALL_DUMP);
130 
131  PyDict* dict = new PyDict();
132  dict->SetItemString("types", m_db.GetAdTypeData());
133  dict->SetItemString("groups", m_db.GetAdGroupData());
134  PyObject* args = new PyObject("util.KeyVal", dict);
135  if (is_log_enabled(CORP__RSP_DUMP))
136  args->Dump(CORP__RSP_DUMP, "");
137  return args;
138 }
139 
140 PyResult CorporationService::Handle_GetRecruitmentAdsByCriteria( PyCallArgs& call )
141 { // return sm.RemoteSvc('corporationSvc').GetRecruitmentAdsByCriteria(typeMask, isInAlliance, minMembers, maxMembers)
142  _log(CORP__CALL, "CorporationService::Handle_GetRecruitmentAdsByCriteria()");
143  call.Dump(CORP__CALL_DUMP);
144 
145  Call_GetRecruitmentAdsByCriteria args;
146  if (!args.Decode(&call.tuple)) {
147  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
148  return nullptr;
149  }
150 
151  return m_db.GetAdRegistryData(args.typeMask, args.inAlliance, args.minMembers, args.maxMembers);
152 }
153 
154 PyResult CorporationService::Handle_GetRecruitmentAdsForCorporation( PyCallArgs& call )
155 {
156  // recruitments = self.GetCorpRegistry().GetRecruitmentAdsForCorporation()
157  _log(CORP__CALL, "CorporationService::Handle_GetRecruitmentAdsForCorporation()");
158  call.Dump(CORP__CALL_DUMP);
159 
160  return m_db.GetAdRegistryData();
161 }
162 
163 
168 PyResult CorporationService::Handle_CreateMedal(PyCallArgs &call)
169 {
170  // destroy = sm.StartService('medals').CreateMedal(mName, mDesc, cMedalData)
171  // destroy = true will close window
172 
173  //take the money, send wallet blink event record the transaction in corp journal.
174  // if not enough corp funds, throw from here and avoid the overhead of decoding call...
175  std::string reason = "DESC: Medal Creation by ";
176  reason += call.client->GetName();
177  reason += " in "; // just extra shit. this will show in tooltip. ;)
178  reason += stDataMgr.GetStationName(call.client->GetStationID());
180  call.client->GetCorporationID(),
181  call.client->GetStationID(),
182  sConfig.rates.medalCreateCost,
183  reason.c_str(),
185  call.client->GetStationID(),
187 
188  Call_CreateMedal args;
189  if (!args.Decode(&call.tuple)) {
190  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
191  return nullptr;
192  }
193 
194  if (args.title.size() > 30)
195  throw UserError ("MedalNameTooLong");
196  if (args.description.size() < 3)
197  throw UserError ("MedalDescriptionTooShort");
198  if (args.description.size() > 150)
199  throw UserError ("MedalDescriptionTooLong");
200 
201  // not sure of the requirements for these errors....
202  // MedalNameInvalid, MedalNameInvalid2, MedalDescriptionInvalid2
203 
204  uint16 medalID = m_db.CreateMedal(call.client->GetCorporationID(), call.client->GetCharacterID(), args.title, args.description);
205  if (medalID == 0) {
206  // error on save.
207  call.client->SendErrorMsg("Error when saving Medal Data. Ref: ServerError xxxxx");
208  return nullptr;
209  }
210 
211  PyList* list(nullptr);
212  std::vector<Corp::MedalData> dataList;
213  //if (is_log_enabled(CORP__PKT_TRACE))
214  // args.data->Dump(CORP__PKT_TRACE, "");
215  for (PyList::const_iterator itr = args.data->begin(); itr != args.data->end(); ++itr) {
216  list = (*itr)->AsList();
217  if (list == nullptr)
218  continue;
219  // type: 1 = ribbon, 2 = medal
221  data.part = PyRep::IntegerValue(list->GetItem(0));
222  data.graphic = PyRep::StringContent(list->GetItem(1));
223  data.color = PyRep::IntegerValue(list->GetItem(2));
224  dataList.push_back( data );
225  }
226 
227  // this will either save data or it wont...
228  m_db.SaveMedalData(medalID, dataList);
229 
230  return PyStatic.NewFalse();
231 }
232 
233 PyResult CorporationService::Handle_GetMedalsReceived(PyCallArgs &call) {
234  // this should be cached
235  // medalInfo, medalGraphics = sm.StartService('medals').GetMedalsReceived(charID)
236  /*
237  * 13:25:05 [CorpCallDump] Call Arguments:
238  * 13:25:05 [CorpCallDump] Tuple: 1 elements
239  * 13:25:05 [CorpCallDump] [ 0] Integer: 90000000
240  */
241  _log(CORP__CALL, "CorporationService::Handle_GetMedalsReceived()");
242  call.Dump(CORP__CALL_DUMP);
243 
244  Call_SingleIntegerArg arg;
245  if (!arg.Decode(&call.tuple)) {
246  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
247  return nullptr;
248  }
249 
250  PyTuple* res = new PyTuple(2);
251  res->SetItem(0, m_db.GetMedalsReceived(arg.arg));
252  res->SetItem(1, m_db.GetMedalsReceivedDetails(arg.arg));
253  if (is_log_enabled(CORP__RSP_DUMP))
254  res->Dump(CORP__RSP_DUMP, "");
255  return res;
256 }
257 
258 PyResult CorporationService::Handle_GetMedalDetails(PyCallArgs &call)
259 { // working
260  _log(CORP__CALL, "CorporationService::Handle_GetMedalDetails()");
261  call.Dump(CORP__CALL_DUMP);
262 
263  Call_SingleIntegerArg arg;
264  if (!arg.Decode(&call.tuple)) {
265  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
266  return nullptr;
267  }
268 
269  return m_db.GetMedalDetails(arg.arg);
270 }
271 
272 PyResult CorporationService::Handle_GetAllCorpMedals( PyCallArgs& call )
273 { //working
274  // medals, medalDetails = sm.RemoteSvc('corporationSvc').GetAllCorpMedals(corpID)
275  _log(CORP__CALL, "CorporationService::Handle_GetAllCorpMedals()");
276  call.Dump(CORP__CALL_DUMP);
277 
278  Call_SingleIntegerArg arg;
279  if (!arg.Decode(&call.tuple)) {
280  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
281  return nullptr;
282  }
283 
284  PyTuple* res = new PyTuple(2);
287  if (is_log_enabled(CORP__RSP_DUMP))
288  res->Dump(CORP__RSP_DUMP, "");
289  return res;
290 }
291 
292 PyResult CorporationService::Handle_GetRecipientsOfMedal(PyCallArgs &call)
293 {
294  // recipients = sm.RemoteSvc('corporationSvc').GetRecipientsOfMedal(medalID)
295  // called from GetMedalSubContent in corp_ui_member_deco
296  _log(CORP__CALL, "CorporationService::Handle_GetRecipientsOfMedal()");
297  call.Dump(CORP__CALL_DUMP);
298 
299  Call_SingleIntegerArg arg;
300  if (!arg.Decode(&call.tuple)) {
301  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
302  return nullptr;
303  }
304 
305  /*
306  * issuerID = recipients.issuerID
307  * date = recipients.date
308  * statusID, statusName = self.GetStatus(recipients.status)
309  * reason = recipients.reason
310  */
311  return m_db.GetRecipientsOfMedal(arg.arg);
312 }
313 
314 PyResult CorporationService::Handle_GiveMedalToCharacters(PyCallArgs &call)
315 {
316  // sm.RemoteSvc('corporationSvc').GiveMedalToCharacters(medalID, recipientID, reason)
317  /*
318  * 13:24:32 [CorpCallDump] Call Arguments:
319  * 13:24:32 [CorpCallDump] Tuple: 3 elements
320  * 13:24:32 [CorpCallDump] [ 0] Integer: 8
321  * 13:24:32 [CorpCallDump] [ 1] List: 1 elements
322  * 13:24:32 [CorpCallDump] [ 1] [ 0] Integer: 90000000
323  * 13:24:32 [CorpCallDump] [ 2] WString: 'testing this shit'
324  */
325  _log(CORP__CALL, "CorporationService::Handle_GiveMedalToCharacters()");
326  call.Dump(CORP__CALL_DUMP);
327 
328  Call_AwardMedal args;
329  if (!args.Decode(&call.tuple)) {
330  codelog(SERVICE__ERROR, "%s: Failed to decode arguments.", GetName());
331  return nullptr;
332  }
333 
334  // can award one medal to multiple chars at once, at 5m isk per award
335  std::vector< uint32 > charVec;
336  for (PyList::const_iterator itr = args.recipientIDs->begin(); itr != args.recipientIDs->end(); ++itr)
337  charVec.push_back(PyRep::IntegerValue(*itr));
338 
339  uint32 cost = sConfig.rates.medalAwardCost;
340  cost *= charVec.size();
341 
342  //take the money, send wallet blink event record the transaction in corp journal.
343  std::string reason = "DESC: Awarding Medal by ";
344  reason += call.client->GetName();
346  call.client->GetCorporationID(),
347  call.client->GetStationID(),
348  cost,
349  reason.c_str(),
351 
352  m_db.GiveMedalToCharacters(call.client->GetCharacterID(), call.client->GetCorporationID(), args.medalID, charVec, args.reason);
353 
354  return nullptr;
355 }
356 
357 PyResult CorporationService::Handle_GetMedalStatuses(PyCallArgs &call)
358 {
359  // return sm.RemoteSvc('corporationSvc').GetMedalStatuses()
360  // statusID, statusName = self.GetStatus(theyareallthesame.status)
361  _log(CORP__CALL, "CorporationService::Handle_GetMedalStatuses()");
362  call.Dump(CORP__CALL_DUMP);
363 
364  // cant find any other references to this, so it's hacked in the db call
365  // statusID, statusName
366  PyRep* res = m_db.GetMedalStatuses();
367  if (is_log_enabled(CORP__RSP_DUMP))
368  res->Dump(CORP__RSP_DUMP, "");
369  return res;
370 }
371 
372 
377 PyResult CorporationService::Handle_SetMedalStatus(PyCallArgs &call)
378 {
379  // sm.RemoteSvc('corporationSvc').SetMedalStatus(statusdict)
380  // this is called from char PD for setting view permissions on received medals
381  /*
382  * 02:24:28 [CorpCall] CorporationService::Handle_SetMedalStatus()
383  * 02:24:28 [CorpCallDump] Call Arguments:
384  * 02:24:28 [CorpCallDump] Tuple: 1 elements
385  * 02:24:28 [CorpCallDump] [ 0] Dictionary: 1 entries
386  * 02:24:28 [CorpCallDump] [ 0] [ 0] Key: Integer: 1 << medalID
387  * 02:24:28 [CorpCallDump] [ 0] [ 0] Value: Integer: 3 << public
388  *
389  * 02:36:18 [CorpCall] CorporationService::Handle_SetMedalStatus()
390  * 02:36:18 [CorpCallDump] Call Arguments:
391  * 02:36:18 [CorpCallDump] Tuple: 1 elements
392  * 02:36:18 [CorpCallDump] [ 0] Dictionary: 1 entries
393  * 02:36:18 [CorpCallDump] [ 0] [ 0] Key: Integer: 1 << medalID
394  * 02:36:18 [CorpCallDump] [ 0] [ 0] Value: Integer: 1 << remove
395  *
396  */
397  _log(CORP__CALL, "CorporationService::Handle_SetMedalStatus()");
398  call.Dump(CORP__CALL_DUMP);
399 
400  call.client->SendInfoModalMsg("Sorry, %s. Saving Permissions for Medals isn't functional yet.", call.client->GetName());
401  return nullptr;
402 }
403 
Base Python wire object.
Definition: PyRep.h:66
#define sConfig
A macro for easier access to the singleton.
Dispatcher *const m_dispatch
PyCallable_Make_InnerDispatcher(CorporationService) CorporationService
PyObjectEx * GetMedalDetails(int32 medalID)
static std::string StringContent(PyRep *pRep)
Definition: PyRep.cpp:103
std::string graphic
Definition: CorpData.h:74
void SendErrorMsg(const char *fmt,...)
Definition: Client.cpp:2719
#define _log(type, fmt,...)
Definition: logsys.h:124
#define stDataMgr
Python's dictionary.
Definition: PyRep.h:719
PyRep * GetMedalsReceivedDetails(int32 charID)
PyRep * GetRecipientsOfMedal(int32 medalID)
PyRep * GetMedalsReceived(int32 charID)
void SendInfoModalMsg(const char *fmt,...)
Definition: Client.cpp:2756
int32 GetCharacterID() const
Definition: Client.h:113
int32 GetCorporationID() const
Definition: Client.h:123
storage_type::const_iterator const_iterator
Definition: PyRep.h:644
Python tuple.
Definition: PyRep.h:567
const char * GetName() const
Definition: PyService.h:54
void Dump(FILE *into, const char *pfx) const
Dumps object to file.
Definition: PyRep.cpp:84
void GiveMedalToCharacters(uint32 issuerID, uint32 corpID, int32 medalID, std::vector< uint32 > &charVec, std::string &reason)
* args
#define is_log_enabled(type)
Definition: logsys.h:78
PyRep * GetAdTypeData()
Python object.
Definition: PyRep.h:826
uint16 CreateMedal(uint32 ownerID, uint32 creatorID, std::string &title, std::string &description)
#define codelog(type, fmt,...)
Definition: logsys.h:128
void SetItem(size_t index, PyRep *object)
Stores Python object.
Definition: PyRep.h:610
PyRep * GetAllCorpMedals(uint32 corpID)
PyRep * GetAdGroupData()
static void TranserFunds(uint32 fromID, uint32 toID, double amount, std::string reason="", uint8 entryTypeID=Journal::EntryType::Undefined, uint32 referenceID=0, uint16 fromKey=Account::KeyType::Cash, uint16 toKey=Account::KeyType::Cash, Client *pClient=nullptr)
#define PyStatic
Definition: PyRep.h:1209
const char * GetName() const
Definition: Client.h:94
PyRep * GetCorpMedalData(uint32 corpID)
Client *const client
Definition: PyCallable.h:49
Python object "ccp_exceptions.UserError".
Definition: PyExceptions.h:121
#define PyCallable_REG_CALL(c, m)
Definition: PyServiceCD.h:78
PyRep * GetMedalStatuses()
unsigned __int32 uint32
Definition: eve-compat.h:50
PyRep * GetMktInfo(uint32 corpID)
void Dump(LogType type) const
Definition: PyCallable.cpp:81
PyObject * GetEmploymentRecord(uint32 charID)
int32 GetStationID() const
Definition: Client.h:114
PyRep * GetAdRegistryData(int64 typeMask=0, bool inAlliance=false, int16 minMembers=0, uint16 maxMembers=12602)
static int64 IntegerValue(PyRep *pRep)
Definition: PyRep.cpp:118
Dispatcher *const m_dispatch
unsigned __int16 uint16
Definition: eve-compat.h:48
Python list.
Definition: PyRep.h:639
void SetItemString(const char *key, PyRep *value)
SetItemString adds or sets a database entry.
Definition: PyRep.h:812
PyTuple * tuple
Definition: PyCallable.h:50
void SaveMedalData(int64 medalID, std::vector< Corp::MedalData > &dataList)
#define sDataMgr