Coverage for jbank/management/commands/wsedi_download.py: 0%

# Coverage for jbank/management/commands/wsedi_download.py : 0%

## 85 statements

Hot-keys on this page

r m x p toggle line displays

j k next/prev highlighted chunk

0 (zero) top of page

1 (one) first highlighted chunk

1#pylint: disable=logging-format-interpolation,too-many-locals,too-many-branches

2 import base64

3 import logging

4 import os

5 import pytz

6 from django.core.management.base import CommandParser

7 from django.utils.timezone import now

8 from jutil.xml import xml_to_dict

9 from jbank.helpers import process_pain002_file_content, parse_start_and_end_date

10 from jbank.models import WsEdiConnection

11 from jbank.wsedi import wsedi_get, wsedi_execute

12 from jutil.command import SafeCommand

13

14

15 logger = logging.getLogger(__name__)

16

17

18 class Command(SafeCommand):

19 help = """

20 Download Finnish bank files

21 """

22

23 def add_arguments(self, parser: CommandParser):

24 parser.add_argument('path', type=str)

25 parser.add_argument('--verbose', action='store_true')

26 parser.add_argument('--overwrite', action='store_true')

27 parser.add_argument('--file-type', type=str, help='E.g. TO, SVM, XP, NDCORPAYL, pain.002.001.03')

28 parser.add_argument('--status', type=str, default='', help='E.g. DLD, NEW')

29 parser.add_argument('--file-reference', type=str, help='Download single file based on file reference')

30 parser.add_argument('--list-only', action='store_true')

31 parser.add_argument('--process-pain002', action='store_true')

32 parser.add_argument('--start-date', type=str)

33 parser.add_argument('--end-date', type=str)

34 parser.add_argument('--ws', type=int)

35

36 def do(self, *args, **options): # pylint: disable=too-many-statements

37 ws = WsEdiConnection.objects.get(id=options['ws']) if options['ws'] else None

38 assert ws is None or isinstance(ws, WsEdiConnection)

39 if ws and not ws.enabled:

40 logger.info('WS connection %s not enabled, exiting', ws)

41 return

42

43 start_date, end_date = parse_start_and_end_date(pytz.timezone('Europe/Helsinki'), **options)

44 path = os.path.abspath(options['path'])

45 command = 'DownloadFileList'

46 time_now = now()

47 file_reference = options['file_reference']

48 if file_reference:

49 command = 'DownloadFile'

50 status = options['status']

51 file_type = options['file_type']

52 if command == 'DownloadFileList' and not file_type:

53 print('--file-type required (e.g. TO, SVM, XP, NDCORPAYL, pain.002.001.03)')

54 return

55 if ws:

56 content = wsedi_execute(ws, command=command, file_type=file_type, status=status, start_date=start_date, end_date=end_date,

57 file_reference=file_reference, verbose=options['verbose'])

58 data = xml_to_dict(content, array_tags=['FileDescriptor'])

59 else:

60 res = wsedi_get(command=command, file_type=file_type, status=status, file_reference=file_reference, verbose=options['verbose'])

61 data = res.json()

62 # "FileDescriptors": {

63 # "FileDescriptor": [

64 # {

65 # "FileReference": "535283541",

66 # "TargetId": "NONE",

67 # "UserFilename": "STOL001.FMV80KT2.WEBSER.PS",

68 # "ParentFileReference": "1218",

69 # "FileType": "TO",

70 # "FileTimestamp": "2017-12-18T20:33:09.362+02:00",

71 # "Status": "DLD",

72 # "LastDownloadTimestamp": "2017-12-19T12:36:34.490+02:00",

73 # "ForwardedTimestamp": "2017-12-18T20:33:09.362+02:00",

74 # "Deletable": "false",

75 # "CustomerNumber": "06720106",

76 # "Modifier": "06720106",

77 # "ModifiedTimestamp": "2017-12-19T12:36:34.490+02:00",

78 # "SourceId": "A",

79 # "Environment": "PRODUCTION"

80 # },

81 # ...

82

83 if command == 'DownloadFileList':

84 if 'FileDescriptors' in data and data['FileDescriptors'] is not None and 'FileDescriptor' in data['FileDescriptors']:

85 for fd in data['FileDescriptors']['FileDescriptor']:

86 file_reference = fd['FileReference']

87 file_type = fd['FileType']

88 file_basename = file_reference + '.' + file_type

89 file_path = os.path.join(path, file_basename)

90 if options['list_only']:

91 print('{file_reference} ({file_type}/{status}): {user_filename} ({timestamp})'.format(

92 file_reference=file_reference, file_type=file_type, status=fd.get('Status'),

93 user_filename=fd.get('UserFilename'), timestamp=fd.get('FileTimestamp')))

94 continue

95 if options['overwrite'] or not os.path.isfile(file_path):

96 command = 'DownloadFile'

97 if ws:

98 content = wsedi_execute(ws, command=command, file_type=file_type, status='', file_reference=file_reference,

99 verbose=options['verbose'])

100 file_data = xml_to_dict(content)

101 else:

102 res = wsedi_get(command=command, file_type=file_type, status='', file_reference=file_reference, verbose=options['verbose'])

103 file_data = res.json()

104 if 'Content' not in file_data:

105 logger.error('WS-EDI {} HTTP {} but Content block missing: {}'.format(command, res.status_code, file_data))

106 raise Exception("WS-EDI {} HTTP {} but Content block missing".format(command, res.status_code))

107 bcontent = base64.b64decode(file_data['Content'])

108 with open(file_path, 'wb') as fp:

109 fp.write(bcontent)

110 logger.info('Wrote file {}'.format(file_path))

111

112 # process selected files immediately

113 if options['process_pain002'] and file_type in ['XP', 'pain.002.001.03', 'NDCORPAYL']:

114 process_pain002_file_content(bcontent, file_path, created=time_now)

115 else:

116 print('Skipping old file {}'.format(file_path))

117 else:

118 print('Empty file list downloaded')

119 elif command == 'DownloadFile':

120 bcontent = base64.b64decode(data['Content'])

121 file_path = os.path.join(path, file_reference)

122 if options['overwrite'] or not os.path.isfile(file_path):

123 with open(file_path, 'wb') as fp:

124 fp.write(bcontent)

125 logger.info('Wrote file {}'.format(file_path))

126 else:

127 print('Skipping old file {}'.format(file_path))