ey-commerce-lib 1.0.14__tar.gz → 1.0.15__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of ey-commerce-lib might be problematic. Click here for more details.

Files changed (68) hide show
  1. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/PKG-INFO +1 -1
  2. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/pyproject.toml +1 -1
  3. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/main.py +40 -1
  4. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/parser/order.py +1 -1
  5. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/schemas/dxm_commodity_product.py +7 -7
  6. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/utils/dxm_commodity_product.py +32 -28
  7. ey_commerce_lib-1.0.15/src/ey_commerce_lib/utils/float.py +30 -0
  8. ey_commerce_lib-1.0.15/tests/dxm/test_purchase.py +91 -0
  9. ey_commerce_lib-1.0.14/tests/dxm/test_purchase.py +0 -57
  10. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/.gitignore +0 -0
  11. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/.python-version +0 -0
  12. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/README.md +0 -0
  13. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/pytest.ini +0 -0
  14. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/__init__.py +0 -0
  15. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/__init__.py +0 -0
  16. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/constant/__init__.py +0 -0
  17. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/constant/order.py +0 -0
  18. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/exception/__init__.py +0 -0
  19. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/exception/common.py +0 -0
  20. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/order.py +0 -0
  21. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/parser/__init__.py +0 -0
  22. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/parser/common.py +0 -0
  23. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/parser/count.py +0 -0
  24. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/parser/ebay_product.py +0 -0
  25. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/parser/purchase.py +0 -0
  26. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/parser/warehouse.py +0 -0
  27. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/schemas/__init__.py +0 -0
  28. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/schemas/common.py +0 -0
  29. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/schemas/ebay_product.py +0 -0
  30. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/schemas/order.py +0 -0
  31. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/schemas/warehouse.py +0 -0
  32. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/utils/__init__.py +0 -0
  33. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/dxm/utils/mark.py +0 -0
  34. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/__init__.py +0 -0
  35. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/constant/__init__.py +0 -0
  36. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/constant/response.py +0 -0
  37. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/main.py +0 -0
  38. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/parser/__init__.py +0 -0
  39. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/parser/order.py +0 -0
  40. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/schemas/__init__.py +0 -0
  41. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/schemas/query/__init__.py +0 -0
  42. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/schemas/query/order.py +0 -0
  43. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/schemas/vo/__init__.py +0 -0
  44. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/four_seller/schemas/vo/order.py +0 -0
  45. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/__init__.py +0 -0
  46. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/main.py +0 -0
  47. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/schemas/__init__.py +0 -0
  48. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/schemas/query/__init__.py +0 -0
  49. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/schemas/query/order.py +0 -0
  50. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/schemas/query/product.py +0 -0
  51. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/schemas/response/__init__.py +0 -0
  52. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/schemas/response/order.py +0 -0
  53. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/kogan/schemas/response/product.py +0 -0
  54. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/model.py +0 -0
  55. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/py.typed +0 -0
  56. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/takesend/__init__.py +0 -0
  57. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/takesend/config.py +0 -0
  58. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/takesend/main.py +0 -0
  59. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/utils/__init__.py +0 -0
  60. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/utils/close.py +0 -0
  61. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/utils/dxm.py +0 -0
  62. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/utils/list_util.py +0 -0
  63. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/src/ey_commerce_lib/utils/str.py +0 -0
  64. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/tests/__init__.py +0 -0
  65. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/tests/dxm/__init__.py +0 -0
  66. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/tests/kogan/__init__.py +0 -0
  67. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/tests/kogan/test_client.py +0 -0
  68. {ey_commerce_lib-1.0.14 → ey_commerce_lib-1.0.15}/uv.lock +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: ey-commerce-lib
3
- Version: 1.0.14
3
+ Version: 1.0.15
4
4
  Summary: eeyoung电商客户端调用封装
5
5
  Author-email: 饶奇奇 <1124393197@qq.com>
6
6
  Requires-Python: >=3.10
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "ey-commerce-lib"
3
- version = "1.0.14"
3
+ version = "1.0.15"
4
4
  description = "eeyoung电商客户端调用封装"
5
5
  readme = "README.md"
6
6
  authors = [
@@ -1,6 +1,8 @@
1
1
  import asyncio
2
+ import time
2
3
 
3
4
  from httpx import AsyncClient, Timeout
5
+ from playwright.async_api import async_playwright
4
6
 
5
7
  from ey_commerce_lib.dxm.constant.order import DxmOrderRuleType
6
8
  from ey_commerce_lib.dxm.parser.common import get_page_info, get_purchase_pagination_info
@@ -24,7 +26,8 @@ class DxmClient:
24
26
  self.__headers = headers
25
27
  self.__sem = asyncio.Semaphore(sem)
26
28
  timeout = Timeout(connect=5.0, read=20.0, write=10.0, pool=10.0)
27
- self.__async_client = AsyncClient(base_url="https://www.dianxiaomi.com", cookies=cookies, headers=headers,
29
+ self.__base_url = 'https://www.dianxiaomi.com'
30
+ self.__async_client = AsyncClient(base_url=self.__base_url, cookies=cookies, headers=headers,
28
31
  timeout=timeout)
29
32
 
30
33
  async def page_order_base_async(self, query: DxmOrderSearchForm):
@@ -694,6 +697,42 @@ class DxmClient:
694
697
  data=data)
695
698
  return ViewDxmCommodityProductResponse.model_validate(view_dxm_commodity_product_res.json())
696
699
 
700
+ async def update_dxm_commodity_front_sku(self, proid: str, front_sku: str):
701
+ """
702
+ 更新店小秘 仓库-商品详情中的平台sku
703
+ :param proid:
704
+ :param front_sku:
705
+ :return:
706
+ """
707
+ # 打开浏览器
708
+ try:
709
+ async with async_playwright() as p:
710
+ browser = await p.chromium.launch(headless=True)
711
+ context = await browser.new_context()
712
+ # 设置cookie和headers
713
+ await context.add_cookies([
714
+ {
715
+ "name": name, # cookie 名称
716
+ "value": value, # cookie 值
717
+ "domain": ".dianxiaomi.com", # 替换为你的目标域名
718
+ "path": "/", # cookie 路径
719
+ }
720
+ for name, value in self.__cookies.items()
721
+ ])
722
+ page = await context.new_page()
723
+ # 访问
724
+ await page.goto(f'{self.__base_url}/dxmCommodityProduct/openEditModal.htm?id={proid}&editOrCopy=0')
725
+ # 输入sku
726
+ await page.locator('input.variationValue.ui-autocomplete-input').fill(front_sku)
727
+ # 失去焦点
728
+ await page.locator('input.variationValue.ui-autocomplete-input').press('Tab')
729
+ # 休眠两秒
730
+ await asyncio.sleep(2)
731
+ # 点击保存
732
+ await page.locator('.button.btn-orange.m-left10').first.click()
733
+ except Exception as e:
734
+ raise Exception(f'更新店小秘 仓库-商品详情中的平台sku失败-失败原因:{e}')
735
+
697
736
  async def __aenter__(self):
698
737
  return self
699
738
 
@@ -39,7 +39,7 @@ def get_single_order_item_list(order_element: html.HtmlElement):
39
39
  try:
40
40
  float(price.replace(',', ''))
41
41
  except:
42
- raise Exception(f'价格格式错误, sku是{sku}')
42
+ raise Exception(f'价格格式错误, sku是{sku}--价格是{price}')
43
43
  sku_list.append({
44
44
  'sku': sku,
45
45
  'quantity': int(quantity),
@@ -285,7 +285,7 @@ class DxmCommodityProduct(BaseModel):
285
285
  current_sku_count: int = Field(0, alias="currentSkuCount", description="当前SKU计数")
286
286
  reference_by_group: int = Field(0, alias="referenceByGroup", description="按组引用")
287
287
  agent_name: Optional[str] = Field(None, alias="agentName", description="代理商名称")
288
- development_name: str = Field(..., alias="developmentName", description="开发人员名称")
288
+ development_name: Optional[str] = Field(..., alias="developmentName", description="开发人员名称")
289
289
  sales_name: Optional[str] = Field(None, alias="salesName", description="销售人员名称")
290
290
  productuu_id: Optional[str] = Field(None, alias="productuuId", description="商品UUID")
291
291
  auth_id: Optional[str] = Field(None, alias="authId", description="授权ID")
@@ -335,12 +335,12 @@ class ProductDTO(BaseModel):
335
335
  description="DXM商品列表")
336
336
  spu: Optional[str] = Field(None, alias="spu", description="SPU编码")
337
337
  dxm_product_packs: List[Any] = Field(..., alias="dxmProductPacks", description="DXM商品包装列表")
338
- supplier_product_relation_map_list: List[SupplierProductRelation] = Field(...,
338
+ supplier_product_relation_map_list: Optional[List[SupplierProductRelation]] = Field(...,
339
339
  alias="supplierProductRelationMapList",
340
340
  description="供应商商品关系映射列表")
341
- dxm_warehouse_product_list: List[DxmWarehouseProduct] = Field(..., alias="dxmWarehouseProductList",
341
+ dxm_warehouse_product_list: Optional[List[DxmWarehouseProduct]] = Field(..., alias="dxmWarehouseProductList",
342
342
  description="DXM仓库商品列表")
343
- count: int = Field(0, alias="count", description="计数")
343
+ count: Optional[int] = Field(0, alias="count", description="计数")
344
344
 
345
345
  model_config = ConfigDict(populate_by_name=True)
346
346
 
@@ -377,7 +377,7 @@ class EditDxmCommodityProduct(BaseModel):
377
377
  width: int
378
378
  height: int
379
379
  qc_type: int = Field(..., alias="qcType")
380
- product_status: str = Field(..., alias="productStatus")
380
+ product_status: int = Field(..., alias="productStatus")
381
381
  child_ids: str = Field("", alias="childIds")
382
382
  child_nums: str = Field("", alias="childNums")
383
383
  process_fee: int = Field(..., alias="processFee")
@@ -408,8 +408,8 @@ class EditSupplierProductRelationMap(BaseModel):
408
408
 
409
409
 
410
410
  class EditObj(BaseModel):
411
- dxm_commodity_product: DxmCommodityProduct = Field(..., alias="dxmCommodityProduct")
412
- dxm_product_customs: DxmProductCustoms = Field(..., alias="dxmProductCustoms")
411
+ dxm_commodity_product: EditDxmCommodityProduct = Field(..., alias="dxmCommodityProduct")
412
+ dxm_product_customs: EditDxmProductCustoms = Field(..., alias="dxmProductCustoms")
413
413
  warehouse_id_list: str = Field("", alias="warehouseIdList")
414
414
  supplier_product_relation_map_list: List[EditSupplierProductRelationMap] = Field(..., alias="supplierProductRelationMapList")
415
415
  dxm_product_packs: List = Field(..., alias="dxmProductPacks")
@@ -1,4 +1,7 @@
1
+ import json
2
+
1
3
  from ey_commerce_lib.dxm.schemas.dxm_commodity_product import ViewDxmCommodityProductResponse, EditObj
4
+ from ey_commerce_lib.utils.float import truncate_decimal_str
2
5
 
3
6
 
4
7
  def get_edit_commodity_product_by_view_dxm_response(data: ViewDxmCommodityProductResponse):
@@ -14,7 +17,7 @@ def get_edit_commodity_product_by_view_dxm_response(data: ViewDxmCommodityProduc
14
17
  name_en = dxm_commodity_product.name_en
15
18
  sku_code = dxm_commodity_product.sku_code
16
19
  sku = dxm_commodity_product.sku
17
- product_variation_str = dxm_commodity_product.product_variation_str
20
+ product_variation_str = ','.join(dxm_commodity_product.product_variation_str_list)
18
21
  sbm_id = dxm_commodity_product.sbm_id
19
22
  agent_id = dxm_commodity_product.agent_id
20
23
  development_id = dxm_commodity_product.development_id
@@ -46,7 +49,7 @@ def get_edit_commodity_product_by_view_dxm_response(data: ViewDxmCommodityProduc
46
49
  name_cn_bg = dxm_product_customs.name_cn
47
50
  name_en_bg = dxm_product_customs.name_en
48
51
  weight_bg = dxm_product_customs.weight
49
- price_bg = dxm_commodity_product.price_bg
52
+ price_bg = dxm_product_customs.price
50
53
  material_bg = dxm_commodity_product.material_bg
51
54
  purpose_bg = dxm_commodity_product.purpose_bg
52
55
  hgbm_bg = dxm_commodity_product.hgbm_bg
@@ -54,7 +57,7 @@ def get_edit_commodity_product_by_view_dxm_response(data: ViewDxmCommodityProduc
54
57
 
55
58
  warehouse_id_list = data.product_dto.warehouse_id_list
56
59
 
57
- supplier_product_relation_map_list = data.product_dto.supplier_product_relation_map_list
60
+ supplier_product_relation_map_list = data.product_dto.supplier_product_relation_map_list or []
58
61
  new_supplier_product_relation_map_list = []
59
62
  for supplier_product_relation_map in supplier_product_relation_map_list:
60
63
  supplier_id = supplier_product_relation_map.supplier_id
@@ -65,22 +68,22 @@ def get_edit_commodity_product_by_view_dxm_response(data: ViewDxmCommodityProduc
65
68
  })
66
69
 
67
70
  dxm_product_packs = data.product_dto.dxm_product_packs
68
-
71
+ # sbmId 必须为字符串
69
72
  return EditObj.model_validate({
70
73
  'dxmCommodityProduct': {
71
- 'productId': product_id,
74
+ 'productId': str(product_id),
72
75
  'name': name,
73
76
  'nameEn': name_en,
74
77
  'skuCode': sku_code,
75
78
  'sku': sku,
76
79
  'productVariationStr': product_variation_str,
77
- 'sbmId': sbm_id,
78
- 'agentId': agent_id,
79
- 'developmentId': development_id,
80
- 'salesId': sales_id,
81
- 'weight': weight,
82
- 'allowWeightError': allow_weight_error,
83
- 'price': price,
80
+ 'sbmId': sbm_id if sbm_id is not None else '',
81
+ 'agentId': str(agent_id),
82
+ 'developmentId': str(development_id),
83
+ 'salesId': str(sales_id),
84
+ 'weight': truncate_decimal_str(weight),
85
+ 'allowWeightError': '',
86
+ 'price': truncate_decimal_str(price),
84
87
  'sourceUrl': source_url,
85
88
  'imgUrl': img_url,
86
89
  'isUsed': is_used,
@@ -90,29 +93,30 @@ def get_edit_commodity_product_by_view_dxm_response(data: ViewDxmCommodityProduc
90
93
  'width': width,
91
94
  'height': height,
92
95
  'qcType': qc_type,
93
- 'productStatus': product_status,
94
- 'childIds': child_ids,
95
- 'childNums': child_nums,
96
+ 'productStatus': 1,
97
+ 'childIds': child_ids if child_ids is not None else '',
98
+ 'childNums': child_nums if child_nums is not None else '',
96
99
  'processFee': process_fee,
97
- 'qcContent': qc_content,
100
+ 'qcContent': qc_content if qc_content is not None else '',
98
101
  'qcImgNum': qc_img_num,
99
- 'groupState': group_state,
100
- 'ncm': ncm,
101
- 'cest': cest,
102
- 'unit': unit,
103
- 'origin': origin
102
+ 'groupState': str(group_state),
103
+ 'ncm': ncm if ncm is not None else '',
104
+ 'cest': cest if cest is not None else '',
105
+ 'unit': unit if unit is not None else '',
106
+ 'origin': origin if origin is not None else '0'
104
107
  },
105
108
  'dxmProductCustoms': {
106
109
  'nameCnBg': name_cn_bg,
107
110
  'nameEnBg': name_en_bg,
108
- 'weightBg': weight_bg,
109
- 'priceBg': price_bg,
110
- 'materialBg': material_bg,
111
- 'purposeBg': purpose_bg,
112
- 'hgbmBg': hgbm_bg,
113
- 'dangerDesBg': danger_des_bg
111
+ 'weightBg': truncate_decimal_str(weight_bg),
112
+ 'priceBg': truncate_decimal_str(price_bg, 4),
113
+ 'materialBg': material_bg if material_bg is not None else '',
114
+ 'purposeBg': purpose_bg if purpose_bg is not None else '',
115
+ 'hgbmBg': hgbm_bg if hgbm_bg is not None else '',
116
+ 'dangerDesBg': danger_des_bg if danger_des_bg is not None else '0'
114
117
  },
115
- 'warehouseIdList': warehouse_id_list,
118
+ 'warehouseIdList': warehouse_id_list if warehouse_id_list is not None else '',
116
119
  'supplierProductRelationMapList': new_supplier_product_relation_map_list,
117
120
  'dxmProductPacks': dxm_product_packs
118
121
  }).model_dump_json(by_alias=True)
122
+
@@ -0,0 +1,30 @@
1
+ from decimal import Decimal, ROUND_DOWN
2
+
3
+
4
+ def truncate_decimal(number, digits=2):
5
+ """
6
+ 截断保留指定位数的小数(不四舍五入),并保留末尾的 0
7
+ :param number: 输入的数字(int/float)
8
+ :param digits: 保留的小数位数(默认2位)
9
+ :return: 返回字符串形式,确保末尾 0 不省略
10
+ """
11
+ if isinstance(number, int):
12
+ return f"{number}.{'0' * digits}"
13
+
14
+ decimal_num = Decimal(str(number))
15
+ truncated = decimal_num.quantize(
16
+ Decimal('0.' + '0' * digits),
17
+ rounding=ROUND_DOWN
18
+ )
19
+ return format(truncated, f".{digits}f") # 强制保留末尾 0
20
+
21
+
22
+ def truncate_decimal_str(number, digits=2):
23
+ """
24
+ 使用decimal模块实现(最精确的方式)
25
+ """
26
+ return str(truncate_decimal(number, digits))
27
+
28
+
29
+ if __name__ == '__main__':
30
+ print(truncate_decimal(200.000, 4))
@@ -0,0 +1,91 @@
1
+ import json
2
+
3
+ import pytest
4
+
5
+ from ey_commerce_lib.dxm.constant.order import ORDER_SEARCH_APPROVAL_BASE_FORM, \
6
+ ORDER_SEARCH_PENDING_PROCESSING_BASE_FORM, ORDER_SEARCH_SELF_WAREHOUSE_BASE_FORM, \
7
+ ORDER_SEARCH_OUT_OF_STOCK_BASE_FORM, ORDER_SEARCH_HAVE_GOODS_BASE_FORM
8
+ from ey_commerce_lib.dxm.main import DxmClient
9
+ from ey_commerce_lib.dxm.schemas.warehouse import WarehouseProductQuery
10
+ from ey_commerce_lib.dxm.utils.mark import get_custom_mark_content_list_by_data_custom_mark, \
11
+ generate_add_or_update_user_comment_data_by_content_list
12
+ from ey_commerce_lib.four_seller.main import FourSellerClient
13
+ from ey_commerce_lib.four_seller.schemas.query.order import FourSellerOrderQueryModel
14
+ from ey_commerce_lib.takesend.main import TakeSendClient
15
+ import ey_commerce_lib.dxm.utils.dxm_commodity_product as dxm_commodity_product_util
16
+
17
+
18
+ async def login_success(user_token: str):
19
+ print(f'user_token: {user_token}')
20
+ pass
21
+
22
+
23
+ @pytest.mark.asyncio
24
+ async def test_auto_login_4seller():
25
+ # user_token = await auto_login_4seller(user_name="sky@eeyoung.com", password="ey010203@@")
26
+ # print(user_token)
27
+ async with FourSellerClient(
28
+ user_name="xxxxx",
29
+ password="xxxxxx",
30
+ login_success_call_back=login_success,
31
+ user_token="xxxxxx") as four_seller_client:
32
+ await four_seller_client.list_history_order(FourSellerOrderQueryModel())
33
+
34
+
35
+ cookies = {
36
+ 'dxm_i': 'MTAyNzg5NiFhVDB4TURJM09EazIhZjc5ZTMxMjZmN2Q3NTk5OGZlMDg4YjQzNzNlNzlmOWY',
37
+ 'dxm_t': 'MTcxNDk2NDU4MiFkRDB4TnpFME9UWTBOVGd5IWIzZWRjYTc3YTdjYWE0MmIxMWYwNjFhOTlmMDgxZjY5',
38
+ 'dxm_c': 'TWVOMVpiclYhWXoxTlpVNHhXbUp5VmchNmM5MmM5ODc1MDBkODVjOWJmOTFlMzdhNGJiNWI3Njk',
39
+ 'dxm_w': 'ZDc3NWVhOTdkOTEyNGE4ZmRkODBmYzc2YmFlOGVjZjEhZHoxa056YzFaV0U1TjJRNU1USTBZVGhtWkdRNE1HWmpOelppWVdVNFpXTm1NUSFmZWZiZGZiMTEwMzhlN2M4M2MzYjZmYjAxYTcxMjViMw',
40
+ 'dxm_s': 'aMHO7LWKAQe6NzFrV3O4cceXkBriLGNmwondOR7INWs',
41
+ 'MYJ_MKTG_fapsc5t4tc': 'JTdCJTdE',
42
+ 'MYJ_fapsc5t4tc': 'JTdCJTIyZGV2aWNlSWQlMjIlM0ElMjJkMGRlYzNkYi00MTNlLTQyZjktOWIxNC0xYzBhZTY4MTk4ZmIlMjIlMkMlMjJ1c2VySWQlMjIlM0ElMjIxMDI3ODk2JTIyJTJDJTIycGFyZW50SWQlMjIlM0ElMjIyNTg2MzQlMjIlMkMlMjJzZXNzaW9uSWQlMjIlM0ExNzMxMDU5MDc1MjU0JTJDJTIyb3B0T3V0JTIyJTNBZmFsc2UlMkMlMjJsYXN0RXZlbnRUaW1lJTIyJTNBMTczMTA1OTA3NTQyNCUyQyUyMmxhc3RFdmVudElkJTIyJTNBMTE2JTdE',
43
+ 'MYJ_fapsc5t4tc': 'JTdCJTIyZGV2aWNlSWQlMjIlM0ElMjJkMGRlYzNkYi00MTNlLTQyZjktOWIxNC0xYzBhZTY4MTk4ZmIlMjIlMkMlMjJ1c2VySWQlMjIlM0ElMjIxMDI3ODk2JTIyJTJDJTIycGFyZW50SWQlMjIlM0ElMjIyNTg2MzQlMjIlMkMlMjJzZXNzaW9uSWQlMjIlM0ExNzMxMDU5MDc1MTEwJTJDJTIyb3B0T3V0JTIyJTNBZmFsc2UlMkMlMjJsYXN0RXZlbnRUaW1lJTIyJTNBMTczMTA1OTA3NTk5NiUyQyUyMmxhc3RFdmVudElkJTIyJTNBMTE2JTdE',
44
+ '_dxm_ad_client_id': '7AEFA0B78CE1B35075D391C5226612CED',
45
+ 'Hm_lvt_f8001a3f3d9bf5923f780580eb550c0b': '1731459796,1731547149,1731590878,1731893161',
46
+ 'HMACCOUNT': 'F266E8F609D8D8B1',
47
+ 'MYJ_fapsc5t4tc': 'JTdCJTIyZGV2aWNlSWQlMjIlM0ElMjJkMGRlYzNkYi00MTNlLTQyZjktOWIxNC0xYzBhZTY4MTk4ZmIlMjIlMkMlMjJ1c2VySWQlMjIlM0ElMjIxMDI3ODk2JTIyJTJDJTIycGFyZW50SWQlMjIlM0ElMjIyNTg2MzQlMjIlMkMlMjJzZXNzaW9uSWQlMjIlM0ExNzMxOTAxNDMzMTk3JTJDJTIyb3B0T3V0JTIyJTNBZmFsc2UlMkMlMjJsYXN0RXZlbnRJZCUyMiUzQTExNiU3RA==',
48
+ 'Hm_lpvt_f8001a3f3d9bf5923f780580eb550c0b': '1731901433',
49
+ 'JSESSIONID': 'CD9C8372185D453012E5EEFBA64E2C9C',
50
+ }
51
+
52
+ headers = {
53
+ 'accept': 'text/html, */*; q=0.01',
54
+ 'accept-language': 'zh-CN,zh;q=0.9',
55
+ 'cache-control': 'no-cache',
56
+ 'content-type': 'application/x-www-form-urlencoded; charset=UTF-8',
57
+ 'origin': 'https://www.dianxiaomi.com',
58
+ 'pragma': 'no-cache',
59
+ 'priority': 'u=1, i',
60
+ 'referer': 'https://www.dianxiaomi.com/sys/index.htm?go=m420',
61
+ 'sec-ch-ua': '"Google Chrome";v="131", "Chromium";v="131", "Not_A Brand";v="24"',
62
+ 'sec-ch-ua-mobile': '?0',
63
+ 'sec-ch-ua-platform': '"Windows"',
64
+ 'sec-fetch-dest': 'empty',
65
+ 'sec-fetch-mode': 'cors',
66
+ 'sec-fetch-site': 'same-origin',
67
+ 'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36',
68
+ 'x-requested-with': 'XMLHttpRequest',
69
+ }
70
+
71
+
72
+ @pytest.mark.asyncio
73
+ async def test_dxm_api():
74
+ async with (DxmClient(headers=headers, cookies=cookies) as dxm_client):
75
+ # data = await dxm_client.list_order_detail_async(query=ORDER_SEARCH_HAVE_GOODS_BASE_FORM)
76
+ # for order in data:
77
+ # for pair_info in order.get('detail').get('pair_info_list'):
78
+ # print(pair_info.get('proid'))
79
+ data = await dxm_client.update_dxm_commodity_front_sku('17773195771232287', 'fuck112')
80
+
81
+
82
+ @pytest.mark.asyncio
83
+ async def test_warehouse():
84
+ async with (DxmClient(headers=headers, cookies=cookies) as dxm_client):
85
+ print(await dxm_client.page_warehouse_product(WarehouseProductQuery()))
86
+
87
+
88
+ @pytest.mark.asyncio
89
+ async def test_tasksend_api():
90
+ async with (TakeSendClient(username="", password="") as tasksend_client):
91
+ await tasksend_client.login()
@@ -1,57 +0,0 @@
1
- import json
2
-
3
- import pytest
4
-
5
- from ey_commerce_lib.dxm.constant.order import ORDER_SEARCH_APPROVAL_BASE_FORM, \
6
- ORDER_SEARCH_PENDING_PROCESSING_BASE_FORM, ORDER_SEARCH_SELF_WAREHOUSE_BASE_FORM, \
7
- ORDER_SEARCH_OUT_OF_STOCK_BASE_FORM, ORDER_SEARCH_HAVE_GOODS_BASE_FORM
8
- from ey_commerce_lib.dxm.main import DxmClient
9
- from ey_commerce_lib.dxm.schemas.warehouse import WarehouseProductQuery
10
- from ey_commerce_lib.dxm.utils.mark import get_custom_mark_content_list_by_data_custom_mark, \
11
- generate_add_or_update_user_comment_data_by_content_list
12
- from ey_commerce_lib.four_seller.main import FourSellerClient
13
- from ey_commerce_lib.four_seller.schemas.query.order import FourSellerOrderQueryModel
14
- from ey_commerce_lib.takesend.main import TakeSendClient
15
- import ey_commerce_lib.dxm.utils.dxm_commodity_product as dxm_commodity_product_util
16
-
17
-
18
- async def login_success(user_token: str):
19
- print(f'user_token: {user_token}')
20
- pass
21
-
22
-
23
- @pytest.mark.asyncio
24
- async def test_auto_login_4seller():
25
- # user_token = await auto_login_4seller(user_name="sky@eeyoung.com", password="ey010203@@")
26
- # print(user_token)
27
- async with FourSellerClient(
28
- user_name="xxxxx",
29
- password="xxxxxx",
30
- login_success_call_back=login_success,
31
- user_token="xxxxxx") as four_seller_client:
32
- await four_seller_client.list_history_order(FourSellerOrderQueryModel())
33
-
34
-
35
-
36
-
37
-
38
- @pytest.mark.asyncio
39
- async def test_dxm_api():
40
- async with (DxmClient(headers=headers, cookies=cookies) as dxm_client):
41
- # data = await dxm_client.list_order_detail_async(query=ORDER_SEARCH_HAVE_GOODS_BASE_FORM)
42
- # for order in data:
43
- # for pair_info in order.get('detail').get('pair_info_list'):
44
- # print(pair_info.get('proid'))
45
- data = await dxm_client.view_dxm_commodity_product('17773195770895797')
46
- print(json.dumps(dxm_commodity_product_util.get_edit_commodity_product_by_view_dxm_response(data)))
47
-
48
- @pytest.mark.asyncio
49
- async def test_warehouse():
50
- async with (DxmClient(headers=headers, cookies=cookies) as dxm_client):
51
- print(await dxm_client.page_warehouse_product(WarehouseProductQuery()))
52
-
53
-
54
- @pytest.mark.asyncio
55
- async def test_tasksend_api():
56
- async with (TakeSendClient(username="", password="") as tasksend_client):
57
- await tasksend_client.login()