[Android] 안드로이드 파이어베이스 사용자마다 데이터 다르게 관리하기
모바일앱을 개발하다가 파이어베이스로 사용자 로그인 및 데이터를 관리하고 있었는데 파이어베이스에 사진을 올리는 것은 되지만 어플 사용자마다 다르게 데이터를 관리하는 것이 문제였다.
그러다가 문득 생각이 든게 파이어베이스 스토리지에 사진을 저장할 때 폴더명을 사용자의 uid로 하고 데이터를 가져오는 것도 사용자의 uid 폴더에서만 가져오게 하면 되지 않을까? 라는 생각에 실행해보았다.
먼저 파이어베이스 스토리지에 이미지를 보내는 코드이다.
try {
progressDialog = new ProgressDialog(this);
progressDialog.setTitle("파일 업로드중....");
progressDialog.show();
StorageReference storageRef = storage.getReference();
FirebaseUser user = FirebaseAuth.getInstance().getCurrentUser();
String the_uid = user.getUid();
Uri file = Uri.fromFile(new File(uri));
final StorageReference riversRef = storageRef.child(the_uid+"/"+file.getLastPathSegment());
UploadTask uploadTask = riversRef.putFile(file);
Task<Uri> urlTask = uploadTask.continueWithTask(new Continuation<UploadTask.TaskSnapshot, Task<Uri>>() {
@Override
public Task<Uri> then(@NonNull Task<UploadTask.TaskSnapshot> task) throws Exception {
if (!task.isSuccessful()) {
throw task.getException();
}
// Continue with the task to get the download URL
return riversRef.getDownloadUrl();
}
}).addOnCompleteListener(new OnCompleteListener<Uri>() {
@Override
public void onComplete(@NonNull Task<Uri> task) {
if (task.isSuccessful())
{
Toast.makeText(UploadActivity.this, "업로드 성공", Toast.LENGTH_SHORT).show();
//파이어베이스에 데이터베이스 업로드
@SuppressWarnings("VisibleForTests")
Uri downloadUrl = task.getResult();
ImageDTO imageDTO = new ImageDTO();
imageDTO.setImageUrl(downloadUrl.toString());
imageDTO.setTitle(file.getLastPathSegment());
imageDTO.setDescription(etDesc.getText().toString());
imageDTO.setUid(mAuth.getCurrentUser().getUid());
// imageDTO.setUserid(mAuth.getCurrentUser().getEmail());
//image 라는 테이블에 json 형태로 담긴다.
//database.getReference().child("Profile").setValue(imageDTO);
// .push() : 데이터가 쌓인다.
database.getReference().child(the_uid).push().setValue(imageDTO);
finish();
} else {
// Handle failures
// ...
}
}
});
}catch (NullPointerException e)
{
Toast.makeText(UploadActivity.this, "이미지 선택 안함", Toast.LENGTH_SHORT).show();
}
}
평범하게 파이어베이스 스토리지 데이터를 가져오는 코드에다가
FirebaseUser user = FirebaseAuth.getInstance().getCurrentUser();
String the_uid = user.getUid();
를 추가해줘서 사용자의 uid를 얻어온다음
final StorageReference riversRef = storageRef.child(the_uid+"/"+file.getLastPathSegment());
위 코드처럼 the_uid를 이용해 사진을 저장할 폴더의 이름을 사용자의 uid로 하고 그 폴더 안에 들어갈 사진이름은 그대로 넣어주었다.
그 다음에 파이어베이스 스토리지에 저장한 사진을 불러오는 코드를 보겠다.
FirebaseUser user = FirebaseAuth.getInstance().getCurrentUser();
String the_uid = user.getUid();
final UploadedImageAdapter uploadedImageAdapter = new UploadedImageAdapter(imageDTOList, uidList);
recyclerView.setAdapter(uploadedImageAdapter);//데이터 넣기
//옵저버 패턴 --> 변화가 있으면 클라이언트에 알려준다.
firebaseDatabase.getReference().child(the_uid).addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot dataSnapshot) { //변화된 값이 DataSnapshot 으로 넘어온다.
//데이터가 쌓이기 때문에 clear()
imageDTOList.clear();
uidList.clear();
for(DataSnapshot ds : dataSnapshot.getChildren()) //여러 값을 불러와 하나씩
{
ImageDTO imageDTO = ds.getValue(ImageDTO.class);
String uidKey = ds.getKey();
imageDTOList.add(imageDTO);
uidList.add(uidKey);
}
uploadedImageAdapter.notifyDataSetChanged();
}
처음 코드랑 같이 uid를 가져오는 코드를 먼저 작성해준 뒤
firebaseDatabase.getReference().child(the_uid).addValueEventListener(new ValueEventListener(
위 코드 부분에 child에 데이터를 가져오는 이름 부분만 the_uid로 바꿔주면 자신의 uid에 맞게 데이터를 불러와서 보여진다.
이처럼 파이어베이스의 uid를 통해서 사용자마다 각자 고유의 데이터를 저장하고 불러오는 것이 가능하게 구현하였다.
위 그림처럼 로그인한 사용자마다 다르게 정상적으로 폴더에 저장되는 것을 볼 수 있다.