인프런 영문 브랜드 로고
인프런 영문 브랜드 로고

인프런 커뮤니티 질문&답변

문신호님의 프로필 이미지
문신호

작성한 질문수

남박사의 파이썬으로 실전 웹사이트 만들기

회원가입 만들기 오류 문의 (AttributeError: 'Cursor' object has no attribute 'count') 오류

해결된 질문

작성

·

1.2K

2

안녕하세요

 

몇일째 오류랑 씨름하다가 여기까지 왔는데.. 도저희 해결이 안나서 문의 남깁니다.

 구글링이나.. 다른분들 오류 해결하시는거 찾아보면서 해도.. 계속오류 나면서 하니까 진도가 너무 늦네요..ㅠ

 

파이썬으로 실전 웹사이트 만들기 - 회원가입 페이지 만들기 중입니다.

-오류내용-

-코드-

(run.py)

from flask import Flask
from flask import request
from flask import render_template
from flask_pymongo import PyMongo
from bson.objectid import ObjectId
from flask import abort
from flask import redirect
from flask import url_for
from flask import flash
import math

import time
from datetime import datetime


app = Flask(__name__)
app.config["MONGO_URI"] = "mongodb://localhost:27017/myweb"
app.config["SECRET_KEY"] = "abcd"
mongo = PyMongo(app)


@app.template_filter('formatdatetime')
def format_datetime(value):
    if value is None:
        return ""

    now_timestamp = time.time()
    offset = datetime.fromtimestamp(
        now_timestamp) - datetime.utcfromtimestamp(now_timestamp)
    value = datetime.fromtimestamp((int(value) / 1000)) + offset
    return value.strftime('%Y-%m-%d %H:%M:%S')


@app.route("/list")
def lists():
    # 페이지 값 (값이 없는 경우 기본값는 1)
    page = request.args.get("page", 1, type=int)
    # 한페이지당 몇개의 게시물을 출력할지
    limit = request.args.get("limit", 5, type=int)

    search = request.args.get("search", -1, type=int)
    keyword = request.args.get("keyword", type=str)

    # 최종적으로 완성된 쿼리를 만들 변수
    query = {}
    # 검색어 상태를 추가할 리스트 변수
    search_list = []

    if search == 0:
        search_list.append({"title": {"$regex": keyword}})
    elif search == 1:
        search_list.append({"contents": {"$regex": keyword}})
    elif search == 2:
        search_list.append({"title": {"$regex": keyword}})
        search_list.append({"contents": {"$regex": keyword}})
    elif search == 3:
        search_list.append({"name": {"$regex": keyword}})

    # 검색 대상이 한개라도 존재할 경우 query 변수에 $or 리스트를 쿼리 합니다.
    if len(search_list) > 0:
        query = {"$or": search_list}

    print(query)

    board = mongo.db.board
    datas = board.find({}).skip((page - 1) * limit).limit(limit)

    # 게시물의 총 갯수
    tot_count = board.count_documents({})
    # 마지막 페이지의 수를 구한다.
    last_page_num = math.ceil(tot_count / limit)
    # 페이지 블럭을 5개씩 표기
    block_size = 5
    # 현재 블럭의 위치
    block_num = int((page - 1) / block_size)
    # 블럭의 시작 위치
    block_start = int((block_size * block_num) + 1)
    # 블럭의 끝 위치
    block_last = math.ceil(block_start + (block_size - 1))

    return render_template("list.html", datas=list(datas), limit=limit, page=page, block_start=block_start, block_last=block_last, last_page_num=last_page_num, search=search, keyword=keyword)


@ app.route("/view/<idx>")
def board_view(idx):
    # idx = request.args.get("idx")
    if idx is not None:
        page = request.args.get("page")
        search = request.args.get("search")
        keyword = request.args.get("keyword")

        board = mongo.db.board
        data = board.find_one({"_id": ObjectId(idx)})

        if data is not None:
            result = {
                "id": data.get("_id"),
                "name": data.get("name"),
                "title": data.get("title"),
                "contents": data.get("contents"),
                "pubdate": data.get("pubdate"),
                "view": data.get("view")
            }

            return render_template("view.html", result=result, page=page, search=search, keyword=keyword)
    return abort(404)


@ app.route("/write", methods=["GET", "POST"])
def board_write():
    if request.method == "POST":
        name = request.form.get("name")
        title = request.form.get("title")
        contents = request.form.get("contents")
        print(name, title, contents)

        current_utc_time = round(datetime.utcnow().timestamp() * 1000)
        board = mongo.db.board
        post = {
            "name": name,
            "title": title,
            "contents": contents,
            "pubdate": current_utc_time,
            "view": 0,
        }

        x = board.insert_one(post)
        print(x.inserted_id)
        return redirect(url_for("board_view", idx=x.inserted_id))
    else:
        return render_template("write.html")


@app.route("/join", methods=["GET", "POST"])
def member_join():

    if request.method == "POST":
        name = request.form.get("name", type=str)
        email = request.form.get("email", type=str)
        pass1 = request.form.get("pass", type=str)
        pass2 = request.form.get("pass2", type=str)

        if name == "" or email == "" or pass1 == "" or pass2 == "":
            flash("입력되지 않은 값이 있습니다.")
            return render_template("join.html")

        if pass1 != pass2:
            flash("비밀번호가 일치하지 않습니다.")
            return render_template("join.html")

        members = mongo.db.members
        cnt = members.find({"email": email}).count()

        if cnt > 0:
            flash("중복된 이메일 주소입니다.")
            return render_template("join.html")

        current_utc_time = round(datetime.utcnow().timestamp(*1000))

        post = {
            "name": name,
            "email": email,
            "pass": pass1,
            "joindate": current_utc_time,
            "logintime": " ",
            "logincount": 0
        }
        members.insert_one(post)

        return ""
    else:
        return render_template("join.html")


if __name__ == "__main__":
    app.run(host="0.0.0.0", debug=True, port=9000)

 

(join.html)

{% with messages = get_flashed_messages() %}
{% if messages %}
<script>
    alert('{{messages[-1]}}');
</script>
{% endif %}
{% endwith %}

<table>
    <form name="form" action="/join" method="POST">
        <thead>
            <caption>회원가입</caption>
        </thead>
        <tbody>
            <tr>
                <td>이름</td>
                <td><input type="text" name="name"></td>
            </tr>
            <tr>
                <td>이메일</td>
                <td><input type="text" nmae="email"></td>
            </tr>
            <tr>
                <td>비밀번호</td>
                <td><input type="password" name="pass"></td>
            </tr>
            <tr>
                <td>비밀번호 확인</td>
                <td><input type="password" name="pass2"></td>
            </tr>
            <tr>
                <td colspan="2"><input type="submit" value="가입하기"></td>
            </tr>
        </tbody>
    </form>
</table>
 

답변 1

0

남박사님의 프로필 이미지
남박사
지식공유자

해결 안되시는건 항상 질문 답변 게시판을 활용해주시면 됩니다~.

 

말씀하신 count() 함수는 몽고DB 3.7부터 deprecated 되었습니다. 따라서,

 

# 3.6
cnt = members.find({"email": email}).count()

# 3.7 >=
cnt = members.count_documents({"email": email})

 

위 처럼 코드를 수정해보시기 바랍니다. 좀 더 자세한 정보는 몽고DB 공식사이트 문서도 한번 참고해보세요.

문신호님의 프로필 이미지
문신호
질문자

남박사님 답변주셔서 감사합니다! 적용했더니 문제가 사라졌습니다. 다른 문제가 있는데.. 질문란에 다시 올리겠습니다! 감사합니다!

문신호님의 프로필 이미지
문신호

작성한 질문수

질문하기