parent
f41e0caa74
commit
82d7ca48bb
5 changed files with 104 additions and 7 deletions
|
@ -426,7 +426,9 @@ pub mod username {
|
|||
pub mod ssh {
|
||||
use super::*;
|
||||
use crate::AccountsSSH;
|
||||
use ssh_key::AuthorizedKeys;
|
||||
use ldap3::Mod;
|
||||
use ssh_key::{AuthorizedKeys, SshSig};
|
||||
use std::collections::HashSet;
|
||||
use std::fs;
|
||||
|
||||
// this is for a legacy member who has forgotten their account password to be able to set an email.
|
||||
|
@ -479,7 +481,7 @@ pub mod ssh {
|
|||
|
||||
// check if there is ane listing entry, use that auth if exists
|
||||
if let Ok(result) = sqlx::query_as::<_, AccountsSSH>(
|
||||
r#"
|
||||
r#"
|
||||
SELECT *
|
||||
FROM accounts_ssh
|
||||
WHERE user == ?
|
||||
|
@ -495,7 +497,7 @@ pub mod ssh {
|
|||
// not in db, generate auth and save
|
||||
let auth = random_string(50);
|
||||
if sqlx::query_as::<_, AccountsSSH>(
|
||||
"
|
||||
"
|
||||
INSERT OR REPLACE INTO accounts_ssh (user, auth_code, email)
|
||||
VALUES (?1, ?2, ?3)
|
||||
",
|
||||
|
@ -514,4 +516,96 @@ pub mod ssh {
|
|||
// return the full thing
|
||||
Ok(json!({"result": "success","success": { "auth": auth,"keys": keys }}).into())
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize)]
|
||||
struct RequestVerify {
|
||||
user: String,
|
||||
auth_signed: String,
|
||||
}
|
||||
|
||||
// echo "auth code" | ssh-keygen -Y sign -n file -f /path/to/key
|
||||
pub async fn verify(mut req: Request<State>) -> tide::Result {
|
||||
let RequestVerify {
|
||||
user,
|
||||
auth_signed,
|
||||
} = req.body_json().await?;
|
||||
|
||||
let db = &req.state().db;
|
||||
let config = &req.state().config;
|
||||
let details = if let Ok(result) = sqlx::query_as::<_, AccountsSSH>(
|
||||
r#"
|
||||
SELECT *
|
||||
FROM accounts_ssh
|
||||
WHERE user == ?
|
||||
"#,
|
||||
)
|
||||
.bind(&user)
|
||||
.fetch_one(db)
|
||||
.await
|
||||
{
|
||||
result
|
||||
} else {
|
||||
return Ok(json!({ "result": "error"}).into());
|
||||
};
|
||||
|
||||
// check if <root>/<user>/.ssh/authorized_keys exists
|
||||
//let root = "/skynet_old";
|
||||
let root = ".";
|
||||
let path = format!("{}/{}/.ssh/authorized_keys", root, user);
|
||||
|
||||
let sig = match SshSig::from_pem(auth_signed) {
|
||||
Ok(x) => x,
|
||||
Err(_) => {
|
||||
return Ok(json!({ "result": "error", "error": "Incorrect signed format"}).into());
|
||||
}
|
||||
};
|
||||
|
||||
// when ye echo it adds a newline to the end of the "file", need to duplicate it here.
|
||||
let msg_tmp = format!("{}\n", details.auth_code);
|
||||
let msg = msg_tmp.as_bytes();
|
||||
|
||||
let mut valid = false;
|
||||
if fs::read_to_string(&path).is_ok() {
|
||||
if let Ok(x) = AuthorizedKeys::read_file(path) {
|
||||
for entry in x {
|
||||
let key = entry.public_key();
|
||||
match key.verify("file", msg, &sig) {
|
||||
Ok(_) => {
|
||||
valid = true;
|
||||
break;
|
||||
}
|
||||
Err(_) => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if !valid {
|
||||
return Ok(json!({"result": "error", "error": "no valid key"}).into());
|
||||
}
|
||||
|
||||
// add to ldap
|
||||
let mut ldap = LdapConn::new(&config.ldap_host)?;
|
||||
ldap.simple_bind(&config.ldap_admin, &config.ldap_admin_pw)?.success()?;
|
||||
|
||||
let mods = vec![Mod::Replace(String::from("mail"), HashSet::from([details.email]))];
|
||||
|
||||
let dn = format!("uid={},ou=users,dc=skynet,dc=ie", &user);
|
||||
ldap.modify(&dn, mods)?.success()?;
|
||||
ldap.unbind()?;
|
||||
|
||||
// delete from tmp
|
||||
sqlx::query_as::<_, AccountsSSH>(
|
||||
r#"
|
||||
DELETE FROM accounts_ssh
|
||||
WHERE user == ?
|
||||
"#,
|
||||
)
|
||||
.bind(&user)
|
||||
.fetch_optional(db)
|
||||
.await?;
|
||||
|
||||
// return the full thing
|
||||
Ok(json!({"result": "success", "success": "key valid"}).into())
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue