質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
87.20%
Flask

FlaskはPython用のマイクロフレームワークであり、Werkzeug・Jinja 2・good intentionsをベースにしています。

SQLAlchemy

SQLAlchemyとはPython 用のORMライブラリです。MIT Licenceのオープンソースとして提供されています。

データベース設計

データベース設計はデータベースの論理的や物理的な部分を特定する工程です。

解決済

flask-sqlalchemyで外部キー制約の設定時にエラーが出る

asasika_R
asasika_R

総合スコア25

Flask

FlaskはPython用のマイクロフレームワークであり、Werkzeug・Jinja 2・good intentionsをベースにしています。

SQLAlchemy

SQLAlchemyとはPython 用のORMライブラリです。MIT Licenceのオープンソースとして提供されています。

データベース設計

データベース設計はデータベースの論理的や物理的な部分を特定する工程です。

1回答

0評価

0クリップ

273閲覧

投稿2022/06/10 07:04

編集2022/06/20 11:38

flaskを用いて家計簿のようなものを作成しようとしたのですが、外部キー制約の設定ができません。

プログラミング言語はpython,アプリケーションを作るためにflaskを使用し、データベース操作のために
pythonのormであるflask-sqlalchemyを使っています。

アプリケーションの概要ですが、まず、日用品や交際費などのようにジャンル別にカテゴリーを作成し、カテゴリーごとの予算を設定します。お金を使うごとに何にお金をどれくらい使ったかを記録し、それらの情報をウェブページ上に載せるというものです。なお一番下にpythonのコードすべてを載せています。
(HTMLは割愛)

データベースですが、Categoryというクラスにカテゴリーの情報を、Detailというクラスにお金を使用したときの情報を入れておきたいと考えています。また、これら二つのクラスをカテゴリ名を用いて一対多リレーションシップとしてデータベースを作成したいと考えています。

こちらがflask-sqlalchemyの公式ドキュメントのDeclearing Modelsのone to many relationshipを参考に作ったデータベースです。

python

class Category(db.Model): name = db.Column(db.String,db.ForeignKey('name'),primary_key=True) budget = db.Column(db.Integer,nullable=False) remaining_budget = db.Column(db.Integer,nullable=False) month = db.Column(db.Integer,nullable=False) class Detail(db.Model): id = db.Column(db.Integer,primary_key=True) name = db.relationship('Category',backref='Detail',lazy=True) used_money = db.Column(db.Integer,nullable=False) purchased_item = db.Column(db.String,nullable=False) date = db.Column(db.String,nullable=False)

こちらを実行すると出てきたエラー文がこちらです。
sqlalchemy.exc.NoForeignKeysError: Could not determine join condition between parent/child tables on relationship Detail.name - there are no foreign keys linking these tables. Ensure that referencing columns are associated with a ForeignKey or ForeignKeyConstraint, or specify a 'primaryjoin' expression.

エラー文を見るに、二つのテーブルをつなぐ外部キーがないとされているようですが、公式ドキュメント通りに外部キー制約を設定しているつもりなので、なぜこのようなことが起きているのかさっぱりわかりません。データベースについても勉強中なので根本的な間違いなのかもしれません。
なぜこのエラーが起きているのか、そしてその対応策を教えていただきたいです。

pythonのコード

python

from flask import Flask from flask import render_template,redirect,request,session from flask_sqlalchemy import SQLAlchemy from flask_migrate import Migrate import os import datetime app = Flask(__name__) app.config['AQLALCHEMY_DARABASE_URI'] = 'sqlite:///database.db' db = SQLAlchemy(app) migrate = Migrate(app,db) today = datetime.date.today() class Category(db.Model): name = db.Column(db.String,db.ForeignKey('name'),primary_key=True) budget = db.Column(db.Integer,nullable=False) remaining_budget = db.Column(db.Integer,nullable=False) month = db.Column(db.Integer,nullable=False) class Detail(db.Model): id = db.Column(db.Integer,primary_key=True) name = db.relationship('Category',backref='Detail',lazy=True) used_money = db.Column(db.Integer,nullable=False) purchased_item = db.Column(db.String,nullable=False) date = db.Column(db.String,nullable=False) @app.route('/') def index(): display_categorys = Category.query.filter_by(month = today.month).all() display_details = Category.query.filter_by(month = today.month).all() month = today.month day = today.day return render_template('index.html',categorys=display_categorys,details=display_details,this_month=month,day=day) @app.route('/create_category' ,methods=['GET','POST']) def create_category(): if request.method == 'GET': return render_template('create_category.html') else: category_name = request.form.get('category_name') budget = request.form.get('budget') add_category = Category(category_name=category_name,budget=budget) db.session.add(add_category) db.session.commit() return redirect('/index') @app.route('/create_detail' ,methods=['GET','POST']) def create_detail(): if request.method == 'GET': return render_template('create_detail.html') else: purchased_item = request.form.get('purchased_item') used_money = request.form.get('used_money') add_detail = Detail(purchased_item=purchased_item,used_money=used_money) db.session.add(add_detail) db.session.commit()

良い質問の評価を上げる

以下のような質問は評価を上げましょう

  • 質問内容が明確
  • 自分も答えを知りたい
  • 質問者以外のユーザにも役立つ

評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

気になる質問をクリップする

クリップした質問は、後からいつでもマイページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

  • プログラミングに関係のない質問
  • やってほしいことだけを記載した丸投げの質問
  • 問題・課題が含まれていない質問
  • 意図的に内容が抹消された質問
  • 過去に投稿した質問と同じ内容の質問
  • 広告と受け取られるような投稿

評価を下げると、トップページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

まだ回答がついていません

会員登録して回答してみよう

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
87.20%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問

同じタグがついた質問を見る

Flask

FlaskはPython用のマイクロフレームワークであり、Werkzeug・Jinja 2・good intentionsをベースにしています。

SQLAlchemy

SQLAlchemyとはPython 用のORMライブラリです。MIT Licenceのオープンソースとして提供されています。

データベース設計

データベース設計はデータベースの論理的や物理的な部分を特定する工程です。