1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
use std::{
    path::PathBuf,
    sync::Arc,
};

use log::info;
use failure::Fail;

use crate::{
    project::{Project, ProjectLoadFuzzyError},
    web::Server,
    live_session::LiveSession,
};

const DEFAULT_PORT: u16 = 34872;

#[derive(Debug)]
pub struct ServeOptions {
    pub fuzzy_project_path: PathBuf,
    pub port: Option<u16>,
}

#[derive(Debug, Fail)]
pub enum ServeError {
   #[fail(display = "Project load error: {}", _0)]
   ProjectLoadError(#[fail(cause)] ProjectLoadFuzzyError),
}

impl_from!(ServeError {
    ProjectLoadFuzzyError => ProjectLoadError,
});

pub fn serve(options: &ServeOptions) -> Result<(), ServeError> {
    info!("Looking for project at {}", options.fuzzy_project_path.display());

    let project = Arc::new(Project::load_fuzzy(&options.fuzzy_project_path)?);

    info!("Found project at {}", project.file_location.display());
    info!("Using project {:#?}", project);

    let live_session = Arc::new(LiveSession::new(Arc::clone(&project)).unwrap());
    let server = Server::new(Arc::clone(&live_session));

    let port = options.port
        .or(project.serve_port)
        .unwrap_or(DEFAULT_PORT);

    println!("Rojo server listening on port {}", port);

    server.listen(port);

    Ok(())
}