mirror of
https://gitlab.com/hibou-io/hibou-odoo/suite.git
synced 2025-01-20 12:37:31 +02:00
Need to investigate form for Amazon orders. Installing it complains that `action_...` doesn't actually exist. I started making pass through methods like `action_unlock` in sale_order.common, but then came to an action that would only exist in inherited views and not in this specific new form.
107 lines
4.1 KiB
Python
107 lines
4.1 KiB
Python
# © 2021 Hibou Corp.
|
|
|
|
from io import BytesIO
|
|
from base64 import b64encode, b64decode
|
|
from json import loads, dumps
|
|
|
|
from odoo import models, fields, api
|
|
from odoo.addons.component.core import Component
|
|
from odoo.addons.queue_job.exception import RetryableJobError
|
|
|
|
FEED_RETRY_PATTERN = {
|
|
1: 1 * 60,
|
|
5: 2 * 60,
|
|
10: 10 * 60,
|
|
}
|
|
|
|
|
|
class AmazonFeed(models.Model):
|
|
_name = 'amazon.feed'
|
|
_description = 'Amazon Feed'
|
|
_order = 'id desc'
|
|
_rec_name = 'external_id'
|
|
|
|
backend_id = fields.Many2one('amazon.backend', string='Backend')
|
|
external_id = fields.Char(string='Amazon Feed ID')
|
|
type = fields.Selection([
|
|
('POST_ORDER_FULFILLMENT_DATA', 'Order Fulfillment Data'),
|
|
('POST_PRODUCT_DATA', 'Product Data'),
|
|
('POST_INVENTORY_AVAILABILITY_DATA', 'Product Inventory'),
|
|
('POST_PRODUCT_PRICING_DATA', 'Product Pricing'),
|
|
], string='Feed Type')
|
|
content_type = fields.Selection([
|
|
('text/xml', 'XML'),
|
|
], string='Content Type')
|
|
data = fields.Binary(string='Data', attachment=True)
|
|
response = fields.Binary(string='Response', attachment=True)
|
|
state = fields.Selection([
|
|
('new', 'New'),
|
|
('submitted', 'Submitted'),
|
|
('error_on_submit', 'Submission Error'),
|
|
], string='State', default='new')
|
|
amazon_state = fields.Selection([
|
|
('not_sent', ''),
|
|
('invalid', 'Invalid'),
|
|
('UNCONFIRMED', 'Request Pending'),
|
|
('SUBMITTED', 'Submitted'),
|
|
('IN_SAFETY_NET', 'Safety Net'),
|
|
('IN_QUEUE', 'Queued'),
|
|
('IN_PROGRESS', 'Processing'),
|
|
('DONE', 'Done'),
|
|
('CANCELLED', 'Cancelled'),
|
|
('AWAITING_ASYNCHRONOUS_REPLY', 'Awaiting Asynchronous Reply'),
|
|
], default='not_sent')
|
|
amazon_stock_picking_id = fields.Many2one('amazon.stock.picking',
|
|
string='Shipment',
|
|
ondelete='set null')
|
|
amazon_product_product_id = fields.Many2one('amazon.product.product',
|
|
string='Listing',
|
|
ondelete='set null')
|
|
|
|
def submit_feed(self):
|
|
for feed in self:
|
|
api_instance = feed.backend_id.get_wrapped_api()
|
|
feeds_api = api_instance.feeds()
|
|
feed_io = BytesIO(b64decode(feed.data))
|
|
res1, res2 = feeds_api.submit_feed(feed.type, feed_io, content_type=feed.content_type)
|
|
feed_id = res2.payload.get('feedId')
|
|
if not feed_id:
|
|
if res2.payload:
|
|
feed.response = b64encode(dumps(res2.payload))
|
|
feed.state = 'error_on_submit'
|
|
else:
|
|
feed.state = 'submitted'
|
|
feed.external_id = feed_id
|
|
# First attempt will be delayed 1 minute
|
|
# Next 5 retries will be delayed 10 min each
|
|
# The rest will be delayed 30 min each
|
|
feed.with_delay(priority=100).check_feed()
|
|
|
|
def check_feed(self):
|
|
for feed in self.filtered('external_id'):
|
|
api_instance = feed.backend_id.get_wrapped_api()
|
|
feeds_api = api_instance.feeds()
|
|
res3 = feeds_api.get_feed(feed.external_id)
|
|
status = res3.payload['processingStatus']
|
|
try:
|
|
feed.amazon_state = status
|
|
except ValueError:
|
|
feed.amazon_state = 'invalid'
|
|
if status in ('IN_QUEUE', 'IN_PROGRESS'):
|
|
raise RetryableJobError('Check back later on: ' + str(status), ignore_retry=True)
|
|
if status in ('DONE', ):
|
|
feed_document_id = res3.payload['resultFeedDocumentId']
|
|
if feed_document_id:
|
|
response = feeds_api.get_feed_result_document(feed_document_id)
|
|
try:
|
|
feed.response = b64encode(response)
|
|
except TypeError:
|
|
feed.response = b64encode(response.encode())
|
|
|
|
# queue a job to process the response
|
|
feed.with_delay(priority=10).process_feed_result()
|
|
|
|
def process_feed_result(self):
|
|
for feed in self:
|
|
pass
|