Starchik1 commited on
Commit
5bb5d81
·
verified ·
1 Parent(s): 6112711

Update main.py

Browse files
Files changed (1) hide show
  1. main.py +39 -94
main.py CHANGED
@@ -1,122 +1,67 @@
1
  from flask import Flask, request, jsonify, Response
2
  import random
3
  import string
4
- import os
5
  import threading
6
- import time
7
- from pathlib import Path
8
 
9
  app = Flask(__name__)
10
- app.config['UPLOAD_FOLDER'] = 'temp_uploads'
11
- Path(app.config['UPLOAD_FOLDER']).mkdir(exist_ok=True)
12
-
13
- # Конфигурация памяти
14
- MAX_MEMORY = 12 * 1024 * 1024 * 1024 # 12 GB
15
- CHUNK_SIZE = 100 * 1024 * 1024 # 4 MB
16
- MAX_FILE_SIZE = 20 * 1024 * 1024 * 1024 # 20 GB
17
 
18
  transfers = {}
19
- active_memory = 0
20
- lock = threading.Lock()
21
-
22
- class TransferManager:
23
- def __init__(self):
24
- self.transfers = {}
25
- self.file_locks = {}
26
-
27
- def create_transfer(self, filename, filesize):
28
- if filesize > MAX_FILE_SIZE:
29
- raise ValueError("File size exceeds maximum limit")
30
-
31
- transfer_id = ''.join(random.choices(string.ascii_letters + string.digits, k=4))
32
- file_path = os.path.join(app.config['UPLOAD_FOLDER'], transfer_id)
33
-
34
- with lock:
35
- self.transfers[transfer_id] = {
36
- 'filename': filename,
37
- 'filesize': filesize,
38
- 'received': 0,
39
- 'file_path': file_path,
40
- 'created_at': time.time(),
41
- 'status': 'uploading'
42
- }
43
- self.file_locks[transfer_id] = threading.Lock()
44
-
45
- return transfer_id
46
 
47
- manager = TransferManager()
 
 
 
 
48
 
49
- @app.route('/init_upload', methods=['POST'])
50
- def init_upload():
51
  filename = request.json.get('filename')
52
- filesize = request.json.get('filesize')
53
 
54
- try:
55
- transfer_id = manager.create_transfer(filename, filesize)
56
- return jsonify({'transfer_id': transfer_id})
57
- except Exception as e:
58
- return jsonify({'error': str(e)}), 400
 
 
 
 
59
 
60
  @app.route('/upload/<transfer_id>', methods=['POST'])
61
- def upload_chunk(transfer_id):
62
- if transfer_id not in manager.transfers:
63
  return jsonify({'error': 'Invalid transfer ID'}), 404
64
 
65
- chunk = request.data
66
- chunk_size = len(chunk)
 
 
67
 
68
- with lock:
69
- transfer = manager.transfers[transfer_id]
70
- if transfer['status'] != 'uploading':
71
- return jsonify({'error': 'Transfer completed'}), 400
72
-
73
- try:
74
- with manager.file_locks[transfer_id], open(transfer['file_path'], 'ab') as f:
75
- f.write(chunk)
76
- transfer['received'] += chunk_size
77
-
78
- if transfer['received'] >= transfer['filesize']:
79
- transfer['status'] = 'ready'
80
-
81
- return jsonify({
82
- 'received': transfer['received'],
83
- 'status': transfer['status']
84
- })
85
- except Exception as e:
86
- return jsonify({'error': str(e)}), 500
87
 
88
  @app.route('/download/<transfer_id>', methods=['GET'])
89
  def download_file(transfer_id):
90
- def generate():
91
- file_path = manager.transfers.get(transfer_id, {}).get('file_path')
92
- if not file_path or not os.path.exists(file_path):
93
- yield b'File not found'
94
- return
95
 
96
- with open(file_path, 'rb') as f:
97
- while True:
98
- chunk = f.read(CHUNK_SIZE)
99
- if not chunk:
 
 
 
100
  break
101
- yield chunk
102
-
103
- # Автоочистка через 1 час
104
- threading.Timer(3600, cleanup_transfer, args=[transfer_id]).start()
105
-
106
  return Response(
107
  generate(),
108
  mimetype='application/octet-stream',
109
- headers={'Content-Disposition': f'attachment; filename="{manager.transfers[transfer_id]["filename"]}"'}
110
  )
111
 
112
- def cleanup_transfer(transfer_id):
113
- with lock:
114
- if transfer_id in manager.transfers:
115
- try:
116
- os.remove(manager.transfers[transfer_id]['file_path'])
117
- except:
118
- pass
119
- del manager.transfers[transfer_id]
120
-
121
  if __name__ == '__main__':
122
- app.run(host='0.0.0.0', port=5000, threaded=True)
 
1
  from flask import Flask, request, jsonify, Response
2
  import random
3
  import string
4
+ from collections import deque
5
  import threading
 
 
6
 
7
  app = Flask(__name__)
 
 
 
 
 
 
 
8
 
9
  transfers = {}
10
+ transfer_data = {}
11
+ transfer_lock = threading.Lock()
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
12
 
13
+ def generate_short_id(length=8):
14
+ while True:
15
+ token = ''.join(random.choices(string.ascii_letters + string.digits, k=length))
16
+ if token not in transfers:
17
+ return token
18
 
19
+ @app.route('/create_transfer', methods=['POST'])
20
+ def create_transfer():
21
  filename = request.json.get('filename')
22
+ filesize = request.json.get('filesize', 0)
23
 
24
+ transfer_id = generate_short_id(8)
25
+ with transfer_lock:
26
+ transfers[transfer_id] = {
27
+ 'filename': filename,
28
+ 'filesize': filesize,
29
+ 'completed': False
30
+ }
31
+ transfer_data[transfer_id] = deque()
32
+ return jsonify({'transfer_id': transfer_id})
33
 
34
  @app.route('/upload/<transfer_id>', methods=['POST'])
35
+ def upload_file(transfer_id):
36
+ if transfer_id not in transfers:
37
  return jsonify({'error': 'Invalid transfer ID'}), 404
38
 
39
+ data = request.data
40
+ with transfer_lock:
41
+ transfer_data[transfer_id].append(data)
42
+ transfers[transfer_id]['completed'] = request.headers.get('X-Transfer-Complete') == 'true'
43
 
44
+ return jsonify({'status': 'chunk uploaded'})
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
45
 
46
  @app.route('/download/<transfer_id>', methods=['GET'])
47
  def download_file(transfer_id):
48
+ if transfer_id not in transfers:
49
+ return jsonify({'error': 'Invalid transfer ID'}), 404
 
 
 
50
 
51
+ def generate():
52
+ while True:
53
+ with transfer_lock:
54
+ if transfer_data[transfer_id]:
55
+ chunk = transfer_data[transfer_id].popleft()
56
+ yield chunk
57
+ elif transfers[transfer_id]['completed']:
58
  break
59
+
 
 
 
 
60
  return Response(
61
  generate(),
62
  mimetype='application/octet-stream',
63
+ headers={'Content-Disposition': f'attachment; filename="{transfers[transfer_id]["filename"]}"'}
64
  )
65
 
 
 
 
 
 
 
 
 
 
66
  if __name__ == '__main__':
67
+ app.run(host='0.0.0.0', port=5000)