728x90
✔︎ 이 포스팅은 3개의 글로 나누어져 있습니다. 또한 Mac 환경에서 Xcode 가 제공하는 iOS Simulator 로 빌드후 배포하는 것에 포커스가 맞추어져 있습니다. 참고하시어 시리즈 글을 읽으시면 건강에 좋습니다!

(1편) Flutter X Firebase, 환경 설정 하기 https://ondemand.tistory.com/266 
(2편, 이글) Flutter X Firebase, 패키지 임포트 및 UI 코드 만들기 https://ondemand.tistory.com/276
(3편) Flutter X Firebase, Firestore 객체로 CRUD 코드 만들기https://ondemand.tistory.com/277
 

먹고 살기 바쁘다 보니 첫 포스팅을 올리고 두달여만에 후속 포스팅을 올립니다. 그 사이에 생성해 둔 Firebase 의 Firestore 가 보안 정책 만료가 되었네요. 스스로 적어둔 지난번 포스팅을 다시 참고해 가면서 Firebase 에 Firestore NoSQL DB 를 사용 가능하도록 변경하고 글을 시작하도록 하겠습니다. 지난번 글은 아래의 링크입니다! (블로그가 역시 이렇게 좋습니다 ㅎㅎ)

 

Flutter X Firebase, 플러터에서 Firestore NoSQL DB 를 사용해보자 - iOS 와 VS Code 를 중심으로!

Flutter 를 이용하면서 Firebase 를 이용하는 방법을 살펴보겠습니다. 둘 다 구글에서 만든 것이라 그런지 연동하는 것이 어렵지 않습니다. 다만 손이 좀 가게되고 처음 다루는 경우에 조금 헤멜 수 �

ondemand.tistory.com


Firestore 정책 업데이트 하기 

Firebase 의 Firestore 는 최초 생성시 30일간 인증 없이 접근할 수 있는 Rule을 제공합니다. Firestore 콘솔의 <Rules> 탭에서 확인할 수 있습니다. 아마도 8월 14일에 DB 를 생성했고 그 시점으로부터 +1m 시점이 만료 시점으로 잡힌 것 같네요. 불필요한 비용 발생을 막기 위해서 들어가는 코드라고 생각하면 괜찮다는 생각이 듭니다.

물론 실제로 상용 서비스에서 Firestore 를 사용하는 경우에는 날짜 단위의 정책이 아니라 인증을 받은 경우 액세스가 가능하도록 변경하는 것이 좋을 것 같습니다. 자세한 내용은 Firestore 의 Rule 관련한 가이드를 살펴보시기 바랍니다! (이 글이 Firestore 를 위한 글은 아니라서라고 변명해 봅니다)

 

Firestore 사용을 위한 패키지 Import

지난 포스팅을 잘 따라오셨다면 Firestore 사용을 위한 준비가 끝났습니다. main.dart 파일을 열어서 추가한 Firestore 패키지를 코드에서 사용할 수 있도록 해보겠습니다. dart_todo 앱의 전체 코드 구조는 아래와 같습니다. 

2행에 추가된 것처럼 cloud_firestore.dart 를 import 해주셔야 합니다. 간단한 프로젝트이기 때문에 코드의 구조도 간단합니다. Firestore 를 다루는 코드는 당연히 가장 마지막에 있는 _TodoListPageState 클래스에 기술되어 있습니다. 8행에서 시작되는 Todo 클래스는 Firestore 에 저장할 객체를 들고 있을 코드상의 객체를 위한 클래스 입니다. Firestore 에 생성한 컬럼과 동일한 구조, 자료타입으로 만들어 두었습니다. 

StatelessWidget 으로 선언된 MyApp 은 기본 스캐폴딩을 통해 생성된 코드로 타이틀의 설정, 진입점을 TodoListPage 클래스로 지정해 준 정도의 변경사항만 가지고 있습니다. 코드는 아래와 같습니다

class Todo {
  bool isDone = false;
  String title;

  Todo(this.title, {this.isDone = false});
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: '할 일 관리',
      theme: ThemeData(
        primarySwatch: Colors.red,
      ),
      home: TodoListPage(),
    );
  }
}

 

_TodoListPageState 클래스 살펴보기

Todo 앱은 ListTile 위젯으로 할일 하나하나를 표현하고 ListTile 은 ListView 의 Child 가 됩니다. ListView 는 다시 Expanded 위젯으로 감싸여 화면에 보여지게 됩니다. Expanded 위젯은 다시 StreamBuilder 위젯으로 감싸 스트림으로 Firestore 의 변경사항과 UI 의 변경이 이루어지도록 코드를 만들었습니다 (네, 제가 한건 아니고 <오준석의 플러터 생존코딩> 책의 내용입니다!)

위젯을 빌드하는 코드를 살펴보겠습니다. 위젯을 또 위젯이 감싸고 또 감싸고... 하는 연속이다 보니 복잡해 보이네요. UI 코드 보다는 StreamBuilder 위젯의 내용을 중점적으로 보시면 됩니다. 

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('남은 할 일'),
      ),
      body: Padding(
        padding: const EdgeInsets.all(8.0),
        child: Column(
          children: <Widget>[
            Row(
              children: <Widget>[
                Expanded(
                  child: TextField(controller: _todoController),
                ),
                RaisedButton(
                  child: Text('추 가'),
                  onPressed: () => _addTodo(Todo(_todoController.text)),
                ),
              ],
            ),
            StreamBuilder<QuerySnapshot>(
              stream: Firestore.instance.collection('todo').snapshots(),
              builder: (context, snapshot) {
                if (!snapshot.hasData) {
                  return CircularProgressIndicator();
                }

                final documents = snapshot.data.documents;
                return Expanded(
                  child: ListView(
                    children: documents
                        .map((todo) => _buildItemWidget(todo))
                        .toList(),
                  ),
                );
              },
            ),
          ],
        ),
      ),
    );
  }

StreamBuilder 위젯의 가장 안쪽 코드에 _buildItemWidget 위젯은 할 일 하나하나를 ListTile 위젯으로 리턴하는게 목표인 위젯입니다. 유의할 점은 Firestore 에서 가져온 NoSQL Document 는 DocumentSnapshot 타입을 이용해야 한다는 점입니다. 코드 한번 보시고 가겠습니다. 

  Widget _buildItemWidget(DocumentSnapshot doc) {
    final todo = Todo(doc['title'], isDone: doc['isDone']);
    return ListTile(
      onTap: () => _toggleTodo(doc),
      title: Text(
        todo.title,
        style: todo.isDone
            ? TextStyle(
                decoration: TextDecoration.lineThrough,
                fontStyle: FontStyle.italic,
              )
            : null,
      ),
      trailing: IconButton(
          icon: Icon(Icons.delete_forever), onPressed: () => _deleteTodo(doc)),
    );
  }

네, 이렇게 UI 에서 Firestore 에 있는 정보를 연동할 준비가 되었습니다. 중간 중간에 보이는 _addTodo(doc), _deleteTodo(doc) 그리고 _toggleTodo(doc) 가 실제 비즈니스로직(?)이 들어간 메서드들이 되겠습니다. 절단 신공을 이용하여 이 세가지 메서드는 다음 포스팅에서 확인해 보도록 하겠습니다!

 

오준석의 플러터 생존 코딩

소문난 명강사 ‘오준석’이 안드로이드·iOS 앱 개발자에게 보내는 선물 같은 책앱을 만드는 ‘완벽한 준비’에 시간을 낭비하지 말자. 이 책은 기본을 빠르게 익히고 앱을 직접 만들며 필요한

www.yes24.com

본 포스팅은 제휴마케팅을 통해 소정의 수수료를 지급 받을 수 있습니다

728x90

+ Recent posts