Advertisement
Guest User

Untitled

a guest
Feb 22nd, 2017
98
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Rust 3.92 KB | None | 0 0
  1. extern crate notify;
  2. extern crate hyper;
  3. extern crate regex_env;
  4.  
  5. use notify::{RecommendedWatcher, Watcher, RecursiveMode};
  6. use std::sync::mpsc::{channel, Sender, Receiver};
  7. use notify::DebouncedEvent;
  8. use std::time::Duration;
  9.  
  10. use std::io::BufWriter;
  11. use std::io::prelude::*;
  12. use std::fs::File;
  13.  
  14. use std::path::Path;
  15. use std::path::PathBuf;
  16.  
  17. use hyper::Client;
  18.  
  19. use regex_env::env;
  20.  
  21. fn main() {
  22.     let (tx, rx) = channel();
  23.  
  24.     if let Err(e) = setup(tx) {
  25.         println!("{}", e);
  26.         std::process::exit(1);
  27.     }
  28.  
  29.     println!("Waiting for changes to /etc/letsencrypt/live... Hit Ctrl-C to stop.");
  30.  
  31.     handle(rx);
  32. }
  33.  
  34. fn setup(tx: Sender<DebouncedEvent>) -> Result<(), String> {
  35.     let mut watcher: RecommendedWatcher = match Watcher::new(tx, Duration::from_secs(1)) {
  36.         Ok(i) => i,
  37.         Err(e) => {
  38.             let msg = format!("Failed to initialise notify ({})", e);
  39.             return Err(msg);
  40.         }
  41.     };
  42.  
  43.     if let Err(e) = watcher.watch("/etc/letsencrypt/live", RecursiveMode::Recursive) {
  44.         let msg = format!("Something went wrong watching the folder /etc/letsencrypt/live: {}", e);
  45.         return Err(msg);
  46.     };
  47.  
  48.     Ok(())
  49. }
  50.  
  51. fn handle(rx: Receiver<DebouncedEvent>) {
  52.     while let Ok(event) = rx.recv() {
  53.         let _ = match event {
  54.             DebouncedEvent::Create(file) => created(file),
  55.             DebouncedEvent::Write(file) => created(file),
  56.             DebouncedEvent::Remove(file) => removed(file),
  57.             DebouncedEvent::Rename(from, to) => renamed(from, to),
  58.             DebouncedEvent::Chmod(file) => created(file),
  59.             _ => continue
  60.         };
  61.     }
  62. }
  63.  
  64. fn created(p: PathBuf) {
  65.     if Path::new(&p).is_dir() && Path::new(&p.join("privkey.pem")).is_file() && Path::new(&p.join("fullchain.pem")).is_file() {
  66.         let paths = vec![
  67.             p.join("privkey.pem"),
  68.             p.join("fullchain.pem"),
  69.         ];
  70.  
  71.         if let Ok(site_name) = p.strip_prefix("/etc/letsencrypt/live") {
  72.             let mut buffer = Vec::new();
  73.  
  74.             for path in paths {
  75.                 let mut file = File::open(path).expect("Unable to open file");
  76.  
  77.                 let _ = file.read_to_end(&mut buffer);
  78.             };
  79.  
  80.             if let Some(name) = site_name.to_str() {
  81.                 let output_file = format!("/var/certs/letsencrypt/{}.pem", name);
  82.  
  83.                 if !Path::new("/var/certs/letsencrypt").is_dir() {
  84.                     let _ = match std::fs::create_dir("/var/certs/letsencrypt") {
  85.                         Err(e) => {
  86.                             println!("Error creating the directory /var/certs/letsencrypt: {}", e);
  87.                         },
  88.                         Ok(t) => t,
  89.                     };
  90.                 }
  91.  
  92.                 let output = File::create(output_file).expect("Unable to create file");
  93.  
  94.                 let mut f = BufWriter::new(output);
  95.  
  96.                 f.write_all(&buffer).expect("Unable to write data");
  97.             }
  98.         }
  99.     }
  100.  
  101.     notify();
  102. }
  103.  
  104. fn renamed(from: PathBuf, to: PathBuf) {
  105.     created(to);
  106.     removed(from);
  107. }
  108.  
  109. fn removed(p: PathBuf) {
  110.     if let Ok(site_name) = p.strip_prefix("/etc/letsencrypt/live") {
  111.         if let Some(name) = site_name.to_str() {
  112.             let output_file = format!("/var/certs/letsencrypt/{}.pem", name);
  113.  
  114.             if Path::new(&output_file).is_file() {
  115.                 let _ = std::fs::remove_file(output_file);
  116.             }
  117.         }
  118.     }
  119.  
  120.     notify();
  121. }
  122.  
  123. fn notify() {
  124.     if let Some(ip) = env(r"^loadbalancer.ip=(.*)$", "/var/www/config/global/.env") {
  125.         let response = Client::new().head(&format!("http://{}:9999", ip)).send();
  126.  
  127.         match response {
  128.             Ok(res) => println!("Response: {}", res.status),
  129.             Err(e) => println!("Error: {}", e),
  130.         }
  131.     } else {
  132.         println!("Unable to notify the load balancer, IP address not found in global env file");
  133.     }
  134. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement