From b735e67fef864b675d86a33eb8409d379bd62307 Mon Sep 17 00:00:00 2001 From: Trygve Laugstøl Date: Mon, 2 Oct 2017 16:32:42 +0200 Subject: o Sorting products before downloading to be consistent across runs. o Storing the URL for each product. --- src/ee/digikey/__init__.py | 23 +++++++++++++++++++---- src/ee/tools/digikey_download_facts.py | 8 +++----- 2 files changed, 22 insertions(+), 9 deletions(-) (limited to 'src') diff --git a/src/ee/digikey/__init__.py b/src/ee/digikey/__init__.py index 934c0d2..957aa40 100644 --- a/src/ee/digikey/__init__.py +++ b/src/ee/digikey/__init__.py @@ -71,9 +71,10 @@ class Digikey(object): @total_ordering class DigikeyProduct(object): - def __init__(self, part_number, mpn, attributes=None, categories=None): + def __init__(self, part_number, mpn, url, attributes=None, categories=None): self.part_number = _clean(part_number) self.mpn = _clean(mpn) + self.url = url self.attributes = attributes or [] self.categories = categories or [] self.quantity_available = None @@ -95,9 +96,14 @@ class DigikeyProduct(object): return next((a for a in self.attributes if a.attribute_type.id == _id), None) def to_ini(self, c: configparser.ConfigParser): + def set(cfg, key, value): + if value: + cfg[key] = value + c["overview"] = {}; overview = c["overview"] overview["part_number"] = self.part_number + set(overview, "url", self.url) if self.mpn: overview["mpn"] = self.mpn c["attributes"] = {}; @@ -113,13 +119,19 @@ class DigikeyProduct(object): @staticmethod def from_ini(digikey, c): + def get(c, key): + try: + return c[key] + except KeyError: + return None + overview = c["overview"] attributes = [] for k, value in c.items("attributes"): (type_id, label) = DigikeyProduct.from_ini_r.match(k).groups() a_type = digikey.get_attribute_type(int(type_id), label) attributes.append(DigikeyAttributeValue(value, a_type)) - return DigikeyProduct(overview["part_number"], overview["mpn"], attributes) + return DigikeyProduct(overview["part_number"], overview["mpn"], get(overview, "url"), attributes) class DigikeyAttributeType(object): @@ -211,6 +223,8 @@ class DigikeyClient(object): attributes = [] categories = [] + url = _first((link.get("href") for link in tree.xpath("/html/head/link[@rel='canonical' and @href]"))) + part_number = mpn = None for n in tree.xpath("//*[@itemprop='productID' and @content]"): part_number = n.get("content") @@ -241,7 +255,7 @@ class DigikeyClient(object): attributes.append(DigikeyAttributeValue(value, a_type)) if part_number and mpn: - p = DigikeyProduct(part_number, mpn, attributes, categories) + p = DigikeyProduct(part_number, mpn, url, attributes, categories) for n in tree.xpath("//*[@itemprop='description']"): p.description = _to_string(n) return p @@ -252,13 +266,14 @@ class DigikeyClient(object): products = tree.xpath("//*[@itemtype='http://schema.org/Product']") for product in products: + url = _first((a.get("href") for a in product.xpath(".//*[@class='tr-image']//a[@href]"))) part_number = _first(product.xpath(".//*[@itemprop='productid' and @content]")) mpn = _first(product.xpath(".//*[@itemprop='name']")) if part_number is not None and mpn is not None: res.append(DigikeyProduct( part_number.get("content").strip().replace('sku:', ''), - mpn.text)) + mpn.text, url)) return len(products) diff --git a/src/ee/tools/digikey_download_facts.py b/src/ee/tools/digikey_download_facts.py index 9842c40..cc75f74 100644 --- a/src/ee/tools/digikey_download_facts.py +++ b/src/ee/tools/digikey_download_facts.py @@ -97,14 +97,12 @@ for q in queries: if len(viable_products): # Pick the first one, should be as good as any - part_number = viable_products[0].part_number + part_number = sorted(viable_products, key=lambda p: p.part_number)[0].part_number log.info("Got many hits for term '{}', will use {} for downloading attributes.".format(q.query, part_number)) todos.append(part_number) else: - for k, g in hits: - log.info("Got many results with many parts: {}: {}".format(k, list(g))) - on_product(list(g)[0]) + log.warn("Got many results: {}".format(", ".join([p.part_number for p in response.products]))) elif response.response_type == SearchResponseTypes.TOO_MANY: log.warn("Too many results ({}), select a category first".format(response.count)) elif response.response_type == SearchResponseTypes.NO_MATCHES: @@ -114,7 +112,7 @@ for q in queries: response = client.search(part_number) if response.response_type == SearchResponseTypes.SINGLE: - p = response.products[0] + p = sorted(response.products, key=lambda p: p.part_number)[0] log.info("Downloaded {}".format(p.mpn)) on_product(p) else: -- cgit v1.2.3