blueprintSvc.py (7491B)
1 #Embedded file name: C:\BuildAgent\work\20d73f1b24eed06e\eve\release\V24.01\eve\client\script\industry\blueprintSvc.py 2 from collections import defaultdict 3 import blue 4 import evetypes 5 import telemetry 6 import industry 7 import threadutils 8 from carbon.common.script.sys.service import Service 9 from eve.common.lib import appConst as const 10 from eve.common.script.sys import idCheckers 11 from eve.common.script.util import industryCommon 12 from caching.memoize import Memoize 13 from eveexceptions import UserError 14 import eve.client.script.industry.mixins 15 16 class BlueprintService(Service): 17 __guid__ = 'svc.blueprintSvc' 18 __servicename__ = 'Blueprint' 19 __displayname__ = 'Blueprint Service' 20 __notifyevents__ = ['OnBlueprintsUpdated', 'OnSessionChanged', 'OnIndustryJob'] 21 22 def Run(self, *args, **kwargs): 23 Service.Run(self, *args, **kwargs) 24 self.blueprintManager = sm.RemoteSvc('blueprintManager') 25 self.blueprintLimit = self.blueprintManager.GetLimits()['maxBlueprintResults'] 26 self.bpSummaries = {} 27 self.blueprintChanges = defaultdict(dict) 28 29 def OnBlueprintsUpdated(self, ownerID): 30 self.GetAllBlueprintsForOwner.clear_memoized(self, ownerID) 31 self.GetOwnerBlueprintsAtFacility.clear_memoized() 32 self.bpSummaries.pop(ownerID, None) 33 sm.ScatterEvent('OnBlueprintReload', ownerID) 34 35 @telemetry.ZONE_METHOD 36 def OnIndustryJob(self, jobID, ownerID, blueprintID, installerID, status, successfulRuns): 37 self.blueprintChanges[ownerID][blueprintID] = (jobID, status) 38 self._UpdateOnIndustryJobChange(ownerID) 39 40 @threadutils.throttled(3.0) 41 def _UpdateOnIndustryJobChange(self, ownerID): 42 blueprintChangesForOwner = self.blueprintChanges.pop(ownerID, None) 43 if not blueprintChangesForOwner: 44 return 45 self.GetOwnerBlueprintsAtFacility.clear_memoized() 46 for blueprint in self.GetAllBlueprintsForOwner(ownerID)[0]: 47 if not blueprintChangesForOwner: 48 break 49 changeInfoForBlueprint = blueprintChangesForOwner.pop(blueprint.itemID, None) 50 if changeInfoForBlueprint is None: 51 continue 52 jobID, status = changeInfoForBlueprint 53 if status < industry.STATUS_COMPLETED: 54 blueprint.jobID = jobID 55 else: 56 blueprint.jobID = None 57 58 def OnSessionChanged(self, isRemote, session, change): 59 if 'corprole' in change: 60 self.OnBlueprintsUpdated(session.corpid) 61 62 @telemetry.ZONE_METHOD 63 def GetBlueprintType(self, blueprintTypeID, isCopy = False): 64 try: 65 ret = cfg.blueprints[blueprintTypeID] 66 if isCopy or evetypes.GetCategoryID(blueprintTypeID) == const.categoryAncientRelic: 67 ret = ret.copy() 68 ret.original = False 69 return ret 70 except KeyError: 71 raise UserError('IndustryBlueprintNotFound') 72 73 def GetBlueprintTypeCopy(self, typeID, original = True, runsRemaining = None, materialEfficiency = None, timeEfficiency = None): 74 bpData = self.GetBlueprintType(typeID).copy() 75 bpData.original = original and evetypes.GetCategoryID(typeID) != const.categoryAncientRelic 76 if runsRemaining is not None: 77 bpData.runsRemaining = runsRemaining 78 if materialEfficiency is not None: 79 bpData.materialEfficiency = materialEfficiency 80 if timeEfficiency is not None: 81 bpData.timeEfficiency = timeEfficiency 82 return bpData 83 84 @telemetry.ZONE_METHOD 85 def GetBlueprintItem(self, blueprintID): 86 return industryCommon.BlueprintInstance(self.blueprintManager.GetBlueprintData(blueprintID)) 87 88 @Memoize(10) 89 def GetBlueprintItemMemoized(self, blueprintID): 90 return self.GetBlueprintItem(blueprintID) 91 92 def GetBlueprint(self, blueprintID, blueprintTypeID, isCopy = False): 93 try: 94 return self.GetBlueprintItem(blueprintID) 95 except UserError: 96 return self.GetBlueprintType(blueprintTypeID, isCopy=isCopy) 97 98 @staticmethod 99 def GetBlueprintByProduct(productTypeID): 100 try: 101 blueprint = cfg.blueprints.index('productTypeID', productTypeID) 102 if blueprint and evetypes.IsPublished(blueprint.blueprintTypeID): 103 return blueprint 104 return None 105 except KeyError: 106 return None 107 108 @telemetry.ZONE_METHOD 109 def GetOwnerBlueprints(self, ownerID, facilityID = None): 110 if facilityID is None: 111 return self.GetAllBlueprintsForOwner(ownerID) 112 return self.GetOwnerBlueprintsAtFacility(ownerID, facilityID) 113 114 @Memoize(15) 115 def GetOwnerBlueprintsAtFacility(self, ownerID, facilityID): 116 bps = [] 117 if ownerID not in self.bpSummaries: 118 bps, bpCounts = self.GetAllBlueprintsForOwner(ownerID) 119 else: 120 bpCounts = self.bpSummaries[ownerID] 121 if not bps: 122 bps, _ = self.blueprintManager.GetBlueprintDataByOwner(ownerID, facilityID) 123 bps = self._AttachFacilities(bps) 124 return ([ bp for bp in bps if bp.facilityID == facilityID ], bpCounts) 125 126 def GetTotalNumBlueprintsForOwner(self, ownerID): 127 if ownerID not in self.bpSummaries: 128 _, bpCounts = self.GetAllBlueprintsForOwner(ownerID) 129 else: 130 bpCounts = self.bpSummaries[ownerID] 131 return sum((n for n in bpCounts.itervalues())) 132 133 @Memoize(15) 134 def GetAllBlueprintsForOwner(self, ownerID): 135 bps, bpCounts = self.blueprintManager.GetBlueprintDataByOwner(ownerID, None) 136 bps = self._AttachFacilities(bps) 137 self.bpSummaries[ownerID] = bpCounts 138 return (bps, bpCounts) 139 140 def GetCharacterBlueprints(self, facilityID = None): 141 return self.GetOwnerBlueprints(session.charid, facilityID) 142 143 def GetCorporationBlueprints(self, facilityID = None): 144 return self.GetOwnerBlueprints(session.corpid, facilityID) 145 146 def CanSeeCorpBlueprints(self): 147 if idCheckers.IsNPC(session.corpid): 148 return False 149 return session.corprole & (const.corpRoleCanRentResearchSlot | const.corpRoleFactoryManager | const.corpRoleCanRentFactorySlot) > 0 150 151 def _AttachFacilities(self, blueprints): 152 locations = set() 153 facilities = set() 154 blueprintObjects = [] 155 for data in blueprints: 156 try: 157 blueprint = industryCommon.BlueprintInstance(data) 158 blueprintObjects.append(blueprint) 159 if blueprint.locationTypeID not in (const.typeAssetSafetyWrap, const.typeOffice): 160 locations.add(blueprint.locationID) 161 if blueprint.facilityID: 162 locations.add(blueprint.facilityID) 163 facilities.add(blueprint.facilityID) 164 blue.pyos.BeNice() 165 except KeyError: 166 self.LogError('Unable to load blueprint instance: ', data) 167 168 cfg.evelocations.Prime(locations) 169 facilitiesByID = {} 170 if len(facilities): 171 facilitiesByID = {f.facilityID:f for f in sm.GetService('facilitySvc').GetFacilities(facilities)} 172 for blueprint in blueprintObjects: 173 if blueprint.facilityID: 174 try: 175 blueprint.facility = facilitiesByID[blueprint.facilityID] 176 except KeyError: 177 self.LogWarn('Could not load facility', blueprint.facilityID) 178 179 return blueprintObjects