diff --git a/build_release_unix.sh b/build_release_unix.sh
index 3b657f1..283acdf 100644
--- a/build_release_unix.sh
+++ b/build_release_unix.sh
@@ -3,7 +3,7 @@ echo "Creating output directory"
mkdir -p release/tmp
echo "Copying package files"
-cp -r web src migrations Cargo.toml Cargo.lock res/unix/Makefile release/tmp
+cp -r web docs/swagger src migrations Cargo.toml Cargo.lock res/unix/Makefile release/tmp
echo "Creating tarball"
POLARIS_VERSION=$(grep -m 1 ^version Cargo.toml | awk '{print $3}' | tr -d '"\r\n')
diff --git a/build_release_windows.ps1 b/build_release_windows.ps1
index 6fcaf82..7e55363 100644
--- a/build_release_windows.ps1
+++ b/build_release_windows.ps1
@@ -29,13 +29,18 @@ Copy-Item .\web\style .\release\tmp\web\style -recurse
Copy-Item .\web\tags .\release\tmp\web\tags -recurse
Copy-Item .\web\favicon.png .\release\tmp\web\
Copy-Item .\web\index.html .\release\tmp\web\
+Copy-Item .\docs\swagger .\release\tmp\swagger -recurse
""
"Creating installer"
heat dir .\release\tmp\web\ -ag -g1 -dr AppDataPolaris -cg WebUI -sfrag -var wix.WebUIDir -out .\release\tmp\web_ui_fragment.wxs
+heat dir .\release\tmp\swagger\ -ag -g1 -dr AppDataPolaris -cg SwaggerUI -sfrag -var wix.SwaggerUIDir -out .\release\tmp\swagger_ui_fragment.wxs
+
candle -wx -ext WixUtilExtension -arch x64 -out .\release\tmp\web_ui_fragment.wixobj .\release\tmp\web_ui_fragment.wxs
+candle -wx -ext WixUtilExtension -arch x64 -out .\release\tmp\swagger_ui_fragment.wixobj .\release\tmp\swagger_ui_fragment.wxs
candle -wx -ext WixUtilExtension -arch x64 -out .\release\tmp\installer.wixobj .\res\windows\installer\installer.wxs
-light -dWebUIDir=".\release\tmp\web" -wx -ext WixUtilExtension -ext WixUIExtension -spdb -sw1076 -sice:ICE38 -sice:ICE64 -out .\release\Polaris_$POLARIS_VERSION.msi .\release\tmp\installer.wixobj .\release\tmp\web_ui_fragment.wixobj
+
+light -dWebUIDir=".\release\tmp\web" -dSwaggerUIDir=".\release\tmp\swagger" -wx -ext WixUtilExtension -ext WixUIExtension -spdb -sw1076 -sice:ICE38 -sice:ICE64 -out .\release\Polaris_$POLARIS_VERSION.msi .\release\tmp\installer.wixobj .\release\tmp\web_ui_fragment.wixobj .\release\tmp\swagger_ui_fragment.wixobj
"Cleaning up"
Remove-Item -Recurse .\release\tmp
diff --git a/res/unix/Makefile b/res/unix/Makefile
index 893c28e..06f1d2b 100644
--- a/res/unix/Makefile
+++ b/res/unix/Makefile
@@ -11,6 +11,7 @@ install: build
install -d $(POLARIS_DATA_DIR)
install ./target/release/polaris $(POLARIS_BIN_DIR)
cp -r ./web $(POLARIS_DATA_DIR)
+ cp -r ./swagger $(POLARIS_DATA_DIR)
@echo "Polaris installation complete!"
clean:
diff --git a/res/windows/installer/installer.wxs b/res/windows/installer/installer.wxs
index 71f10c5..f6b6a63 100644
--- a/res/windows/installer/installer.wxs
+++ b/res/windows/installer/installer.wxs
@@ -52,6 +52,7 @@
+
diff --git a/src/api_tests.rs b/src/api_tests.rs
index a83ee4c..5f3077c 100644
--- a/src/api_tests.rs
+++ b/src/api_tests.rs
@@ -2,73 +2,21 @@ use rocket::http::hyper::header::*;
use rocket::http::uri::Uri;
use rocket::http::Status;
use rocket::local::Client;
-use std::fs;
-use std::ops::Deref;
-use std::path::PathBuf;
-use std::sync::Arc;
use std::{thread, time};
use crate::api;
use crate::config;
-use crate::db;
use crate::ddns;
use crate::index;
-use crate::server;
use crate::vfs;
+use crate::test::get_test_environment;
+
const TEST_USERNAME: &str = "test_user";
const TEST_PASSWORD: &str = "test_password";
const TEST_MOUNT_NAME: &str = "collection";
const TEST_MOUNT_SOURCE: &str = "test/collection";
-struct TestEnvironment {
- pub client: Client,
- command_sender: Arc,
- db: Arc,
-}
-
-impl TestEnvironment {
- pub fn update_index(&self) {
- index::update(self.db.deref()).unwrap();
- }
-}
-
-impl Drop for TestEnvironment {
- fn drop(&mut self) {
- self.command_sender.deref().exit().unwrap();
- }
-}
-
-fn get_test_environment(db_name: &str) -> TestEnvironment {
- let mut db_path = PathBuf::new();
- db_path.push("test");
- db_path.push(db_name);
- if db_path.exists() {
- fs::remove_file(&db_path).unwrap();
- }
-
- let db = Arc::new(db::DB::new(&db_path).unwrap());
-
- let web_dir_path = PathBuf::from("web");
- let command_sender = index::init(db.clone());
-
- let server = server::get_server(
- 5050,
- "/",
- "/api",
- &web_dir_path,
- db.clone(),
- command_sender.clone(),
- )
- .unwrap();
- let client = Client::new(server).unwrap();
- TestEnvironment {
- client,
- command_sender,
- db,
- }
-}
-
fn complete_initial_setup(client: &Client) {
let configuration = config::Config {
album_art_pattern: None,
diff --git a/src/main.rs b/src/main.rs
index c9a8cb2..df77e89 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -71,11 +71,15 @@ mod metadata;
mod playlist;
mod serve;
mod server;
+mod swagger;
+#[cfg(test)]
+mod test;
mod thumbnails;
mod ui;
mod user;
mod utils;
mod vfs;
+mod web;
static LOG_CONFIG: simplelog::Config = simplelog::Config {
time: Some(Level::Error),
@@ -149,6 +153,7 @@ fn run() -> Result<()> {
options.optopt("p", "port", "set polaris to run on a custom port", "PORT");
options.optopt("d", "database", "set the path to index database", "FILE");
options.optopt("w", "web", "set the path to web client files", "DIRECTORY");
+ options.optopt("s", "swagger", "set the path to swagger files", "DIRECTORY");
options.optopt(
"l",
"log",
@@ -220,10 +225,10 @@ fn run() -> Result<()> {
// API mount target
let prefix_url = config.prefix_url.unwrap_or_else(|| "".to_string());
- let api_url = format!("{}/api", &prefix_url);
+ let api_url = format!("/{}api", &prefix_url);
info!("Mounting API on {}", api_url);
- // Static files mount target
+ // Web client mount target
let web_dir_name = matches.opt_str("w");
let mut default_web_dir = utils::get_data_root()?;
default_web_dir.push("web");
@@ -231,8 +236,19 @@ fn run() -> Result<()> {
.map(|n| Path::new(n.as_str()).to_path_buf())
.unwrap_or(default_web_dir);
info!("Static files location is {}", web_dir_path.display());
- let static_url = format!("/{}", &prefix_url);
- info!("Mounting static files on {}", static_url);
+ let web_url = format!("/{}", &prefix_url);
+ info!("Mounting web client files on {}", web_url);
+
+ // Swagger files mount target
+ let swagger_dir_name = matches.opt_str("s");
+ let mut default_swagger_dir = utils::get_data_root()?;
+ default_swagger_dir.push("swagger");
+ let swagger_dir_path = swagger_dir_name
+ .map(|n| Path::new(n.as_str()).to_path_buf())
+ .unwrap_or(default_swagger_dir);
+ info!("Swagger files location is {}", swagger_dir_path.display());
+ let swagger_url = format!("/{}swagger", &prefix_url);
+ info!("Mounting swagger files on {}", swagger_url);
// Start server
info!("Starting up server");
@@ -244,9 +260,11 @@ fn run() -> Result<()> {
let server = server::get_server(
port,
- &static_url,
&api_url,
+ &web_url,
&web_dir_path,
+ &swagger_url,
+ &swagger_dir_path,
db.clone(),
command_sender,
)?;
diff --git a/src/server.rs b/src/server.rs
index f0ccd3a..cdaf255 100644
--- a/src/server.rs
+++ b/src/server.rs
@@ -1,28 +1,41 @@
use rocket;
-use rocket_contrib::serve::StaticFiles;
use std::path::PathBuf;
use std::sync::Arc;
-use crate::api;
use crate::db::DB;
use crate::errors;
use crate::index::CommandSender;
+pub struct StaticDirs {
+ pub web_dir_path: PathBuf,
+ pub swagger_dir_path: PathBuf,
+}
+
pub fn get_server(
port: u16,
- static_url: &str,
api_url: &str,
+ web_url: &str,
web_dir_path: &PathBuf,
+ swagger_url: &str,
+ swagger_dir_path: &PathBuf,
db: Arc,
command_sender: Arc,
) -> Result {
+
let config = rocket::Config::build(rocket::config::Environment::Production)
.port(port)
.finalize()?;
+ let static_dirs = Arc::new(StaticDirs {
+ web_dir_path: web_dir_path.to_path_buf(),
+ swagger_dir_path: swagger_dir_path.to_path_buf(),
+ });
+
Ok(rocket::custom(config)
.manage(db)
.manage(command_sender)
- .mount(&static_url, StaticFiles::from(web_dir_path))
- .mount(&api_url, api::get_routes()))
+ .manage(static_dirs)
+ .mount(&swagger_url, crate::swagger::get_routes())
+ .mount(&web_url, crate::web::get_routes())
+ .mount(&api_url, crate::api::get_routes()))
}
diff --git a/src/swagger.rs b/src/swagger.rs
new file mode 100644
index 0000000..6a47a45
--- /dev/null
+++ b/src/swagger.rs
@@ -0,0 +1,38 @@
+use rocket::response::NamedFile;
+use rocket::State;
+use std::io;
+use std::path::PathBuf;
+use std::sync::Arc;
+
+use crate::server::StaticDirs;
+
+pub fn get_routes() -> Vec {
+ routes![
+ index,
+ files,
+ ]
+}
+
+#[get("/", rank = 9)]
+fn index(static_dirs: State>) -> io::Result {
+ let mut path = static_dirs.swagger_dir_path.clone();
+ path.push("index.html");
+ NamedFile::open(path)
+}
+
+#[get("/", rank = 9)]
+fn files(static_dirs: State>, file: PathBuf) -> Option {
+ let path = static_dirs.swagger_dir_path.clone().join(file.clone());
+ NamedFile::open(path).ok()
+}
+
+#[test]
+fn test_index() {
+ use rocket::http::Status;
+ use crate::test::get_test_environment;
+
+ let env = get_test_environment("swagger_index.sqlite");
+ let client = &env.client;
+ let response = client.get("/swagger").dispatch();
+ assert_eq!(response.status(), Status::Ok);
+}
diff --git a/src/test.rs b/src/test.rs
new file mode 100644
index 0000000..668de13
--- /dev/null
+++ b/src/test.rs
@@ -0,0 +1,62 @@
+use rocket;
+use rocket::local::Client;
+use std::fs;
+use std::ops::Deref;
+use std::path::PathBuf;
+use std::sync::Arc;
+
+use crate::db::DB;
+use crate::index;
+use crate::server;
+
+pub struct TestEnvironment {
+ pub client: Client,
+ command_sender: Arc,
+ db: Arc,
+}
+
+impl TestEnvironment {
+ pub fn update_index(&self) {
+ index::update(self.db.deref()).unwrap();
+ }
+}
+
+impl Drop for TestEnvironment {
+ fn drop(&mut self) {
+ self.command_sender.deref().exit().unwrap();
+ }
+}
+
+pub fn get_test_environment(db_name: &str) -> TestEnvironment {
+ let mut db_path = PathBuf::new();
+ db_path.push("test");
+ db_path.push(db_name);
+ if db_path.exists() {
+ fs::remove_file(&db_path).unwrap();
+ }
+
+ let db = Arc::new(DB::new(&db_path).unwrap());
+
+ let web_dir_path = PathBuf::from("web");
+ let mut swagger_dir_path = PathBuf::from("docs");
+ swagger_dir_path.push("swagger");
+ let command_sender = index::init(db.clone());
+
+ let server = server::get_server(
+ 5050,
+ "/api",
+ "/",
+ &web_dir_path,
+ "/swagger",
+ &swagger_dir_path,
+ db.clone(),
+ command_sender.clone(),
+ )
+ .unwrap();
+ let client = Client::new(server).unwrap();
+ TestEnvironment {
+ client,
+ command_sender,
+ db,
+ }
+}
diff --git a/src/web.rs b/src/web.rs
new file mode 100644
index 0000000..b935b71
--- /dev/null
+++ b/src/web.rs
@@ -0,0 +1,38 @@
+use rocket::response::NamedFile;
+use rocket::State;
+use std::io;
+use std::path::PathBuf;
+use std::sync::Arc;
+
+use crate::server::StaticDirs;
+
+pub fn get_routes() -> Vec {
+ routes![
+ index,
+ files,
+ ]
+}
+
+#[get("/", rank = 10)]
+fn index(static_dirs: State>) -> io::Result {
+ let mut path = static_dirs.web_dir_path.clone();
+ path.push("index.html");
+ NamedFile::open(path)
+}
+
+#[get("/", rank = 10)]
+fn files(static_dirs: State>, file: PathBuf) -> Option {
+ let path = static_dirs.web_dir_path.clone().join(file.clone());
+ NamedFile::open(path).ok()
+}
+
+#[test]
+fn test_index() {
+ use rocket::http::Status;
+ use crate::test::get_test_environment;
+
+ let env = get_test_environment("web_index.sqlite");
+ let client = &env.client;
+ let response = client.get("/").dispatch();
+ assert_eq!(response.status(), Status::Ok);
+}