-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
Signed-off-by: Anthony M. Bonafide <AnthonyMBonafide@gmail.com>
- Loading branch information
There are no files selected for viewing
Large diffs are not rendered by default.
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
application_port: 8080 | ||
database: | ||
host: "127.0.0.1" | ||
port: 5432 | ||
username: "postgres" | ||
password: "password" | ||
database_name: "newsletter" | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
-- Add migration script here | ||
|
||
CREATE TABLE subscriptions( | ||
id UUID NOT NULL, | ||
PRIMARY KEY(id), | ||
emil TEXT NOT NULL UNIQUE, | ||
name TEXT NOT NULL, | ||
subscribed_at TIMESTAMPTZ NOT NULL | ||
); |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
#!/usr/bin/env bash | ||
|
||
set -x | ||
set -eo pipefail | ||
|
||
if ! [ -x "$(command -v psql)" ]; then | ||
echo >&2 "Error psql not installed." | ||
exit 1 | ||
fi | ||
|
||
if ! [ -x "$(command -v sqlx)" ]; then | ||
echo >&2 "Error sqlx not installed." | ||
echo >&2 "Use:" | ||
echo >&2 "cargo install --version="~0.7" sqlx-cli --no-default-features --features rustls,postgres" | ||
echo >&2 "to install it" | ||
exit 1 | ||
fi | ||
|
||
DB_USER="${POSTGRES_USER:=postgres}" | ||
DB_PASSWORD="${POSTGRES_PASSWORD:=password}" | ||
DB_NAME="${POSTGRES_NAME:=newsletter}" | ||
DB_PORT="${POSTGRES_PORT:=5432}" | ||
DB_HOST="${POSTGRES_HOST:=localhost}" | ||
|
||
if [[ -z "${SKIP_DOCKER}" ]]; then | ||
podman run -e POSTGRES_USER=${DB_USER} -e POSTGRES_PASSWORD=${DB_PASSWORD} -e POSTGRES_DB=${DB_NAME} -p "${DB_PORT}":5432 -d postgres postgres -N 1000 | ||
fi | ||
|
||
export PGPASSWORD="${DB_PASSWORD}" | ||
|
||
until psql -h "${DB_HOST}" -U "${DB_USER}" -p "${DB_PORT}" -d "postgres" -c '\q'; do | ||
echo >&2 "Postgress is still unavailable - sleeping" | ||
sleep 1 | ||
done | ||
|
||
echo >&2 "Postgres is up and running on port ${DB_PORT} - running migrations now!" | ||
|
||
DATABASE_URL=postgres://${DB_USER}:${DB_PASSWORD}@${DB_HOST}:${DB_PORT}/${DB_NAME} | ||
export DATABASE_URL | ||
|
||
sqlx database create | ||
sqlx migrate run | ||
|
||
echo >&2 "Postgres has been migrated, ready to go!" |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
#[derive(serde::Deserialize)] | ||
pub struct Settings{ | ||
pub database: DatabaseSettings, | ||
pub application_port: u16, | ||
} | ||
|
||
#[derive(serde::Deserialize)] | ||
pub struct DatabaseSettings{ | ||
pub username: String, | ||
pub password:String, | ||
pub port: u16, | ||
pub host: String, | ||
pub database_name:String, | ||
} | ||
|
||
impl DatabaseSettings { | ||
pub fn connection_string(&self) -> String { | ||
format!("postgres://{}:{}@{}:{}/{}", self.username, self.password, self.host, self.password, self.database_name) | ||
} | ||
} | ||
|
||
|
||
pub fn get_configuration() -> Result<Settings, config::ConfigError>{ | ||
let settings = config::Config::builder() | ||
.add_source(config::File::new("configuration.yaml", config::FileFormat::Yaml)) | ||
.build()?; | ||
|
||
settings.try_deserialize() | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,28 +1,7 @@ | ||
use std::net::TcpListener; | ||
pub mod configuration; | ||
pub mod routes; | ||
pub mod startup; | ||
|
||
use actix_web::{dev::Server, web, App, HttpResponse, HttpServer}; | ||
#[derive(serde::Deserialize, serde::Serialize)] | ||
struct FormData { | ||
name: String, | ||
email: String, | ||
} | ||
|
||
async fn health_check() -> HttpResponse { | ||
HttpResponse::Ok().finish() | ||
} | ||
|
||
async fn subscribe(_form: web::Form<FormData>) -> HttpResponse { | ||
HttpResponse::Ok().finish() | ||
} | ||
|
||
pub fn run(tcp_listener: TcpListener) -> Result<Server, std::io::Error> { | ||
let server = HttpServer::new(|| { | ||
App::new() | ||
.route("/health_check", web::get().to(health_check)) | ||
.route("/subscribe", web::post().to(subscribe)) | ||
}) | ||
.listen(tcp_listener)? | ||
.run(); | ||
|
||
Ok(server) | ||
} | ||
pub use startup::run; | ||
pub use configuration::get_configuration; |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,9 +1,11 @@ | ||
use std::net::TcpListener; | ||
|
||
use zero2prod::run; | ||
use zero2prod::{configuration::get_configuration, run}; | ||
|
||
#[tokio::main] | ||
async fn main() -> Result<(), std::io::Error> { | ||
let listener = TcpListener::bind("127.0.0.1:8080")?; | ||
let config = get_configuration().expect("Failed to read configuration"); | ||
let address = format!("127.0.0.1:{}", config.application_port); | ||
let listener = TcpListener::bind(address)?; | ||
run(listener)?.await | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
|
||
use actix_web::HttpResponse; | ||
pub async fn health_check() -> HttpResponse { | ||
HttpResponse::Ok().finish() | ||
} | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
|
||
mod health_check; | ||
mod subscriptions; | ||
|
||
pub use health_check::*; | ||
pub use subscriptions::*; | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
use std::net::TcpListener; | ||
Check warning on line 1 in src/routes/subscriptions.rs GitHub Actions / Check (1.76.0)
Check warning on line 1 in src/routes/subscriptions.rs GitHub Actions / Check (stable)
Check failure on line 1 in src/routes/subscriptions.rs GitHub Actions / Clippy (stable)
|
||
|
||
use actix_web::{dev::Server, web, App, HttpResponse, HttpServer}; | ||
Check warning on line 3 in src/routes/subscriptions.rs GitHub Actions / Check (1.76.0)
Check warning on line 3 in src/routes/subscriptions.rs GitHub Actions / Check (stable)
Check failure on line 3 in src/routes/subscriptions.rs GitHub Actions / Clippy (stable)
|
||
#[derive(serde::Deserialize, serde::Serialize)] | ||
pub struct FormData { | ||
name: String, | ||
email: String, | ||
} | ||
|
||
pub async fn subscribe(_form: web::Form<FormData>) -> HttpResponse { | ||
HttpResponse::Ok().finish() | ||
} | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
use std::net::TcpListener; | ||
use actix_web::{dev::Server, web, App, HttpServer}; | ||
use crate::routes::{health_check, subscribe}; | ||
|
||
pub fn run(tcp_listener: TcpListener) -> Result<Server, std::io::Error> { | ||
let server = HttpServer::new(|| { | ||
App::new() | ||
.route("/health_check", web::get().to(health_check)) | ||
.route("/subscribe", web::post().to(subscribe)) | ||
}) | ||
.listen(tcp_listener)? | ||
.run(); | ||
|
||
Ok(server) | ||
} |