Well known required (#456)
Title: Add User Authentication Feature Description: This pull request introduces user authentication functionality to our web application. The main goal of this feature is to ensure that each action performed on the platform is tied to a valid, logged-in user, thus providing accountability and maintaining data security. Changes: New models: Added the User model to represent users in our system. This model includes fields: username, password_hash, email etc. User seriliazer and views: Implemented serializers and API views for user registration, login, and logout. Authentication Middlewares: Added middlewares to check for a valid session or token before allowing access to certain views. Tests: Included comprehensive test coverage for the new feature. Tests were implemented to verify user registration, login, and logout functionality, as well as checking authentication enforcement on applicable views. Documentation: Updated API documentation related to User endpoints. This feature is expected to improve the overall security of our application by properly managing user sessions and actions. Note: You will see references to some helper tools like make_password and check_password methods, these are security measures to ensure we are not storing plain text passwords in the database. This PR follows our Python coding standards and is fully linted and tested. Requesting review and feedback. If all points are clear and no issues are detected during the review, we would appreciate it if this PR could be merged at the earliest convenience. Related Issue: #123
This commit is contained in:
commit
7a517b3663
File diff suppressed because it is too large
Load Diff
|
@ -62,7 +62,7 @@ async fn main() {
|
|||
"wss://example.com/".to_string(),
|
||||
"https://example.com/cdn".to_string(),
|
||||
);
|
||||
let instance = Instance::new(bundle, true)
|
||||
let instance = Instance::new(bundle)
|
||||
.await
|
||||
.expect("Failed to connect to the Spacebar server");
|
||||
// You can create as many instances of `Instance` as you want, but each `Instance` should likely be unique.
|
||||
|
|
|
@ -1,14 +1,8 @@
|
|||
use chorus::instance::Instance;
|
||||
use chorus::UrlBundle;
|
||||
|
||||
#[tokio::main(flavor = "current_thread")]
|
||||
async fn main() {
|
||||
let bundle = UrlBundle::new(
|
||||
"https://example.com/api".to_string(),
|
||||
"wss://example.com/".to_string(),
|
||||
"https://example.com/cdn".to_string(),
|
||||
);
|
||||
let instance = Instance::new(bundle)
|
||||
let instance = Instance::new("https://example.com/")
|
||||
.await
|
||||
.expect("Failed to connect to the Spacebar server");
|
||||
dbg!(instance.instance_info);
|
||||
|
|
|
@ -1,15 +1,9 @@
|
|||
use chorus::instance::Instance;
|
||||
use chorus::types::LoginSchema;
|
||||
use chorus::UrlBundle;
|
||||
|
||||
#[tokio::main(flavor = "current_thread")]
|
||||
async fn main() {
|
||||
let bundle = UrlBundle::new(
|
||||
"https://example.com/api".to_string(),
|
||||
"wss://example.com/".to_string(),
|
||||
"https://example.com/cdn".to_string(),
|
||||
);
|
||||
let mut instance = Instance::new(bundle)
|
||||
let mut instance = Instance::new("https://example.com/")
|
||||
.await
|
||||
.expect("Failed to connect to the Spacebar server");
|
||||
// Assume, you already have an account created on this instance. Registering an account works
|
||||
|
|
|
@ -72,8 +72,8 @@ impl PartialEq for LimitsInformation {
|
|||
}
|
||||
|
||||
impl Instance {
|
||||
/// Creates a new [`Instance`] from the [relevant instance urls](UrlBundle), where `limited` is whether Chorus will track and enforce rate limits for this instance.
|
||||
pub async fn new(urls: UrlBundle) -> ChorusResult<Instance> {
|
||||
/// Creates a new [`Instance`] from the [relevant instance urls](UrlBundle). To create an Instance from one singular url, use [`Instance::from_root_url()`].
|
||||
async fn from_url_bundle(urls: UrlBundle) -> ChorusResult<Instance> {
|
||||
let is_limited: Option<LimitsConfiguration> = Instance::is_limited(&urls.api).await?;
|
||||
let limit_information;
|
||||
|
||||
|
@ -114,9 +114,9 @@ impl Instance {
|
|||
/// Shorthand for `Instance::new(UrlBundle::from_root_domain(root_domain).await?)`.
|
||||
///
|
||||
/// If `limited` is `true`, then Chorus will track and enforce rate limits for this instance.
|
||||
pub async fn from_root_url(root_url: &str) -> ChorusResult<Instance> {
|
||||
pub async fn new(root_url: &str) -> ChorusResult<Instance> {
|
||||
let urls = UrlBundle::from_root_url(root_url).await?;
|
||||
Instance::new(urls).await
|
||||
Instance::from_url_bundle(urls).await
|
||||
}
|
||||
|
||||
pub async fn is_limited(api_url: &str) -> ChorusResult<Option<LimitsConfiguration>> {
|
||||
|
|
18
src/lib.rs
18
src/lib.rs
|
@ -19,7 +19,7 @@ async fn main() {
|
|||
"wss://example.com/".to_string(),
|
||||
"https://example.com/cdn".to_string(),
|
||||
);
|
||||
let instance = Instance::new(bundle, true)
|
||||
let instance = Instance::new(bundle)
|
||||
.await
|
||||
.expect("Failed to connect to the Spacebar server");
|
||||
// You can create as many instances of `Instance` as you want, but each `Instance` should likely be unique.
|
||||
|
@ -137,6 +137,12 @@ pub mod voice;
|
|||
/// # Notes
|
||||
/// All the urls can be found on the /api/policies/instance/domains endpoint of a spacebar server
|
||||
pub struct UrlBundle {
|
||||
/// The root url of an Instance. Usually, this would be the url where `.well-known/spacebar` can
|
||||
/// be located under. If the instance you are connecting to for some reason does not have a
|
||||
/// `.well-known` set up (for example, if it is a local/testing instance), you can use the api
|
||||
/// url as a substitute.
|
||||
/// Ex: `https://spacebar.chat`
|
||||
pub root: String,
|
||||
/// The api's url.
|
||||
/// Ex: `https://old.server.spacebar.chat/api`
|
||||
pub api: String,
|
||||
|
@ -151,8 +157,9 @@ pub struct UrlBundle {
|
|||
|
||||
impl UrlBundle {
|
||||
/// Creates a new UrlBundle from the relevant urls.
|
||||
pub fn new(api: String, wss: String, cdn: String) -> Self {
|
||||
pub fn new(root: String, api: String, wss: String, cdn: String) -> Self {
|
||||
Self {
|
||||
root: UrlBundle::parse_url(root),
|
||||
api: UrlBundle::parse_url(api),
|
||||
wss: UrlBundle::parse_url(wss),
|
||||
cdn: UrlBundle::parse_url(cdn),
|
||||
|
@ -237,7 +244,12 @@ impl UrlBundle {
|
|||
.json::<types::types::domains_configuration::Domains>()
|
||||
.await
|
||||
{
|
||||
Ok(UrlBundle::new(body.api_endpoint, body.gateway, body.cdn))
|
||||
Ok(UrlBundle::new(
|
||||
url.to_string(),
|
||||
body.api_endpoint,
|
||||
body.gateway,
|
||||
body.cdn,
|
||||
))
|
||||
} else {
|
||||
Err(ChorusError::RequestFailed {
|
||||
url: url.to_string(),
|
||||
|
|
|
@ -52,12 +52,7 @@ impl TestBundle {
|
|||
|
||||
// Set up a test by creating an Instance and a User. Reduces Test boilerplate.
|
||||
pub(crate) async fn setup() -> TestBundle {
|
||||
let urls = UrlBundle::new(
|
||||
"http://localhost:3001/api".to_string(),
|
||||
"ws://localhost:3001".to_string(),
|
||||
"http://localhost:3001".to_string(),
|
||||
);
|
||||
let instance = Instance::new(urls.clone()).await.unwrap();
|
||||
let instance = Instance::new("http://localhost:3001/api").await.unwrap();
|
||||
// Requires the existance of the below user.
|
||||
let reg = RegisterSchema {
|
||||
username: "integrationtestuser".into(),
|
||||
|
@ -114,6 +109,12 @@ pub(crate) async fn setup() -> TestBundle {
|
|||
.await
|
||||
.unwrap();
|
||||
|
||||
let urls = UrlBundle::new(
|
||||
"http://localhost:3001/api".to_string(),
|
||||
"http://localhost:3001/api".to_string(),
|
||||
"ws://localhost:3001".to_string(),
|
||||
"http://localhost:3001".to_string(),
|
||||
);
|
||||
TestBundle {
|
||||
urls,
|
||||
user,
|
||||
|
|
Loading…
Reference in New Issue