test_yaml.py 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473
  1. # -*- coding: utf-8 -*-
  2. import pytest
  3. import datetime
  4. import difflib
  5. import finoex
  6. import ioex.calcex
  7. import ioex.datetimeex
  8. import os
  9. import pytz
  10. yaml = pytest.importorskip('yaml')
  11. def get_figure_a():
  12. return ioex.calcex.Figure(12.3, u'km')
  13. def get_figure_b():
  14. return ioex.calcex.Figure(12300, u'米')
  15. def get_sum_a():
  16. return finoex.Sum(1.23, u'EUR')
  17. def get_sum_b():
  18. return finoex.Sum(20.45, u'€')
  19. def get_item_a():
  20. return finoex.Item(
  21. name = u'item a',
  22. price_brutto = get_sum_a(),
  23. )
  24. def get_item_b():
  25. return finoex.Item(
  26. name = u'item β',
  27. price_brutto = get_sum_b(),
  28. )
  29. def get_service():
  30. return finoex.Service(
  31. name = u'service',
  32. price_brutto = finoex.Sum(1.0, u'EUR'),
  33. duration = ioex.datetimeex.Duration(years = 2),
  34. )
  35. def get_person_a():
  36. return finoex.Person(
  37. first_name = u'Fabian Peter',
  38. last_name = u'Hammerle',
  39. )
  40. def get_person_b():
  41. return finoex.Person(
  42. first_name = u'名字',
  43. last_name = u'贵姓',
  44. )
  45. def get_campaign_a():
  46. return finoex.Campaign(
  47. name = u'campaign a',
  48. founder = u'company',
  49. end = datetime.datetime(2016, 7, 23, 9, 23, 17, tzinfo = pytz.timezone('Europe/Vienna')),
  50. )
  51. def get_campaign_b():
  52. return finoex.Campaign(
  53. founder = u'company',
  54. name = u'campaign without end',
  55. website_url = u'http://campaign.com',
  56. )
  57. def get_pledge():
  58. return finoex.Pledge(
  59. campaign = get_campaign_a(),
  60. price_brutto = finoex.Sum(10.0, u'EUR'),
  61. reward = u'great',
  62. )
  63. def get_contribution():
  64. return finoex.Contribution(
  65. campaign = get_campaign_a(),
  66. price_brutto = finoex.Sum(10.0, u'EUR'),
  67. reward = u'product',
  68. )
  69. def get_article():
  70. return finoex.Article(
  71. authors = ['a', 'b'],
  72. depth = finoex.Distance(12.3, u'dm'),
  73. features = u'supergeil',
  74. height = finoex.Distance(123., u'cm'),
  75. maximum_load = ioex.calcex.Figure(40., u'kg'),
  76. name = u'article name',
  77. price_brutto = get_sum_a(),
  78. product_id = u'0815',
  79. quantity = 1,
  80. reseller = u'seller',
  81. shipper = u'shipper',
  82. state = u'goood',
  83. width = finoex.Distance(1.23, u'm'),
  84. )
  85. def get_transportation():
  86. return finoex.Transportation(
  87. name = u'ticket',
  88. price_brutto = get_sum_a(),
  89. departure_point = u'home',
  90. destination_point = u'city',
  91. distance = finoex.Distance(3.21, u'km'),
  92. passenger = get_person_a(),
  93. valid_from = datetime.datetime(2016, 7, 14, 13, 50, 4, 0, tzinfo = pytz.timezone('Europe/Vienna')),
  94. valid_until = datetime.datetime(2016, 7, 14, 18, 50, 4, 0, tzinfo = pytz.utc),
  95. ticket_url = u'https://www.example.com',
  96. estimated_arrival_time = ioex.datetimeex.Period(
  97. start = pytz.timezone('Europe/Vienna').localize(datetime.datetime(2016, 7, 24, 23, 47, 2)),
  98. end = pytz.utc.localize(datetime.datetime(2016, 7, 24, 23, 48, 5)),
  99. ),
  100. )
  101. def get_shipping():
  102. return finoex.Shipping(
  103. price_brutto = get_sum_a(),
  104. destination_point = u'home',
  105. )
  106. def get_taxi_ride():
  107. return finoex.TaxiRide(
  108. name = u'taxi ride',
  109. price_brutto = get_sum_a(),
  110. departure_point = u'home',
  111. destination_point = u'city',
  112. distance = finoex.Distance(3.21, u'km'),
  113. driver = u'driver',
  114. arrival_time = datetime.datetime(2016, 5, 2, 18, 10, tzinfo = pytz.timezone('Europe/Vienna')),
  115. departure_time = datetime.datetime(2016, 5, 2, 18, 25, tzinfo = pytz.timezone('Europe/Vienna')),
  116. )
  117. def get_discount_a():
  118. return finoex.Discount(
  119. name = u'discount a',
  120. amount = get_sum_a(),
  121. )
  122. def get_discount_b():
  123. return finoex.Discount(
  124. name = u'discount β',
  125. amount = get_sum_b(),
  126. )
  127. def get_order_a(items = True, discounts = True):
  128. order = finoex.Order(
  129. platform = u'platformπ',
  130. order_id = u'id',
  131. order_date = datetime.datetime(2016, 5, 8, 0, 18, 17),
  132. customer_id = u'customer',
  133. )
  134. if items:
  135. order.items.append(get_item_a())
  136. order.items.append(get_item_b())
  137. if discounts:
  138. order.discounts.append(get_discount_a())
  139. order.discounts.append(get_discount_b())
  140. return order
  141. def get_order_b():
  142. order = finoex.Order(
  143. platform = u'platformπ',
  144. order_id = u'order_b',
  145. order_date = datetime.datetime(2015, 5, 8, 0, 18, 17),
  146. )
  147. return order
  148. def get_order_c():
  149. order = finoex.Order(
  150. platform = u'γάμμα',
  151. order_id = u'order_βήτα',
  152. order_date = datetime.datetime(2014, 5, 8, 0, 18, 17),
  153. customer_id = u'ρώ',
  154. )
  155. return order
  156. def get_distance():
  157. return finoex.Distance(2.4142, u'km')
  158. def to_yaml(data):
  159. class Dumper(yaml.Dumper):
  160. pass
  161. ioex.datetimeex.Duration.register_yaml_representer(yaml.Dumper)
  162. ioex.datetimeex.Period.register_yaml_representer(yaml.Dumper)
  163. ioex.calcex.Figure.register_yaml_representer(yaml.Dumper)
  164. finoex.Sum.register_yaml_representer(yaml.Dumper)
  165. finoex.Distance.register_yaml_representer(yaml.Dumper)
  166. return yaml.dump(
  167. data,
  168. default_flow_style = False,
  169. allow_unicode = True,
  170. Dumper = Dumper,
  171. ) #.decode('utf-8')
  172. def yaml_diff(a, b):
  173. return '\n'.join(difflib.ndiff(
  174. to_yaml(a).split('\n'),
  175. to_yaml(b).split('\n'),
  176. ))
  177. @pytest.mark.parametrize('source_object,expected_yaml', [
  178. [datetime.datetime(2016, 7, 14, 13, 50, 4, 0), '2016-07-14 13:50:04\n...\n'],
  179. [datetime.datetime(2016, 7, 14, 13, 50, 4, 0, tzinfo = pytz.timezone('Europe/Vienna')), '2016-07-14 13:50:04+01:05\n...\n'],
  180. [datetime.datetime(2016, 7, 14, 13, 50, 4, 0, tzinfo = pytz.utc), '2016-07-14 13:50:04+00:00\n...\n'],
  181. [finoex.Distance(1.34, u'km'), u"!distance '1.34 km'\n"],
  182. [finoex.Distance(1.34, u'μm'), u"!distance '1.34 μm'\n"],
  183. [get_discount_a(), u"!discount\namount: !sum '1.23 EUR'\nname: discount a\n"],
  184. [get_discount_b(), u"!discount\namount: !sum '20.45 EUR'\nname: discount β\n"],
  185. [get_figure_a(), u"!figure '12.3 km'\n"],
  186. [get_figure_b(), u"!figure '12300 米'\n"],
  187. [get_item_a(), u"!item\nname: item a\nprice_brutto: !sum '1.23 EUR'\n"],
  188. [get_item_b(), u"!item\nname: item β\nprice_brutto: !sum '20.45 EUR'\n"],
  189. [get_person_a(), u'!person\nfirst_name: Fabian Peter\nlast_name: Hammerle\n'],
  190. [get_person_b(), u'!person\nfirst_name: 名字\nlast_name: 贵姓\n'],
  191. [get_campaign_a(), u"""!campaign
  192. end: 2016-07-23 09:23:17+01:05
  193. founder: company
  194. name: campaign a
  195. """],
  196. [get_campaign_b(), u"""!campaign
  197. founder: company
  198. name: campaign without end
  199. website_url: http://campaign.com
  200. """],
  201. [get_service(), u"""!service
  202. duration: !duration
  203. years: 2
  204. name: service
  205. price_brutto: !sum '1.0 EUR'
  206. """],
  207. [get_pledge(), u"""!pledge
  208. campaign: !campaign
  209. end: 2016-07-23 09:23:17+01:05
  210. founder: company
  211. name: campaign a
  212. price_brutto: !sum '10.0 EUR'
  213. reward: great
  214. """],
  215. [get_contribution(), u"""!contribution
  216. campaign: !campaign
  217. end: 2016-07-23 09:23:17+01:05
  218. founder: company
  219. name: campaign a
  220. price_brutto: !sum '10.0 EUR'
  221. reward: product
  222. """],
  223. [get_order_a(), u"""!order
  224. customer_id: customer
  225. discounts:
  226. - !discount
  227. amount: !sum '1.23 EUR'
  228. name: discount a
  229. - !discount
  230. amount: !sum '20.45 EUR'
  231. name: discount β
  232. items:
  233. - !item
  234. name: item a
  235. price_brutto: !sum '1.23 EUR'
  236. - !item
  237. name: item β
  238. price_brutto: !sum '20.45 EUR'
  239. order_date: 2016-05-08 00:18:17
  240. order_id: id
  241. platform: platformπ
  242. """],
  243. [get_order_a(discounts = False), u"""!order
  244. customer_id: customer
  245. items:
  246. - !item
  247. name: item a
  248. price_brutto: !sum '1.23 EUR'
  249. - !item
  250. name: item β
  251. price_brutto: !sum '20.45 EUR'
  252. order_date: 2016-05-08 00:18:17
  253. order_id: id
  254. platform: platformπ
  255. """],
  256. [get_article(), u"""!article
  257. authors:
  258. - a
  259. - b
  260. depth: !distance '12.3 dm'
  261. features: supergeil
  262. height: !distance '123.0 cm'
  263. maximum_load: !figure '40.0 kg'
  264. name: article name
  265. price_brutto: !sum '1.23 EUR'
  266. product_id: 0815
  267. quantity: 1
  268. reseller: seller
  269. shipper: shipper
  270. state: goood
  271. width: !distance '1.23 m'
  272. """],
  273. [get_transportation(), u"""!transportation
  274. departure_point: home
  275. destination_point: city
  276. distance: !distance '3.21 km'
  277. estimated_arrival_time: !period
  278. end: 2016-07-24 23:48:05+00:00
  279. start: 2016-07-24 23:47:02+02:00
  280. name: ticket
  281. passenger: !person
  282. first_name: Fabian Peter
  283. last_name: Hammerle
  284. price_brutto: !sum '1.23 EUR'
  285. ticket_url: https://www.example.com
  286. valid_from: 2016-07-14 13:50:04+01:05
  287. valid_until: 2016-07-14 18:50:04+00:00
  288. """],
  289. [get_shipping(), u"""!shipping
  290. destination_point: home
  291. price_brutto: !sum '1.23 EUR'
  292. """],
  293. [get_taxi_ride(), u"""!taxi-ride
  294. arrival_time: 2016-05-02 18:10:00+01:05
  295. departure_point: home
  296. departure_time: 2016-05-02 18:25:00+01:05
  297. destination_point: city
  298. distance: !distance '3.21 km'
  299. driver: driver
  300. name: taxi ride
  301. price_brutto: !sum '1.23 EUR'
  302. """],
  303. ])
  304. def test_to_yaml(source_object, expected_yaml):
  305. assert expected_yaml == to_yaml(source_object)
  306. @pytest.mark.parametrize('expected_object,source_yaml', [
  307. [datetime.datetime(2016, 7, 14, 13, 50, 4, 0), '2016-07-14 13:50:04'],
  308. [datetime.datetime(2016, 7, 14, 13, 50, 4, 0, tzinfo = pytz.timezone('Europe/Vienna')), '2016-07-14 13:50:04+01:05'],
  309. [datetime.datetime(2016, 7, 14, 13, 50, 4, 0, tzinfo = pytz.utc), '2016-07-14 13:50:04+00:00'],
  310. [finoex.Distance(1.34, u'km'), u"!distance '1.34 km'\n"],
  311. [finoex.Distance(1.34, u'μm'), u"!distance '1.34 μm'"],
  312. [get_discount_a(), u"!discount\nname: discount a\namount: !sum '1.23 EUR'\n"],
  313. [get_discount_b(), u"!discount\nname: discount β\namount: !sum '20.45 EUR'\n"],
  314. [get_figure_a(), '!figure\nunit: km\nvalue: 12.3\n'],
  315. [get_figure_a(), u'!figure\nunit: km\nvalue: 12.3\n'],
  316. [get_figure_b(), '!figure\nunit: 米\nvalue: 12300\n'],
  317. [get_figure_b(), u'!figure\nunit: 米\nvalue: 12300\n'],
  318. [get_item_a(), u"!item\nname: item a\nprice_brutto: !sum '1.23 EUR'\n"],
  319. [get_item_a(), u"!item\nname: item a\nprice_brutto: !sum 1.23 EUR"],
  320. [get_item_a(), u"!item\nname: item a\nprice_brutto: !sum 1.23 €\n"],
  321. [get_item_b(), u"!item\nname: item β\nprice_brutto: !sum '20.45 EUR'\n"],
  322. [get_person_a(), '!person\nfirst_name: Fabian Peter\nlast_name: Hammerle\n'],
  323. [get_person_a(), u'!person\nfirst_name: Fabian Peter\nlast_name: Hammerle\n'],
  324. [get_person_b(), u'!person\nfirst_name: 名字\nlast_name: 贵姓\n'],
  325. [get_campaign_a(), u"""!campaign
  326. name: campaign a
  327. founder: company
  328. end: 2016-07-23 09:23:17+01:05
  329. """],
  330. [get_campaign_b(), u"""!campaign
  331. founder: company
  332. name: campaign without end
  333. website_url: http://campaign.com
  334. """],
  335. [get_service(), u"""!service
  336. duration: !duration
  337. years: 2
  338. name: service
  339. price_brutto: !sum '1.0 EUR'
  340. """],
  341. [get_pledge(), u"""!pledge
  342. campaign: !campaign
  343. name: campaign a
  344. founder: company
  345. end: 2016-07-23 09:23:17+01:05
  346. price_brutto: !sum '10.0 EUR'
  347. reward: great
  348. """],
  349. [get_contribution(), u"""!contribution
  350. campaign: !campaign
  351. end: 2016-07-23 09:23:17+01:05
  352. founder: company
  353. name: campaign a
  354. price_brutto: !sum '10.0 EUR'
  355. reward: product
  356. """],
  357. [[get_person_a(), get_person_b()], u"""
  358. - !person
  359. first_name: Fabian Peter
  360. last_name: Hammerle
  361. - !person
  362. first_name: 名字
  363. last_name: 贵姓"""],
  364. [get_transportation(), u"""!transportation
  365. departure_point: home
  366. destination_point: city
  367. distance: !distance '3.21 km'
  368. name: ticket
  369. price_brutto: !sum '1.23 EUR'
  370. route_map: null
  371. passenger: !person
  372. first_name: Fabian Peter
  373. last_name: Hammerle
  374. ticket_url: https://www.example.com
  375. valid_from: 2016-07-14 13:50:04+01:05
  376. valid_until: 2016-07-14 18:50:04+00:00
  377. estimated_arrival_time: !period
  378. end: 2016-07-24T23:48:05+00:00
  379. start: 2016-07-24T23:47:02+02:00
  380. """],
  381. [get_shipping(), u"""!shipping
  382. destination_point: home
  383. price_brutto: !sum 1.23 EUR
  384. """],
  385. [get_order_a(), u"""!order
  386. customer_id: customer
  387. discounts:
  388. - !discount
  389. amount: !sum '1.23 EUR'
  390. name: discount a
  391. - !discount
  392. amount: !sum '20.45 EUR'
  393. name: discount β
  394. items:
  395. - !item
  396. name: item a
  397. price_brutto: !sum '1.23 EUR'
  398. - !item
  399. name: item β
  400. price_brutto: !sum '20.45 EUR'
  401. order_date: 2016-05-08 00:18:17
  402. order_id: id
  403. platform: platformπ
  404. """],
  405. [get_article(), u"""!article
  406. authors:
  407. - a
  408. - b
  409. delivery_date: null
  410. features: supergeil
  411. name: article name
  412. price_brutto: !sum '1.23 EUR'
  413. product_id: 0815
  414. quantity: 1
  415. reseller: seller
  416. shipper: shipper
  417. state: goood
  418. depth: !distance 12.3 dm
  419. height: !distance 123.0 cm
  420. maximum_load: !figure 40.0 kg
  421. width: !distance 1.23 m
  422. """],
  423. [get_taxi_ride(), u"""!taxi-ride
  424. arrival_time: 2016-05-02 18:10:00+01:05
  425. departure_point: home
  426. departure_time: 2016-05-02 18:25:00+01:05
  427. destination_point: city
  428. distance: !distance '3.21 km'
  429. driver: driver
  430. name: taxi ride
  431. price_brutto: !sum '1.23 EUR'
  432. route_map: null
  433. """],
  434. ])
  435. def test_from_yaml(expected_object, source_yaml):
  436. class Loader(yaml.Loader):
  437. pass
  438. ioex.datetimeex.Duration.register_yaml_constructor(Loader)
  439. ioex.datetimeex.Period.register_yaml_constructor(Loader)
  440. ioex.calcex.Figure.register_yaml_constructor(Loader)
  441. finoex.Sum.register_yaml_constructor(Loader)
  442. finoex.Distance.register_yaml_constructor(Loader)
  443. loaded_object = yaml.load(source_yaml, Loader=Loader)
  444. assert loaded_object == expected_object