Firestore 쿼리 하위 컬렉션
새로운 Firebase Firestore에서 서브 컬렉션을 조회할 수 있다고 읽었는데, 예를 볼 수 없습니다.예를 들어 다음과 같은 방법으로 Firestore를 설정합니다.
- 댄스[컬렉션]
- 댄스Name
- 노래 [수집]
- 노래Name
"songName== 'X' 위치에서 모든 춤 찾기"를 어떻게 쿼리할 수 있습니까?
2019-05-07 업데이트
오늘은 컬렉션 그룹 쿼리를 릴리스했으며, 이를 통해 하위 컬렉션 간에 쿼리를 수행할 수 있습니다.
예를 들어 웹 SDK에서는 다음과 같이 설명합니다.
db.collectionGroup('Songs')
.where('songName', '==', 'X')
.get()
이렇게 하면 컬렉션 경로의 마지막 부분이 '노래'인 모든 컬렉션의 문서와 일치합니다.
원래 질문은 songName== 'X'가 있는 춤을 찾는 것이었는데, 여전히 직접적으로 가능하지는 않지만 일치하는 각 노래에 대해 부모님을 로드할 수 있습니다.
원답
이것은 아직 존재하지 않는 기능입니다.이를 "수집 그룹 쿼리"라고 하며, 어떤 춤이 포함되어 있는지에 관계없이 모든 노래를 쿼리할 수 있습니다.이것은 우리가 지원하고자 하는 것이지만 언제가 될지에 대한 구체적인 일정은 가지고 있지 않습니다.
이 시점에서 대안적인 구조는 노래를 최상위 컬렉션으로 만들고 노래가 어떤 춤을 추는지를 노래 속성의 일부로 만드는 것입니다.
업데이트 지금 Firestore에서 어레이 포함 지원
이 문서들을 가지고 있는 것.
{danceName: 'Danca name 1', songName: ['Title1','Title2']}
{danceName: 'Danca name 2', songName: ['Title3']}
이런 식으로 하라.
collection("Dances")
.where("songName", "array-contains", "Title1")
.get()...
@Nelson.b.austin 소방서에는 아직 그런 것이 없기 때문에, 저는 당신에게 다음을 의미하는 평평한 구조를 제안합니다.
Dances = {
danceName: 'Dance name 1',
songName_Title1: true,
songName_Title2: true,
songName_Title3: false
}
이렇게 하면 다음과 같은 작업을 수행할 수 있습니다.
var songTitle = 'Title1';
var dances = db.collection("Dances");
var query = dances.where("songName_"+songTitle, "==", true);
이것이 도움이 되길 바랍니다.
2019년 업데이트
Firestore에서 Collection Group Query를 릴리스했습니다.위의 Gil의 답변 또는 공식 컬렉션 그룹 쿼리 문서 참조
이전 답변
Gil Gilbert가 언급한 바와 같이, 수집 그룹 쿼리가 현재 진행 중인 것으로 보입니다.한편, 루트 수준 컬렉션을 사용하고 문서 UID를 사용하여 이러한 컬렉션을 연결하는 것이 좋습니다.
Jeff Delaney는 Angular Firebase에서 Firebase(및 Angular)와 함께 작업하는 모든 사용자를 위한 놀라운 가이드와 리소스를 제공합니다.
Firestore NoSQL 관계형 데이터 모델링 - 여기서는 NoSQL 및 Firestore DB 구조화의 기본 사항을 설명합니다.
예를 들어 Firestore를 사용한 고급 데이터 모델링 - 이것들은 마음 한구석에 기억해야 할 고급 기술입니다.Firestore 기술을 한 단계 업그레이드하려는 사용자에게 유용한 자료
만약 여러분이 노래를 모음이 아닌 하나의 개체로 저장한다면 어떨까요?노래를 필드로 사용하여 각 댄스: Object(수집이 아님)를 입력합니다.
{
danceName: "My Dance",
songs: {
"aNameOfASong": true,
"aNameOfAnotherSong": true,
}
}
그러면 NameOf로 모든 춤을 쿼리할 수 있습니다.노래:
db.collection('Dances')
.where('songs.aNameOfASong', '==', true)
.get()
.then(function(querySnapshot) {
querySnapshot.forEach(function(doc) {
console.log(doc.id, " => ", doc.data());
});
})
.catch(function(error) {
console.log("Error getting documents: ", error);
});
2019년 7월 8일 새로운 업데이트:
db.collectionGroup('Songs')
.where('songName', isEqualTo:'X')
.get()
해결책을 찾았습니다.확인 부탁드립니다.
var museums = Firestore.instance.collectionGroup('Songs').where('songName', isEqualTo: "X");
museums.getDocuments().then((querySnapshot) {
setState(() {
songCounts= querySnapshot.documents.length.toString();
});
});
그런 다음 콘솔에서 클라우드 파이어스토어의 데이터, 규칙, 인덱스, 사용 탭을 볼 수 있습니다.firebase.google.com .마지막으로 인덱스 탭에서 인덱스를 설정해야 합니다.
여기에 컬렉션 ID와 일부 필드 값을 입력합니다.그런 다음 컬렉션 그룹 옵션을 선택합니다.그것을 즐기세요.감사해요.
언제든지 다음과 같이 검색할 수 있습니다:-
this.key$ = new BehaviorSubject(null);
return this.key$.switchMap(key =>
this.angFirestore
.collection("dances").doc("danceName").collections("songs", ref =>
ref
.where("songName", "==", X)
)
.snapshotChanges()
.map(actions => {
if (actions.toString()) {
return actions.map(a => {
const data = a.payload.doc.data() as Dance;
const id = a.payload.doc.id;
return { id, ...data };
});
} else {
return false;
}
})
);
쿼리 제한
Cloud Firestore는 다음 유형의 쿼리를 지원하지 않습니다.
서로 다른 필드에 범위 필터를 사용하여 쿼리합니다.
여러 컬렉션 또는 하위 컬렉션에 걸쳐 단일 쿼리를 수행합니다.각 쿼리는 단일 문서 모음에 대해 실행됩니다.데이터 구조가 쿼리에 미치는 영향에 대한 자세한 내용은 데이터 구조 선택을 참조하십시오.
논리적 OR 쿼리입니다.이 경우 각 OR 조건에 대해 별도의 쿼리를 생성하고 쿼리 결과를 앱에 병합해야 합니다.
!= 절을 사용하여 쿼리합니다.이 경우 쿼리를 보다 큰 쿼리와 보다 작은 쿼리로 분할해야 합니다.예를 들어 "age", "!=", "30")이 지원되지 않는 쿼리 절은 두 개의 쿼리를 결합하여 동일한 결과 집합을 얻을 수 있습니다. 하나는 "age", "<", "30")의 절이고 다른 하나는 "age", ">, 30)의 절입니다.
저는 여기서 관찰 가능한 것들과 Angular Fire 포장지와 함께 일하고 있습니다. 하지만 여기 제가 어떻게 그것을 할 수 있었는지에 대한 방법이 방법이 있습니다.
이건 좀 미친 짓입니다. 저는 아직도 관찰할 수 있는 것에 대해 배우고 있습니다. 그리고 제가 너무 많이 했을 수도 있습니다.하지만 그것은 멋진 운동이었습니다.
일부 설명(RxJS 전문가가 아님):
- songId$는 ID를 방출하는 관측 가능한 값입니다.
- dance$는 해당 ID를 읽은 다음 첫 번째 값만 가져오는 관찰 가능한 값입니다.
- 그런 다음 모든 노래의 모음 그룹을 쿼리하여 모든 인스턴스를 찾습니다.
- 인스턴스를 기반으로 부모 Dances로 이동하여 ID를 가져옵니다.
- 이제 모든 댄스 ID를 확보했으므로 데이터를 얻기 위해 쿼리를 수행해야 합니다.하지만 저는 그것이 잘 수행되기를 원했기 때문에 하나씩 쿼리하는 대신 10개의 버킷으로 배치했습니다(최대 각도가 필요함).
in
질의하다 - 우리는 N개의 버킷으로 끝나고 값을 얻기 위해 파이어스토어에서 N개의 쿼리를 수행해야 합니다.
- 일단 우리가 파이어스토어에서 쿼리를 수행하면 여전히 실제로 데이터를 구문 분석해야 합니다.
- 마지막으로 모든 쿼리 결과를 병합하여 모든 Dance가 포함된 단일 배열을 얻을 수 있습니다.
type Song = {id: string, name: string};
type Dance = {id: string, name: string, songs: Song[]};
const songId$: Observable<Song> = new Observable();
const dance$ = songId$.pipe(
take(1), // Only take 1 song name
switchMap( v =>
// Query across collectionGroup to get all instances.
this.db.collectionGroup('songs', ref =>
ref.where('id', '==', v.id)).get()
),
switchMap( v => {
// map the Song to the parent Dance, return the Dance ids
const obs: string[] = [];
v.docs.forEach(docRef => {
// We invoke parent twice to go from doc->collection->doc
obs.push(docRef.ref.parent.parent.id);
});
// Because we return an array here this one emit becomes N
return obs;
}),
// Firebase IN support up to 10 values so we partition the data to query the Dances
bufferCount(10),
mergeMap( v => { // query every partition in parallel
return this.db.collection('dances', ref => {
return ref.where( firebase.firestore.FieldPath.documentId(), 'in', v);
}).get();
}),
switchMap( v => {
// Almost there now just need to extract the data from the QuerySnapshots
const obs: Dance[] = [];
v.docs.forEach(docRef => {
obs.push({
...docRef.data(),
id: docRef.id
} as Dance);
});
return of(obs);
}),
// And finally we reduce the docs fetched into a single array.
reduce((acc, value) => acc.concat(value), []),
);
const parentDances = await dance$.toPromise();
제 코드를 복사해서 붙여넣고 변수 이름을 당신 것으로 바꿨는데, 오류가 있는지는 모르겠지만 저는 잘 작동했습니다.오류가 발견되거나 모의 소방서에서 테스트할 수 있는 더 나은 방법을 제안할 수 있으면 알려주세요.
var songs = []
db.collection('Dances')
.where('songs.aNameOfASong', '==', true)
.get()
.then(function(querySnapshot) {
var songLength = querySnapshot.size
var i=0;
querySnapshot.forEach(function(doc) {
songs.push(doc.data())
i ++;
if(songLength===i){
console.log(songs
}
console.log(doc.id, " => ", doc.data());
});
})
.catch(function(error) {
console.log("Error getting documents: ", error);
});
플랫 데이터 구조를 사용하는 것이 더 나을 수 있습니다.
문서는 이 페이지에서 서로 다른 데이터 구조의 장단점을 지정합니다.
특히 하위 집합이 있는 구조물의 제한에 대해:
하위 컬렉션을 쉽게 삭제하거나 하위 컬렉션 간에 복합 쿼리를 수행할 수 없습니다.
플랫 데이터 구조의 장점으로 알려진 것과 대조적입니다.
루트 레벨 컬렉션은 각 컬렉션 내에서 강력한 쿼리 기능과 함께 최고의 유연성과 확장성을 제공합니다.
언급URL : https://stackoverflow.com/questions/46573014/firestore-query-subcollections
'programing' 카테고리의 다른 글
메시지가 수신되었을 때 Android의 Firebase Messaging이 갑자기 중단되기 시작했습니다. (0) | 2023.07.04 |
---|---|
URL 쿼리에 대한 이름 값 모음? (0) | 2023.07.04 |
데이터 프레임을 s3 Python에 직접 csv에 저장 (0) | 2023.07.04 |
Git 별칭 - 여러 명령 및 매개 변수 (0) | 2023.07.04 |
SQL 서버의 포트 번호 식별 방법 (0) | 2023.07.04 |