The relevant Story for Central Office staff being able to activate products, from the earlier collection of stories is:
- As a Product Manager, I need to be able to activate Product objects so that I can manage Product availability
The Central Office owns the store_available flag of products, so their version of to_message_dict, living in hms_code.co_objects.Product, is, at least initially, much simpler:
def to_message_data(self) -> (dict,): """ Creates and returns a dictionary representation of the instance that is safe to be passed to a DaemonMessage instance during or after creation as the data of that message. """ return { 'oid':str(self.oid), # - Properties from BaseProduct: 'store_available':self.store_available, # - Date/time values, since we may well want/need to # keep those in sync across environments 'modified':datetime.strftime( self.modified, self.__class__._data_time_string ), }
The related message transmission, with a product_to_activate Product object and the Central Office signing_key is just as easy as the new-Product transmission that we looked at prior:
product_message = DaemonMessage( 'update', product_to_activate.to_message_data(), signing_key ) sender = RabbitMQSender() sender.send_message(product_message)
The same message structure and transmission process will also address the Central Office's need to be able to deactivate products, another of the original iteration stories:
-
As a Product Manager, I need to be able to deactivate Product objects so that I can manage Product availability
The Artisan Gateway method that accepts those messages and updates the relevant Product is ArtisanGatewayDaemon.update_product. Like create_product, it logs fairly extensively through its execution:
def update_product(self, properties:(dict,)) -> None: self.info('%s.update_product called' % self.__class__.__name__) if type(properties) != dict: raise TypeError( '%s.update_product expects a dict of Product ' 'properties, but was passed "%s" (%s)' % ( self.__class__.__name__, properties, type(properties).__name__ ) ) self.debug('properties ... %s:' % (type(properties))) self.debug(str(properties)) # - Retrieve the existing object, and get its data-dict # representation existing_object = Product.get(properties['oid']) self.debug( 'Product %s retrieved successfully' % existing_object.oid ) data_dict = existing_object.to_data_dict() # - Update the data-dict with the values from properties data_dict.update(properties) # - Make sure it's flagged as dirty, so that save will # *update* instead of *create* the instance-record, # for data-stores where that applies data_dict['is_dirty'] = True # - Create a new instance of the class with the revised # data-dict... new_object = Product.from_data_dict(data_dict) # ...and save it. new_object.save() self.info('Product %s updated successfully' % new_object.oid)