#rocket-web #login #rocket #web-apps #rocket-framework

nightly rocket-auth-login

为Rocket Web应用程序提供登录和认证。此包提供了处理登录表单和处理私有cookie的函数。

4个版本

使用旧的Rust 2015

0.2.3 2018年7月20日
0.2.2 2018年1月16日
0.2.1 2017年12月20日
0.2.0 2017年11月19日

2245Web编程

每月23次下载

Apache-2.0

44KB
316

% Rocket-auth-login - Rust Rocket框架的认证和登录库

需要Nightly Rust

使用nightly-2017-11-22-x86_64-pc-windows-msvc测试,在Windows上使用rustup安装并将其设置为默认值:

rustup toolchain install nightly-2017-11-22-x86_64-pc-windows-msvc
rustup default nightly-2017-11-22-x86_64-pc-windows-msvc

或在Linux上:

rustup toolchain install nightly-2017-11-22-x86_64-unknown-linux-gnu
rustup default nightly-2017-11-22-x86_64-unknown-linux-gnu

Cargo.toml

在cargo.toml中添加

    rocket-auth-login = "0.5.*"

导入和使用语句


    extern crate rocket_auth_login as auth;
    use auth::authorization;
    

描述

Rocket-auth-login是一个用Rust编写的认证和登录处理库。

此包提供了特质,您将在程序中定义的两个不同自定义类型上实现这些特质。这些特质包含处理登录表单数据和存储和检索cookie的有用方法。您将定义的两个自定义结构将执行以下操作

  • 存储登录表单的内容

    • 用于验证用户凭据
    • 当认证成功时,此结构将被序列化为一个存储在私有cookie中的String
    • 可以通过请求保护器检索cookie数据结构,用于指定的用户类型

版本说明

版本2.0将任何传递给重定向方法的cookie的所有权传递出去,这并不方便。版本2.1使用对cookie的可变引用,允许在调用重定向方法后修改它们(重定向结构可以存储在变量中,并在需要时返回)。

数据结构

在您的应用程序中定义两个自定义数据结构,它们将

登录表单数据结构


    #[derive(Debug, Clone, Serialize, Deserialize)]    
    pub struct AdministratorForm {
        pub username: String,
        pub password: String,
    }

    #[derive(Debug, Clone, Serialize, Deserialize)]
    pub struct AdministratorCookie {
        pub userid: u32,
        pub username: String,
        pub display: Option<String>,
    }

特质实现

特质CookieId由两个数据结构实现。仅由登录数据结构实现的特质是AuthorizeForm,而由cookie数据结构实现的特质是AuthorizeCookie。更详细的示例,请查看任何示例中的administrator.rs文件。

CookieId

每个 数据结构都必须实现 CookieId 特性。对于 cookie_id() 的实现,两个数据结构应该是相同的,因为这两个数据结构将具有相同的cookie标识符(登录表单数据结构将使用指定的cookie标识符创建cookie,而cookie数据结构将读取与指定标识符关联的cookie)。这是一个只有单个方法的简单特性。对于 cookide_id() 方法的实现如下:


    // Both structures will use the same code for the `CookieId`
    impl CookieId for {StructNameHere} {
        fn cookie_id<'a>() -> &'a str {
            "acid"
        }
    }

AuthorizeCookie

AuthorizeCookie 特性定义了cookie数据结构的几个方法。在cookie数据结构上,你必须实现两个函数,还有一个名为 delete_cookie() 的函数,它有一个默认实现,用于删除具有指定名称的私有cookie,该名称由 CookieId::cookie_id() 指定。在cookie数据结构上你必须实现的函数有

  • store_cookie(&self) ->String
    • 将cookie数据结构序列化为字符串以存储在私有cookie中
  • retrieve_cookie(String) -> Self
    • 从cookie包含的字符串反序列化cookie数据结构

AuthorizeForm

AuthorizeForm 特性定义了在登录表单数据结构上实现的一些方法,其中只有两个必须在你的代码中实现。其余的是可选的。同时,关联类型 CookieType 应该设置为cookie数据结构类型


    impl AuthorizeForm for AdministratorForm {
        type CookieType = AdministratorCookie;

必需

  • fn authenticate(&self) -> Result<Self::CookieType, AuthFail>

    • 通过 &self 参数接受一个登录表单数据结构
    • 返回
      • Ok( CookieType ),其中 CookieType 将被cookie数据结构替换
      • Err( AuthFail::new(attempted_username.to_string(), reason_auth_failed.to_string()) )
  • fn new_form(&str, &str, Option<HashMap<String, String>>) -> Self

    • 从提交的表单数据创建登录表单数据结构的新实例。此方法由 FromForm 实现在 LoginCont 结构上调用(该容器用于存储登录表单数据结构,请参阅下面的路由示例)。参数包括
      1. 用户名 - 来自名为 username 的输入字段
      2. 密码 - 来自名为 password 的输入字段
      3. 其他内容 - 一个 Option<HashMap<String, String>>,它包含除 usernamepassword 之外的所有表单字段。当用户名和密码字段具有不同的名称时(此时 authenticate() 可以在额外的哈希映射中查看字段而不是常规的用户名和密码字段)或者当登录表单需要其他字段时,会使用此内容。

可选(可以重写)

  • fn flash_redirect(&self, ok_redir: &str, err_redir: &str, cookies: &mutCookies) -> Result<Redirect, Flash<Redirect>>
    • 调用authenticate()方法,如果成功则创建私有cookie以登录用户。在身份验证成功后,将用户重定向到ok_redir页面。如果身份验证失败,则调用fail_url()构建查询字符串,并将其附加到err_redir(这允许用户名持续存在并在登录表单中填写)并且设置一个FlashMessage(一个一旦读取就会被删除的cookie),表明表单失败的原因。
  • fn 重定向(&self, ok_redir: &str, err_redir: &str, cookies: &mutCookies) -> Result<重定向,重定向>
    • flash_redirect()相同,除了它不设置Flashmessage,它只重定向到ok_redir页面或err_redir页面(带有fail_url()返回的查询字符串附加)。
  • fn fail_url(用户: &str) ->String
    • 创建一个查询字符串,并将其附加到url上,以指示用户尝试用哪个用户名登录。默认实现创建以下字符串:"?user={username}",其中{username}是指定的用户名。
  • fn clean_username(字符串: &str) ->String
    • 清洗用户名。默认情况下,它使用来自sanitize()方法的sanitization模块(sanitization.rs)。
  • fn clean_password(字符串: &str) ->String
    • 清洗密码。默认情况下,它使用来自sanitize_password()方法的sanitization模块(sanitization.rs)。
  • fn clean_extras(string: &str) -> String清洗任何额外字段。默认情况下,它使用来自sanitize()方法的sanitization模块(sanitization.rs)。

多用户类型

添加多个用户类型(例如管理员和普通用户类型)是可能的,并且相当简单。为此,只需为每种类型创建两个数据结构(登录表单数据结构和cookie数据结构)并为每种用户类型定义不同的cookie标识符(管理员类型可能返回类似"aid"的值,而用户类型可能返回类似"uid"的值)。

路由

在您的路由中,您将使用cookie数据类型作为请求保护程序(确保查看页面的用户已登录为指定的用户类型)。使用AdministratorCookie类型的路由看起来像


    #[get("/login", rank = 1)]
    fn logged_in(_user: AuthCont<AdministratorCookie>) -> Html<String> {
        let admin: AdministratorCookie = _user.cookie;
        Html( format!("Welcome {}, you are logged in as an administrator.", admin.username) )
    }
    // OR to use the type directly
    fn logged_in(admin: AdministratorCookie

登录表单处理

登录处理路由将是一个post路由


    #[allow(unused_mut)]
    #[post("/login", data = "<form>")]
    fn process_login(form: Form<LoginCont<AdministratorForm>>, mut cookies: Cookies) -> Result<Redirect, Flash<Redirect>> {
        let inner = form.into_inner();
        let login = inner.form;
        login.flash_redirect("/login", "/login", cookies)
    }

安全性

该库将以明文形式发送密码。强烈建议您使用TLS。甚至有一个示例展示了如何使用此crate的TLS。更改非常少。如果您绝对需要在发送密码之前对密码进行散列,所有示例都包含一个来自http://www.movable-type.co.uk/scripts/sha256.html的sha256.js文件,可用于此目的。此外,login.js文件在第15行附近的注释代码可以用于在发送之前使用sha256.js文件散列密码。此方法极其不推荐。SHA散列速度快,因此非常容易受到彩虹表攻击。不使用TLS时,仅使用散列密码的安全性几乎与明文相同。请使用TLS。(Let's Encrypt)提供免费证书,因此没有理由不在生产环境中使用https。

版权声明:Rocket-auth-login crate和Rust代码示例采用Apache 2.0许可协议。然而,示例中的布局/设计是我创建的。如果您至少在HTML输出中放入一个HTML注释“设计©2017Andrew Prindle”,则可以使用它。其余的应用程序您可以使用而不必向用户显示任何形式的信用,但必须遵守Apache 2.0许可协议的条款。

依赖关系

~12–21MB
~388K SLoC