|
4 | 4 |
|
5 | 5 | use std::path::PathBuf; |
6 | 6 |
|
7 | | -use clap::Parser; |
8 | 7 | use hmac::{digest::InvalidLength, Hmac, Mac}; |
9 | 8 | use sha2::Sha256; |
10 | 9 |
|
11 | 10 | use crate::pathutils::Paths; |
12 | 11 |
|
13 | | -#[derive(Parser, Clone)] |
| 12 | +#[derive(Clone)] |
14 | 13 | pub struct EnvVars { |
15 | 14 | // Database |
16 | | - #[arg(env)] |
17 | 15 | /// Database name |
18 | 16 | pub db_name: String, |
19 | | - #[arg(env)] |
20 | 17 | /// Database hostname |
21 | 18 | pub db_host: String, |
22 | | - #[arg(env)] |
23 | 19 | /// Database port |
24 | 20 | pub db_port: String, |
25 | | - #[arg(env)] |
26 | 21 | /// Database username |
27 | 22 | pub db_user: String, |
28 | | - #[arg(env)] |
29 | 23 | /// Database password |
30 | 24 | pub db_password: String, |
31 | 25 |
|
32 | 26 | // Auth |
33 | | - #[arg(env)] |
34 | 27 | /// OAuth app client id (public token) |
35 | 28 | pub gh_client_id: String, |
36 | | - #[arg(env)] |
37 | 29 | /// An org admin's Github token (with the `read:org` permission) |
38 | 30 | pub gh_org_admin_token: String, |
39 | | - #[arg(env)] |
40 | 31 | /// JWT encryption secret (make it a long, randomized string) |
41 | 32 | jwt_secret: String, |
42 | | - #[arg(env)] |
43 | 33 | /// OAuth app client secret |
44 | 34 | pub gh_client_secret: String, |
45 | | - #[arg(env, default_value = "")] |
46 | 35 | /// Github organization name |
47 | 36 | pub gh_org_name: String, |
48 | | - #[arg(env, default_value = "")] |
49 | 37 | /// Github organization team slug (this team has access to admin dashboard) |
50 | 38 | pub gh_org_team_slug: String, |
51 | | - #[arg(env, default_value = "")] |
52 | 39 | /// The usernames of the admins (additional to org team members, comma separated) |
53 | 40 | pub gh_admin_usernames: String, |
54 | | - #[arg(env, default_value = "")] |
55 | 41 | /// URL of Slack webhook for sending notifications |
56 | 42 | pub slack_webhook_url: String, |
57 | 43 |
|
58 | 44 | // Other configs |
59 | | - #[arg(env, default_value = "10")] |
60 | 45 | /// Maximum number of papers that can be uploaded at a time |
61 | 46 | pub max_upload_limit: usize, |
62 | | - #[arg(env, default_value = "./log/application.log")] |
63 | 47 | /// Location where logs are stored |
64 | 48 | pub log_location: PathBuf, |
65 | 49 |
|
66 | 50 | // Paths |
67 | | - #[arg(env, default_value = "https://static.metakgp.org")] |
68 | 51 | /// The URL of the static files server (odin's vault) |
69 | 52 | static_files_url: String, |
70 | | - #[arg(env, default_value = "/srv/static")] |
71 | 53 | /// The path where static files are served from |
72 | 54 | static_file_storage_location: PathBuf, |
73 | | - #[arg(env, default_value = "/iqps/uploaded")] |
74 | 55 | /// The path where uploaded papers are stored temporarily, relative to the `static_file_storage_location` |
75 | 56 | uploaded_qps_path: PathBuf, |
76 | | - #[arg(env, default_value = "/peqp/qp")] |
77 | 57 | /// The path where library papers (scrapped) are stored, relative to the `static_file_storage_location` |
78 | 58 | library_qps_path: PathBuf, |
79 | 59 |
|
80 | 60 | // Server |
81 | | - #[arg(env, default_value = "8080")] |
82 | 61 | /// The port the server listens on |
83 | 62 | pub server_port: i32, |
84 | 63 |
|
85 | 64 | // CORS |
86 | | - #[arg(env, default_value = "https://qp.metakgp.org,http://localhost:5173")] |
87 | 65 | /// List of origins allowed (as a list of values separated by commas `origin1, origin2`) |
88 | 66 | pub cors_allowed_origins: String, |
89 | 67 |
|
90 | | - #[arg(skip)] |
91 | 68 | /// All paths must be handled using this |
92 | 69 | pub paths: Paths, |
93 | 70 | } |
94 | 71 |
|
95 | | -impl EnvVars { |
| 72 | +impl EnvVars { |
| 73 | + /// Parses the environment variables into the struct |
| 74 | + pub fn parse() -> Result<Self, Box<dyn std::error::Error>> { |
| 75 | + let db_name = std::env::var("DB_NAME")?; |
| 76 | + let db_host = std::env::var("DB_HOST")?; |
| 77 | + let db_port = std::env::var("DB_PORT")?; |
| 78 | + let db_user = std::env::var("DB_USER")?; |
| 79 | + let db_password = std::env::var("DB_PASSWORD")?; |
| 80 | + let gh_client_id = std::env::var("GH_CLIENT_ID")?; |
| 81 | + let gh_org_admin_token = std::env::var("GH_ORG_ADMIN_TOKEN")?; |
| 82 | + let jwt_secret = std::env::var("JWT_SECRET")?; |
| 83 | + let gh_client_secret = std::env::var("GH_CLIENT_SECRET")?; |
| 84 | + let gh_org_name = std::env::var("GH_ORG_NAME").unwrap_or_default(); |
| 85 | + let gh_org_team_slug = std::env::var("GH_ORG_TEAM_SLUG").unwrap_or_default(); |
| 86 | + let gh_admin_usernames = std::env::var("GH_ADMIN_USERNAMES").unwrap_or_default(); |
| 87 | + let slack_webhook_url = std::env::var("SLACK_WEBHOOK_URL").unwrap_or_default(); |
| 88 | + let max_upload_limit = std::env::var("MAX_UPLOAD_LIMIT") |
| 89 | + .unwrap_or_else(|_| "10".to_string()) |
| 90 | + .parse::<usize>()?; |
| 91 | + let log_location = std::env::var("LOG_LOCATION") |
| 92 | + .unwrap_or_else(|_| "./log/application.log".to_string()) |
| 93 | + .into(); |
| 94 | + let static_files_url = std::env::var("STATIC_FILES_URL") |
| 95 | + .unwrap_or_else(|_| "https://static.metakgp.org".to_string()); |
| 96 | + let static_file_storage_location = std::env::var("STATIC_FILE_STORAGE_LOCATION") |
| 97 | + .unwrap_or_else(|_| "/srv/static".to_string()) |
| 98 | + .into(); |
| 99 | + let uploaded_qps_path = std::env::var("UPLOADED_QPS_PATH") |
| 100 | + .unwrap_or_else(|_| "/iqps/uploaded".to_string()) |
| 101 | + .into(); |
| 102 | + let library_qps_path = std::env::var("LIBRARY_QPS_PATH") |
| 103 | + .unwrap_or_else(|_| "/peqp/qp".to_string()) |
| 104 | + .into(); |
| 105 | + let server_port = std::env::var("SERVER_PORT") |
| 106 | + .unwrap_or_else(|_| "8080".to_string()) |
| 107 | + .parse::<i32>()?; |
| 108 | + let cors_allowed_origins = std::env::var("CORS_ALLOWED_ORIGINS") |
| 109 | + .unwrap_or_else(|_| "https://qp.metakgp.org,http://localhost:5173".to_string()); |
| 110 | + Ok(Self { |
| 111 | + db_name, |
| 112 | + db_host, |
| 113 | + db_port, |
| 114 | + db_user, |
| 115 | + db_password, |
| 116 | + gh_client_id, |
| 117 | + gh_org_admin_token, |
| 118 | + jwt_secret, |
| 119 | + gh_client_secret, |
| 120 | + gh_org_name, |
| 121 | + gh_org_team_slug, |
| 122 | + gh_admin_usernames, |
| 123 | + slack_webhook_url, |
| 124 | + max_upload_limit, |
| 125 | + log_location, |
| 126 | + static_files_url, |
| 127 | + static_file_storage_location, |
| 128 | + uploaded_qps_path, |
| 129 | + library_qps_path, |
| 130 | + server_port, |
| 131 | + cors_allowed_origins, |
| 132 | + paths: Paths::default(), |
| 133 | + }) |
| 134 | + } |
| 135 | + |
96 | 136 | /// Processes the environment variables after reading. |
97 | 137 | pub fn process(mut self) -> Result<Self, Box<dyn std::error::Error>> { |
98 | 138 | self.paths = Paths::new( |
|
0 commit comments