سؤال

أحاول حذف ملف مؤقت بعد مشاركته عبر ميزة Android's Neain.Action_Send. في الوقت الحالي ، أبدأ النشاط لتحقيق نتيجة وفي onActivityResult ، أقوم بحذف الملف. لسوء الحظ ، لا يعمل هذا إلا إذا قمت بتصحيحها بنقطة توقف ، لكن عندما أتركها تعمل بحرية وأقول ، أرسل بريدًا إلكترونيًا إلى الملف ، ليس للبريد الإلكتروني أي مرفق.

أعتقد أن ما يحدث هو أن نشاطي هو حذف الملف قبل إرساله بالبريد الإلكتروني. ما لا أحصل عليه هو لماذا ، لا ينبغي استدعاء onactivityResult فقط بعد الانتهاء من النشاط الآخر؟

لقد حاولت أيضًا حذف الملف في Onresume ، لكن لا حظ.

هل هناك طريقة أفضل للقيام بذلك؟

هل كانت مفيدة؟

المحلول 4

لقد تمكنت من العمل مع:

File tbd = new File(sharePath);
tbd.deleteOnExit();

يبدو أن هذا يحذف الملف عند إغلاق النشاط.

نصائح أخرى

لقد لاحظت نفس السلوك مع نهج مماثل. أثناء مشاهدة Logcat للأخطاء ، رأيت Gmail يشكو من أنه لم يتمكن من العثور على المرفق. لذا ، نعم ، يبدو أن النية تعود قبل أن يقرأ Gmail بالفعل ملف المرفق.

لم أتجول إلى حل حتى الآن ، لكن من المحتمل أن يكون الأمر مثل:

  • انقل الملف إلى بعض الدليل حتى أعلم أنه قررت إرسالها
  • أرسله كمرفق عبر Action_Send
  • في onResume التالي لنشاط شاشة البدء ، قم بحذف الملفات في دليل "إرسال" أقدم من بعض الإطار الزمني الذي حدث طويلًا بما يكفي حتى حدث إرساله فعليًا

قد يكون اختيار إطار زمني مناسب أمرًا صعبًا لأنه من المحتمل ألا يكون Gmail (أو غيرهم من مزودي Action_Send) قراءة الملف فعليًا حتى يكون لديه اتصال بالشبكة. أفكر في أن 24 ساعة يجب أن تكون معقولة وفي حالتي ، أتعامل مع سجلات التشخيص ، لذا لا يوجد ضرر حقيقي في حذف واحدة في وقت مبكر جدًا إذا كان المستخدم خارج الشبكة لفترة طويلة من الزمن.

إذا كان محتوى ملفك نصًا ، فقد لا يكون منهجًا أبسط فاحشًا هو قراءة محتويات الملف واستخدام intent.putextra (Android.content.intent.extra_text ، yourtext) لتضمينه في جسم الرسالة .

ما فعلته هو ما يلي.

لقد استخدمت:

myfile.deleteOnExit();

ومع ذلك ، كما ذكر الدكتور في التعليق أدناه اجابة صحيحة, ، هذا لا يضمن حذف الملف. لهذا السبب أقوم بحذف الملف أيضًا بعد إرجاع النشاط المشترك. أقوم بحذف الملف إذا كان الملف موجودًا. لأن التطبيق تحطمت في بعض الأحيان ، أضعه في الداخل try{} ويعمل.

لا أعرف لماذا لا يعمل من أجلك ، ولكن بالنسبة لي ، فهو يعمل على الأقل مع مرفق Gmail ، Sextsecure ، Hangouts.

في الفصل الدراسي:

static File file;

في الطريقة التي يطالب القصد:

        Intent share = new Intent(Intent.ACTION_SEND);
        share.setType("image/png");

        // Compress the bitmap to PNG
        ByteArrayOutputStream bytes = new ByteArrayOutputStream();
        bitmap.compress(Bitmap.CompressFormat.PNG, 100, bytes);

        // Temporarily store the image to Flash
        File sdCard = Environment.getExternalStorageDirectory();
        File dir = new File (sdCard.getAbsolutePath() + "/FolderName");
        dir.mkdirs();

        // This file is static.
        file = new File(dir, "FileName.png");

        try {
            file.createNewFile();
            FileOutputStream fo = new FileOutputStream(file);
            fo.write(bytes.toByteArray());
            fo.flush();
            fo.close();
        } catch (IOException e) {
            e.printStackTrace();
        }

        // Share compressed image
        share.putExtra(Intent.EXTRA_STREAM, Uri.parse("file:///"+file.getPath()));

        /** START ACTIVITY **/
        startActivityForResult(Intent.createChooser(share,"Share Image"),1);

        // Delete Temporary file
        file.deleteOnExit();     // sometimes works

بطريقة إضافية:

protected void onActivityResult(int requestCode, int resultCode, Intent data) {   
        // Because app crashes sometimes without the try->catch 
        try {
            // if file exists in memory
            if (file.exists()) {
                file.delete();
            }
        } catch (Exception e) {
            Log.d(LOG,"Some error happened?");
        }

    }

هناك إجابة محتملة أخرى تتمثل في إنشاء مؤشر ترابط جديد عند استئناف التطبيق الخاص بك ، وتحديد الوقت الحالي على الفور ، ونوم الخيط لفترة طويلة تشعر أنه من المعقول إرسال الملف ، وعندما يستأنف مؤشر الترابط ، فقط حذف الملفات التي تم إنشاؤها قبل الوقت الذي تم وضع علامة عليه مسبقًا. سيمنحك هذا القدرة على حذف ما كان في موقع التخزين فقط في وقت استئناف تطبيقك ، ولكن أيضًا يمنح الوقت لـ Gmail لإخراج البريد الإلكتروني. قصاصة الكود: (أنا أستخدم C#/Xamarin ، ولكن يجب أن تحصل على الفكرة)

public static void ClearTempFiles()
{
    Task.Run(() =>
    {

        try
        {
            DateTime threadStartTime = DateTime.UtcNow;
            await Task.Delay(TimeSpan.FromMinutes(DeletionDelayMinutes));
            DirectoryInfo tempFileDir = new DirectoryInfo(TempFilePath);
            FileInfo[] tempFiles = tempFileDir.GetFiles();
            foreach (FileInfo tempFile in tempFiles)
            {
                if (tempFile.CreationTimeUtc < threadStartTime)
                {
                    File.Delete(tempFile.FullName);
                }
            }
        }
        catch { }
    });
}

martijn pieters هذه الإجابة هي حل مختلف يتولى أسئلة متعددة. إذا كان هناك أي شيء ، فإن الأسئلة الأخرى التي نشرتها ، يجب تمييزها كتكررات لأنها نفس السؤال. لقد نشرت على كل واحد منهم لضمان أن كل من لديه هذه المشكلة ، يمكنه العثور على الحل.

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