هل هناك خدعة خاصة لتنزيل ملف مضغوط وكتابةه إلى القرص مع بيثون؟

StackOverflow https://stackoverflow.com/questions/576238

  •  05-09-2019
  •  | 
  •  

سؤال

أنا ftping ملف zip من موقع FTP بعيد باستخدام Python's FTPLIB. ثم أحاول كتابة ذلك على القرص. يعمل ملف الكتابة، ولكن معظم المحاولات لفتح الرمز البريدي باستخدام WinZip أو WinRAR فشل؛ كلا التطبيقين المطالبة بالملف تالف. بشكل غريب، عند النقر بزر الماوس الأيمن وحاول استخراج الملف باستخدام WinRAR، الملف إرادة مقتطف.

إذن أن تكون واضحا، سوف يعمل الملف الكتابة، ولكن لن افتح داخل التطبيقات الرمز البريدي الشعبية، ولكن إرادة إلغاء ضغط باستخدام تلك التطبيقات نفسها. لاحظ أن وحدة Python ZipFile أبدا فشل في استخراج الكود البريدية.

فيما يلي الكود الذي أستخدمه للحصول على ملف ZIP من موقع FTP (يرجى تجاهل الجدولة السيئة، هذه ليست المشكلة).

filedata = None
def appender(chunk):
    global filedata
    filedata += chunk


def getfile(filename):
  try:
      ftp = None

      try:
          ftp = FTP(address)
          ftp.login('user', 'password')

      except Exception, e:
          print e

      command = 'RETR ' + filename

      idx = filename.rfind('/')
      path = filename[0:idx]
      ftp.cwd(path)
      fileonly = filename[idx+1:len(filename)]

      ftp.retrbinary('RETR ' + filename, appender)

      global filedata
      data = filedata

      ftp.close()

      filedata = ''
      return data

  except Exception, e:
      print e

data = getfile('/archives/myfile.zip')    
file = open(pathtoNTFileShare, 'wb')
file.write(data)
file.close()
هل كانت مفيدة؟

المحلول

تمرير الملف. كتابة مباشرة داخل الوظيفة المكشوفة بدلا من تمرير Aflender. سيعمل هذا وسيعمل أيضا على استخدام الكثير من ذاكرة الوصول العشوائي عند تنزيل ملف كبير.

إذا كنت ترغب في تخزين البيانات داخل متغير، فيمكنك أيضا الحصول على متغير باسم:

blocks = []

ثم تمر إلى مكربة بدلا من avender:

blocks.append

وظيفة averfender الحالية الخاصة بك خطأ. + = لن يعمل بشكل صحيح عندما تكون هناك بيانات ثنائية لأنها ستحاول القيام بسلسلة إلحاقا وتتوقف عند الأول الذي يراه.

كما ذكرنا lee b يمكنك أيضا استخدام Urllib2 أو حليقة. لكن الرمز الحالي هو الصحيح تقريبا إذا قمت بإجراء التعديلات الصغيرة المذكورة أعلاه.

نصائح أخرى

لم أستخدم تلك المكتبة أبدا، لكن Urllib2 يعمل بشكل جيد، وهو أكثر صرامة. حليقة أفضل.

النظر إلى التعليمات البرمجية الخاصة بك، أستطيع أن أرى بعض الأشياء خطأ. استثناءك يصطاد فقط يطبع الاستثناء، ثم يستمر. بالنسبة للأخطاء القاتلة مثل عدم الحصول على اتصال FTP، يحتاجون إلى طباعة الرسالة ثم الخروج. أيضا، يبدأ Filedata الخاص بك حتى لا شيء، ثم يستخدم Applender + = للإضافة إلى ذلك، لذلك أنت تحاول إلحاق سلسلة + بلا شيء، مما يعطي TypeEror عندما أحاول ذلك هنا. أنا مندهشا من العمل على الإطلاق؛ كنت قد خمنت أن Aflender سيقوم بإلقاء استثناء، وبالتالي فإن نسخة FTP ستجهز.

أثناء إعادة القراءة، لاحظت فقط إجابة أخرى حول استخدام + = على البيانات الثنائية. قد يكون ذلك؛ يحاول Python أن تكون ذكية في بعض الأحيان، ويمكن أن تكون "المساعدة" عند الانضمام إلى سلاسل بمسافة بيضاء أو غير نارية، أو شيء من هذا القبيل. أفضل رهان لديك للحصول على الملف مفتوح (دعونا نسميها outfile)، واستخدام applender الخاص بك إلى outfile.write (قطعة).

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top