mirror of
https://github.com/fastapi-users/fastapi-users.git
synced 2025-08-19 07:17:37 +08:00
Automated deployment: Mon Feb 3 09:51:52 UTC 2020 b7bb7c2e31abd420ac3668443d2a57f798120e53
This commit is contained in:
@ -424,6 +424,13 @@
|
||||
Login
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#logout" class="md-nav__link">
|
||||
Logout
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
@ -577,6 +584,13 @@
|
||||
Login
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#logout" class="md-nav__link">
|
||||
Logout
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
@ -653,6 +667,14 @@
|
||||
<blockquote>
|
||||
<p>Check documentation about <a href="../../../usage/routes/#post-loginname">login route</a>.</p>
|
||||
</blockquote>
|
||||
<h2 id="logout">Logout<a class="headerlink" href="#logout" title="Permanent link">¶</a></h2>
|
||||
<p>This method will remove the authentication cookie:</p>
|
||||
<div class="admonition success">
|
||||
<p class="admonition-title"><code>200 OK</code></p>
|
||||
</div>
|
||||
<blockquote>
|
||||
<p>Check documentation about <a href="../../../usage/routes/#post-logoutname">logout route</a>.</p>
|
||||
</blockquote>
|
||||
<h2 id="authentication">Authentication<a class="headerlink" href="#authentication" title="Permanent link">¶</a></h2>
|
||||
<p>This method expects that you provide a valid cookie in the headers.</p>
|
||||
<h2 id="next-steps">Next steps<a class="headerlink" href="#next-steps" title="Permanent link">¶</a></h2>
|
||||
|
@ -588,6 +588,7 @@
|
||||
<p>You can have <strong>several</strong> authentication methods, e.g. a cookie authentication for browser-based queries and a JWT token authentication for pure API queries.</p>
|
||||
<p>When checking authentication, each method is run one after the other. The first method yielding a user wins. If no method yields a user, an <code>HTTPException</code> is raised.</p>
|
||||
<p>Each defined method will generate a <a href="../../usage/routes/#post-loginname"><code>/login/{name}</code></a> route where <code>name</code> is defined on the authentication method object.</p>
|
||||
<p>Each defined method will generate a <a href="../../usage/routes/#post-logoutname"><code>/logout/{name}</code></a> route where <code>name</code> is defined on the authentication method object.</p>
|
||||
<h2 id="provided-methods">Provided methods<a class="headerlink" href="#provided-methods" title="Permanent link">¶</a></h2>
|
||||
<ul>
|
||||
<li><a href="jwt/">JWT authentication</a></li>
|
||||
|
@ -412,6 +412,13 @@
|
||||
Login
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#logout" class="md-nav__link">
|
||||
Logout
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
@ -577,6 +584,13 @@
|
||||
Login
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#logout" class="md-nav__link">
|
||||
Logout
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
@ -646,6 +660,14 @@
|
||||
<blockquote>
|
||||
<p>Check documentation about <a href="../../../usage/routes/#post-loginname">login route</a>.</p>
|
||||
</blockquote>
|
||||
<h2 id="logout">Logout<a class="headerlink" href="#logout" title="Permanent link">¶</a></h2>
|
||||
<p>This method is not applicable to this backend and won't do anything.</p>
|
||||
<div class="admonition success">
|
||||
<p class="admonition-title"><code>202 Accepted</code></p>
|
||||
</div>
|
||||
<blockquote>
|
||||
<p>Check documentation about <a href="../../../usage/routes/#post-logoutname">logout route</a>.</p>
|
||||
</blockquote>
|
||||
<h2 id="authentication">Authentication<a class="headerlink" href="#authentication" title="Permanent link">¶</a></h2>
|
||||
<p>This method expects that you provide a <code>Bearer</code> authentication with a valid JWT.</p>
|
||||
<div class="codehilite"><pre><span></span>curl http://localhost:9000/protected-route -H<span class="s1">'Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoiOTIyMWZmYzktNjQwZi00MzcyLTg2ZDMtY2U2NDJjYmE1NjAzIiwiYXVkIjoiZmFzdGFwaS11c2VyczphdXRoIiwiZXhwIjoxNTcxNTA0MTkzfQ.M10bjOe45I5Ncu_uXvOmVV8QxnL-nZfcH96U90JaocI'</span>
|
||||
|
@ -571,7 +571,80 @@
|
||||
<div class="superfences-tabs">
|
||||
<input name="__tabs_1" type="radio" id="__tab_1_0" checked="checked" />
|
||||
<label for="__tab_1_0">SQLAlchemy</label>
|
||||
<div class="superfences-content"><div class="codehilite"><pre><span></span>
|
||||
<div class="superfences-content"><div class="codehilite"><pre><span></span><span class="kn">import</span> <span class="nn">databases</span>
|
||||
<span class="kn">import</span> <span class="nn">sqlalchemy</span>
|
||||
<span class="kn">from</span> <span class="nn">fastapi</span> <span class="kn">import</span> <span class="n">FastAPI</span>
|
||||
<span class="kn">from</span> <span class="nn">fastapi_users</span> <span class="kn">import</span> <span class="n">FastAPIUsers</span><span class="p">,</span> <span class="n">models</span>
|
||||
<span class="kn">from</span> <span class="nn">fastapi_users.authentication</span> <span class="kn">import</span> <span class="n">JWTAuthentication</span>
|
||||
<span class="kn">from</span> <span class="nn">fastapi_users.db</span> <span class="kn">import</span> <span class="n">SQLAlchemyBaseUserTable</span><span class="p">,</span> <span class="n">SQLAlchemyUserDatabase</span>
|
||||
<span class="kn">from</span> <span class="nn">sqlalchemy.ext.declarative</span> <span class="kn">import</span> <span class="n">DeclarativeMeta</span><span class="p">,</span> <span class="n">declarative_base</span>
|
||||
|
||||
<span class="n">DATABASE_URL</span> <span class="o">=</span> <span class="s2">"sqlite:///./test.db"</span>
|
||||
<span class="n">SECRET</span> <span class="o">=</span> <span class="s2">"SECRET"</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">User</span><span class="p">(</span><span class="n">models</span><span class="o">.</span><span class="n">BaseUser</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserCreate</span><span class="p">(</span><span class="n">User</span><span class="p">,</span> <span class="n">models</span><span class="o">.</span><span class="n">BaseUserCreate</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserUpdate</span><span class="p">(</span><span class="n">User</span><span class="p">,</span> <span class="n">models</span><span class="o">.</span><span class="n">BaseUserUpdate</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserDB</span><span class="p">(</span><span class="n">User</span><span class="p">,</span> <span class="n">models</span><span class="o">.</span><span class="n">BaseUserDB</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="n">database</span> <span class="o">=</span> <span class="n">databases</span><span class="o">.</span><span class="n">Database</span><span class="p">(</span><span class="n">DATABASE_URL</span><span class="p">)</span>
|
||||
<span class="n">Base</span><span class="p">:</span> <span class="n">DeclarativeMeta</span> <span class="o">=</span> <span class="n">declarative_base</span><span class="p">()</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserTable</span><span class="p">(</span><span class="n">Base</span><span class="p">,</span> <span class="n">SQLAlchemyBaseUserTable</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="n">engine</span> <span class="o">=</span> <span class="n">sqlalchemy</span><span class="o">.</span><span class="n">create_engine</span><span class="p">(</span>
|
||||
<span class="n">DATABASE_URL</span><span class="p">,</span> <span class="n">connect_args</span><span class="o">=</span><span class="p">{</span><span class="s2">"check_same_thread"</span><span class="p">:</span> <span class="kc">False</span><span class="p">}</span>
|
||||
<span class="p">)</span>
|
||||
<span class="n">Base</span><span class="o">.</span><span class="n">metadata</span><span class="o">.</span><span class="n">create_all</span><span class="p">(</span><span class="n">engine</span><span class="p">)</span>
|
||||
|
||||
<span class="n">users</span> <span class="o">=</span> <span class="n">UserTable</span><span class="o">.</span><span class="n">__table__</span>
|
||||
<span class="n">user_db</span> <span class="o">=</span> <span class="n">SQLAlchemyUserDatabase</span><span class="p">(</span><span class="n">UserDB</span><span class="p">,</span> <span class="n">database</span><span class="p">,</span> <span class="n">users</span><span class="p">)</span>
|
||||
|
||||
|
||||
<span class="n">auth_backends</span> <span class="o">=</span> <span class="p">[</span>
|
||||
<span class="n">JWTAuthentication</span><span class="p">(</span><span class="n">secret</span><span class="o">=</span><span class="n">SECRET</span><span class="p">,</span> <span class="n">lifetime_seconds</span><span class="o">=</span><span class="mi">3600</span><span class="p">),</span>
|
||||
<span class="p">]</span>
|
||||
|
||||
<span class="n">app</span> <span class="o">=</span> <span class="n">FastAPI</span><span class="p">()</span>
|
||||
<span class="n">fastapi_users</span> <span class="o">=</span> <span class="n">FastAPIUsers</span><span class="p">(</span>
|
||||
<span class="n">user_db</span><span class="p">,</span> <span class="n">auth_backends</span><span class="p">,</span> <span class="n">User</span><span class="p">,</span> <span class="n">UserCreate</span><span class="p">,</span> <span class="n">UserUpdate</span><span class="p">,</span> <span class="n">UserDB</span><span class="p">,</span> <span class="n">SECRET</span><span class="p">,</span>
|
||||
<span class="p">)</span>
|
||||
<span class="n">app</span><span class="o">.</span><span class="n">include_router</span><span class="p">(</span><span class="n">fastapi_users</span><span class="o">.</span><span class="n">router</span><span class="p">,</span> <span class="n">prefix</span><span class="o">=</span><span class="s2">"/users"</span><span class="p">,</span> <span class="n">tags</span><span class="o">=</span><span class="p">[</span><span class="s2">"users"</span><span class="p">])</span>
|
||||
|
||||
|
||||
<span class="nd">@fastapi_users</span><span class="o">.</span><span class="n">on_after_register</span><span class="p">()</span>
|
||||
<span class="k">def</span> <span class="nf">on_after_register</span><span class="p">(</span><span class="n">user</span><span class="p">:</span> <span class="n">User</span><span class="p">):</span>
|
||||
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"User </span><span class="si">{user.id}</span><span class="s2"> has registered."</span><span class="p">)</span>
|
||||
|
||||
|
||||
<span class="nd">@fastapi_users</span><span class="o">.</span><span class="n">on_after_forgot_password</span><span class="p">()</span>
|
||||
<span class="k">def</span> <span class="nf">on_after_forgot_password</span><span class="p">(</span><span class="n">user</span><span class="p">:</span> <span class="n">User</span><span class="p">,</span> <span class="n">token</span><span class="p">:</span> <span class="nb">str</span><span class="p">):</span>
|
||||
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"User </span><span class="si">{user.id}</span><span class="s2"> has forgot their password. Reset token: </span><span class="si">{token}</span><span class="s2">"</span><span class="p">)</span>
|
||||
|
||||
|
||||
<span class="nd">@app</span><span class="o">.</span><span class="n">on_event</span><span class="p">(</span><span class="s2">"startup"</span><span class="p">)</span>
|
||||
<span class="k">async</span> <span class="k">def</span> <span class="nf">startup</span><span class="p">():</span>
|
||||
<span class="k">await</span> <span class="n">database</span><span class="o">.</span><span class="n">connect</span><span class="p">()</span>
|
||||
|
||||
|
||||
<span class="nd">@app</span><span class="o">.</span><span class="n">on_event</span><span class="p">(</span><span class="s2">"shutdown"</span><span class="p">)</span>
|
||||
<span class="k">async</span> <span class="k">def</span> <span class="nf">shutdown</span><span class="p">():</span>
|
||||
<span class="k">await</span> <span class="n">database</span><span class="o">.</span><span class="n">disconnect</span><span class="p">()</span>
|
||||
</pre></div></div>
|
||||
<input name="__tabs_1" type="radio" id="__tab_1_1" />
|
||||
<label for="__tab_1_1">MongoDB</label>
|
||||
@ -628,7 +701,58 @@
|
||||
</pre></div></div>
|
||||
<input name="__tabs_1" type="radio" id="__tab_1_2" />
|
||||
<label for="__tab_1_2">Tortoise ORM</label>
|
||||
<div class="superfences-content"><div class="codehilite"><pre><span></span>
|
||||
<div class="superfences-content"><div class="codehilite"><pre><span></span><span class="kn">from</span> <span class="nn">fastapi</span> <span class="kn">import</span> <span class="n">FastAPI</span>
|
||||
<span class="kn">from</span> <span class="nn">fastapi_users</span> <span class="kn">import</span> <span class="n">FastAPIUsers</span><span class="p">,</span> <span class="n">models</span>
|
||||
<span class="kn">from</span> <span class="nn">fastapi_users.authentication</span> <span class="kn">import</span> <span class="n">JWTAuthentication</span>
|
||||
<span class="kn">from</span> <span class="nn">fastapi_users.db</span> <span class="kn">import</span> <span class="n">TortoiseBaseUserModel</span><span class="p">,</span> <span class="n">TortoiseUserDatabase</span>
|
||||
<span class="kn">from</span> <span class="nn">tortoise.contrib.starlette</span> <span class="kn">import</span> <span class="n">register_tortoise</span>
|
||||
|
||||
<span class="n">DATABASE_URL</span> <span class="o">=</span> <span class="s2">"sqlite://./test.db"</span>
|
||||
<span class="n">SECRET</span> <span class="o">=</span> <span class="s2">"SECRET"</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">User</span><span class="p">(</span><span class="n">models</span><span class="o">.</span><span class="n">BaseUser</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserCreate</span><span class="p">(</span><span class="n">User</span><span class="p">,</span> <span class="n">models</span><span class="o">.</span><span class="n">BaseUserCreate</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserUpdate</span><span class="p">(</span><span class="n">User</span><span class="p">,</span> <span class="n">models</span><span class="o">.</span><span class="n">BaseUserUpdate</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserDB</span><span class="p">(</span><span class="n">User</span><span class="p">,</span> <span class="n">models</span><span class="o">.</span><span class="n">BaseUserDB</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="k">class</span> <span class="nc">UserModel</span><span class="p">(</span><span class="n">TortoiseBaseUserModel</span><span class="p">):</span>
|
||||
<span class="k">pass</span>
|
||||
|
||||
|
||||
<span class="n">user_db</span> <span class="o">=</span> <span class="n">TortoiseUserDatabase</span><span class="p">(</span><span class="n">UserDB</span><span class="p">,</span> <span class="n">UserModel</span><span class="p">)</span>
|
||||
<span class="n">app</span> <span class="o">=</span> <span class="n">FastAPI</span><span class="p">()</span>
|
||||
<span class="n">register_tortoise</span><span class="p">(</span><span class="n">app</span><span class="p">,</span> <span class="n">db_url</span><span class="o">=</span><span class="n">DATABASE_URL</span><span class="p">,</span> <span class="n">modules</span><span class="o">=</span><span class="p">{</span><span class="s2">"models"</span><span class="p">:</span> <span class="p">[</span><span class="s2">"test"</span><span class="p">]})</span>
|
||||
|
||||
<span class="n">auth_backends</span> <span class="o">=</span> <span class="p">[</span>
|
||||
<span class="n">JWTAuthentication</span><span class="p">(</span><span class="n">secret</span><span class="o">=</span><span class="n">SECRET</span><span class="p">,</span> <span class="n">lifetime_seconds</span><span class="o">=</span><span class="mi">3600</span><span class="p">),</span>
|
||||
<span class="p">]</span>
|
||||
|
||||
<span class="n">fastapi_users</span> <span class="o">=</span> <span class="n">FastAPIUsers</span><span class="p">(</span>
|
||||
<span class="n">user_db</span><span class="p">,</span> <span class="n">auth_backends</span><span class="p">,</span> <span class="n">User</span><span class="p">,</span> <span class="n">UserCreate</span><span class="p">,</span> <span class="n">UserUpdate</span><span class="p">,</span> <span class="n">UserDB</span><span class="p">,</span> <span class="n">SECRET</span><span class="p">,</span>
|
||||
<span class="p">)</span>
|
||||
<span class="n">app</span><span class="o">.</span><span class="n">include_router</span><span class="p">(</span><span class="n">fastapi_users</span><span class="o">.</span><span class="n">router</span><span class="p">,</span> <span class="n">prefix</span><span class="o">=</span><span class="s2">"/users"</span><span class="p">,</span> <span class="n">tags</span><span class="o">=</span><span class="p">[</span><span class="s2">"users"</span><span class="p">])</span>
|
||||
|
||||
|
||||
<span class="nd">@fastapi_users</span><span class="o">.</span><span class="n">on_after_register</span><span class="p">()</span>
|
||||
<span class="k">def</span> <span class="nf">on_after_register</span><span class="p">(</span><span class="n">user</span><span class="p">:</span> <span class="n">User</span><span class="p">):</span>
|
||||
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"User </span><span class="si">{user.id}</span><span class="s2"> has registered."</span><span class="p">)</span>
|
||||
|
||||
|
||||
<span class="nd">@fastapi_users</span><span class="o">.</span><span class="n">on_after_forgot_password</span><span class="p">()</span>
|
||||
<span class="k">def</span> <span class="nf">on_after_forgot_password</span><span class="p">(</span><span class="n">user</span><span class="p">:</span> <span class="n">User</span><span class="p">,</span> <span class="n">token</span><span class="p">:</span> <span class="nb">str</span><span class="p">):</span>
|
||||
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"User </span><span class="si">{user.id}</span><span class="s2"> has forgot their password. Reset token: </span><span class="si">{token}</span><span class="s2">"</span><span class="p">)</span>
|
||||
</pre></div></div>
|
||||
</div>
|
||||
<h2 id="what-now">What now?<a class="headerlink" href="#what-now" title="Permanent link">¶</a></h2>
|
||||
|
@ -454,6 +454,13 @@
|
||||
After forgot password
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#after-update" class="md-nav__link">
|
||||
After update
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
</ul>
|
||||
@ -603,6 +610,13 @@
|
||||
After forgot password
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#after-update" class="md-nav__link">
|
||||
After update
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
</ul>
|
||||
@ -693,6 +707,21 @@
|
||||
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"User </span><span class="si">{user.id}</span><span class="s2"> has forgot their password. Reset token: </span><span class="si">{token}</span><span class="s2">"</span><span class="p">)</span>
|
||||
</pre></div>
|
||||
|
||||
<h3 id="after-update">After update<a class="headerlink" href="#after-update" title="Permanent link">¶</a></h3>
|
||||
<p>This event handler is called after a successful update user request. It is called with <strong>three arguments</strong>:</p>
|
||||
<ul>
|
||||
<li>The <strong>user</strong> which was updated.</li>
|
||||
<li>The dictionary containing the updated fields.</li>
|
||||
<li>The original <strong><code>Request</code> object</strong>.</li>
|
||||
</ul>
|
||||
<p>It may be useful if you wish for example update your user in a data analytics or customer success platform.</p>
|
||||
<p>You can define it as an <code>async</code> or standard method.</p>
|
||||
<p>Example:</p>
|
||||
<div class="codehilite"><pre><span></span><span class="nd">@fastapi_users</span><span class="o">.</span><span class="n">on_after_update</span><span class="p">()</span>
|
||||
<span class="k">def</span> <span class="nf">on_after_update</span><span class="p">(</span><span class="n">user</span><span class="p">:</span> <span class="n">User</span><span class="p">,</span> <span class="n">updated_user_data</span><span class="p">:</span> <span class="n">Dict</span><span class="p">[</span><span class="nb">str</span><span class="p">,</span> <span class="n">Any</span><span class="p">],</span> <span class="n">request</span><span class="p">:</span> <span class="n">Request</span><span class="p">):</span>
|
||||
<span class="nb">print</span><span class="p">(</span><span class="sa">f</span><span class="s2">"User </span><span class="si">{user.id}</span><span class="s2"> has been updated with the following data: </span><span class="si">{updated_user_data}</span><span class="s2">"</span><span class="p">)</span>
|
||||
</pre></div>
|
||||
|
||||
<h2 id="next-steps">Next steps<a class="headerlink" href="#next-steps" title="Permanent link">¶</a></h2>
|
||||
<p>Check out a <a href="../full_example/">full example</a> that will show you the big picture.</p>
|
||||
|
||||
|
File diff suppressed because one or more lines are too long
BIN
sitemap.xml.gz
BIN
sitemap.xml.gz
Binary file not shown.
74
src/full_sqlalchemy.py
Normal file
74
src/full_sqlalchemy.py
Normal file
@ -0,0 +1,74 @@
|
||||
import databases
|
||||
import sqlalchemy
|
||||
from fastapi import FastAPI
|
||||
from fastapi_users import FastAPIUsers, models
|
||||
from fastapi_users.authentication import JWTAuthentication
|
||||
from fastapi_users.db import SQLAlchemyBaseUserTable, SQLAlchemyUserDatabase
|
||||
from sqlalchemy.ext.declarative import DeclarativeMeta, declarative_base
|
||||
|
||||
DATABASE_URL = "sqlite:///./test.db"
|
||||
SECRET = "SECRET"
|
||||
|
||||
|
||||
class User(models.BaseUser):
|
||||
pass
|
||||
|
||||
|
||||
class UserCreate(User, models.BaseUserCreate):
|
||||
pass
|
||||
|
||||
|
||||
class UserUpdate(User, models.BaseUserUpdate):
|
||||
pass
|
||||
|
||||
|
||||
class UserDB(User, models.BaseUserDB):
|
||||
pass
|
||||
|
||||
|
||||
database = databases.Database(DATABASE_URL)
|
||||
Base: DeclarativeMeta = declarative_base()
|
||||
|
||||
|
||||
class UserTable(Base, SQLAlchemyBaseUserTable):
|
||||
pass
|
||||
|
||||
|
||||
engine = sqlalchemy.create_engine(
|
||||
DATABASE_URL, connect_args={"check_same_thread": False}
|
||||
)
|
||||
Base.metadata.create_all(engine)
|
||||
|
||||
users = UserTable.__table__
|
||||
user_db = SQLAlchemyUserDatabase(UserDB, database, users)
|
||||
|
||||
|
||||
auth_backends = [
|
||||
JWTAuthentication(secret=SECRET, lifetime_seconds=3600),
|
||||
]
|
||||
|
||||
app = FastAPI()
|
||||
fastapi_users = FastAPIUsers(
|
||||
user_db, auth_backends, User, UserCreate, UserUpdate, UserDB, SECRET,
|
||||
)
|
||||
app.include_router(fastapi_users.router, prefix="/users", tags=["users"])
|
||||
|
||||
|
||||
@fastapi_users.on_after_register()
|
||||
def on_after_register(user: User):
|
||||
print(f"User {user.id} has registered.")
|
||||
|
||||
|
||||
@fastapi_users.on_after_forgot_password()
|
||||
def on_after_forgot_password(user: User, token: str):
|
||||
print(f"User {user.id} has forgot their password. Reset token: {token}")
|
||||
|
||||
|
||||
@app.on_event("startup")
|
||||
async def startup():
|
||||
await database.connect()
|
||||
|
||||
|
||||
@app.on_event("shutdown")
|
||||
async def shutdown():
|
||||
await database.disconnect()
|
52
src/full_tortoise.py
Normal file
52
src/full_tortoise.py
Normal file
@ -0,0 +1,52 @@
|
||||
from fastapi import FastAPI
|
||||
from fastapi_users import FastAPIUsers, models
|
||||
from fastapi_users.authentication import JWTAuthentication
|
||||
from fastapi_users.db import TortoiseBaseUserModel, TortoiseUserDatabase
|
||||
from tortoise.contrib.starlette import register_tortoise
|
||||
|
||||
DATABASE_URL = "sqlite://./test.db"
|
||||
SECRET = "SECRET"
|
||||
|
||||
|
||||
class User(models.BaseUser):
|
||||
pass
|
||||
|
||||
|
||||
class UserCreate(User, models.BaseUserCreate):
|
||||
pass
|
||||
|
||||
|
||||
class UserUpdate(User, models.BaseUserUpdate):
|
||||
pass
|
||||
|
||||
|
||||
class UserDB(User, models.BaseUserDB):
|
||||
pass
|
||||
|
||||
|
||||
class UserModel(TortoiseBaseUserModel):
|
||||
pass
|
||||
|
||||
|
||||
user_db = TortoiseUserDatabase(UserDB, UserModel)
|
||||
app = FastAPI()
|
||||
register_tortoise(app, db_url=DATABASE_URL, modules={"models": ["test"]})
|
||||
|
||||
auth_backends = [
|
||||
JWTAuthentication(secret=SECRET, lifetime_seconds=3600),
|
||||
]
|
||||
|
||||
fastapi_users = FastAPIUsers(
|
||||
user_db, auth_backends, User, UserCreate, UserUpdate, UserDB, SECRET,
|
||||
)
|
||||
app.include_router(fastapi_users.router, prefix="/users", tags=["users"])
|
||||
|
||||
|
||||
@fastapi_users.on_after_register()
|
||||
def on_after_register(user: User):
|
||||
print(f"User {user.id} has registered.")
|
||||
|
||||
|
||||
@fastapi_users.on_after_forgot_password()
|
||||
def on_after_forgot_password(user: User, token: str):
|
||||
print(f"User {user.id} has forgot their password. Reset token: {token}")
|
@ -507,6 +507,13 @@
|
||||
POST /login/{name}
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#post-logoutname" class="md-nav__link">
|
||||
POST /logout/{name}
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
@ -691,6 +698,13 @@
|
||||
POST /login/{name}
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
<a href="#post-logoutname" class="md-nav__link">
|
||||
POST /logout/{name}
|
||||
</a>
|
||||
|
||||
</li>
|
||||
|
||||
<li class="md-nav__item">
|
||||
@ -880,6 +894,20 @@
|
||||
<span class="p">}</span>
|
||||
</pre></div>
|
||||
|
||||
</div>
|
||||
<h3 id="post-logoutname"><code>POST /logout/{name}</code><a class="headerlink" href="#post-logoutname" title="Permanent link">¶</a></h3>
|
||||
<p>Logout the authenticated user against the method named <code>name</code>. Check the corresponding <a href="../../configuration/authentication/">authentication method</a> to view the success response.</p>
|
||||
<div class="admonition fail">
|
||||
<p class="admonition-title"><code>401 Unauthorized</code></p>
|
||||
<p>Missing token or inactive user.</p>
|
||||
</div>
|
||||
<div class="admonition success">
|
||||
<p class="admonition-title"><code>200 OK</code></p>
|
||||
<p>The logout process was successful.</p>
|
||||
</div>
|
||||
<div class="admonition success">
|
||||
<p class="admonition-title"><code>202 Accepted</code></p>
|
||||
<p>The logout process is not applicable for this authentication backend (e.g. JWT).</p>
|
||||
</div>
|
||||
<h3 id="post-forgot-password"><code>POST /forgot-password</code><a class="headerlink" href="#post-forgot-password" title="Permanent link">¶</a></h3>
|
||||
<p>Request a reset password procedure. Will generate a temporary token and call the <code>on_after_forgot_password</code> <a href="../../configuration/router/#event-handlers">event handlers</a> if the user exists.</p>
|
||||
|
Reference in New Issue
Block a user