استفاده از Storage در Firebase
در ادامه سری آموزش های Firebase, به مبحث Storage در Firebase میپردازیم.
فضای ذخیره سازی یکی از مهم ترین قسمت های یک برنامه client-server میباشد. در آموزش های قبلی client-server به چگونگی ارسال و دریافت فایل ها اشاره کردیم. اما در Firebase استفاده از Storage بسیار ساده تر است و با داشتن یک فضای ذخیره سازی در Firebase میتوانید تصاویر و ویدیو های کاربران خود را ذخیره کنید و در صورت پاک شدن برنامه از روی گوشی های آنها, نگران از دست رفتن فایل های آنها نباشید.
در ابتدا باید Dependency مربوط به Storage را build.gradle اضافه کنیم :
compile 'com.google.firebase:firebase-storage:10.0.1'
و برای شروع یک Instance از FirebaseStorage میسازیم
private void storage() { FirebaseStorage storage = FirebaseStorage.getInstance(); }
اطلاعات شما در یک Firebase Storage bucket ذخیره خواهد شد. فایل ها در Bucket به صورت hierarchical ذخیره میشوند. مثال این نوع ذخیره سازی را در سیستم های کامپیوتری میتوانید مشاهده کنید که شما یک پوشه دارید و در داخل آن پوشه چند پوشه دیگر و به همین روال فایل های خود را دسته بندی میکنید. Firebase نیز از همین روش برای ذخیره سازی فایل های شما استفاده میکند.
برای استفاده از Storage نیاز است تا یک Reference بسازید. با استفاده از همین Reference میتوانید فایل های خود را آپلود و دانلود کنید. برای ساختن Reference به یک URL نیاز دارید و این URL مختص به پروژه شما می باشد. اگر به قسمت Storage پنل Firebase بروید میتوانید این URL را مشاهده کنید.
برای راحتی کار تمام Key ها و URL های مرتبط به Firebase را در یک فایل XML در Resource قرار میدهیم
<?xml version="1.0" encoding="utf-8"?> <resources> <string name="storage_url">gc://BUCKET_URL</string> </resources>
و آنرا به پروژه اضافه میکنیم
@BindString(R.string.storage_url) String bucketURL; private void storage() { FirebaseStorage storage = FirebaseStorage.getInstance(); StorageReference storageReference = storage.getReferenceFromUrl(bucketURL); }
بر اساس ساختار فایلی که تعریف شد باید Reference ها را نیز همانگونه ساختار بندی کنیم
StorageReference root = storageReference.child("vhdrjb"); StorageReference profiles = root.child("profile"); StorageReference covers = root.child("covers"); StorageReference galleries = root.child("galleries"); StorageReference profilePic = profiles.child("profilePic"); StorageReference coverPic = covers.child("coverPic"); StorageReference galleryPic = galleries.child("galleryPic");
با توجه به این کد چنین ساختاری برای ما ایجاد شده است
همچنین میتوانید بین این Reference ها جابجایی داشته باشید. متد که برای اینکار وجود دارد getParent و getRoot می باشد و هرکدام نیز یک StorageReference بر میگرداند. دقت داشته باشید که اگر آیتمی وجود نداشته باشد مقدار StorageReference برابر null خواهد بود.
به سه روش میتوانید فایل خود را درون StorageReference قراردهید
- put byte : فایل مورد نظر را تبدیل به آرایه ای از بایت ها میکنیم و قرار میدهیم
- put stream : فایل مورد نظر را به stream تبدیل میکنیم و قرار میدهیم
- put file : فایل را مستفیما قرار میدهیم
در اینجا ما تصاویر را از Image View ها به Firebase ارسال میکنیم
private void storage() { ... upload(profilePic.putBytes(getByte(profile))); upload(coverPic.putBytes(getByte(cover))); upload(galleryPic.putBytes(getByte(gallery))); .... }
در اینجا ما به دو متد نیاز داریم :
- upload : در این متد وضعیت آپلود را کنترل میکنیم
} private void upload(UploadTask uploadTask) { uploadTask.addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>() { @Override public void onSuccess(UploadTask.TaskSnapshot taskSnapshot) { Log.d("Zero To Hero Upload Log", "Url =" + taskSnapshot.getDownloadUrl()); } }); }
- getByte : در این متد تصویر Image View را به آرایه ای ازبایت ها تبدیل میکنیم
private byte[] getByte(ImageView imageView) { imageView.setDrawingCacheEnabled(true); imageView.buildDrawingCache(); Bitmap bitmap = ((BitmapDrawable) imageView.getDrawable()).getBitmap(); ByteArrayOutputStream baos = new ByteArrayOutputStream(); bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos); return baos.toByteArray(); }
همچنین میتوانید فایل آپلود شده را به همان روشی که آپلود کرده ایم, دانلود کرد.
برای مثال برای دریافت تصویر profilePic آپلود شده StorageReference آنرا به متدی به نام download میدهیم
File profileDownload = download(profilePic);
و متد download را اینگونه مینویسم
private File download(StorageReference storageReference) { try { File file = File.createTempFile("download", "jpg"); storageReference.getFile(file).addOnSuccessListener(new OnSuccessListener<FileDownloadTask.TaskSnapshot>() { @Override public void onSuccess(FileDownloadTask.TaskSnapshot taskSnapshot) { } }); return file; } catch (IOException e) { e.printStackTrace(); } return null; }
همچنین برای حذف فایل میتوانید چننی عمل کنید
private boolean delete(StorageReference storageReference) { status = false; storageReference.delete().addOnSuccessListener(new OnSuccessListener<Void>() { @Override public void onSuccess(Void aVoid) { status = true; } }); return status; }
و برای استفاده از آن StorageReference مورد نظر را به آن ارجاع دهید
delete(profiles);
در مقاله بعدی به مبحث Database میپردازیم.
سری مقالات Firebase همچنان ادامه دارد
با ما همراه باشید
مطالب زیر را حتما مطالعه کنید
آموزش Gradle – اهمیت Project Automation
درک مفهوم کدنویسی تمیز در اندروید
5 هک ساده برای کاهش سایز فایل APK
آشنایی با RecyclerView در اندروید
Open/Closed Principle در قوانین Solid
توابع در زبان برنامه نویسی Kotlin
4 Comments
Join the discussion and tell us your opinion.
دیدگاهتان را بنویسید لغو پاسخ
برای نوشتن دیدگاه باید وارد بشوید.
سلام ممنون از اموزش خوبتون
من از vpn برای استفاده از Firebase Database استفاده میکنم و جواب هم میگیرم اما هر چی تلاش میکنم نمیتونم از قابلیت Storage توی برنامم حتی با vpn نتیجه بگیرم .
ایا این امکان هست که Storage حتی با vpn هم در ایران قابل اجرا نیست؟
اگر نه . میشه اسم برنامه ی vpn ی که استفاده میکنید رو بدونم؟
ممنون میشم اگه کمکم کنید
سلام دوست عزیز. از همون VPN که برای Database استفاده میکنید میتونید برای Storage هم استفاده کنید. سرویس Storage برای در حالت پیش فرض فقط برای کاربرانی هست که Authorize شدن. یعنی برای استفاده از Storage باید ابتدا کاربر از سرویس Authenticate احراز هویت بشه و بعدش بتونه از Storage استفاده کنه. در قسمت Rule که برای Storage هست این تنظیمات قرار بدین احتمالا درست میشه. اگر بازم درست نشد در انجمن مطرح کنید تا قدم به قدم بررسی کنیم.
تنظیمات :
match /{allPaths=**} {
allow read, write: if request.auth != null;
}
به این حالت تغییر بدین :
match /{allPaths=**} {
allow read, write: if true;
}
سلام من از این قابلیت استفاده کرده ام اما متاسفانه در ایران برای کاربر های ایرانی فیلتر هست
می خواستم بدونم آیا راهی هست که بشود استفاده کرد یا سیستم دیگر مثل فایربیس هست (البته رایگان)
و یا میشود داخل برنامه از proxy (فیلتر شکن)استفاده کرد زیاد سرج کردم اما چیزی پیدا نکردم
اگر میشه کمکم کنید ممنون . من خودم دوست دارم از proxy استفاده کنم اما نمی دونم چه جوری
ممنون بابت سایت خوبتان
با سلام. ممنون از همراهیتون. بله متاسفانه این سرویس هم در دسته تحریم ها هست. اینکه از داخل برنامه بتونید vpn بسازید شک دارم بشه. ولی تنها روشی که خودمون هم برای تست ها ازش استفاده میکنیم vpn هایی هستن که روی خود گوشی اجرا میشن. عملا میشه گفت این سرویس فعلا تو ایران امکان پذیر نیست. مگه اینکه تک تک کاربر هاتون از vpn استفاده کنن که منطقی به نظر نمیاد. اگر روشی هم پیدا کردیم بشه تحریم های اینجوری از داخل خود برنامه رفع کرد حتما به مقاله تبدیلش میکنیم و در دسترس کاربرای سایت قرار میدیم.