diff --git a/Dockerfile b/Dockerfile
new file mode 100644
index 0000000..59e0bbe
--- /dev/null
+++ b/Dockerfile
@@ -0,0 +1,27 @@
+FROM microsoft/dotnet:1.1.0-sdk-projectjson
+
+RUN apt-get update
+RUN wget -qO- https://deb.nodesource.com/setup_4.x | bash -
+RUN apt-get install -y build-essential nodejs
+
+
+COPY . /app
+
+
+WORKDIR /app/src/LanBackup.WebApp
+RUN ["dotnet", "restore"]
+
+WORKDIR /app/src/LanBackup.DataCore
+RUN ["dotnet", "restore"]
+
+WORKDIR /app/src/LanBackup.ModelsCore
+RUN ["dotnet", "restore"]
+
+
+
+WORKDIR /app/src/LanBackup.WebApp
+RUN ["dotnet", "build"]
+
+EXPOSE 5000/tcp
+
+CMD ["dotnet", "run", "--server.urls", "http://*:5000"]
diff --git a/LanBackup.sln b/LanBackup.sln
new file mode 100644
index 0000000..bb42bd5
--- /dev/null
+++ b/LanBackup.sln
@@ -0,0 +1,108 @@
+
+Microsoft Visual Studio Solution File, Format Version 12.00
+# Visual Studio 14
+VisualStudioVersion = 14.0.25420.1
+MinimumVisualStudioVersion = 10.0.40219.1
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{F99F86DB-318D-4D40-803F-B6C0BC10A222}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{555C50F9-9FB8-4846-9043-759A63B67965}"
+ ProjectSection(SolutionItems) = preProject
+ Dockerfile = Dockerfile
+ global.json = global.json
+ NuGet.config = NuGet.config
+ Readme.md = Readme.md
+ EndProjectSection
+EndProject
+Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "LanBackup.ModelsCore", "src\LanBackup.ModelsCore\LanBackup.ModelsCore.xproj", "{CDC21836-C111-4DB4-96C1-A37128DF2127}"
+EndProject
+Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "LanBackup.DataCore", "src\LanBackup.DataCore\LanBackup.DataCore.xproj", "{B4144721-0F2C-4750-ABA3-5238490A71FF}"
+EndProject
+Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "LanBackup.WebApp", "src\LanBackup.WebApp\LanBackup.WebApp.xproj", "{315453E2-9C17-46F3-9CCC-2FC0688342C2}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "LanBackupAgent", "LanBackupAgent", "{9EF05F3D-E711-452B-885A-EDA277B36D20}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "LanBackupServices", "LanBackupServices", "{067F2B55-97D6-46C0-AD33-F7F56BD06F40}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "test", "test", "{18488CFA-6E13-4F3B-A5B4-74958B8BB813}"
+EndProject
+Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "LanBackup.WebAppSpa.Tests", "test\LanBackup.WebAppSpa.Tests\LanBackup.WebAppSpa.Tests.xproj", "{F124A292-3711-4FD1-9C54-63D5CF613D37}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "LanBackupAgent", "src\LanBackupAgent\LanBackupAgent.csproj", "{CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "_stylecop", "_stylecop", "{3F8C9C01-BB62-433C-92E6-20439354352A}"
+ ProjectSection(SolutionItems) = preProject
+ misc\_stylecop\stylecop.json = misc\_stylecop\stylecop.json
+ misc\_stylecop\StyleCopeRules.ruleset = misc\_stylecop\StyleCopeRules.ruleset
+ EndProjectSection
+EndProject
+Project("{930C7802-8A8C-48F9-8165-68863BCCD9DD}") = "LanBackupAgentSetup", "src\LanBackupAgentSetup\LanBackupAgentSetup.wixproj", "{F530020F-0DF2-49B8-9401-1C1C282077F5}"
+EndProject
+Global
+ GlobalSection(SolutionConfigurationPlatforms) = preSolution
+ Debug|Any CPU = Debug|Any CPU
+ Debug|x86 = Debug|x86
+ Release|Any CPU = Release|Any CPU
+ Release|x86 = Release|x86
+ EndGlobalSection
+ GlobalSection(ProjectConfigurationPlatforms) = postSolution
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Debug|x86.Build.0 = Debug|Any CPU
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Release|Any CPU.Build.0 = Release|Any CPU
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Release|x86.ActiveCfg = Release|Any CPU
+ {CDC21836-C111-4DB4-96C1-A37128DF2127}.Release|x86.Build.0 = Release|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Debug|x86.Build.0 = Debug|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Release|Any CPU.Build.0 = Release|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Release|x86.ActiveCfg = Release|Any CPU
+ {B4144721-0F2C-4750-ABA3-5238490A71FF}.Release|x86.Build.0 = Release|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Debug|x86.Build.0 = Debug|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Release|Any CPU.Build.0 = Release|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Release|x86.ActiveCfg = Release|Any CPU
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2}.Release|x86.Build.0 = Release|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Debug|x86.Build.0 = Debug|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Release|Any CPU.Build.0 = Release|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Release|x86.ActiveCfg = Release|Any CPU
+ {F124A292-3711-4FD1-9C54-63D5CF613D37}.Release|x86.Build.0 = Release|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Debug|x86.Build.0 = Debug|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Release|Any CPU.Build.0 = Release|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Release|x86.ActiveCfg = Release|Any CPU
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C}.Release|x86.Build.0 = Release|Any CPU
+ {F530020F-0DF2-49B8-9401-1C1C282077F5}.Debug|Any CPU.ActiveCfg = Debug|x86
+ {F530020F-0DF2-49B8-9401-1C1C282077F5}.Debug|x86.ActiveCfg = Debug|x86
+ {F530020F-0DF2-49B8-9401-1C1C282077F5}.Debug|x86.Build.0 = Debug|x86
+ {F530020F-0DF2-49B8-9401-1C1C282077F5}.Release|Any CPU.ActiveCfg = Release|x86
+ {F530020F-0DF2-49B8-9401-1C1C282077F5}.Release|x86.ActiveCfg = Release|x86
+ {F530020F-0DF2-49B8-9401-1C1C282077F5}.Release|x86.Build.0 = Release|x86
+ EndGlobalSection
+ GlobalSection(SolutionProperties) = preSolution
+ HideSolutionNode = FALSE
+ EndGlobalSection
+ GlobalSection(NestedProjects) = preSolution
+ {CDC21836-C111-4DB4-96C1-A37128DF2127} = {067F2B55-97D6-46C0-AD33-F7F56BD06F40}
+ {B4144721-0F2C-4750-ABA3-5238490A71FF} = {067F2B55-97D6-46C0-AD33-F7F56BD06F40}
+ {315453E2-9C17-46F3-9CCC-2FC0688342C2} = {067F2B55-97D6-46C0-AD33-F7F56BD06F40}
+ {9EF05F3D-E711-452B-885A-EDA277B36D20} = {F99F86DB-318D-4D40-803F-B6C0BC10A222}
+ {067F2B55-97D6-46C0-AD33-F7F56BD06F40} = {F99F86DB-318D-4D40-803F-B6C0BC10A222}
+ {F124A292-3711-4FD1-9C54-63D5CF613D37} = {18488CFA-6E13-4F3B-A5B4-74958B8BB813}
+ {CB7EE867-93E8-43E3-9EEE-9068AED1DE6C} = {9EF05F3D-E711-452B-885A-EDA277B36D20}
+ {F530020F-0DF2-49B8-9401-1C1C282077F5} = {9EF05F3D-E711-452B-885A-EDA277B36D20}
+ EndGlobalSection
+EndGlobal
diff --git a/NuGet.config b/NuGet.config
new file mode 100644
index 0000000..2ad0f8b
--- /dev/null
+++ b/NuGet.config
@@ -0,0 +1,7 @@
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Readme.md b/Readme.md
new file mode 100644
index 0000000..e54e166
--- /dev/null
+++ b/Readme.md
@@ -0,0 +1,108 @@
+
+
+**Overview:**
+
+The goal of this system is to allow centralized backup of certain specified data (files and folders) into designated storage locations, inside internal network of the organization.
+
+Used technologies: **.NET**, **ASP.NET Core** SPA with **Angular2**
+
+*System overview diagram:*
+
+
+**Screenshots**
+
+{:height="150px" width="200px"}
+{:height="150px" width="200px"}
+{:height="150px" width="200px"}
+{:height="150px" width="200px"}
+{:height="150px" width="200px"}
+{:height="150px" width="200px"}
+{:height="150px" width="200px"}
+{:height="150px" width="200px"}
+
+
+
+**Quick Start:**
+- check prerequisite:
+ - server:
+ - .NET runtime https://www.microsoft.com/net/download/framework
+ - .NET Core runtime https://www.microsoft.com/net/download/core#/runtime
+ - IIS server installed (works also with IIS Express)
+ - MSSQL (version 2012+) installed on machine (can be the express/community/dev)
+ - clients:
+ - .NET runtime https://www.microsoft.com/net/download/framework
+- download releases:
+ - client: ...
+ - server: ...
+- install server package on the server machine:
+ - follow the instructions to deploy on IIS from https://docs.microsoft.com/en-us/aspnet/core/publishing/iis
+ - update the ***appsettings.json*** file with necesary info:
+ - AdminEmail: to match your own admin email
+ - ***DefaultConnection*** connection string to point to an instance of MSSQL - used to store user membership data.
+ - ***BackupsConnectionString*** connection string to point to an instance of MSSQL - used to store application data.
+ - default admin user is **admin@admin** with password **Admin$0**. Use it on first app run and change the password and eventually grant Admin role to other users as well.
+- install agents setup on the client machines
+ - configure "C:\Program Files (x86)\LanBackupAgent\LanBackupAgent.exe.config" file.
+ - change **webApiUrl** setting to match your server IP and port configured above.
+ - restart LanBackuAgent service in service console (*services.msc*).
+
+
+
+**Application architecture**
+
+
+
+
+**Database schema**
+
+
+
+
+**Development Start**
+- verify **prerequisite**:
+ - Visual Studio 2015 with Update 3 (can be Community Edition https://go.microsoft.com/fwlink/?LinkId=691978)
+ - .NET SDK (installed with VS2015)
+ - .NET Core SDK https://www.microsoft.com/net/download/core#/sdk
+ - IIS Express (installed with VS2015)
+ - MSSQL (version 2012+) installed on machine (can be the express/community/dev) (https://www.microsoft.com/en-us/sql-server/sql-server-editions-express)
+- **clone** this repo on your machine:
+ ```
+ git clone
+ ```
+- open solution in Visual Studio, all solution packages are available online and normally should **restore** by themself when opening the solution, wait for all packages to be restored automatically.
+- Let's **build**
+- set **startup** project ***LanBackup.WebApp***
+- **RUN** the app (F5 or Ctrl+F5).
+- Two databases defined in the project config file will be created automatically at the first run of the project. One database is for AspNetIdentity, the second is to hold app data.
+- To configure Microsoft Azure **Application Insight** I recommend setting in project "LanBackup.WebApp" the ***user secret*** file with a structure like:
+ ```
+ {
+ "clientSettings": {
+ "AdminEmail": "personal@personal",
+ "InstrumentationEnabled": true,
+ "InstrumentationKey": "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX"
+ },
+ "ApplicationInsights": {
+ "InstrumentationKey": "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX"
+ }
+ }
+ ```
+ here the "clientSettings" are specific for JS client side app (Angular2)
+ and the "ApplicationInsights" part is used on the ASP.NET CORE side
+- You might want to configure file "***.\LanBackup\.vs\config\applicationhost.config***" with appropiate binding info : IP and port, if you wish to test it in your network
+
+
+
+**TODOs**
+- Functional
+ - show logs filtered by computer IP
+ - paginated list with sorting and sort direction
+- Deployment
+ - configure install and run in docker container
+- Testing
+ - add more unit tests on webapi serverside
+ - add more integrations tests on webapi server side
+ - add more unit tests on angular client side
+
+
+
\ No newline at end of file
diff --git a/global.json b/global.json
new file mode 100644
index 0000000..9d09ab5
--- /dev/null
+++ b/global.json
@@ -0,0 +1,6 @@
+{
+ "projects": [ "src", "test" ],
+ "sdk": {
+ "version": "1.0.0-preview2-003131"
+ }
+}
diff --git a/misc/_stylecop/StyleCopeRules.ruleset b/misc/_stylecop/StyleCopeRules.ruleset
new file mode 100644
index 0000000..a181ac0
--- /dev/null
+++ b/misc/_stylecop/StyleCopeRules.ruleset
@@ -0,0 +1,10 @@
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/misc/design/Design.doc b/misc/design/Design.doc
new file mode 100644
index 0000000..72426cf
Binary files /dev/null and b/misc/design/Design.doc differ
diff --git a/misc/design/Design.pdf b/misc/design/Design.pdf
new file mode 100644
index 0000000..6bb20ec
Binary files /dev/null and b/misc/design/Design.pdf differ
diff --git a/misc/docs/images/backupconfigurations_edit_custom.png b/misc/docs/images/backupconfigurations_edit_custom.png
new file mode 100644
index 0000000..ea63e61
Binary files /dev/null and b/misc/docs/images/backupconfigurations_edit_custom.png differ
diff --git a/misc/docs/images/backupconfigurations_list_custom.png b/misc/docs/images/backupconfigurations_list_custom.png
new file mode 100644
index 0000000..688547e
Binary files /dev/null and b/misc/docs/images/backupconfigurations_list_custom.png differ
diff --git a/misc/docs/images/component_interactions.png b/misc/docs/images/component_interactions.png
new file mode 100644
index 0000000..d90bf99
Binary files /dev/null and b/misc/docs/images/component_interactions.png differ
diff --git a/misc/docs/images/dashboard_admin_custom.png b/misc/docs/images/dashboard_admin_custom.png
new file mode 100644
index 0000000..6897b4b
Binary files /dev/null and b/misc/docs/images/dashboard_admin_custom.png differ
diff --git a/misc/docs/images/dashboard_anonymous_custom.png b/misc/docs/images/dashboard_anonymous_custom.png
new file mode 100644
index 0000000..8ef4d27
Binary files /dev/null and b/misc/docs/images/dashboard_anonymous_custom.png differ
diff --git a/misc/docs/images/db_schema.png b/misc/docs/images/db_schema.png
new file mode 100644
index 0000000..f654750
Binary files /dev/null and b/misc/docs/images/db_schema.png differ
diff --git a/misc/docs/images/login_custom.png b/misc/docs/images/login_custom.png
new file mode 100644
index 0000000..8cbf2f2
Binary files /dev/null and b/misc/docs/images/login_custom.png differ
diff --git a/misc/docs/images/logs_list_custom.png b/misc/docs/images/logs_list_custom.png
new file mode 100644
index 0000000..051ac25
Binary files /dev/null and b/misc/docs/images/logs_list_custom.png differ
diff --git a/misc/docs/images/profile_custom.png b/misc/docs/images/profile_custom.png
new file mode 100644
index 0000000..8db9822
Binary files /dev/null and b/misc/docs/images/profile_custom.png differ
diff --git a/misc/docs/images/system_overview.png b/misc/docs/images/system_overview.png
new file mode 100644
index 0000000..5a3ab2c
Binary files /dev/null and b/misc/docs/images/system_overview.png differ
diff --git a/misc/docs/images/users_list_custom.png b/misc/docs/images/users_list_custom.png
new file mode 100644
index 0000000..fd2b61e
Binary files /dev/null and b/misc/docs/images/users_list_custom.png differ
diff --git a/misc/media/3dde7c96ec5ff7038408777aba39514b.ico.zip b/misc/media/3dde7c96ec5ff7038408777aba39514b.ico.zip
new file mode 100644
index 0000000..6e26065
Binary files /dev/null and b/misc/media/3dde7c96ec5ff7038408777aba39514b.ico.zip differ
diff --git a/misc/media/app_icon.png b/misc/media/app_icon.png
new file mode 100644
index 0000000..2343671
Binary files /dev/null and b/misc/media/app_icon.png differ
diff --git a/misc/media/app_icon.png.ico b/misc/media/app_icon.png.ico
new file mode 100644
index 0000000..ab5c571
Binary files /dev/null and b/misc/media/app_icon.png.ico differ
diff --git a/misc/media/favicon.ico b/misc/media/favicon.ico
new file mode 100644
index 0000000..fc8ac4a
Binary files /dev/null and b/misc/media/favicon.ico differ
diff --git a/misc/media/icons/android-icon-144x144.png b/misc/media/icons/android-icon-144x144.png
new file mode 100644
index 0000000..6375071
Binary files /dev/null and b/misc/media/icons/android-icon-144x144.png differ
diff --git a/misc/media/icons/android-icon-192x192.png b/misc/media/icons/android-icon-192x192.png
new file mode 100644
index 0000000..e36bd37
Binary files /dev/null and b/misc/media/icons/android-icon-192x192.png differ
diff --git a/misc/media/icons/android-icon-36x36.png b/misc/media/icons/android-icon-36x36.png
new file mode 100644
index 0000000..26adb4a
Binary files /dev/null and b/misc/media/icons/android-icon-36x36.png differ
diff --git a/misc/media/icons/android-icon-48x48.png b/misc/media/icons/android-icon-48x48.png
new file mode 100644
index 0000000..91af4d0
Binary files /dev/null and b/misc/media/icons/android-icon-48x48.png differ
diff --git a/misc/media/icons/android-icon-72x72.png b/misc/media/icons/android-icon-72x72.png
new file mode 100644
index 0000000..4e836e8
Binary files /dev/null and b/misc/media/icons/android-icon-72x72.png differ
diff --git a/misc/media/icons/android-icon-96x96.png b/misc/media/icons/android-icon-96x96.png
new file mode 100644
index 0000000..e11d96b
Binary files /dev/null and b/misc/media/icons/android-icon-96x96.png differ
diff --git a/misc/media/icons/apple-icon-114x114.png b/misc/media/icons/apple-icon-114x114.png
new file mode 100644
index 0000000..7b1479a
Binary files /dev/null and b/misc/media/icons/apple-icon-114x114.png differ
diff --git a/misc/media/icons/apple-icon-120x120.png b/misc/media/icons/apple-icon-120x120.png
new file mode 100644
index 0000000..4502a13
Binary files /dev/null and b/misc/media/icons/apple-icon-120x120.png differ
diff --git a/misc/media/icons/apple-icon-144x144.png b/misc/media/icons/apple-icon-144x144.png
new file mode 100644
index 0000000..6375071
Binary files /dev/null and b/misc/media/icons/apple-icon-144x144.png differ
diff --git a/misc/media/icons/apple-icon-152x152.png b/misc/media/icons/apple-icon-152x152.png
new file mode 100644
index 0000000..c94d3fb
Binary files /dev/null and b/misc/media/icons/apple-icon-152x152.png differ
diff --git a/misc/media/icons/apple-icon-180x180.png b/misc/media/icons/apple-icon-180x180.png
new file mode 100644
index 0000000..3b98ed3
Binary files /dev/null and b/misc/media/icons/apple-icon-180x180.png differ
diff --git a/misc/media/icons/apple-icon-57x57.png b/misc/media/icons/apple-icon-57x57.png
new file mode 100644
index 0000000..df22a4b
Binary files /dev/null and b/misc/media/icons/apple-icon-57x57.png differ
diff --git a/misc/media/icons/apple-icon-60x60.png b/misc/media/icons/apple-icon-60x60.png
new file mode 100644
index 0000000..c7eeac4
Binary files /dev/null and b/misc/media/icons/apple-icon-60x60.png differ
diff --git a/misc/media/icons/apple-icon-72x72.png b/misc/media/icons/apple-icon-72x72.png
new file mode 100644
index 0000000..4e836e8
Binary files /dev/null and b/misc/media/icons/apple-icon-72x72.png differ
diff --git a/misc/media/icons/apple-icon-76x76.png b/misc/media/icons/apple-icon-76x76.png
new file mode 100644
index 0000000..0677d61
Binary files /dev/null and b/misc/media/icons/apple-icon-76x76.png differ
diff --git a/misc/media/icons/apple-icon-precomposed.png b/misc/media/icons/apple-icon-precomposed.png
new file mode 100644
index 0000000..1c96ed3
Binary files /dev/null and b/misc/media/icons/apple-icon-precomposed.png differ
diff --git a/misc/media/icons/apple-icon.png b/misc/media/icons/apple-icon.png
new file mode 100644
index 0000000..1c96ed3
Binary files /dev/null and b/misc/media/icons/apple-icon.png differ
diff --git a/misc/media/icons/browserconfig.xml b/misc/media/icons/browserconfig.xml
new file mode 100644
index 0000000..c554148
--- /dev/null
+++ b/misc/media/icons/browserconfig.xml
@@ -0,0 +1,2 @@
+
+#ffffff
\ No newline at end of file
diff --git a/misc/media/icons/favicon-16x16.png b/misc/media/icons/favicon-16x16.png
new file mode 100644
index 0000000..d5dd67d
Binary files /dev/null and b/misc/media/icons/favicon-16x16.png differ
diff --git a/misc/media/icons/favicon-32x32.png b/misc/media/icons/favicon-32x32.png
new file mode 100644
index 0000000..43363c2
Binary files /dev/null and b/misc/media/icons/favicon-32x32.png differ
diff --git a/misc/media/icons/favicon-96x96.png b/misc/media/icons/favicon-96x96.png
new file mode 100644
index 0000000..e11d96b
Binary files /dev/null and b/misc/media/icons/favicon-96x96.png differ
diff --git a/misc/media/icons/favicon.ico b/misc/media/icons/favicon.ico
new file mode 100644
index 0000000..fc8ac4a
Binary files /dev/null and b/misc/media/icons/favicon.ico differ
diff --git a/misc/media/icons/manifest.json b/misc/media/icons/manifest.json
new file mode 100644
index 0000000..013d4a6
--- /dev/null
+++ b/misc/media/icons/manifest.json
@@ -0,0 +1,41 @@
+{
+ "name": "App",
+ "icons": [
+ {
+ "src": "\/android-icon-36x36.png",
+ "sizes": "36x36",
+ "type": "image\/png",
+ "density": "0.75"
+ },
+ {
+ "src": "\/android-icon-48x48.png",
+ "sizes": "48x48",
+ "type": "image\/png",
+ "density": "1.0"
+ },
+ {
+ "src": "\/android-icon-72x72.png",
+ "sizes": "72x72",
+ "type": "image\/png",
+ "density": "1.5"
+ },
+ {
+ "src": "\/android-icon-96x96.png",
+ "sizes": "96x96",
+ "type": "image\/png",
+ "density": "2.0"
+ },
+ {
+ "src": "\/android-icon-144x144.png",
+ "sizes": "144x144",
+ "type": "image\/png",
+ "density": "3.0"
+ },
+ {
+ "src": "\/android-icon-192x192.png",
+ "sizes": "192x192",
+ "type": "image\/png",
+ "density": "4.0"
+ }
+ ]
+}
\ No newline at end of file
diff --git a/misc/media/icons/ms-icon-144x144.png b/misc/media/icons/ms-icon-144x144.png
new file mode 100644
index 0000000..6375071
Binary files /dev/null and b/misc/media/icons/ms-icon-144x144.png differ
diff --git a/misc/media/icons/ms-icon-150x150.png b/misc/media/icons/ms-icon-150x150.png
new file mode 100644
index 0000000..d50f4fc
Binary files /dev/null and b/misc/media/icons/ms-icon-150x150.png differ
diff --git a/misc/media/icons/ms-icon-310x310.png b/misc/media/icons/ms-icon-310x310.png
new file mode 100644
index 0000000..c940e37
Binary files /dev/null and b/misc/media/icons/ms-icon-310x310.png differ
diff --git a/misc/media/icons/ms-icon-70x70.png b/misc/media/icons/ms-icon-70x70.png
new file mode 100644
index 0000000..20712ee
Binary files /dev/null and b/misc/media/icons/ms-icon-70x70.png differ
diff --git a/misc/media/license.rtf b/misc/media/license.rtf
new file mode 100644
index 0000000..b95e553
--- /dev/null
+++ b/misc/media/license.rtf
@@ -0,0 +1,210 @@
+{\rtf1\adeflang1025\ansi\ansicpg1252\uc1\adeff31507\deff0\stshfdbch31506\stshfloch31506\stshfhich31506\stshfbi31507\deflang1033\deflangfe1033\themelang1033\themelangfe0\themelangcs0{\fonttbl{\f0\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\f0\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}
+{\f37\fbidi \fswiss\fcharset0\fprq2{\*\panose 020f0502020204030204}Calibri;}{\flomajor\f31500\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}
+{\fdbmajor\f31501\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\fhimajor\f31502\fbidi \fswiss\fcharset0\fprq2{\*\panose 020f0302020204030204}Calibri Light;}
+{\fbimajor\f31503\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\flominor\f31504\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}
+{\fdbminor\f31505\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\fhiminor\f31506\fbidi \fswiss\fcharset0\fprq2{\*\panose 020f0502020204030204}Calibri;}
+{\fbiminor\f31507\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\f41\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\f42\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}
+{\f44\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\f45\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\f46\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\f47\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}
+{\f48\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\f49\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\f41\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\f42\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}
+{\f44\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\f45\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\f46\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\f47\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}
+{\f48\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\f49\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\f411\fbidi \fswiss\fcharset238\fprq2 Calibri CE;}{\f412\fbidi \fswiss\fcharset204\fprq2 Calibri Cyr;}
+{\f414\fbidi \fswiss\fcharset161\fprq2 Calibri Greek;}{\f415\fbidi \fswiss\fcharset162\fprq2 Calibri Tur;}{\f416\fbidi \fswiss\fcharset177\fprq2 Calibri (Hebrew);}{\f417\fbidi \fswiss\fcharset178\fprq2 Calibri (Arabic);}
+{\f418\fbidi \fswiss\fcharset186\fprq2 Calibri Baltic;}{\f419\fbidi \fswiss\fcharset163\fprq2 Calibri (Vietnamese);}{\flomajor\f31508\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}
+{\flomajor\f31509\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\flomajor\f31511\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\flomajor\f31512\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}
+{\flomajor\f31513\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\flomajor\f31514\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\flomajor\f31515\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}
+{\flomajor\f31516\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\fdbmajor\f31518\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\fdbmajor\f31519\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}
+{\fdbmajor\f31521\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\fdbmajor\f31522\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\fdbmajor\f31523\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}
+{\fdbmajor\f31524\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\fdbmajor\f31525\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\fdbmajor\f31526\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}
+{\fhimajor\f31528\fbidi \fswiss\fcharset238\fprq2 Calibri Light CE;}{\fhimajor\f31529\fbidi \fswiss\fcharset204\fprq2 Calibri Light Cyr;}{\fhimajor\f31531\fbidi \fswiss\fcharset161\fprq2 Calibri Light Greek;}
+{\fhimajor\f31532\fbidi \fswiss\fcharset162\fprq2 Calibri Light Tur;}{\fhimajor\f31533\fbidi \fswiss\fcharset177\fprq2 Calibri Light (Hebrew);}{\fhimajor\f31534\fbidi \fswiss\fcharset178\fprq2 Calibri Light (Arabic);}
+{\fhimajor\f31535\fbidi \fswiss\fcharset186\fprq2 Calibri Light Baltic;}{\fhimajor\f31536\fbidi \fswiss\fcharset163\fprq2 Calibri Light (Vietnamese);}{\fbimajor\f31538\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}
+{\fbimajor\f31539\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\fbimajor\f31541\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\fbimajor\f31542\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}
+{\fbimajor\f31543\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\fbimajor\f31544\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\fbimajor\f31545\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}
+{\fbimajor\f31546\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\flominor\f31548\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\flominor\f31549\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}
+{\flominor\f31551\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\flominor\f31552\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\flominor\f31553\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}
+{\flominor\f31554\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\flominor\f31555\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\flominor\f31556\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}
+{\fdbminor\f31558\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\fdbminor\f31559\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\fdbminor\f31561\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}
+{\fdbminor\f31562\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\fdbminor\f31563\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\fdbminor\f31564\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}
+{\fdbminor\f31565\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\fdbminor\f31566\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\fhiminor\f31568\fbidi \fswiss\fcharset238\fprq2 Calibri CE;}
+{\fhiminor\f31569\fbidi \fswiss\fcharset204\fprq2 Calibri Cyr;}{\fhiminor\f31571\fbidi \fswiss\fcharset161\fprq2 Calibri Greek;}{\fhiminor\f31572\fbidi \fswiss\fcharset162\fprq2 Calibri Tur;}
+{\fhiminor\f31573\fbidi \fswiss\fcharset177\fprq2 Calibri (Hebrew);}{\fhiminor\f31574\fbidi \fswiss\fcharset178\fprq2 Calibri (Arabic);}{\fhiminor\f31575\fbidi \fswiss\fcharset186\fprq2 Calibri Baltic;}
+{\fhiminor\f31576\fbidi \fswiss\fcharset163\fprq2 Calibri (Vietnamese);}{\fbiminor\f31578\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\fbiminor\f31579\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}
+{\fbiminor\f31581\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\fbiminor\f31582\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\fbiminor\f31583\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}
+{\fbiminor\f31584\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\fbiminor\f31585\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\fbiminor\f31586\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}}
+{\colortbl;\red0\green0\blue0;\red0\green0\blue255;\red0\green255\blue255;\red0\green255\blue0;\red255\green0\blue255;\red255\green0\blue0;\red255\green255\blue0;\red255\green255\blue255;\red0\green0\blue128;\red0\green128\blue128;\red0\green128\blue0;
+\red128\green0\blue128;\red128\green0\blue0;\red128\green128\blue0;\red128\green128\blue128;\red192\green192\blue192;}{\*\defchp \f31506\fs22 }{\*\defpap \ql \li0\ri0\sa160\sl259\slmult1
+\widctlpar\wrapdefault\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 }\noqfpromote {\stylesheet{\ql \li0\ri0\sa160\sl259\slmult1\widctlpar\wrapdefault\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \rtlch\fcs1 \af31507\afs22\alang1025
+\ltrch\fcs0 \f31506\fs22\lang2057\langfe1033\cgrid\langnp2057\langfenp1033 \snext0 \sqformat \spriority0 Normal;}{\*\cs10 \additive \ssemihidden \sunhideused \spriority1 Default Paragraph Font;}{\*
+\ts11\tsrowd\trftsWidthB3\trpaddl108\trpaddr108\trpaddfl3\trpaddft3\trpaddfb3\trpaddfr3\trcbpat1\trcfpat1\tblind0\tblindtype3\tsvertalt\tsbrdrt\tsbrdrl\tsbrdrb\tsbrdrr\tsbrdrdgl\tsbrdrdgr\tsbrdrh\tsbrdrv \ql \li0\ri0\sa160\sl259\slmult1
+\widctlpar\wrapdefault\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \rtlch\fcs1 \af31507\afs22\alang1025 \ltrch\fcs0 \f31506\fs22\lang1033\langfe1033\cgrid\langnp1033\langfenp1033 \snext11 \ssemihidden \sunhideused Normal Table;}}
+{\*\rsidtbl \rsid1381853\rsid6624395\rsid10097776\rsid11094156\rsid12995017}{\mmathPr\mmathFont34\mbrkBin0\mbrkBinSub0\msmallFrac0\mdispDef1\mlMargin0\mrMargin0\mdefJc1\mwrapIndent1440\mintLim0\mnaryLim1}{\info{\author Claudiu Farcas}
+{\operator Claudiu Farcas}{\creatim\yr2017\mo1\dy27\hr1\min13}{\revtim\yr2017\mo1\dy27\hr1\min13}{\version2}{\edmins0}{\nofpages1}{\nofwords5}{\nofchars29}{\nofcharsws33}{\vern23}}{\*\xmlnstbl {\xmlns1 http://schemas.microsoft.com/office/word/2003/wordml}
+}\paperw11907\paperh16840\margl1440\margr1440\margt1440\margb1440\gutter0\ltrsect
+\widowctrl\ftnbj\aenddoc\trackmoves0\trackformatting1\donotembedsysfont1\relyonvml0\donotembedlingdata0\grfdocevents0\validatexml1\showplaceholdtext0\ignoremixedcontent0\saveinvalidxml0\showxmlerrors1\noxlattoyen
+\expshrtn\noultrlspc\dntblnsbdb\nospaceforul\formshade\horzdoc\dgmargin\dghspace110\dgvspace180\dghorigin1440\dgvorigin1440\dghshow2\dgvshow2
+\jexpand\viewkind1\viewscale120\pgbrdrhead\pgbrdrfoot\splytwnine\ftnlytwnine\htmautsp\nolnhtadjtbl\useltbaln\alntblind\lytcalctblwd\lyttblrtgr\lnbrkrule\nobrkwrptbl\snaptogridincell\allowfieldendsel\wrppunct
+\asianbrkrule\rsidroot11094156\newtblstyruls\nogrowautofit\usenormstyforlist\noindnmbrts\felnbrelev\nocxsptable\indrlsweleven\noafcnsttbl\afelev\utinl\hwelev\spltpgpar\notcvasp\notbrkcnstfrctbl\notvatxbx\krnprsnet\cachedcolbal \nouicompat \fet0
+{\*\wgrffmtfilter 2450}\nofeaturethrottle1\ilfomacatclnup0\ltrpar \sectd \ltrsect\psz9\linex0\endnhere\sectlinegrid360\sectdefaultcl\sectrsid6624395\sftnbj {\*\pnseclvl1\pnucrm\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl2
+\pnucltr\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl3\pndec\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl4\pnlcltr\pnstart1\pnindent720\pnhang {\pntxta )}}{\*\pnseclvl5\pndec\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl6
+\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl7\pnlcrm\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl8\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl9\pnlcrm\pnstart1\pnindent720\pnhang
+{\pntxtb (}{\pntxta )}}\pard\plain \ltrpar\ql \li0\ri0\sa160\sl259\slmult1\widctlpar\wrapdefault\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \rtlch\fcs1 \af31507\afs22\alang1025 \ltrch\fcs0
+\f31506\fs22\lang2057\langfe1033\cgrid\langnp2057\langfenp1033 {\rtlch\fcs1 \af31507 \ltrch\fcs0 \insrsid11094156 NO LICENSE FILE}{\rtlch\fcs1 \af31507 \ltrch\fcs0 \insrsid1381853
+\par }{\rtlch\fcs1 \af31507 \ltrch\fcs0 \insrsid11094156 FREE FOR EVERYONE
+\par }{\*\themedata 504b030414000600080000002100e9de0fbfff0000001c020000130000005b436f6e74656e745f54797065735d2e786d6cac91cb4ec3301045f748fc83e52d4a
+9cb2400825e982c78ec7a27cc0c8992416c9d8b2a755fbf74cd25442a820166c2cd933f79e3be372bd1f07b5c3989ca74aaff2422b24eb1b475da5df374fd9ad
+5689811a183c61a50f98f4babebc2837878049899a52a57be670674cb23d8e90721f90a4d2fa3802cb35762680fd800ecd7551dc18eb899138e3c943d7e503b6
+b01d583deee5f99824e290b4ba3f364eac4a430883b3c092d4eca8f946c916422ecab927f52ea42b89a1cd59c254f919b0e85e6535d135a8de20f20b8c12c3b0
+0c895fcf6720192de6bf3b9e89ecdbd6596cbcdd8eb28e7c365ecc4ec1ff1460f53fe813d3cc7f5b7f020000ffff0300504b030414000600080000002100a5d6
+a7e7c0000000360100000b0000005f72656c732f2e72656c73848fcf6ac3300c87ef85bd83d17d51d2c31825762fa590432fa37d00e1287f68221bdb1bebdb4f
+c7060abb0884a4eff7a93dfeae8bf9e194e720169aaa06c3e2433fcb68e1763dbf7f82c985a4a725085b787086a37bdbb55fbc50d1a33ccd311ba548b6309512
+0f88d94fbc52ae4264d1c910d24a45db3462247fa791715fd71f989e19e0364cd3f51652d73760ae8fa8c9ffb3c330cc9e4fc17faf2ce545046e37944c69e462
+a1a82fe353bd90a865aad41ed0b5b8f9d6fd010000ffff0300504b0304140006000800000021006b799616830000008a0000001c0000007468656d652f746865
+6d652f7468656d654d616e616765722e786d6c0ccc4d0ac3201040e17da17790d93763bb284562b2cbaebbf600439c1a41c7a0d29fdbd7e5e38337cedf14d59b
+4b0d592c9c070d8a65cd2e88b7f07c2ca71ba8da481cc52c6ce1c715e6e97818c9b48d13df49c873517d23d59085adb5dd20d6b52bd521ef2cdd5eb9246a3d8b
+4757e8d3f729e245eb2b260a0238fd010000ffff0300504b030414000600080000002100b6f4679893070000c9200000160000007468656d652f7468656d652f
+7468656d65312e786d6cec59cd8b1bc915bf07f23f347d97f5d5ad8fc1f2a24fcfda33b6b164873dd648a5eef2547789aad28cc56208de532e81c026e49085bd
+ed21842cecc22eb9e48f31d8249b3f22afaa5bdd5552c99e191c3061463074977eefd5afde7bf5de53d5ddcf5e26d4bbc05c1096f6fcfa9d9aefe174ce16248d
+7afeb3d9a4d2f13d2151ba4094a5b8e76fb0f03fbbf7eb5fdd454732c609f6403e1547a8e7c752ae8eaa5531876124eeb0154ee1bb25e30992f0caa3ea82a34b
+d09bd06aa3566b55134452df4b51026a1f2f97648ebd9952e9dfdb2a1f53784da5500373caa74a35b6243476715e5708b11143cabd0b447b3eccb3609733fc52
+fa1e4542c2173dbfa6fffceabdbb5574940b517940d6909be8bf5c2e17589c37f49c3c3a2b260d823068f50bfd1a40e53e6edc1eb7c6ad429f06a0f91c569a71
+b175b61bc320c71aa0ecd1a17bd41e35eb16ded0dfdce3dc0fd5c7c26b50a63fd8c34f2643b0a285d7a00c1feee1c3417730b2f56b50866fede1dbb5fe28685b
+fa3528a6243ddf43d7c25673b85d6d0159327aec8477c360d26ee4ca4b144443115d6a8a254be5a1584bd00bc6270050408a24493db959e1259a43140f112567
+9c7827248a21f056286502866b8ddaa4d684ffea13e827ed5174849121ad780113b137a4f87862cec94af6fc07a0d537206f7ffef9cdeb1fdfbcfee9cd575fbd
+79fdf77c6eadca923b466964cafdf2dd1ffef3cd6fbd7ffff0ed2f5fff319b7a172f4cfcbbbffdeedd3ffef93ef5b0e2d2146ffff4fdbb1fbf7ffbe7dfffebaf
+5f3bb4f7393a33e1339260e13dc297de5396c0021dfcf119bf9ec42c46c494e8a791402952b338f48f656ca11f6d10450edc00db767cce21d5b880f7d72f2cc2
+d398af2571687c182716f094313a60dc6985876a2ec3ccb3751ab927e76b13f714a10bd7dc43945a5e1eaf579063894be530c616cd2714a5124538c5d253dfb1
+738c1dabfb8210cbaea764ce99604be97d41bc01224e93ccc899154da5d03149c02f1b1741f0b7659bd3e7de8051d7aa47f8c246c2de40d4417e86a965c6fb68
+2d51e252394309350d7e8264ec2239ddf0b9891b0b099e8e3065de78818570c93ce6b05ec3e90f21cdb8dd7e4a37898de4929cbb749e20c64ce4889d0f6394ac
+5cd829496313fbb938871045de13265df05366ef10f50e7e40e941773f27d872f787b3c133c8b026a53240d4376beef0e57dccacf89d6ee8126157aae9f3c44a
+b17d4e9cd131584756689f604cd1255a60ec3dfbdcc160c05696cd4bd20f62c82ac7d815580f901dabea3dc5027a25d5dcece7c91322ac909de2881de073bad9
+493c1b9426881fd2fc08bc6eda7c0ca52e7105c0633a3f37818f08f480102f4ea33c16a0c308ee835a9fc4c82a60ea5db8e375c32dff5d658fc1be7c61d1b8c2
+be04197c6d1948eca6cc7b6d3343d49aa00c9819822ec3956e41c4727f29a28aab165b3be596f6a62ddd00dd91d5f42424fd6007b4d3fb84ffbbde073a8cb77f
+f9c6b10f3e4ebfe3566c25ab6b763a8792c9f14e7f7308b7dbd50c195f904fbfa919a175fa04431dd9cf58b73dcd6d4fe3ffdff73487f6f36d2773a8dfb8ed64
+7ce8306e3b99fc70e5e3743265f3027d8d3af0c80e7af4b14f72f0d46749289dca0dc527421ffc08f83db398c0a092d3279eb838055cc5f0a8ca1c4c60e1228e
+b48cc799fc0d91f134462b381daafb4a492472d591f0564cc0a1911e76ea5678ba4e4ed9223becacd7d5c16656590592e5782d2cc6e1a04a66e856bb3cc02bd4
+6bb6913e68dd1250b2d721614c6693683a48b4b783ca48fa58178ce620a157f65158741d2c3a4afdd6557b2c805ae115f8c1edc1cff49e1f06200242701e07cd
+f942f92973f5d6bbda991fd3d3878c69450034d8db08283ddd555c0f2e4fad2e0bb52b78da2261849b4d425b46377822869fc17974aad1abd0b8aeafbba54b2d
+7aca147a3e08ad9246bbf33e1637f535c8ede6069a9a9982a6de65cf6f35430899395af5fc251c1ac363b282d811ea3717a211dcbccc25cf36fc4d32cb8a0b39
+4222ce0cae934e960d122231f728497abe5a7ee1069aea1ca2b9d51b90103e59725d482b9f1a3970baed64bc5ce2b934dd6e8c284b67af90e1b35ce1fc568bdf
+1cac24d91adc3d8d1797de195df3a708422c6cd795011744c0dd413db3e682c0655891c8caf8db294c79da356fa3740c65e388ae62945714339967709dca0b3a
+faadb081f196af190c6a98242f8467912ab0a651ad6a5a548d8cc3c1aafb6121653923699635d3ca2aaa6abab39835c3b60cecd8f26645de60b53531e434b3c2
+67a97b37e576b7b96ea74f28aa0418bcb09fa3ea5ea12018d4cac92c6a8af17e1a56393b1fb56bc776811fa07695226164fdd656ed8edd8a1ae19c0e066f54f9
+416e376a6168b9ed2bb5a5f5adb979b1cdce5e40f2184197bba6526857c2c92e47d0104d754f92a50dd8222f65be35e0c95b73d2f3bfac85fd60d80887955a27
+1c57826650ab74c27eb3d20fc3667d1cd66ba341e31514161927f530bbb19fc00506dde4f7f67a7cefee3ed9ded1dc99b3a4caf4dd7c5513d777f7f5c6e1bb7b
+8f40d2f9b2d598749bdd41abd26df627956034e854bac3d6a0326a0ddba3c9681876ba9357be77a1c141bf390c5ae34ea5551f0e2b41aba6e877ba9576d068f4
+8376bf330efaaff23606569ea58fdc16605ecdebde7f010000ffff0300504b0304140006000800000021000dd1909fb60000001b010000270000007468656d65
+2f7468656d652f5f72656c732f7468656d654d616e616765722e786d6c2e72656c73848f4d0ac2301484f78277086f6fd3ba109126dd88d0add40384e4350d36
+3f2451eced0dae2c082e8761be9969bb979dc9136332de3168aa1a083ae995719ac16db8ec8e4052164e89d93b64b060828e6f37ed1567914b284d262452282e
+3198720e274a939cd08a54f980ae38a38f56e422a3a641c8bbd048f7757da0f19b017cc524bd62107bd5001996509affb3fd381a89672f1f165dfe514173d985
+0528a2c6cce0239baa4c04ca5bbabac4df000000ffff0300504b01022d0014000600080000002100e9de0fbfff0000001c020000130000000000000000000000
+0000000000005b436f6e74656e745f54797065735d2e786d6c504b01022d0014000600080000002100a5d6a7e7c0000000360100000b00000000000000000000
+000000300100005f72656c732f2e72656c73504b01022d00140006000800000021006b799616830000008a0000001c0000000000000000000000000019020000
+7468656d652f7468656d652f7468656d654d616e616765722e786d6c504b01022d0014000600080000002100b6f4679893070000c92000001600000000000000
+000000000000d60200007468656d652f7468656d652f7468656d65312e786d6c504b01022d00140006000800000021000dd1909fb60000001b01000027000000
+000000000000000000009d0a00007468656d652f7468656d652f5f72656c732f7468656d654d616e616765722e786d6c2e72656c73504b050600000000050005005d010000980b00000000}
+{\*\colorschememapping 3c3f786d6c2076657273696f6e3d22312e302220656e636f64696e673d225554462d3822207374616e64616c6f6e653d22796573223f3e0d0a3c613a636c724d
+617020786d6c6e733a613d22687474703a2f2f736368656d61732e6f70656e786d6c666f726d6174732e6f72672f64726177696e676d6c2f323030362f6d6169
+6e22206267313d226c743122207478313d22646b3122206267323d226c743222207478323d22646b322220616363656e74313d22616363656e74312220616363
+656e74323d22616363656e74322220616363656e74333d22616363656e74332220616363656e74343d22616363656e74342220616363656e74353d22616363656e74352220616363656e74363d22616363656e74362220686c696e6b3d22686c696e6b2220666f6c486c696e6b3d22666f6c486c696e6b222f3e}
+{\*\latentstyles\lsdstimax374\lsdlockeddef0\lsdsemihiddendef0\lsdunhideuseddef0\lsdqformatdef0\lsdprioritydef99{\lsdlockedexcept \lsdqformat1 \lsdpriority0 \lsdlocked0 Normal;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 1;
+\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 2;\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 3;\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 4;
+\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 5;\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 6;\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 7;
+\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 8;\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 9;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 1;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 5;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 6;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 7;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 8;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index 9;
+\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 1;\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 2;\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 3;
+\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 4;\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 5;\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 6;
+\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 7;\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 8;\lsdsemihidden1 \lsdunhideused1 \lsdpriority39 \lsdlocked0 toc 9;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Normal Indent;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 footnote text;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 annotation text;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 header;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 footer;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 index heading;\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority35 \lsdlocked0 caption;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 table of figures;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 envelope address;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 envelope return;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 footnote reference;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 annotation reference;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 line number;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 page number;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 endnote reference;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 endnote text;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 table of authorities;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 macro;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 toa heading;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Bullet;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Number;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List 3;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List 5;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Bullet 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Bullet 3;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Bullet 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Bullet 5;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Number 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Number 3;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Number 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Number 5;\lsdqformat1 \lsdpriority10 \lsdlocked0 Title;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Closing;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Signature;\lsdsemihidden1 \lsdunhideused1 \lsdpriority1 \lsdlocked0 Default Paragraph Font;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text Indent;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Continue;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Continue 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Continue 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Continue 4;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 List Continue 5;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Message Header;\lsdqformat1 \lsdpriority11 \lsdlocked0 Subtitle;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Salutation;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Date;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text First Indent;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text First Indent 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Note Heading;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text Indent 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Body Text Indent 3;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Block Text;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Hyperlink;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 FollowedHyperlink;\lsdqformat1 \lsdpriority22 \lsdlocked0 Strong;
+\lsdqformat1 \lsdpriority20 \lsdlocked0 Emphasis;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Document Map;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Plain Text;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 E-mail Signature;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Top of Form;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Bottom of Form;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Normal (Web);\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Acronym;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Address;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Cite;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Code;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Definition;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Keyboard;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Preformatted;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Sample;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Typewriter;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 HTML Variable;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Normal Table;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 annotation subject;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 No List;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Outline List 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Outline List 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Outline List 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Simple 1;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Simple 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Simple 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Classic 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Classic 2;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Classic 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Classic 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Colorful 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Colorful 2;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Colorful 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Columns 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Columns 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Columns 3;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Columns 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Columns 5;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 2;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 5;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 6;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 7;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Grid 8;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 2;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 4;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 5;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 6;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 7;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table List 8;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table 3D effects 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table 3D effects 2;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table 3D effects 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Contemporary;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Elegant;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Professional;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Subtle 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Subtle 2;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Web 1;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Web 2;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Web 3;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Balloon Text;\lsdpriority39 \lsdlocked0 Table Grid;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Table Theme;\lsdsemihidden1 \lsdlocked0 Placeholder Text;
+\lsdqformat1 \lsdpriority1 \lsdlocked0 No Spacing;\lsdpriority60 \lsdlocked0 Light Shading;\lsdpriority61 \lsdlocked0 Light List;\lsdpriority62 \lsdlocked0 Light Grid;\lsdpriority63 \lsdlocked0 Medium Shading 1;\lsdpriority64 \lsdlocked0 Medium Shading 2;
+\lsdpriority65 \lsdlocked0 Medium List 1;\lsdpriority66 \lsdlocked0 Medium List 2;\lsdpriority67 \lsdlocked0 Medium Grid 1;\lsdpriority68 \lsdlocked0 Medium Grid 2;\lsdpriority69 \lsdlocked0 Medium Grid 3;\lsdpriority70 \lsdlocked0 Dark List;
+\lsdpriority71 \lsdlocked0 Colorful Shading;\lsdpriority72 \lsdlocked0 Colorful List;\lsdpriority73 \lsdlocked0 Colorful Grid;\lsdpriority60 \lsdlocked0 Light Shading Accent 1;\lsdpriority61 \lsdlocked0 Light List Accent 1;
+\lsdpriority62 \lsdlocked0 Light Grid Accent 1;\lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 1;\lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 1;\lsdpriority65 \lsdlocked0 Medium List 1 Accent 1;\lsdsemihidden1 \lsdlocked0 Revision;
+\lsdqformat1 \lsdpriority34 \lsdlocked0 List Paragraph;\lsdqformat1 \lsdpriority29 \lsdlocked0 Quote;\lsdqformat1 \lsdpriority30 \lsdlocked0 Intense Quote;\lsdpriority66 \lsdlocked0 Medium List 2 Accent 1;\lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 1;
+\lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 1;\lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 1;\lsdpriority70 \lsdlocked0 Dark List Accent 1;\lsdpriority71 \lsdlocked0 Colorful Shading Accent 1;\lsdpriority72 \lsdlocked0 Colorful List Accent 1;
+\lsdpriority73 \lsdlocked0 Colorful Grid Accent 1;\lsdpriority60 \lsdlocked0 Light Shading Accent 2;\lsdpriority61 \lsdlocked0 Light List Accent 2;\lsdpriority62 \lsdlocked0 Light Grid Accent 2;\lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 2;
+\lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 2;\lsdpriority65 \lsdlocked0 Medium List 1 Accent 2;\lsdpriority66 \lsdlocked0 Medium List 2 Accent 2;\lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 2;\lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 2;
+\lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 2;\lsdpriority70 \lsdlocked0 Dark List Accent 2;\lsdpriority71 \lsdlocked0 Colorful Shading Accent 2;\lsdpriority72 \lsdlocked0 Colorful List Accent 2;\lsdpriority73 \lsdlocked0 Colorful Grid Accent 2;
+\lsdpriority60 \lsdlocked0 Light Shading Accent 3;\lsdpriority61 \lsdlocked0 Light List Accent 3;\lsdpriority62 \lsdlocked0 Light Grid Accent 3;\lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 3;\lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 3;
+\lsdpriority65 \lsdlocked0 Medium List 1 Accent 3;\lsdpriority66 \lsdlocked0 Medium List 2 Accent 3;\lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 3;\lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 3;\lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 3;
+\lsdpriority70 \lsdlocked0 Dark List Accent 3;\lsdpriority71 \lsdlocked0 Colorful Shading Accent 3;\lsdpriority72 \lsdlocked0 Colorful List Accent 3;\lsdpriority73 \lsdlocked0 Colorful Grid Accent 3;\lsdpriority60 \lsdlocked0 Light Shading Accent 4;
+\lsdpriority61 \lsdlocked0 Light List Accent 4;\lsdpriority62 \lsdlocked0 Light Grid Accent 4;\lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 4;\lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 4;\lsdpriority65 \lsdlocked0 Medium List 1 Accent 4;
+\lsdpriority66 \lsdlocked0 Medium List 2 Accent 4;\lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 4;\lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 4;\lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 4;\lsdpriority70 \lsdlocked0 Dark List Accent 4;
+\lsdpriority71 \lsdlocked0 Colorful Shading Accent 4;\lsdpriority72 \lsdlocked0 Colorful List Accent 4;\lsdpriority73 \lsdlocked0 Colorful Grid Accent 4;\lsdpriority60 \lsdlocked0 Light Shading Accent 5;\lsdpriority61 \lsdlocked0 Light List Accent 5;
+\lsdpriority62 \lsdlocked0 Light Grid Accent 5;\lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 5;\lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 5;\lsdpriority65 \lsdlocked0 Medium List 1 Accent 5;\lsdpriority66 \lsdlocked0 Medium List 2 Accent 5;
+\lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 5;\lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 5;\lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 5;\lsdpriority70 \lsdlocked0 Dark List Accent 5;\lsdpriority71 \lsdlocked0 Colorful Shading Accent 5;
+\lsdpriority72 \lsdlocked0 Colorful List Accent 5;\lsdpriority73 \lsdlocked0 Colorful Grid Accent 5;\lsdpriority60 \lsdlocked0 Light Shading Accent 6;\lsdpriority61 \lsdlocked0 Light List Accent 6;\lsdpriority62 \lsdlocked0 Light Grid Accent 6;
+\lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 6;\lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 6;\lsdpriority65 \lsdlocked0 Medium List 1 Accent 6;\lsdpriority66 \lsdlocked0 Medium List 2 Accent 6;
+\lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 6;\lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 6;\lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 6;\lsdpriority70 \lsdlocked0 Dark List Accent 6;\lsdpriority71 \lsdlocked0 Colorful Shading Accent 6;
+\lsdpriority72 \lsdlocked0 Colorful List Accent 6;\lsdpriority73 \lsdlocked0 Colorful Grid Accent 6;\lsdqformat1 \lsdpriority19 \lsdlocked0 Subtle Emphasis;\lsdqformat1 \lsdpriority21 \lsdlocked0 Intense Emphasis;
+\lsdqformat1 \lsdpriority31 \lsdlocked0 Subtle Reference;\lsdqformat1 \lsdpriority32 \lsdlocked0 Intense Reference;\lsdqformat1 \lsdpriority33 \lsdlocked0 Book Title;\lsdsemihidden1 \lsdunhideused1 \lsdpriority37 \lsdlocked0 Bibliography;
+\lsdsemihidden1 \lsdunhideused1 \lsdqformat1 \lsdpriority39 \lsdlocked0 TOC Heading;\lsdpriority41 \lsdlocked0 Plain Table 1;\lsdpriority42 \lsdlocked0 Plain Table 2;\lsdpriority43 \lsdlocked0 Plain Table 3;\lsdpriority44 \lsdlocked0 Plain Table 4;
+\lsdpriority45 \lsdlocked0 Plain Table 5;\lsdpriority40 \lsdlocked0 Grid Table Light;\lsdpriority46 \lsdlocked0 Grid Table 1 Light;\lsdpriority47 \lsdlocked0 Grid Table 2;\lsdpriority48 \lsdlocked0 Grid Table 3;\lsdpriority49 \lsdlocked0 Grid Table 4;
+\lsdpriority50 \lsdlocked0 Grid Table 5 Dark;\lsdpriority51 \lsdlocked0 Grid Table 6 Colorful;\lsdpriority52 \lsdlocked0 Grid Table 7 Colorful;\lsdpriority46 \lsdlocked0 Grid Table 1 Light Accent 1;\lsdpriority47 \lsdlocked0 Grid Table 2 Accent 1;
+\lsdpriority48 \lsdlocked0 Grid Table 3 Accent 1;\lsdpriority49 \lsdlocked0 Grid Table 4 Accent 1;\lsdpriority50 \lsdlocked0 Grid Table 5 Dark Accent 1;\lsdpriority51 \lsdlocked0 Grid Table 6 Colorful Accent 1;
+\lsdpriority52 \lsdlocked0 Grid Table 7 Colorful Accent 1;\lsdpriority46 \lsdlocked0 Grid Table 1 Light Accent 2;\lsdpriority47 \lsdlocked0 Grid Table 2 Accent 2;\lsdpriority48 \lsdlocked0 Grid Table 3 Accent 2;
+\lsdpriority49 \lsdlocked0 Grid Table 4 Accent 2;\lsdpriority50 \lsdlocked0 Grid Table 5 Dark Accent 2;\lsdpriority51 \lsdlocked0 Grid Table 6 Colorful Accent 2;\lsdpriority52 \lsdlocked0 Grid Table 7 Colorful Accent 2;
+\lsdpriority46 \lsdlocked0 Grid Table 1 Light Accent 3;\lsdpriority47 \lsdlocked0 Grid Table 2 Accent 3;\lsdpriority48 \lsdlocked0 Grid Table 3 Accent 3;\lsdpriority49 \lsdlocked0 Grid Table 4 Accent 3;
+\lsdpriority50 \lsdlocked0 Grid Table 5 Dark Accent 3;\lsdpriority51 \lsdlocked0 Grid Table 6 Colorful Accent 3;\lsdpriority52 \lsdlocked0 Grid Table 7 Colorful Accent 3;\lsdpriority46 \lsdlocked0 Grid Table 1 Light Accent 4;
+\lsdpriority47 \lsdlocked0 Grid Table 2 Accent 4;\lsdpriority48 \lsdlocked0 Grid Table 3 Accent 4;\lsdpriority49 \lsdlocked0 Grid Table 4 Accent 4;\lsdpriority50 \lsdlocked0 Grid Table 5 Dark Accent 4;
+\lsdpriority51 \lsdlocked0 Grid Table 6 Colorful Accent 4;\lsdpriority52 \lsdlocked0 Grid Table 7 Colorful Accent 4;\lsdpriority46 \lsdlocked0 Grid Table 1 Light Accent 5;\lsdpriority47 \lsdlocked0 Grid Table 2 Accent 5;
+\lsdpriority48 \lsdlocked0 Grid Table 3 Accent 5;\lsdpriority49 \lsdlocked0 Grid Table 4 Accent 5;\lsdpriority50 \lsdlocked0 Grid Table 5 Dark Accent 5;\lsdpriority51 \lsdlocked0 Grid Table 6 Colorful Accent 5;
+\lsdpriority52 \lsdlocked0 Grid Table 7 Colorful Accent 5;\lsdpriority46 \lsdlocked0 Grid Table 1 Light Accent 6;\lsdpriority47 \lsdlocked0 Grid Table 2 Accent 6;\lsdpriority48 \lsdlocked0 Grid Table 3 Accent 6;
+\lsdpriority49 \lsdlocked0 Grid Table 4 Accent 6;\lsdpriority50 \lsdlocked0 Grid Table 5 Dark Accent 6;\lsdpriority51 \lsdlocked0 Grid Table 6 Colorful Accent 6;\lsdpriority52 \lsdlocked0 Grid Table 7 Colorful Accent 6;
+\lsdpriority46 \lsdlocked0 List Table 1 Light;\lsdpriority47 \lsdlocked0 List Table 2;\lsdpriority48 \lsdlocked0 List Table 3;\lsdpriority49 \lsdlocked0 List Table 4;\lsdpriority50 \lsdlocked0 List Table 5 Dark;
+\lsdpriority51 \lsdlocked0 List Table 6 Colorful;\lsdpriority52 \lsdlocked0 List Table 7 Colorful;\lsdpriority46 \lsdlocked0 List Table 1 Light Accent 1;\lsdpriority47 \lsdlocked0 List Table 2 Accent 1;\lsdpriority48 \lsdlocked0 List Table 3 Accent 1;
+\lsdpriority49 \lsdlocked0 List Table 4 Accent 1;\lsdpriority50 \lsdlocked0 List Table 5 Dark Accent 1;\lsdpriority51 \lsdlocked0 List Table 6 Colorful Accent 1;\lsdpriority52 \lsdlocked0 List Table 7 Colorful Accent 1;
+\lsdpriority46 \lsdlocked0 List Table 1 Light Accent 2;\lsdpriority47 \lsdlocked0 List Table 2 Accent 2;\lsdpriority48 \lsdlocked0 List Table 3 Accent 2;\lsdpriority49 \lsdlocked0 List Table 4 Accent 2;
+\lsdpriority50 \lsdlocked0 List Table 5 Dark Accent 2;\lsdpriority51 \lsdlocked0 List Table 6 Colorful Accent 2;\lsdpriority52 \lsdlocked0 List Table 7 Colorful Accent 2;\lsdpriority46 \lsdlocked0 List Table 1 Light Accent 3;
+\lsdpriority47 \lsdlocked0 List Table 2 Accent 3;\lsdpriority48 \lsdlocked0 List Table 3 Accent 3;\lsdpriority49 \lsdlocked0 List Table 4 Accent 3;\lsdpriority50 \lsdlocked0 List Table 5 Dark Accent 3;
+\lsdpriority51 \lsdlocked0 List Table 6 Colorful Accent 3;\lsdpriority52 \lsdlocked0 List Table 7 Colorful Accent 3;\lsdpriority46 \lsdlocked0 List Table 1 Light Accent 4;\lsdpriority47 \lsdlocked0 List Table 2 Accent 4;
+\lsdpriority48 \lsdlocked0 List Table 3 Accent 4;\lsdpriority49 \lsdlocked0 List Table 4 Accent 4;\lsdpriority50 \lsdlocked0 List Table 5 Dark Accent 4;\lsdpriority51 \lsdlocked0 List Table 6 Colorful Accent 4;
+\lsdpriority52 \lsdlocked0 List Table 7 Colorful Accent 4;\lsdpriority46 \lsdlocked0 List Table 1 Light Accent 5;\lsdpriority47 \lsdlocked0 List Table 2 Accent 5;\lsdpriority48 \lsdlocked0 List Table 3 Accent 5;
+\lsdpriority49 \lsdlocked0 List Table 4 Accent 5;\lsdpriority50 \lsdlocked0 List Table 5 Dark Accent 5;\lsdpriority51 \lsdlocked0 List Table 6 Colorful Accent 5;\lsdpriority52 \lsdlocked0 List Table 7 Colorful Accent 5;
+\lsdpriority46 \lsdlocked0 List Table 1 Light Accent 6;\lsdpriority47 \lsdlocked0 List Table 2 Accent 6;\lsdpriority48 \lsdlocked0 List Table 3 Accent 6;\lsdpriority49 \lsdlocked0 List Table 4 Accent 6;
+\lsdpriority50 \lsdlocked0 List Table 5 Dark Accent 6;\lsdpriority51 \lsdlocked0 List Table 6 Colorful Accent 6;\lsdpriority52 \lsdlocked0 List Table 7 Colorful Accent 6;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Mention;
+\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Smart Hyperlink;\lsdsemihidden1 \lsdunhideused1 \lsdlocked0 Hashtag;}}{\*\datastore 0105000002000000180000004d73786d6c322e534158584d4c5265616465722e362e3000000000000000000000060000
+d0cf11e0a1b11ae1000000000000000000000000000000003e000300feff090006000000000000000000000001000000010000000000000000100000feffffff00000000feffffff0000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+fffffffffffffffffdfffffffeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
+ffffffffffffffffffffffffffffffff52006f006f007400200045006e00740072007900000000000000000000000000000000000000000000000000000000000000000000000000000000000000000016000500ffffffffffffffffffffffff0c6ad98892f1d411a65f0040963251e5000000000000000000000000e001
+8bcc2978d201feffffff00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffff00000000000000000000000000000000000000000000000000000000
+00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffff0000000000000000000000000000000000000000000000000000
+000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffff000000000000000000000000000000000000000000000000
+0000000000000000000000000000000000000000000000000105000000000000}}
\ No newline at end of file
diff --git a/misc/webApi/swagger.json b/misc/webApi/swagger.json
new file mode 100644
index 0000000..1cb7c99
--- /dev/null
+++ b/misc/webApi/swagger.json
@@ -0,0 +1 @@
+{"swagger":"2.0","info":{"version":"v1","title":"LanBackups API","description":"ASP.NET Core Web API for LAN Backup service","termsOfService":"None","contact":{"name":"Claudiu Farcas","url":"http://www.asp.net","email":""},"license":{"name":"Free as a bird","url":"http://url.com"}},"basePath":"/","paths":{"/api/BackupConfig":{"get":{"tags":["BackupConfig"],"summary":"retrieve all backup configurations","operationId":"ApiBackupConfigGet","consumes":[],"produces":["application/json"],"parameters":[{"name":"idx","in":"header","required":false,"type":"string"},{"name":"siz","in":"header","required":false,"type":"string"}],"responses":{"200":{"description":"Success","schema":{"$ref":"#/definitions/PaginatedList[BackupConfiguration,String]"}}},"deprecated":false},"post":{"tags":["BackupConfig"],"summary":"create backup configuration","operationId":"ApiBackupConfigPost","consumes":["application/json","text/json","application/json-patch+json"],"produces":["application/json"],"parameters":[{"name":"backup","in":"body","description":"","required":false,"schema":{"$ref":"#/definitions/BackupConfiguration"}}],"responses":{"200":{"description":"Success","schema":{"$ref":"#/definitions/BackupConfiguration"}},"400":{"description":"Client Error","schema":{"$ref":"#/definitions/BackupConfiguration"}}},"deprecated":false}},"/api/BackupConfig/{id}":{"get":{"tags":["BackupConfig"],"summary":"retrieve backup configuration by ID","operationId":"ApiBackupConfigByIdGet","consumes":[],"produces":["application/json"],"parameters":[{"name":"id","in":"path","description":"","required":true,"type":"string"}],"responses":{"200":{"description":"Success","schema":{"$ref":"#/definitions/BackupConfiguration"}},"404":{"description":"Client Error","schema":{"$ref":"#/definitions/BackupConfiguration"}}},"deprecated":false},"put":{"tags":["BackupConfig"],"summary":"Update backup configuration","operationId":"ApiBackupConfigByIdPut","consumes":["application/json","text/json","application/json-patch+json"],"produces":["application/json"],"parameters":[{"name":"id","in":"path","description":"","required":true,"type":"string"},{"name":"backup","in":"body","description":"","required":false,"schema":{"$ref":"#/definitions/BackupConfiguration"}}],"responses":{"200":{"description":"Success","schema":{"$ref":"#/definitions/BackupConfiguration"}},"400":{"description":"Client Error","schema":{"$ref":"#/definitions/BackupConfiguration"}}},"deprecated":false},"delete":{"tags":["BackupConfig"],"summary":"delete backup configuration by id","operationId":"ApiBackupConfigByIdDelete","consumes":[],"produces":["application/json"],"parameters":[{"name":"id","in":"path","description":"","required":true,"type":"string"}],"responses":{"200":{"description":"Success","schema":{"type":"string"}},"404":{"description":"Client Error","schema":{"type":"string"}}},"deprecated":false}},"/api/BackupConfig/client/{clientid}":{"get":{"tags":["BackupConfig"],"summary":"retrieve backup configuration by ID","operationId":"ApiBackupConfigClientByClientidGet","consumes":[],"produces":["application/json"],"parameters":[{"name":"clientid","in":"path","description":"","required":true,"type":"string"}],"responses":{"200":{"description":"Success","schema":{"type":"array","items":{"$ref":"#/definitions/BackupConfiguration"}}},"404":{"description":"Client Error","schema":{"type":"array","items":{"$ref":"#/definitions/BackupConfiguration"}}}},"deprecated":false}},"/api/Logs":{"get":{"tags":["Logs"],"summary":"retrieves paginated logs from DB","operationId":"ApiLogsGet","consumes":[],"produces":["application/json"],"parameters":[{"name":"idx","in":"header","description":"page index","required":false,"type":"string"},{"name":"siz","in":"header","description":"page size","required":false,"type":"string"}],"responses":{"200":{"description":"Success","schema":{"$ref":"#/definitions/PaginatedList[BackupLog,DateTime]"}}},"deprecated":false},"post":{"tags":["Logs"],"summary":"Create an entry in the logs","operationId":"ApiLogsPost","consumes":["application/json","text/json","application/json-patch+json"],"produces":["application/json"],"parameters":[{"name":"log","in":"body","description":"","required":false,"schema":{"$ref":"#/definitions/BackupLog"}}],"responses":{"200":{"description":"Success","schema":{"format":"int32","type":"integer"}},"400":{"description":"Client Error","schema":{"format":"int32","type":"integer"}}},"deprecated":false}},"/api/Logs/{id}":{"get":{"tags":["Logs"],"summary":"retrieves alog record by ID","operationId":"ApiLogsByIdGet","consumes":[],"produces":["application/json"],"parameters":[{"name":"id","in":"path","description":"","required":true,"type":"integer","format":"int32"}],"responses":{"200":{"description":"Success","schema":{"$ref":"#/definitions/BackupLog"}},"404":{"description":"Client Error","schema":{"$ref":"#/definitions/BackupLog"}}},"deprecated":false}},"/api/Logs/client/{clientid}":{"get":{"tags":["Logs"],"summary":"retrieve all logs of a clientIP","operationId":"ApiLogsClientByClientidGet","consumes":[],"produces":["application/json"],"parameters":[{"name":"clientid","in":"path","description":"","required":true,"type":"string"}],"responses":{"200":{"description":"Success","schema":{"type":"array","items":{"$ref":"#/definitions/BackupLog"}}},"404":{"description":"Client Error","schema":{"type":"array","items":{"$ref":"#/definitions/BackupLog"}}}},"deprecated":false}},"/api/Logs/config/{configurationid}":{"get":{"tags":["Logs"],"summary":"retrieves all logs of a specific configuration","operationId":"ApiLogsConfigByConfigurationidGet","consumes":[],"produces":["application/json"],"parameters":[{"name":"configurationid","in":"path","description":"","required":true,"type":"string"}],"responses":{"200":{"description":"Success","schema":{"type":"array","items":{"$ref":"#/definitions/BackupLog"}}},"404":{"description":"Client Error","schema":{"type":"array","items":{"$ref":"#/definitions/BackupLog"}}}},"deprecated":false}},"/api/Users/register":{"post":{"tags":["Users"],"operationId":"ApiUsersRegisterPost","consumes":["application/json","text/json","application/json-patch+json"],"produces":["application/json"],"parameters":[{"name":"dtouser","in":"body","required":false,"schema":{"$ref":"#/definitions/User"}}],"responses":{"200":{"description":"Success","schema":{"$ref":"#/definitions/IdentityResult"}},"400":{"description":"Client Error","schema":{"$ref":"#/definitions/IdentityResult"}}},"deprecated":false}},"/api/Users/login":{"post":{"tags":["Users"],"operationId":"ApiUsersLoginPost","consumes":["application/json","text/json","application/json-patch+json"],"produces":[],"parameters":[{"name":"dtouser","in":"body","required":false,"schema":{"$ref":"#/definitions/User"}}],"responses":{"200":{"description":"Success"}},"deprecated":false}},"/api/Users/pwchange":{"post":{"tags":["Users"],"operationId":"ApiUsersPwchangePost","consumes":["application/json","text/json","application/json-patch+json"],"produces":[],"parameters":[{"name":"dtouser","in":"body","required":false,"schema":{"$ref":"#/definitions/User"}}],"responses":{"200":{"description":"Success"}},"deprecated":false}},"/api/Users/list":{"get":{"tags":["Users"],"operationId":"ApiUsersListGet","consumes":[],"produces":[],"responses":{"200":{"description":"Success"}},"deprecated":false},"post":{"tags":["Users"],"operationId":"ApiUsersListPost","consumes":["application/json","text/json","application/json-patch+json"],"produces":[],"parameters":[{"name":"user","in":"body","required":false,"schema":{"$ref":"#/definitions/User"}}],"responses":{"200":{"description":"Success"}},"deprecated":false}}},"definitions":{"PaginatedList[BackupConfiguration,String]":{"type":"object","properties":{"pi":{"format":"int32","type":"integer"},"tp":{"format":"int32","type":"integer"},"recs":{"type":"array","items":{"$ref":"#/definitions/BackupConfiguration"}},"hp":{"type":"boolean","readOnly":true},"hn":{"type":"boolean","readOnly":true}}},"BackupConfiguration":{"required":["clientIP"],"type":"object","properties":{"id":{"type":"string"},"rowVersion":{"format":"byte","type":"string"},"clientIP":{"pattern":"^(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})$","type":"string"},"srcFolder":{"type":"string"},"srcUser":{"type":"string"},"srcPass":{"type":"string"},"destLanFolder":{"type":"string"},"destUser":{"type":"string"},"destPass":{"type":"string"},"isActive":{"type":"boolean"},"crontab":{"type":"string"}}},"PaginatedList[BackupLog,DateTime]":{"type":"object","properties":{"pi":{"format":"int32","type":"integer"},"tp":{"format":"int32","type":"integer"},"recs":{"type":"array","items":{"$ref":"#/definitions/BackupLog"}},"hp":{"type":"boolean","readOnly":true},"hn":{"type":"boolean","readOnly":true}}},"BackupLog":{"type":"object","properties":{"id":{"format":"int32","type":"integer"},"rowVersion":{"format":"byte","type":"string"},"clientIP":{"pattern":"^(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})$","type":"string"},"configurationID":{"type":"string"},"description":{"type":"string"},"logError":{"type":"string"},"status":{"type":"string"},"dateTime":{"format":"date-time","type":"string"}}},"User":{"type":"object","properties":{"email":{"type":"string"},"password":{"type":"string"},"newPassword":{"type":"string"},"isAdmin":{"type":"boolean"},"succeeded":{"type":"boolean"},"isLockedOut":{"type":"boolean"}}},"IdentityResult":{"type":"object","properties":{"succeeded":{"type":"boolean","readOnly":true},"errors":{"type":"array","items":{"$ref":"#/definitions/IdentityError"},"readOnly":true}}},"IdentityError":{"type":"object","properties":{"code":{"type":"string"},"description":{"type":"string"}}}},"securityDefinitions":{}}
\ No newline at end of file
diff --git a/src/LanBackup.DataCore/BackupsContext.cs b/src/LanBackup.DataCore/BackupsContext.cs
new file mode 100644
index 0000000..b35a32b
--- /dev/null
+++ b/src/LanBackup.DataCore/BackupsContext.cs
@@ -0,0 +1,30 @@
+using LanBackup.ModelsCore;
+using Microsoft.EntityFrameworkCore;
+
+namespace LanBackup.DataCore
+{
+ public class BackupsContext : DbContext
+ {
+ public BackupsContext(DbContextOptions options) : base(options)
+ { }
+
+ protected override void OnModelCreating(ModelBuilder modelBuilder)
+ {
+ //BackupConfiguration - entity
+ modelBuilder.Entity().ToTable("Backups");
+ modelBuilder.Entity().Property(p => p.RowVersion)
+ .IsRowVersion()
+ .IsConcurrencyToken();
+ modelBuilder.Entity().HasIndex(p => p.ClientIP);
+
+ //BackupLog - entity
+ modelBuilder.Entity().Property(p => p.ID).ValueGeneratedOnAdd(); //equivalent of [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
+ modelBuilder.Entity().HasIndex(p => p.ClientIP);
+ modelBuilder.Entity().HasIndex(p => p.ConfigurationID);
+
+ }
+
+ public DbSet Backups { get; set; }
+ public DbSet Logs { get; set; }
+ }
+}
diff --git a/src/LanBackup.DataCore/DatabaseManager.cs b/src/LanBackup.DataCore/DatabaseManager.cs
new file mode 100644
index 0000000..a1ee6ad
--- /dev/null
+++ b/src/LanBackup.DataCore/DatabaseManager.cs
@@ -0,0 +1,84 @@
+using System.Collections.Generic;
+using System.Linq;
+using LanBackup.ModelsCore;
+
+namespace LanBackup.DataCore
+{
+ ///
+ /// Database manager class (repository)
+ ///
+ public class DatabaseManager
+ {
+
+ private BackupsContext context;
+
+ ///
+ /// constructor
+ ///
+ ///
+ public DatabaseManager(BackupsContext mcontext)
+ {
+ context = mcontext;
+ }
+
+ ///
+ /// create a backup
+ ///
+ ///
+ /// the new backup ID
+ public string CreateBackupConfig(BackupConfiguration backup)
+ {
+ context.Backups.Add(backup);
+ context.SaveChanges();
+ return backup.ID;
+ }
+
+ ///
+ /// retrieve all backups
+ ///
+ ///
+ public IEnumerable GetBackupConfigs()
+ {
+ var list = context.Backups.ToList();
+ return list;
+ }
+
+ ///
+ /// gets the backup by ID
+ ///
+ /// backup ID
+ /// backup
+ public BackupConfiguration GetBackupConfig(string id)
+ {
+ return context.Backups.FirstOrDefault(b => b.ID == id);
+ }
+
+ public IEnumerable GetBackupConfigByClient(string clientid)
+ {
+ return context.Backups.Where(b => b.ClientIP == clientid);
+ }
+
+ ///
+ /// Update backup configuration
+ ///
+ ///
+ ///
+ public int UpdateBackupConfig(BackupConfiguration entity)
+ {
+ context.Backups.Update(entity);
+ return context.SaveChanges();
+ }
+
+ ///
+ /// delete backup configuration
+ ///
+ ///
+ ///
+ public int DeleteBackupConfig(string id)
+ {
+ BackupConfiguration entity = context.Backups.Find(id);
+ context.Backups.Remove(entity);
+ return context.SaveChanges();
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/LanBackup.DataCore.xproj b/src/LanBackup.DataCore/LanBackup.DataCore.xproj
new file mode 100644
index 0000000..76c6a09
--- /dev/null
+++ b/src/LanBackup.DataCore/LanBackup.DataCore.xproj
@@ -0,0 +1,19 @@
+
+
+
+ 14.0
+ $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)
+
+
+
+ b4144721-0f2c-4750-aba3-5238490a71ff
+ LanBackup.DataCore
+ .\obj
+ .\bin\
+ v4.6.2
+
+
+ 2.0
+
+
+
\ No newline at end of file
diff --git a/src/LanBackup.DataCore/Migrations/20170106103933_InitMigration.Designer.cs b/src/LanBackup.DataCore/Migrations/20170106103933_InitMigration.Designer.cs
new file mode 100644
index 0000000..9050b4e
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170106103933_InitMigration.Designer.cs
@@ -0,0 +1,50 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ [Migration("20170106103933_InitMigration")]
+ partial class InitMigration
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.ToTable("Backups");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170106103933_InitMigration.cs b/src/LanBackup.DataCore/Migrations/20170106103933_InitMigration.cs
new file mode 100644
index 0000000..db480b3
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170106103933_InitMigration.cs
@@ -0,0 +1,37 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public partial class InitMigration : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.CreateTable(
+ name: "Backups",
+ columns: table => new
+ {
+ ID = table.Column(nullable: false),
+ ClientIP = table.Column(nullable: false),
+ DestLanFolder = table.Column(nullable: true),
+ DestPass = table.Column(nullable: true),
+ DestUser = table.Column(nullable: true),
+ RowVersion = table.Column(rowVersion: true, nullable: true),
+ SrcFolder = table.Column(nullable: true),
+ SrcPass = table.Column(nullable: true),
+ SrcUser = table.Column(nullable: true)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_Backups", x => x.ID);
+ });
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropTable(
+ name: "Backups");
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170109195131_ExtraFields.Designer.cs b/src/LanBackup.DataCore/Migrations/20170109195131_ExtraFields.Designer.cs
new file mode 100644
index 0000000..f46c2b5
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170109195131_ExtraFields.Designer.cs
@@ -0,0 +1,54 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ [Migration("20170109195131_ExtraFields")]
+ partial class ExtraFields
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("Crontab");
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.ToTable("Backups");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170109195131_ExtraFields.cs b/src/LanBackup.DataCore/Migrations/20170109195131_ExtraFields.cs
new file mode 100644
index 0000000..9cb00ba
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170109195131_ExtraFields.cs
@@ -0,0 +1,43 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public partial class ExtraFields : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.AlterColumn(
+ name: "ClientIP",
+ table: "Backups",
+ nullable: false);
+
+ migrationBuilder.AddColumn(
+ name: "Crontab",
+ table: "Backups",
+ nullable: true);
+
+ migrationBuilder.CreateIndex(
+ name: "IX_Backups_ClientIP",
+ table: "Backups",
+ column: "ClientIP");
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropIndex(
+ name: "IX_Backups_ClientIP",
+ table: "Backups");
+
+ migrationBuilder.DropColumn(
+ name: "Crontab",
+ table: "Backups");
+
+ migrationBuilder.AlterColumn(
+ name: "ClientIP",
+ table: "Backups",
+ nullable: false);
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170110003346_LogsTable.Designer.cs b/src/LanBackup.DataCore/Migrations/20170110003346_LogsTable.Designer.cs
new file mode 100644
index 0000000..54bd69d
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170110003346_LogsTable.Designer.cs
@@ -0,0 +1,83 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ [Migration("20170110003346_LogsTable")]
+ partial class LogsTable
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("Crontab");
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.ToTable("Backups");
+ });
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupLog", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd()
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("ClientIP");
+
+ b.Property("ConfigurationID");
+
+ b.Property("Description");
+
+ b.Property("Error");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("Status");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.HasIndex("ConfigurationID");
+
+ b.ToTable("BackupLog");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170110003346_LogsTable.cs b/src/LanBackup.DataCore/Migrations/20170110003346_LogsTable.cs
new file mode 100644
index 0000000..b519f52
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170110003346_LogsTable.cs
@@ -0,0 +1,47 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore.Migrations;
+using Microsoft.EntityFrameworkCore.Metadata;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public partial class LogsTable : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.CreateTable(
+ name: "BackupLog",
+ columns: table => new
+ {
+ ID = table.Column(nullable: false)
+ .Annotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn),
+ ClientIP = table.Column(nullable: true),
+ ConfigurationID = table.Column(nullable: true),
+ Description = table.Column(nullable: true),
+ Error = table.Column(nullable: true),
+ RowVersion = table.Column(rowVersion: true, nullable: true),
+ Status = table.Column(nullable: true)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_BackupLog", x => x.ID);
+ });
+
+ migrationBuilder.CreateIndex(
+ name: "IX_BackupLog_ClientIP",
+ table: "BackupLog",
+ column: "ClientIP");
+
+ migrationBuilder.CreateIndex(
+ name: "IX_BackupLog_ConfigurationID",
+ table: "BackupLog",
+ column: "ConfigurationID");
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropTable(
+ name: "BackupLog");
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170110025655_MissedThings.Designer.cs b/src/LanBackup.DataCore/Migrations/20170110025655_MissedThings.Designer.cs
new file mode 100644
index 0000000..e505991
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170110025655_MissedThings.Designer.cs
@@ -0,0 +1,83 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ [Migration("20170110025655_MissedThings")]
+ partial class MissedThings
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("Crontab");
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.ToTable("Backups");
+ });
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupLog", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd()
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("ClientIP");
+
+ b.Property("ConfigurationID");
+
+ b.Property("Description");
+
+ b.Property("Error");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("Status");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.HasIndex("ConfigurationID");
+
+ b.ToTable("Logs");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170110025655_MissedThings.cs b/src/LanBackup.DataCore/Migrations/20170110025655_MissedThings.cs
new file mode 100644
index 0000000..a02ed3e
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170110025655_MissedThings.cs
@@ -0,0 +1,61 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public partial class MissedThings : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropPrimaryKey(
+ name: "PK_BackupLog",
+ table: "BackupLog");
+
+ migrationBuilder.RenameTable(
+ name: "BackupLog",
+ newName: "Logs");
+
+ migrationBuilder.RenameIndex(
+ name: "IX_BackupLog_ConfigurationID",
+ table: "Logs",
+ newName: "IX_Logs_ConfigurationID");
+
+ migrationBuilder.RenameIndex(
+ name: "IX_BackupLog_ClientIP",
+ table: "Logs",
+ newName: "IX_Logs_ClientIP");
+
+ migrationBuilder.AddPrimaryKey(
+ name: "PK_Logs",
+ table: "Logs",
+ column: "ID");
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropPrimaryKey(
+ name: "PK_Logs",
+ table: "Logs");
+
+ migrationBuilder.RenameTable(
+ name: "Logs",
+ newName: "BackupLog");
+
+ migrationBuilder.RenameIndex(
+ name: "IX_Logs_ConfigurationID",
+ table: "BackupLog",
+ newName: "IX_BackupLog_ConfigurationID");
+
+ migrationBuilder.RenameIndex(
+ name: "IX_Logs_ClientIP",
+ table: "BackupLog",
+ newName: "IX_BackupLog_ClientIP");
+
+ migrationBuilder.AddPrimaryKey(
+ name: "PK_BackupLog",
+ table: "BackupLog",
+ column: "ID");
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170114002049_ExtraFieldsAndValidation.Designer.cs b/src/LanBackup.DataCore/Migrations/20170114002049_ExtraFieldsAndValidation.Designer.cs
new file mode 100644
index 0000000..776a7c1
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170114002049_ExtraFieldsAndValidation.Designer.cs
@@ -0,0 +1,85 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ [Migration("20170114002049_ExtraFieldsAndValidation")]
+ partial class ExtraFieldsAndValidation
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("Crontab");
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("IsActive");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.ToTable("Backups");
+ });
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupLog", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd()
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("ClientIP");
+
+ b.Property("ConfigurationID");
+
+ b.Property("Description");
+
+ b.Property("Error");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("Status");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.HasIndex("ConfigurationID");
+
+ b.ToTable("Logs");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170114002049_ExtraFieldsAndValidation.cs b/src/LanBackup.DataCore/Migrations/20170114002049_ExtraFieldsAndValidation.cs
new file mode 100644
index 0000000..635fc1b
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170114002049_ExtraFieldsAndValidation.cs
@@ -0,0 +1,25 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public partial class ExtraFieldsAndValidation : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.AddColumn(
+ name: "IsActive",
+ table: "Backups",
+ nullable: false,
+ defaultValue: false);
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropColumn(
+ name: "IsActive",
+ table: "Backups");
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170114093121_AddDateTimeToLog.Designer.cs b/src/LanBackup.DataCore/Migrations/20170114093121_AddDateTimeToLog.Designer.cs
new file mode 100644
index 0000000..d42a516
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170114093121_AddDateTimeToLog.Designer.cs
@@ -0,0 +1,87 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ [Migration("20170114093121_AddDateTimeToLog")]
+ partial class AddDateTimeToLog
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("Crontab");
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("IsActive");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.ToTable("Backups");
+ });
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupLog", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd()
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("ClientIP");
+
+ b.Property("ConfigurationID");
+
+ b.Property("DateTime");
+
+ b.Property("Description");
+
+ b.Property("Error");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("Status");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.HasIndex("ConfigurationID");
+
+ b.ToTable("Logs");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170114093121_AddDateTimeToLog.cs b/src/LanBackup.DataCore/Migrations/20170114093121_AddDateTimeToLog.cs
new file mode 100644
index 0000000..6879140
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170114093121_AddDateTimeToLog.cs
@@ -0,0 +1,25 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public partial class AddDateTimeToLog : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.AddColumn(
+ name: "DateTime",
+ table: "Logs",
+ nullable: false,
+ defaultValue: new DateTime(1, 1, 1, 0, 0, 0, 0, DateTimeKind.Unspecified));
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropColumn(
+ name: "DateTime",
+ table: "Logs");
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170114122456_ChangedFieldName.Designer.cs b/src/LanBackup.DataCore/Migrations/20170114122456_ChangedFieldName.Designer.cs
new file mode 100644
index 0000000..5a39bfe
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170114122456_ChangedFieldName.Designer.cs
@@ -0,0 +1,87 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ [Migration("20170114122456_ChangedFieldName")]
+ partial class ChangedFieldName
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("Crontab");
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("IsActive");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.ToTable("Backups");
+ });
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupLog", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd()
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("ClientIP");
+
+ b.Property("ConfigurationID");
+
+ b.Property("DateTime");
+
+ b.Property("Description");
+
+ b.Property("LogError");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("Status");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.HasIndex("ConfigurationID");
+
+ b.ToTable("Logs");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/20170114122456_ChangedFieldName.cs b/src/LanBackup.DataCore/Migrations/20170114122456_ChangedFieldName.cs
new file mode 100644
index 0000000..cf06900
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/20170114122456_ChangedFieldName.cs
@@ -0,0 +1,25 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public partial class ChangedFieldName : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.RenameColumn(
+ name: "Error",
+ table: "Logs",
+ newName: "LogError");
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.RenameColumn(
+ name: "LogError",
+ table: "Logs",
+ newName: "Error");
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/BackupsContextModelSnapshot.cs b/src/LanBackup.DataCore/Migrations/BackupsContextModelSnapshot.cs
new file mode 100644
index 0000000..b67a51d
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/BackupsContextModelSnapshot.cs
@@ -0,0 +1,86 @@
+using System;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+using LanBackup.DataCore;
+
+namespace LanBackup.DataCore.Migrations
+{
+ [DbContext(typeof(BackupsContext))]
+ partial class BackupsContextModelSnapshot : ModelSnapshot
+ {
+ protected override void BuildModel(ModelBuilder modelBuilder)
+ {
+ modelBuilder
+ .HasAnnotation("ProductVersion", "1.1.0-rtm-22752")
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupConfiguration", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd();
+
+ b.Property("ClientIP")
+ .IsRequired();
+
+ b.Property("Crontab");
+
+ b.Property("DestLanFolder");
+
+ b.Property("DestPass");
+
+ b.Property("DestUser");
+
+ b.Property("IsActive");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("SrcFolder");
+
+ b.Property("SrcPass");
+
+ b.Property("SrcUser");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.ToTable("Backups");
+ });
+
+ modelBuilder.Entity("LanBackup.ModelsCore.BackupLog", b =>
+ {
+ b.Property("ID")
+ .ValueGeneratedOnAdd()
+ .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
+
+ b.Property("ClientIP");
+
+ b.Property("ConfigurationID");
+
+ b.Property("DateTime");
+
+ b.Property("Description");
+
+ b.Property("LogError");
+
+ b.Property("RowVersion")
+ .IsConcurrencyToken()
+ .ValueGeneratedOnAddOrUpdate();
+
+ b.Property("Status");
+
+ b.HasKey("ID");
+
+ b.HasIndex("ClientIP");
+
+ b.HasIndex("ConfigurationID");
+
+ b.ToTable("Logs");
+ });
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Migrations/MigrationsContextFactory.cs b/src/LanBackup.DataCore/Migrations/MigrationsContextFactory.cs
new file mode 100644
index 0000000..3f9653e
--- /dev/null
+++ b/src/LanBackup.DataCore/Migrations/MigrationsContextFactory.cs
@@ -0,0 +1,23 @@
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.Extensions.Configuration;
+using System.IO;
+
+namespace LanBackup.DataCore.Migrations
+{
+ public class MigrationsContextFactory : IDbContextFactory
+ {
+ public BackupsContext Create(DbContextFactoryOptions foptions)
+ {
+ var config = new ConfigurationBuilder()
+ .SetBasePath(Directory.GetCurrentDirectory())
+ .AddJsonFile("appsettings.json")
+ .Build();
+
+ var options = new DbContextOptionsBuilder();
+ options.UseSqlServer(config.GetConnectionString("BackupsConnectionString"));
+
+ return new BackupsContext(options.Options);
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/Program.cs b/src/LanBackup.DataCore/Program.cs
new file mode 100644
index 0000000..369255f
--- /dev/null
+++ b/src/LanBackup.DataCore/Program.cs
@@ -0,0 +1,14 @@
+namespace LanBackup.DataCore
+{
+ ///
+ /// Start class
+ ///
+ public class Program
+ {
+ ///
+ /// Entry point
+ ///
+ /// arguments
+ public static void Main(string[] args) { }
+ }
+}
diff --git a/src/LanBackup.DataCore/Properties/AssemblyInfo.cs b/src/LanBackup.DataCore/Properties/AssemblyInfo.cs
new file mode 100644
index 0000000..341658f
--- /dev/null
+++ b/src/LanBackup.DataCore/Properties/AssemblyInfo.cs
@@ -0,0 +1,19 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("LanBackup.DataCore")]
+[assembly: AssemblyTrademark("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("b4144721-0f2c-4750-aba3-5238490a71ff")]
diff --git a/src/LanBackup.DataCore/appsettings.json b/src/LanBackup.DataCore/appsettings.json
new file mode 100644
index 0000000..e3eb32b
--- /dev/null
+++ b/src/LanBackup.DataCore/appsettings.json
@@ -0,0 +1,13 @@
+{
+ "ConnectionStrings": {
+ "BackupsConnectionString": "Server=(localdb)\\mssqllocaldb;Database=BackupsLAN;Trusted_Connection=True;"
+ },
+ "Logging": {
+ "IncludeScopes": false,
+ "LogLevel": {
+ "Default": "Debug",
+ "System": "Information",
+ "Microsoft": "Information"
+ }
+ }
+}
diff --git a/src/LanBackup.DataCore/project.json b/src/LanBackup.DataCore/project.json
new file mode 100644
index 0000000..3262cc2
--- /dev/null
+++ b/src/LanBackup.DataCore/project.json
@@ -0,0 +1,41 @@
+{
+ "version": "1.0.0-*",
+
+ "buildOptions": {
+ "emitEntryPoint": true,
+ "copyToOutput": {
+ "includeFiles": "appsettings.json"
+ },
+ "xmlDoc": true,
+ "additionalArguments": [ "/ruleset:../../misc/_stylecop/StyleCopeRules.ruleset", "/additionalfile:../../misc/_stylecop/stylecop.json" ]
+ },
+
+ "dependencies": {
+ "NETStandard.Library": "1.6.1",
+ "Microsoft.Extensions.Configuration.Json": "1.1.0",
+ "Microsoft.Extensions.Configuration.FileExtensions": "1.1.0",
+ "Microsoft.Extensions.Configuration": "1.1.0",
+ "Microsoft.EntityFrameworkCore.Tools": "1.0.0-preview4-final",
+ "Microsoft.EntityFrameworkCore.SqlServer": "1.1.0",
+ "Microsoft.EntityFrameworkCore": "1.1.0",
+ "LanBackup.ModelsCore": "1.0.0-*",
+ "StyleCop.Analyzers": "1.1.0-beta001"
+ },
+
+ "tools": {
+ "Microsoft.EntityFrameworkCore.Tools": "1.0.0-preview4-final",
+ "Microsoft.EntityFrameworkCore.Tools.DotNet": "1.0.0-preview3-final"
+ },
+
+ "frameworks": {
+ "netcoreapp1.0": {
+ "dependencies": {
+ "Microsoft.NETCore.App": {
+ "type": "platform",
+ "version": "1.1.0"
+ }
+ }
+ }
+ }
+
+}
diff --git a/src/LanBackup.ModelsCore/BackupConfiguration.cs b/src/LanBackup.ModelsCore/BackupConfiguration.cs
new file mode 100644
index 0000000..4784397
--- /dev/null
+++ b/src/LanBackup.ModelsCore/BackupConfiguration.cs
@@ -0,0 +1,54 @@
+using System.ComponentModel.DataAnnotations;
+
+namespace LanBackup.ModelsCore
+{
+ public class BackupConfiguration
+ {
+ public BackupConfiguration()
+ {
+ }
+
+ [Key]
+ public string ID { get; set; }
+
+
+ [Timestamp]
+ [ConcurrencyCheck]
+ public byte[] RowVersion { get; set; }
+
+
+ [RegularExpression(@"^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$")]
+ [Required]
+ [Display(Name = "Client IP")]
+ public string ClientIP { get; set; }
+
+ [Display(Name = "Source folder")]
+ public string SrcFolder { get; set; }
+
+ [Display(Name = "Source folder Username")]
+ public string SrcUser { get; set; }
+
+ [Display(Name = "Source folder Password")]
+ public string SrcPass { get; set; }
+
+ [Display(Name = "Destination LAN folder")]
+ public string DestLanFolder { get; set; }
+
+ [Display(Name = "Destination folder Username")]
+ public string DestUser { get; set; }
+
+ [Display(Name = "Destination folder Password")]
+ public string DestPass { get; set; }
+
+ [Display(Name = "Is Backup Active")]
+ public bool IsActive { get; set; }
+
+
+
+ //TODO - validate to be a CRONTAB expression
+ //[RegularExpression(@"^[A-Z]+[a-zA-Z''-'\s]*$")]
+ [Display(Name = "Crontab schedule expression")]
+ public string Crontab { get; set; }
+
+ }
+}
diff --git a/src/LanBackup.ModelsCore/BackupLog.cs b/src/LanBackup.ModelsCore/BackupLog.cs
new file mode 100644
index 0000000..a645f0d
--- /dev/null
+++ b/src/LanBackup.ModelsCore/BackupLog.cs
@@ -0,0 +1,47 @@
+using System;
+using System.ComponentModel.DataAnnotations;
+using System.ComponentModel.DataAnnotations.Schema;
+
+namespace LanBackup.ModelsCore
+{
+ public class BackupLog
+ {
+
+ public BackupLog()
+ { }
+
+
+ [Key]
+ [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
+ public int ID { get; set; }
+
+
+ [Timestamp]
+ [ConcurrencyCheck]
+ public byte[] RowVersion { get; set; }
+
+
+ [RegularExpression(@"^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$")]
+ [Display(Name = "Client IP")]
+ public string ClientIP { get; set; }
+
+ [Display(Name = "Configuration IP")]
+ public string ConfigurationID { get; set; }
+
+ [Display(Name = "Description")]
+ public string Description { get; set; }
+
+ [Display(Name = "LogError")]
+ public string LogError { get; set; }
+
+ [Display(Name = "Status")]
+ public string Status { get; set; }
+
+
+ [Display(Name = "DateTime")]
+ public DateTime DateTime { get; set; }
+
+
+ }
+
+}
diff --git a/src/LanBackup.ModelsCore/LanBackup.ModelsCore.xproj b/src/LanBackup.ModelsCore/LanBackup.ModelsCore.xproj
new file mode 100644
index 0000000..6bbefbd
--- /dev/null
+++ b/src/LanBackup.ModelsCore/LanBackup.ModelsCore.xproj
@@ -0,0 +1,21 @@
+
+
+
+ 14.0
+ $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)
+
+
+
+
+ cdc21836-c111-4db4-96c1-a37128df2127
+ LanBackup.ModelsCore
+ .\obj
+ .\bin\
+ v4.6.2
+
+
+
+ 2.0
+
+
+
diff --git a/src/LanBackup.ModelsCore/Properties/AssemblyInfo.cs b/src/LanBackup.ModelsCore/Properties/AssemblyInfo.cs
new file mode 100644
index 0000000..1ce8861
--- /dev/null
+++ b/src/LanBackup.ModelsCore/Properties/AssemblyInfo.cs
@@ -0,0 +1,19 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("LanBackup.ModelsCore")]
+[assembly: AssemblyTrademark("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("cdc21836-c111-4db4-96c1-a37128df2127")]
diff --git a/src/LanBackup.ModelsCore/project.json b/src/LanBackup.ModelsCore/project.json
new file mode 100644
index 0000000..65034b1
--- /dev/null
+++ b/src/LanBackup.ModelsCore/project.json
@@ -0,0 +1,15 @@
+{
+ "version": "1.0.0-*",
+
+ "dependencies": {
+ "NETStandard.Library": "1.6.1",
+ "System.ComponentModel.Annotations": "4.3.0",
+ "Microsoft.EntityFrameworkCore": "1.1.0"
+ },
+
+ "frameworks": {
+ "netstandard1.6": {
+ "imports": "dnxcore50"
+ }
+ }
+}
diff --git a/src/LanBackup.WebApp/.dockerignore b/src/LanBackup.WebApp/.dockerignore
new file mode 100644
index 0000000..63d337d
--- /dev/null
+++ b/src/LanBackup.WebApp/.dockerignore
@@ -0,0 +1,2 @@
+docker-compose.yml
+Dockerfile
diff --git a/src/LanBackup.WebApp/.gitignore b/src/LanBackup.WebApp/.gitignore
new file mode 100644
index 0000000..ded4b28
--- /dev/null
+++ b/src/LanBackup.WebApp/.gitignore
@@ -0,0 +1,248 @@
+/Properties/launchSettings.json
+
+## Ignore Visual Studio temporary files, build results, and
+## files generated by popular Visual Studio add-ons.
+
+# User-specific files
+*.suo
+*.user
+*.userosscache
+*.sln.docstates
+
+# User-specific files (MonoDevelop/Xamarin Studio)
+*.userprefs
+
+# Build results
+[Dd]ebug/
+[Dd]ebugPublic/
+[Rr]elease/
+[Rr]eleases/
+x64/
+x86/
+build/
+bld/
+bin/
+Bin/
+obj/
+Obj/
+
+# Visual Studio 2015 cache/options directory
+.vs/
+/wwwroot/dist/**
+/ClientApp/dist/**
+
+# Workaround for https://github.com/aspnet/JavaScriptServices/issues/235
+!/wwwroot/dist/_placeholder.txt
+!/ClientApp/dist/_placeholder.txt
+
+
+# MSTest test Results
+[Tt]est[Rr]esult*/
+[Bb]uild[Ll]og.*
+
+# NUNIT
+*.VisualState.xml
+TestResult.xml
+
+# Build Results of an ATL Project
+[Dd]ebugPS/
+[Rr]eleasePS/
+dlldata.c
+
+# DNX
+project.lock.json
+artifacts/
+
+*_i.c
+*_p.c
+*_i.h
+*.ilk
+*.meta
+*.obj
+*.pch
+*.pdb
+*.pgc
+*.pgd
+*.rsp
+*.sbr
+*.tlb
+*.tli
+*.tlh
+*.tmp
+*.tmp_proj
+*.log
+*.vspscc
+*.vssscc
+.builds
+*.pidb
+*.svclog
+*.scc
+
+# Chutzpah Test files
+_Chutzpah*
+
+# Visual C++ cache files
+ipch/
+*.aps
+*.ncb
+*.opendb
+*.opensdf
+*.sdf
+*.cachefile
+
+# Visual Studio profiler
+*.psess
+*.vsp
+*.vspx
+*.sap
+
+# TFS 2012 Local Workspace
+$tf/
+
+# Guidance Automation Toolkit
+*.gpState
+
+# ReSharper is a .NET coding add-in
+_ReSharper*/
+*.[Rr]e[Ss]harper
+*.DotSettings.user
+
+# JustCode is a .NET coding add-in
+.JustCode
+
+# TeamCity is a build add-in
+_TeamCity*
+
+# DotCover is a Code Coverage Tool
+*.dotCover
+
+# NCrunch
+_NCrunch_*
+.*crunch*.local.xml
+nCrunchTemp_*
+
+# MightyMoose
+*.mm.*
+AutoTest.Net/
+
+# Web workbench (sass)
+.sass-cache/
+
+# Installshield output folder
+[Ee]xpress/
+
+# DocProject is a documentation generator add-in
+DocProject/buildhelp/
+DocProject/Help/*.HxT
+DocProject/Help/*.HxC
+DocProject/Help/*.hhc
+DocProject/Help/*.hhk
+DocProject/Help/*.hhp
+DocProject/Help/Html2
+DocProject/Help/html
+
+# Click-Once directory
+publish/
+
+# Publish Web Output
+*.[Pp]ublish.xml
+*.azurePubxml
+# TODO: Comment the next line if you want to checkin your web deploy settings
+# but database connection strings (with potential passwords) will be unencrypted
+*.pubxml
+*.publishproj
+
+# NuGet Packages
+*.nupkg
+# The packages folder can be ignored because of Package Restore
+**/packages/*
+# except build/, which is used as an MSBuild target.
+!**/packages/build/
+# Uncomment if necessary however generally it will be regenerated when needed
+#!**/packages/repositories.config
+
+# Microsoft Azure Build Output
+csx/
+*.build.csdef
+
+# Microsoft Azure Emulator
+ecf/
+rcf/
+
+# Microsoft Azure ApplicationInsights config file
+ApplicationInsights.config
+
+# Windows Store app package directory
+AppPackages/
+BundleArtifacts/
+
+# Visual Studio cache files
+# files ending in .cache can be ignored
+*.[Cc]ache
+# but keep track of directories ending in .cache
+!*.[Cc]ache/
+
+# Others
+ClientBin/
+~$*
+*~
+*.dbmdl
+*.dbproj.schemaview
+*.pfx
+*.publishsettings
+orleans.codegen.cs
+
+# Workaround for https://github.com/aspnet/JavaScriptServices/issues/235
+/node_modules/**
+!/node_modules/_placeholder.txt
+
+/yarn.lock
+
+# RIA/Silverlight projects
+Generated_Code/
+
+# Backup & report files from converting an old project file
+# to a newer Visual Studio version. Backup files are not needed,
+# because we have git ;-)
+_UpgradeReport_Files/
+Backup*/
+UpgradeLog*.XML
+UpgradeLog*.htm
+
+# SQL Server files
+*.mdf
+*.ldf
+
+# Business Intelligence projects
+*.rdl.data
+*.bim.layout
+*.bim_*.settings
+
+# Microsoft Fakes
+FakesAssemblies/
+
+# GhostDoc plugin setting file
+*.GhostDoc.xml
+
+# Node.js Tools for Visual Studio
+.ntvs_analysis.dat
+
+# Visual Studio 6 build log
+*.plg
+
+# Visual Studio 6 workspace options file
+*.opt
+
+# Visual Studio LightSwitch build output
+**/*.HTMLClient/GeneratedArtifacts
+**/*.DesktopClient/GeneratedArtifacts
+**/*.DesktopClient/ModelManifest.xml
+**/*.Server/GeneratedArtifacts
+**/*.Server/ModelManifest.xml
+_Pvt_Extensions
+
+# Paket dependency manager
+.paket/paket.exe
+
+# FAKE - F# Make
+.fake/
diff --git a/src/LanBackup.WebApp/.vscode/launch.json b/src/LanBackup.WebApp/.vscode/launch.json
new file mode 100644
index 0000000..4bec0a4
--- /dev/null
+++ b/src/LanBackup.WebApp/.vscode/launch.json
@@ -0,0 +1,42 @@
+{
+ "version": "0.2.0",
+ "configurations": [
+ {
+ "name": ".NET Core Launch (web)",
+ "type": "coreclr",
+ "request": "launch",
+ "preLaunchTask": "build",
+ "program": "${workspaceRoot}\\bin\\Debug\\netcoreapp1.1\\aspa.dll",
+ "args": [],
+ "cwd": "${workspaceRoot}",
+ "stopAtEntry": false,
+ "internalConsoleOptions": "openOnSessionStart",
+ "launchBrowser": {
+ "enabled": true,
+ "args": "${auto-detect-url}",
+ "windows": {
+ "command": "cmd.exe",
+ "args": "/C start ${auto-detect-url}"
+ },
+ "osx": {
+ "command": "open"
+ },
+ "linux": {
+ "command": "xdg-open"
+ }
+ },
+ "env": {
+ "ASPNETCORE_ENVIRONMENT": "Development"
+ },
+ "sourceFileMap": {
+ "/Views": "${workspaceRoot}/Views"
+ }
+ },
+ {
+ "name": ".NET Core Attach",
+ "type": "coreclr",
+ "request": "attach",
+ "processId": "${command.pickProcess}"
+ }
+ ]
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/.vscode/tasks.json b/src/LanBackup.WebApp/.vscode/tasks.json
new file mode 100644
index 0000000..9cd37c1
--- /dev/null
+++ b/src/LanBackup.WebApp/.vscode/tasks.json
@@ -0,0 +1,16 @@
+{
+ "version": "0.1.0",
+ "command": "dotnet",
+ "isShellCommand": true,
+ "args": [],
+ "tasks": [
+ {
+ "taskName": "build",
+ "args": [
+ "${workspaceRoot}\\project.json"
+ ],
+ "isBuildCommand": true,
+ "problemMatcher": "$msCompile"
+ }
+ ]
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/app.module.ts b/src/LanBackup.WebApp/ClientApp/app/app.module.ts
new file mode 100644
index 0000000..e8c33f4
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/app.module.ts
@@ -0,0 +1,92 @@
+import { NgModule } from '@angular/core';
+import { RouterModule } from '@angular/router';
+import { UniversalModule } from 'angular2-universal';
+import { AppComponent } from './components/app/app.component'
+import { NavMenuComponent } from './components/navmenu/navmenu.component';
+import { BackupsComponent } from './components/backups/backups.component';
+import { LoginComponent } from './components/login/login.component';
+import { ProfileComponent } from './components/profile/profile.component';
+import { LogsComponent } from './components/logs/logs.component';
+import { UsersComponent } from './components/users/users.component';
+import { DashboardComponent } from './components/dashboard/dashboard.component';
+
+
+import { WebApiService } from './services/webapi.service';
+import { AuthenticationService } from './services/authentication.service';
+import { Ng2PaginationModule } from './shared/ng2-pagination/ng2-pagination'; // <-- import the module
+import { FormsModule } from '@angular/forms';
+import { AuthGuard } from './services/authguard';
+import { ModalComponent } from './shared/modal/modal.component';
+import { BrowserModule } from "@angular/platform-browser";
+
+import { ToastyModule } from 'ng2-toasty';
+
+import { MessageService } from './services/message.service';
+import { NotificationsService } from './services/notifications.service';
+import { AgentsService } from './services/agents.service';
+
+
+import { LoggerService } from './services/logger.service';
+import { Ng2SwitchComponent } from './shared/ng2-switch/ng2-switch';
+import { Progress } from './shared/progressbar/progress';
+import { Bar } from './shared/progressbar/bar';
+import { Progressbar } from './shared/progressbar/progressbar';
+import { AppInsightsModule } from 'ng2-appinsights';
+
+
+import { SharedModule } from './shared/global/SharedModule';
+
+
+
+@NgModule({
+ bootstrap: [AppComponent],
+ declarations: [
+ AppComponent,
+ NavMenuComponent,
+ Progress,
+ Bar,
+ Progressbar,
+ BackupsComponent,
+ LoginComponent,
+ ProfileComponent,
+ ModalComponent,
+ Ng2SwitchComponent,
+ LogsComponent,
+ UsersComponent,
+ DashboardComponent
+ ],
+ imports: [
+ UniversalModule, // Must be first import. This automatically imports BrowserModule, HttpModule, and JsonpModule too.
+ RouterModule.forRoot([
+ { path: '', redirectTo: 'dashboard', pathMatch: 'full' },
+ { path: 'dashboard', component: DashboardComponent },
+ { path: 'backups', component: BackupsComponent },
+ { path: 'logs', component: LogsComponent },
+ { path: 'users', component: UsersComponent, canActivate: [AuthGuard] },
+ { path: 'login', component: LoginComponent },
+ { path: 'profile', component: ProfileComponent, canActivate: [AuthGuard] },
+ { path: '**', redirectTo: 'dashboard' }
+ ]),
+ Ng2PaginationModule,
+ FormsModule,
+ ToastyModule.forRoot(),
+ AppInsightsModule,
+ SharedModule.forBrowser()
+ ],
+ providers: [
+ LoggerService,
+ MessageService,
+ WebApiService,
+ AuthenticationService,
+ AuthGuard,
+ NotificationsService,
+ AgentsService
+ ]
+})
+export class AppModule {
+
+ public AppModule() {
+ console.log('AppModule');
+ }
+
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/bootswatch/css/bootstrap_yeti.css b/src/LanBackup.WebApp/ClientApp/app/bootswatch/css/bootstrap_yeti.css
new file mode 100644
index 0000000..f90228f
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/bootswatch/css/bootstrap_yeti.css
@@ -0,0 +1,7070 @@
+@import url("https://fonts.googleapis.com/css?family=Open+Sans:300italic,400italic,700italic,400,300,700");
+/*!
+ * bootswatch v3.3.7
+ * Homepage: http://bootswatch.com
+ * Copyright 2012-2016 Thomas Park
+ * Licensed under MIT
+ * Based on Bootstrap
+*/
+/*!
+ * Bootstrap v3.3.7 (http://getbootstrap.com)
+ * Copyright 2011-2016 Twitter, Inc.
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ */
+/*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */
+html {
+ font-family: sans-serif;
+ -ms-text-size-adjust: 100%;
+ -webkit-text-size-adjust: 100%;
+}
+body {
+ margin: 0;
+}
+article,
+aside,
+details,
+figcaption,
+figure,
+footer,
+header,
+hgroup,
+main,
+menu,
+nav,
+section,
+summary {
+ display: block;
+}
+audio,
+canvas,
+progress,
+video {
+ display: inline-block;
+ vertical-align: baseline;
+}
+audio:not([controls]) {
+ display: none;
+ height: 0;
+}
+[hidden],
+template {
+ display: none;
+}
+a {
+ background-color: transparent;
+}
+a:active,
+a:hover {
+ outline: 0;
+}
+abbr[title] {
+ border-bottom: 1px dotted;
+}
+b,
+strong {
+ font-weight: bold;
+}
+dfn {
+ font-style: italic;
+}
+h1 {
+ font-size: 2em;
+ margin: 0.67em 0;
+}
+mark {
+ background: #ff0;
+ color: #000;
+}
+small {
+ font-size: 80%;
+}
+sub,
+sup {
+ font-size: 75%;
+ line-height: 0;
+ position: relative;
+ vertical-align: baseline;
+}
+sup {
+ top: -0.5em;
+}
+sub {
+ bottom: -0.25em;
+}
+img {
+ border: 0;
+}
+svg:not(:root) {
+ overflow: hidden;
+}
+figure {
+ margin: 1em 40px;
+}
+hr {
+ -webkit-box-sizing: content-box;
+ -moz-box-sizing: content-box;
+ box-sizing: content-box;
+ height: 0;
+}
+pre {
+ overflow: auto;
+}
+code,
+kbd,
+pre,
+samp {
+ font-family: monospace, monospace;
+ font-size: 1em;
+}
+button,
+input,
+optgroup,
+select,
+textarea {
+ color: inherit;
+ font: inherit;
+ margin: 0;
+}
+button {
+ overflow: visible;
+}
+button,
+select {
+ text-transform: none;
+}
+button,
+html input[type="button"],
+input[type="reset"],
+input[type="submit"] {
+ -webkit-appearance: button;
+ cursor: pointer;
+}
+button[disabled],
+html input[disabled] {
+ cursor: default;
+}
+button::-moz-focus-inner,
+input::-moz-focus-inner {
+ border: 0;
+ padding: 0;
+}
+input {
+ line-height: normal;
+}
+input[type="checkbox"],
+input[type="radio"] {
+ -webkit-box-sizing: border-box;
+ -moz-box-sizing: border-box;
+ box-sizing: border-box;
+ padding: 0;
+}
+input[type="number"]::-webkit-inner-spin-button,
+input[type="number"]::-webkit-outer-spin-button {
+ height: auto;
+}
+input[type="search"] {
+ -webkit-appearance: textfield;
+ -webkit-box-sizing: content-box;
+ -moz-box-sizing: content-box;
+ box-sizing: content-box;
+}
+input[type="search"]::-webkit-search-cancel-button,
+input[type="search"]::-webkit-search-decoration {
+ -webkit-appearance: none;
+}
+fieldset {
+ border: 1px solid #c0c0c0;
+ margin: 0 2px;
+ padding: 0.35em 0.625em 0.75em;
+}
+legend {
+ border: 0;
+ padding: 0;
+}
+textarea {
+ overflow: auto;
+}
+optgroup {
+ font-weight: bold;
+}
+table {
+ border-collapse: collapse;
+ border-spacing: 0;
+}
+td,
+th {
+ padding: 0;
+}
+/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */
+@media print {
+ *,
+ *:before,
+ *:after {
+ background: transparent !important;
+ color: #000 !important;
+ -webkit-box-shadow: none !important;
+ box-shadow: none !important;
+ text-shadow: none !important;
+ }
+ a,
+ a:visited {
+ text-decoration: underline;
+ }
+ a[href]:after {
+ content: " (" attr(href) ")";
+ }
+ abbr[title]:after {
+ content: " (" attr(title) ")";
+ }
+ a[href^="#"]:after,
+ a[href^="javascript:"]:after {
+ content: "";
+ }
+ pre,
+ blockquote {
+ border: 1px solid #999;
+ page-break-inside: avoid;
+ }
+ thead {
+ display: table-header-group;
+ }
+ tr,
+ img {
+ page-break-inside: avoid;
+ }
+ img {
+ max-width: 100% !important;
+ }
+ p,
+ h2,
+ h3 {
+ orphans: 3;
+ widows: 3;
+ }
+ h2,
+ h3 {
+ page-break-after: avoid;
+ }
+ .navbar {
+ display: none;
+ }
+ .btn > .caret,
+ .dropup > .btn > .caret {
+ border-top-color: #000 !important;
+ }
+ .label {
+ border: 1px solid #000;
+ }
+ .table {
+ border-collapse: collapse !important;
+ }
+ .table td,
+ .table th {
+ background-color: #fff !important;
+ }
+ .table-bordered th,
+ .table-bordered td {
+ border: 1px solid #ddd !important;
+ }
+}
+@font-face {
+ font-family: 'Glyphicons Halflings';
+ src: url('../fonts/glyphicons-halflings-regular.eot');
+ src: url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('../fonts/glyphicons-halflings-regular.woff2') format('woff2'), url('../fonts/glyphicons-halflings-regular.woff') format('woff'), url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg');
+}
+.glyphicon {
+ position: relative;
+ top: 1px;
+ display: inline-block;
+ font-family: 'Glyphicons Halflings';
+ font-style: normal;
+ font-weight: normal;
+ line-height: 1;
+ -webkit-font-smoothing: antialiased;
+ -moz-osx-font-smoothing: grayscale;
+}
+.glyphicon-asterisk:before {
+ content: "\002a";
+}
+.glyphicon-plus:before {
+ content: "\002b";
+}
+.glyphicon-euro:before,
+.glyphicon-eur:before {
+ content: "\20ac";
+}
+.glyphicon-minus:before {
+ content: "\2212";
+}
+.glyphicon-cloud:before {
+ content: "\2601";
+}
+.glyphicon-envelope:before {
+ content: "\2709";
+}
+.glyphicon-pencil:before {
+ content: "\270f";
+}
+.glyphicon-glass:before {
+ content: "\e001";
+}
+.glyphicon-music:before {
+ content: "\e002";
+}
+.glyphicon-search:before {
+ content: "\e003";
+}
+.glyphicon-heart:before {
+ content: "\e005";
+}
+.glyphicon-star:before {
+ content: "\e006";
+}
+.glyphicon-star-empty:before {
+ content: "\e007";
+}
+.glyphicon-user:before {
+ content: "\e008";
+}
+.glyphicon-film:before {
+ content: "\e009";
+}
+.glyphicon-th-large:before {
+ content: "\e010";
+}
+.glyphicon-th:before {
+ content: "\e011";
+}
+.glyphicon-th-list:before {
+ content: "\e012";
+}
+.glyphicon-ok:before {
+ content: "\e013";
+}
+.glyphicon-remove:before {
+ content: "\e014";
+}
+.glyphicon-zoom-in:before {
+ content: "\e015";
+}
+.glyphicon-zoom-out:before {
+ content: "\e016";
+}
+.glyphicon-off:before {
+ content: "\e017";
+}
+.glyphicon-signal:before {
+ content: "\e018";
+}
+.glyphicon-cog:before {
+ content: "\e019";
+}
+.glyphicon-trash:before {
+ content: "\e020";
+}
+.glyphicon-home:before {
+ content: "\e021";
+}
+.glyphicon-file:before {
+ content: "\e022";
+}
+.glyphicon-time:before {
+ content: "\e023";
+}
+.glyphicon-road:before {
+ content: "\e024";
+}
+.glyphicon-download-alt:before {
+ content: "\e025";
+}
+.glyphicon-download:before {
+ content: "\e026";
+}
+.glyphicon-upload:before {
+ content: "\e027";
+}
+.glyphicon-inbox:before {
+ content: "\e028";
+}
+.glyphicon-play-circle:before {
+ content: "\e029";
+}
+.glyphicon-repeat:before {
+ content: "\e030";
+}
+.glyphicon-refresh:before {
+ content: "\e031";
+}
+.glyphicon-list-alt:before {
+ content: "\e032";
+}
+.glyphicon-lock:before {
+ content: "\e033";
+}
+.glyphicon-flag:before {
+ content: "\e034";
+}
+.glyphicon-headphones:before {
+ content: "\e035";
+}
+.glyphicon-volume-off:before {
+ content: "\e036";
+}
+.glyphicon-volume-down:before {
+ content: "\e037";
+}
+.glyphicon-volume-up:before {
+ content: "\e038";
+}
+.glyphicon-qrcode:before {
+ content: "\e039";
+}
+.glyphicon-barcode:before {
+ content: "\e040";
+}
+.glyphicon-tag:before {
+ content: "\e041";
+}
+.glyphicon-tags:before {
+ content: "\e042";
+}
+.glyphicon-book:before {
+ content: "\e043";
+}
+.glyphicon-bookmark:before {
+ content: "\e044";
+}
+.glyphicon-print:before {
+ content: "\e045";
+}
+.glyphicon-camera:before {
+ content: "\e046";
+}
+.glyphicon-font:before {
+ content: "\e047";
+}
+.glyphicon-bold:before {
+ content: "\e048";
+}
+.glyphicon-italic:before {
+ content: "\e049";
+}
+.glyphicon-text-height:before {
+ content: "\e050";
+}
+.glyphicon-text-width:before {
+ content: "\e051";
+}
+.glyphicon-align-left:before {
+ content: "\e052";
+}
+.glyphicon-align-center:before {
+ content: "\e053";
+}
+.glyphicon-align-right:before {
+ content: "\e054";
+}
+.glyphicon-align-justify:before {
+ content: "\e055";
+}
+.glyphicon-list:before {
+ content: "\e056";
+}
+.glyphicon-indent-left:before {
+ content: "\e057";
+}
+.glyphicon-indent-right:before {
+ content: "\e058";
+}
+.glyphicon-facetime-video:before {
+ content: "\e059";
+}
+.glyphicon-picture:before {
+ content: "\e060";
+}
+.glyphicon-map-marker:before {
+ content: "\e062";
+}
+.glyphicon-adjust:before {
+ content: "\e063";
+}
+.glyphicon-tint:before {
+ content: "\e064";
+}
+.glyphicon-edit:before {
+ content: "\e065";
+}
+.glyphicon-share:before {
+ content: "\e066";
+}
+.glyphicon-check:before {
+ content: "\e067";
+}
+.glyphicon-move:before {
+ content: "\e068";
+}
+.glyphicon-step-backward:before {
+ content: "\e069";
+}
+.glyphicon-fast-backward:before {
+ content: "\e070";
+}
+.glyphicon-backward:before {
+ content: "\e071";
+}
+.glyphicon-play:before {
+ content: "\e072";
+}
+.glyphicon-pause:before {
+ content: "\e073";
+}
+.glyphicon-stop:before {
+ content: "\e074";
+}
+.glyphicon-forward:before {
+ content: "\e075";
+}
+.glyphicon-fast-forward:before {
+ content: "\e076";
+}
+.glyphicon-step-forward:before {
+ content: "\e077";
+}
+.glyphicon-eject:before {
+ content: "\e078";
+}
+.glyphicon-chevron-left:before {
+ content: "\e079";
+}
+.glyphicon-chevron-right:before {
+ content: "\e080";
+}
+.glyphicon-plus-sign:before {
+ content: "\e081";
+}
+.glyphicon-minus-sign:before {
+ content: "\e082";
+}
+.glyphicon-remove-sign:before {
+ content: "\e083";
+}
+.glyphicon-ok-sign:before {
+ content: "\e084";
+}
+.glyphicon-question-sign:before {
+ content: "\e085";
+}
+.glyphicon-info-sign:before {
+ content: "\e086";
+}
+.glyphicon-screenshot:before {
+ content: "\e087";
+}
+.glyphicon-remove-circle:before {
+ content: "\e088";
+}
+.glyphicon-ok-circle:before {
+ content: "\e089";
+}
+.glyphicon-ban-circle:before {
+ content: "\e090";
+}
+.glyphicon-arrow-left:before {
+ content: "\e091";
+}
+.glyphicon-arrow-right:before {
+ content: "\e092";
+}
+.glyphicon-arrow-up:before {
+ content: "\e093";
+}
+.glyphicon-arrow-down:before {
+ content: "\e094";
+}
+.glyphicon-share-alt:before {
+ content: "\e095";
+}
+.glyphicon-resize-full:before {
+ content: "\e096";
+}
+.glyphicon-resize-small:before {
+ content: "\e097";
+}
+.glyphicon-exclamation-sign:before {
+ content: "\e101";
+}
+.glyphicon-gift:before {
+ content: "\e102";
+}
+.glyphicon-leaf:before {
+ content: "\e103";
+}
+.glyphicon-fire:before {
+ content: "\e104";
+}
+.glyphicon-eye-open:before {
+ content: "\e105";
+}
+.glyphicon-eye-close:before {
+ content: "\e106";
+}
+.glyphicon-warning-sign:before {
+ content: "\e107";
+}
+.glyphicon-plane:before {
+ content: "\e108";
+}
+.glyphicon-calendar:before {
+ content: "\e109";
+}
+.glyphicon-random:before {
+ content: "\e110";
+}
+.glyphicon-comment:before {
+ content: "\e111";
+}
+.glyphicon-magnet:before {
+ content: "\e112";
+}
+.glyphicon-chevron-up:before {
+ content: "\e113";
+}
+.glyphicon-chevron-down:before {
+ content: "\e114";
+}
+.glyphicon-retweet:before {
+ content: "\e115";
+}
+.glyphicon-shopping-cart:before {
+ content: "\e116";
+}
+.glyphicon-folder-close:before {
+ content: "\e117";
+}
+.glyphicon-folder-open:before {
+ content: "\e118";
+}
+.glyphicon-resize-vertical:before {
+ content: "\e119";
+}
+.glyphicon-resize-horizontal:before {
+ content: "\e120";
+}
+.glyphicon-hdd:before {
+ content: "\e121";
+}
+.glyphicon-bullhorn:before {
+ content: "\e122";
+}
+.glyphicon-bell:before {
+ content: "\e123";
+}
+.glyphicon-certificate:before {
+ content: "\e124";
+}
+.glyphicon-thumbs-up:before {
+ content: "\e125";
+}
+.glyphicon-thumbs-down:before {
+ content: "\e126";
+}
+.glyphicon-hand-right:before {
+ content: "\e127";
+}
+.glyphicon-hand-left:before {
+ content: "\e128";
+}
+.glyphicon-hand-up:before {
+ content: "\e129";
+}
+.glyphicon-hand-down:before {
+ content: "\e130";
+}
+.glyphicon-circle-arrow-right:before {
+ content: "\e131";
+}
+.glyphicon-circle-arrow-left:before {
+ content: "\e132";
+}
+.glyphicon-circle-arrow-up:before {
+ content: "\e133";
+}
+.glyphicon-circle-arrow-down:before {
+ content: "\e134";
+}
+.glyphicon-globe:before {
+ content: "\e135";
+}
+.glyphicon-wrench:before {
+ content: "\e136";
+}
+.glyphicon-tasks:before {
+ content: "\e137";
+}
+.glyphicon-filter:before {
+ content: "\e138";
+}
+.glyphicon-briefcase:before {
+ content: "\e139";
+}
+.glyphicon-fullscreen:before {
+ content: "\e140";
+}
+.glyphicon-dashboard:before {
+ content: "\e141";
+}
+.glyphicon-paperclip:before {
+ content: "\e142";
+}
+.glyphicon-heart-empty:before {
+ content: "\e143";
+}
+.glyphicon-link:before {
+ content: "\e144";
+}
+.glyphicon-phone:before {
+ content: "\e145";
+}
+.glyphicon-pushpin:before {
+ content: "\e146";
+}
+.glyphicon-usd:before {
+ content: "\e148";
+}
+.glyphicon-gbp:before {
+ content: "\e149";
+}
+.glyphicon-sort:before {
+ content: "\e150";
+}
+.glyphicon-sort-by-alphabet:before {
+ content: "\e151";
+}
+.glyphicon-sort-by-alphabet-alt:before {
+ content: "\e152";
+}
+.glyphicon-sort-by-order:before {
+ content: "\e153";
+}
+.glyphicon-sort-by-order-alt:before {
+ content: "\e154";
+}
+.glyphicon-sort-by-attributes:before {
+ content: "\e155";
+}
+.glyphicon-sort-by-attributes-alt:before {
+ content: "\e156";
+}
+.glyphicon-unchecked:before {
+ content: "\e157";
+}
+.glyphicon-expand:before {
+ content: "\e158";
+}
+.glyphicon-collapse-down:before {
+ content: "\e159";
+}
+.glyphicon-collapse-up:before {
+ content: "\e160";
+}
+.glyphicon-log-in:before {
+ content: "\e161";
+}
+.glyphicon-flash:before {
+ content: "\e162";
+}
+.glyphicon-log-out:before {
+ content: "\e163";
+}
+.glyphicon-new-window:before {
+ content: "\e164";
+}
+.glyphicon-record:before {
+ content: "\e165";
+}
+.glyphicon-save:before {
+ content: "\e166";
+}
+.glyphicon-open:before {
+ content: "\e167";
+}
+.glyphicon-saved:before {
+ content: "\e168";
+}
+.glyphicon-import:before {
+ content: "\e169";
+}
+.glyphicon-export:before {
+ content: "\e170";
+}
+.glyphicon-send:before {
+ content: "\e171";
+}
+.glyphicon-floppy-disk:before {
+ content: "\e172";
+}
+.glyphicon-floppy-saved:before {
+ content: "\e173";
+}
+.glyphicon-floppy-remove:before {
+ content: "\e174";
+}
+.glyphicon-floppy-save:before {
+ content: "\e175";
+}
+.glyphicon-floppy-open:before {
+ content: "\e176";
+}
+.glyphicon-credit-card:before {
+ content: "\e177";
+}
+.glyphicon-transfer:before {
+ content: "\e178";
+}
+.glyphicon-cutlery:before {
+ content: "\e179";
+}
+.glyphicon-header:before {
+ content: "\e180";
+}
+.glyphicon-compressed:before {
+ content: "\e181";
+}
+.glyphicon-earphone:before {
+ content: "\e182";
+}
+.glyphicon-phone-alt:before {
+ content: "\e183";
+}
+.glyphicon-tower:before {
+ content: "\e184";
+}
+.glyphicon-stats:before {
+ content: "\e185";
+}
+.glyphicon-sd-video:before {
+ content: "\e186";
+}
+.glyphicon-hd-video:before {
+ content: "\e187";
+}
+.glyphicon-subtitles:before {
+ content: "\e188";
+}
+.glyphicon-sound-stereo:before {
+ content: "\e189";
+}
+.glyphicon-sound-dolby:before {
+ content: "\e190";
+}
+.glyphicon-sound-5-1:before {
+ content: "\e191";
+}
+.glyphicon-sound-6-1:before {
+ content: "\e192";
+}
+.glyphicon-sound-7-1:before {
+ content: "\e193";
+}
+.glyphicon-copyright-mark:before {
+ content: "\e194";
+}
+.glyphicon-registration-mark:before {
+ content: "\e195";
+}
+.glyphicon-cloud-download:before {
+ content: "\e197";
+}
+.glyphicon-cloud-upload:before {
+ content: "\e198";
+}
+.glyphicon-tree-conifer:before {
+ content: "\e199";
+}
+.glyphicon-tree-deciduous:before {
+ content: "\e200";
+}
+.glyphicon-cd:before {
+ content: "\e201";
+}
+.glyphicon-save-file:before {
+ content: "\e202";
+}
+.glyphicon-open-file:before {
+ content: "\e203";
+}
+.glyphicon-level-up:before {
+ content: "\e204";
+}
+.glyphicon-copy:before {
+ content: "\e205";
+}
+.glyphicon-paste:before {
+ content: "\e206";
+}
+.glyphicon-alert:before {
+ content: "\e209";
+}
+.glyphicon-equalizer:before {
+ content: "\e210";
+}
+.glyphicon-king:before {
+ content: "\e211";
+}
+.glyphicon-queen:before {
+ content: "\e212";
+}
+.glyphicon-pawn:before {
+ content: "\e213";
+}
+.glyphicon-bishop:before {
+ content: "\e214";
+}
+.glyphicon-knight:before {
+ content: "\e215";
+}
+.glyphicon-baby-formula:before {
+ content: "\e216";
+}
+.glyphicon-tent:before {
+ content: "\26fa";
+}
+.glyphicon-blackboard:before {
+ content: "\e218";
+}
+.glyphicon-bed:before {
+ content: "\e219";
+}
+.glyphicon-apple:before {
+ content: "\f8ff";
+}
+.glyphicon-erase:before {
+ content: "\e221";
+}
+.glyphicon-hourglass:before {
+ content: "\231b";
+}
+.glyphicon-lamp:before {
+ content: "\e223";
+}
+.glyphicon-duplicate:before {
+ content: "\e224";
+}
+.glyphicon-piggy-bank:before {
+ content: "\e225";
+}
+.glyphicon-scissors:before {
+ content: "\e226";
+}
+.glyphicon-bitcoin:before {
+ content: "\e227";
+}
+.glyphicon-btc:before {
+ content: "\e227";
+}
+.glyphicon-xbt:before {
+ content: "\e227";
+}
+.glyphicon-yen:before {
+ content: "\00a5";
+}
+.glyphicon-jpy:before {
+ content: "\00a5";
+}
+.glyphicon-ruble:before {
+ content: "\20bd";
+}
+.glyphicon-rub:before {
+ content: "\20bd";
+}
+.glyphicon-scale:before {
+ content: "\e230";
+}
+.glyphicon-ice-lolly:before {
+ content: "\e231";
+}
+.glyphicon-ice-lolly-tasted:before {
+ content: "\e232";
+}
+.glyphicon-education:before {
+ content: "\e233";
+}
+.glyphicon-option-horizontal:before {
+ content: "\e234";
+}
+.glyphicon-option-vertical:before {
+ content: "\e235";
+}
+.glyphicon-menu-hamburger:before {
+ content: "\e236";
+}
+.glyphicon-modal-window:before {
+ content: "\e237";
+}
+.glyphicon-oil:before {
+ content: "\e238";
+}
+.glyphicon-grain:before {
+ content: "\e239";
+}
+.glyphicon-sunglasses:before {
+ content: "\e240";
+}
+.glyphicon-text-size:before {
+ content: "\e241";
+}
+.glyphicon-text-color:before {
+ content: "\e242";
+}
+.glyphicon-text-background:before {
+ content: "\e243";
+}
+.glyphicon-object-align-top:before {
+ content: "\e244";
+}
+.glyphicon-object-align-bottom:before {
+ content: "\e245";
+}
+.glyphicon-object-align-horizontal:before {
+ content: "\e246";
+}
+.glyphicon-object-align-left:before {
+ content: "\e247";
+}
+.glyphicon-object-align-vertical:before {
+ content: "\e248";
+}
+.glyphicon-object-align-right:before {
+ content: "\e249";
+}
+.glyphicon-triangle-right:before {
+ content: "\e250";
+}
+.glyphicon-triangle-left:before {
+ content: "\e251";
+}
+.glyphicon-triangle-bottom:before {
+ content: "\e252";
+}
+.glyphicon-triangle-top:before {
+ content: "\e253";
+}
+.glyphicon-console:before {
+ content: "\e254";
+}
+.glyphicon-superscript:before {
+ content: "\e255";
+}
+.glyphicon-subscript:before {
+ content: "\e256";
+}
+.glyphicon-menu-left:before {
+ content: "\e257";
+}
+.glyphicon-menu-right:before {
+ content: "\e258";
+}
+.glyphicon-menu-down:before {
+ content: "\e259";
+}
+.glyphicon-menu-up:before {
+ content: "\e260";
+}
+* {
+ -webkit-box-sizing: border-box;
+ -moz-box-sizing: border-box;
+ box-sizing: border-box;
+}
+*:before,
+*:after {
+ -webkit-box-sizing: border-box;
+ -moz-box-sizing: border-box;
+ box-sizing: border-box;
+}
+html {
+ font-size: 10px;
+ -webkit-tap-highlight-color: rgba(0, 0, 0, 0);
+}
+body {
+ font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif;
+ font-size: 15px;
+ line-height: 1.4;
+ color: #222222;
+ background-color: #ffffff;
+}
+input,
+button,
+select,
+textarea {
+ font-family: inherit;
+ font-size: inherit;
+ line-height: inherit;
+}
+a {
+ color: #008cba;
+ text-decoration: none;
+}
+a:hover,
+a:focus {
+ color: #008cba;
+ text-decoration: underline;
+}
+a:focus {
+ outline: 5px auto -webkit-focus-ring-color;
+ outline-offset: -2px;
+}
+figure {
+ margin: 0;
+}
+img {
+ vertical-align: middle;
+}
+.img-responsive,
+.thumbnail > img,
+.thumbnail a > img,
+.carousel-inner > .item > img,
+.carousel-inner > .item > a > img {
+ display: block;
+ max-width: 100%;
+ height: auto;
+}
+.img-rounded {
+ border-radius: 0;
+}
+.img-thumbnail {
+ padding: 4px;
+ line-height: 1.4;
+ background-color: #ffffff;
+ border: 1px solid #dddddd;
+ border-radius: 0;
+ -webkit-transition: all 0.2s ease-in-out;
+ -o-transition: all 0.2s ease-in-out;
+ transition: all 0.2s ease-in-out;
+ display: inline-block;
+ max-width: 100%;
+ height: auto;
+}
+.img-circle {
+ border-radius: 50%;
+}
+hr {
+ margin-top: 21px;
+ margin-bottom: 21px;
+ border: 0;
+ border-top: 1px solid #dddddd;
+}
+.sr-only {
+ position: absolute;
+ width: 1px;
+ height: 1px;
+ margin: -1px;
+ padding: 0;
+ overflow: hidden;
+ clip: rect(0, 0, 0, 0);
+ border: 0;
+}
+.sr-only-focusable:active,
+.sr-only-focusable:focus {
+ position: static;
+ width: auto;
+ height: auto;
+ margin: 0;
+ overflow: visible;
+ clip: auto;
+}
+[role="button"] {
+ cursor: pointer;
+}
+h1,
+h2,
+h3,
+h4,
+h5,
+h6,
+.h1,
+.h2,
+.h3,
+.h4,
+.h5,
+.h6 {
+ font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif;
+ font-weight: 300;
+ line-height: 1.1;
+ color: inherit;
+}
+h1 small,
+h2 small,
+h3 small,
+h4 small,
+h5 small,
+h6 small,
+.h1 small,
+.h2 small,
+.h3 small,
+.h4 small,
+.h5 small,
+.h6 small,
+h1 .small,
+h2 .small,
+h3 .small,
+h4 .small,
+h5 .small,
+h6 .small,
+.h1 .small,
+.h2 .small,
+.h3 .small,
+.h4 .small,
+.h5 .small,
+.h6 .small {
+ font-weight: normal;
+ line-height: 1;
+ color: #999999;
+}
+h1,
+.h1,
+h2,
+.h2,
+h3,
+.h3 {
+ margin-top: 21px;
+ margin-bottom: 10.5px;
+}
+h1 small,
+.h1 small,
+h2 small,
+.h2 small,
+h3 small,
+.h3 small,
+h1 .small,
+.h1 .small,
+h2 .small,
+.h2 .small,
+h3 .small,
+.h3 .small {
+ font-size: 65%;
+}
+h4,
+.h4,
+h5,
+.h5,
+h6,
+.h6 {
+ margin-top: 10.5px;
+ margin-bottom: 10.5px;
+}
+h4 small,
+.h4 small,
+h5 small,
+.h5 small,
+h6 small,
+.h6 small,
+h4 .small,
+.h4 .small,
+h5 .small,
+.h5 .small,
+h6 .small,
+.h6 .small {
+ font-size: 75%;
+}
+h1,
+.h1 {
+ font-size: 39px;
+}
+h2,
+.h2 {
+ font-size: 32px;
+}
+h3,
+.h3 {
+ font-size: 26px;
+}
+h4,
+.h4 {
+ font-size: 19px;
+}
+h5,
+.h5 {
+ font-size: 15px;
+}
+h6,
+.h6 {
+ font-size: 13px;
+}
+p {
+ margin: 0 0 10.5px;
+}
+.lead {
+ margin-bottom: 21px;
+ font-size: 17px;
+ font-weight: 300;
+ line-height: 1.4;
+}
+@media (min-width: 768px) {
+ .lead {
+ font-size: 22.5px;
+ }
+}
+small,
+.small {
+ font-size: 80%;
+}
+mark,
+.mark {
+ background-color: #fcf8e3;
+ padding: .2em;
+}
+.text-left {
+ text-align: left;
+}
+.text-right {
+ text-align: right;
+}
+.text-center {
+ text-align: center;
+}
+.text-justify {
+ text-align: justify;
+}
+.text-nowrap {
+ white-space: nowrap;
+}
+.text-lowercase {
+ text-transform: lowercase;
+}
+.text-uppercase {
+ text-transform: uppercase;
+}
+.text-capitalize {
+ text-transform: capitalize;
+}
+.text-muted {
+ color: #999999;
+}
+.text-primary {
+ color: #008cba;
+}
+a.text-primary:hover,
+a.text-primary:focus {
+ color: #006687;
+}
+.text-success {
+ color: #43ac6a;
+}
+a.text-success:hover,
+a.text-success:focus {
+ color: #358753;
+}
+.text-info {
+ color: #5bc0de;
+}
+a.text-info:hover,
+a.text-info:focus {
+ color: #31b0d5;
+}
+.text-warning {
+ color: #e99002;
+}
+a.text-warning:hover,
+a.text-warning:focus {
+ color: #b67102;
+}
+.text-danger {
+ color: #f04124;
+}
+a.text-danger:hover,
+a.text-danger:focus {
+ color: #d32a0e;
+}
+.bg-primary {
+ color: #fff;
+ background-color: #008cba;
+}
+a.bg-primary:hover,
+a.bg-primary:focus {
+ background-color: #006687;
+}
+.bg-success {
+ background-color: #dff0d8;
+}
+a.bg-success:hover,
+a.bg-success:focus {
+ background-color: #c1e2b3;
+}
+.bg-info {
+ background-color: #d9edf7;
+}
+a.bg-info:hover,
+a.bg-info:focus {
+ background-color: #afd9ee;
+}
+.bg-warning {
+ background-color: #fcf8e3;
+}
+a.bg-warning:hover,
+a.bg-warning:focus {
+ background-color: #f7ecb5;
+}
+.bg-danger {
+ background-color: #f2dede;
+}
+a.bg-danger:hover,
+a.bg-danger:focus {
+ background-color: #e4b9b9;
+}
+.page-header {
+ padding-bottom: 9.5px;
+ margin: 42px 0 21px;
+ border-bottom: 1px solid #dddddd;
+}
+ul,
+ol {
+ margin-top: 0;
+ margin-bottom: 10.5px;
+}
+ul ul,
+ol ul,
+ul ol,
+ol ol {
+ margin-bottom: 0;
+}
+.list-unstyled {
+ padding-left: 0;
+ list-style: none;
+}
+.list-inline {
+ padding-left: 0;
+ list-style: none;
+ margin-left: -5px;
+}
+.list-inline > li {
+ display: inline-block;
+ padding-left: 5px;
+ padding-right: 5px;
+}
+dl {
+ margin-top: 0;
+ margin-bottom: 21px;
+}
+dt,
+dd {
+ line-height: 1.4;
+}
+dt {
+ font-weight: bold;
+}
+dd {
+ margin-left: 0;
+}
+@media (min-width: 768px) {
+ .dl-horizontal dt {
+ float: left;
+ width: 160px;
+ clear: left;
+ text-align: right;
+ overflow: hidden;
+ text-overflow: ellipsis;
+ white-space: nowrap;
+ }
+ .dl-horizontal dd {
+ margin-left: 180px;
+ }
+}
+abbr[title],
+abbr[data-original-title] {
+ cursor: help;
+ border-bottom: 1px dotted #999999;
+}
+.initialism {
+ font-size: 90%;
+ text-transform: uppercase;
+}
+blockquote {
+ padding: 10.5px 21px;
+ margin: 0 0 21px;
+ font-size: 18.75px;
+ border-left: 5px solid #dddddd;
+}
+blockquote p:last-child,
+blockquote ul:last-child,
+blockquote ol:last-child {
+ margin-bottom: 0;
+}
+blockquote footer,
+blockquote small,
+blockquote .small {
+ display: block;
+ font-size: 80%;
+ line-height: 1.4;
+ color: #6f6f6f;
+}
+blockquote footer:before,
+blockquote small:before,
+blockquote .small:before {
+ content: '\2014 \00A0';
+}
+.blockquote-reverse,
+blockquote.pull-right {
+ padding-right: 15px;
+ padding-left: 0;
+ border-right: 5px solid #dddddd;
+ border-left: 0;
+ text-align: right;
+}
+.blockquote-reverse footer:before,
+blockquote.pull-right footer:before,
+.blockquote-reverse small:before,
+blockquote.pull-right small:before,
+.blockquote-reverse .small:before,
+blockquote.pull-right .small:before {
+ content: '';
+}
+.blockquote-reverse footer:after,
+blockquote.pull-right footer:after,
+.blockquote-reverse small:after,
+blockquote.pull-right small:after,
+.blockquote-reverse .small:after,
+blockquote.pull-right .small:after {
+ content: '\00A0 \2014';
+}
+address {
+ margin-bottom: 21px;
+ font-style: normal;
+ line-height: 1.4;
+}
+code,
+kbd,
+pre,
+samp {
+ font-family: Menlo, Monaco, Consolas, "Courier New", monospace;
+}
+code {
+ padding: 2px 4px;
+ font-size: 90%;
+ color: #c7254e;
+ background-color: #f9f2f4;
+ border-radius: 0;
+}
+kbd {
+ padding: 2px 4px;
+ font-size: 90%;
+ color: #ffffff;
+ background-color: #333333;
+ border-radius: 0;
+ -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.25);
+ box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.25);
+}
+kbd kbd {
+ padding: 0;
+ font-size: 100%;
+ font-weight: bold;
+ -webkit-box-shadow: none;
+ box-shadow: none;
+}
+pre {
+ display: block;
+ padding: 10px;
+ margin: 0 0 10.5px;
+ font-size: 14px;
+ line-height: 1.4;
+ word-break: break-all;
+ word-wrap: break-word;
+ color: #333333;
+ background-color: #f5f5f5;
+ border: 1px solid #cccccc;
+ border-radius: 0;
+}
+pre code {
+ padding: 0;
+ font-size: inherit;
+ color: inherit;
+ white-space: pre-wrap;
+ background-color: transparent;
+ border-radius: 0;
+}
+.pre-scrollable {
+ max-height: 340px;
+ overflow-y: scroll;
+}
+.container {
+ margin-right: auto;
+ margin-left: auto;
+ padding-left: 15px;
+ padding-right: 15px;
+}
+@media (min-width: 768px) {
+ .container {
+ width: 750px;
+ }
+}
+@media (min-width: 992px) {
+ .container {
+ width: 970px;
+ }
+}
+@media (min-width: 1200px) {
+ .container {
+ width: 1170px;
+ }
+}
+.container-fluid {
+ margin-right: auto;
+ margin-left: auto;
+ padding-left: 15px;
+ padding-right: 15px;
+}
+.row {
+ margin-left: -15px;
+ margin-right: -15px;
+}
+.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {
+ position: relative;
+ min-height: 1px;
+ padding-left: 15px;
+ padding-right: 15px;
+}
+.col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12 {
+ float: left;
+}
+.col-xs-12 {
+ width: 100%;
+}
+.col-xs-11 {
+ width: 91.66666667%;
+}
+.col-xs-10 {
+ width: 83.33333333%;
+}
+.col-xs-9 {
+ width: 75%;
+}
+.col-xs-8 {
+ width: 66.66666667%;
+}
+.col-xs-7 {
+ width: 58.33333333%;
+}
+.col-xs-6 {
+ width: 50%;
+}
+.col-xs-5 {
+ width: 41.66666667%;
+}
+.col-xs-4 {
+ width: 33.33333333%;
+}
+.col-xs-3 {
+ width: 25%;
+}
+.col-xs-2 {
+ width: 16.66666667%;
+}
+.col-xs-1 {
+ width: 8.33333333%;
+}
+.col-xs-pull-12 {
+ right: 100%;
+}
+.col-xs-pull-11 {
+ right: 91.66666667%;
+}
+.col-xs-pull-10 {
+ right: 83.33333333%;
+}
+.col-xs-pull-9 {
+ right: 75%;
+}
+.col-xs-pull-8 {
+ right: 66.66666667%;
+}
+.col-xs-pull-7 {
+ right: 58.33333333%;
+}
+.col-xs-pull-6 {
+ right: 50%;
+}
+.col-xs-pull-5 {
+ right: 41.66666667%;
+}
+.col-xs-pull-4 {
+ right: 33.33333333%;
+}
+.col-xs-pull-3 {
+ right: 25%;
+}
+.col-xs-pull-2 {
+ right: 16.66666667%;
+}
+.col-xs-pull-1 {
+ right: 8.33333333%;
+}
+.col-xs-pull-0 {
+ right: auto;
+}
+.col-xs-push-12 {
+ left: 100%;
+}
+.col-xs-push-11 {
+ left: 91.66666667%;
+}
+.col-xs-push-10 {
+ left: 83.33333333%;
+}
+.col-xs-push-9 {
+ left: 75%;
+}
+.col-xs-push-8 {
+ left: 66.66666667%;
+}
+.col-xs-push-7 {
+ left: 58.33333333%;
+}
+.col-xs-push-6 {
+ left: 50%;
+}
+.col-xs-push-5 {
+ left: 41.66666667%;
+}
+.col-xs-push-4 {
+ left: 33.33333333%;
+}
+.col-xs-push-3 {
+ left: 25%;
+}
+.col-xs-push-2 {
+ left: 16.66666667%;
+}
+.col-xs-push-1 {
+ left: 8.33333333%;
+}
+.col-xs-push-0 {
+ left: auto;
+}
+.col-xs-offset-12 {
+ margin-left: 100%;
+}
+.col-xs-offset-11 {
+ margin-left: 91.66666667%;
+}
+.col-xs-offset-10 {
+ margin-left: 83.33333333%;
+}
+.col-xs-offset-9 {
+ margin-left: 75%;
+}
+.col-xs-offset-8 {
+ margin-left: 66.66666667%;
+}
+.col-xs-offset-7 {
+ margin-left: 58.33333333%;
+}
+.col-xs-offset-6 {
+ margin-left: 50%;
+}
+.col-xs-offset-5 {
+ margin-left: 41.66666667%;
+}
+.col-xs-offset-4 {
+ margin-left: 33.33333333%;
+}
+.col-xs-offset-3 {
+ margin-left: 25%;
+}
+.col-xs-offset-2 {
+ margin-left: 16.66666667%;
+}
+.col-xs-offset-1 {
+ margin-left: 8.33333333%;
+}
+.col-xs-offset-0 {
+ margin-left: 0%;
+}
+@media (min-width: 768px) {
+ .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {
+ float: left;
+ }
+ .col-sm-12 {
+ width: 100%;
+ }
+ .col-sm-11 {
+ width: 91.66666667%;
+ }
+ .col-sm-10 {
+ width: 83.33333333%;
+ }
+ .col-sm-9 {
+ width: 75%;
+ }
+ .col-sm-8 {
+ width: 66.66666667%;
+ }
+ .col-sm-7 {
+ width: 58.33333333%;
+ }
+ .col-sm-6 {
+ width: 50%;
+ }
+ .col-sm-5 {
+ width: 41.66666667%;
+ }
+ .col-sm-4 {
+ width: 33.33333333%;
+ }
+ .col-sm-3 {
+ width: 25%;
+ }
+ .col-sm-2 {
+ width: 16.66666667%;
+ }
+ .col-sm-1 {
+ width: 8.33333333%;
+ }
+ .col-sm-pull-12 {
+ right: 100%;
+ }
+ .col-sm-pull-11 {
+ right: 91.66666667%;
+ }
+ .col-sm-pull-10 {
+ right: 83.33333333%;
+ }
+ .col-sm-pull-9 {
+ right: 75%;
+ }
+ .col-sm-pull-8 {
+ right: 66.66666667%;
+ }
+ .col-sm-pull-7 {
+ right: 58.33333333%;
+ }
+ .col-sm-pull-6 {
+ right: 50%;
+ }
+ .col-sm-pull-5 {
+ right: 41.66666667%;
+ }
+ .col-sm-pull-4 {
+ right: 33.33333333%;
+ }
+ .col-sm-pull-3 {
+ right: 25%;
+ }
+ .col-sm-pull-2 {
+ right: 16.66666667%;
+ }
+ .col-sm-pull-1 {
+ right: 8.33333333%;
+ }
+ .col-sm-pull-0 {
+ right: auto;
+ }
+ .col-sm-push-12 {
+ left: 100%;
+ }
+ .col-sm-push-11 {
+ left: 91.66666667%;
+ }
+ .col-sm-push-10 {
+ left: 83.33333333%;
+ }
+ .col-sm-push-9 {
+ left: 75%;
+ }
+ .col-sm-push-8 {
+ left: 66.66666667%;
+ }
+ .col-sm-push-7 {
+ left: 58.33333333%;
+ }
+ .col-sm-push-6 {
+ left: 50%;
+ }
+ .col-sm-push-5 {
+ left: 41.66666667%;
+ }
+ .col-sm-push-4 {
+ left: 33.33333333%;
+ }
+ .col-sm-push-3 {
+ left: 25%;
+ }
+ .col-sm-push-2 {
+ left: 16.66666667%;
+ }
+ .col-sm-push-1 {
+ left: 8.33333333%;
+ }
+ .col-sm-push-0 {
+ left: auto;
+ }
+ .col-sm-offset-12 {
+ margin-left: 100%;
+ }
+ .col-sm-offset-11 {
+ margin-left: 91.66666667%;
+ }
+ .col-sm-offset-10 {
+ margin-left: 83.33333333%;
+ }
+ .col-sm-offset-9 {
+ margin-left: 75%;
+ }
+ .col-sm-offset-8 {
+ margin-left: 66.66666667%;
+ }
+ .col-sm-offset-7 {
+ margin-left: 58.33333333%;
+ }
+ .col-sm-offset-6 {
+ margin-left: 50%;
+ }
+ .col-sm-offset-5 {
+ margin-left: 41.66666667%;
+ }
+ .col-sm-offset-4 {
+ margin-left: 33.33333333%;
+ }
+ .col-sm-offset-3 {
+ margin-left: 25%;
+ }
+ .col-sm-offset-2 {
+ margin-left: 16.66666667%;
+ }
+ .col-sm-offset-1 {
+ margin-left: 8.33333333%;
+ }
+ .col-sm-offset-0 {
+ margin-left: 0%;
+ }
+}
+@media (min-width: 992px) {
+ .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {
+ float: left;
+ }
+ .col-md-12 {
+ width: 100%;
+ }
+ .col-md-11 {
+ width: 91.66666667%;
+ }
+ .col-md-10 {
+ width: 83.33333333%;
+ }
+ .col-md-9 {
+ width: 75%;
+ }
+ .col-md-8 {
+ width: 66.66666667%;
+ }
+ .col-md-7 {
+ width: 58.33333333%;
+ }
+ .col-md-6 {
+ width: 50%;
+ }
+ .col-md-5 {
+ width: 41.66666667%;
+ }
+ .col-md-4 {
+ width: 33.33333333%;
+ }
+ .col-md-3 {
+ width: 25%;
+ }
+ .col-md-2 {
+ width: 16.66666667%;
+ }
+ .col-md-1 {
+ width: 8.33333333%;
+ }
+ .col-md-pull-12 {
+ right: 100%;
+ }
+ .col-md-pull-11 {
+ right: 91.66666667%;
+ }
+ .col-md-pull-10 {
+ right: 83.33333333%;
+ }
+ .col-md-pull-9 {
+ right: 75%;
+ }
+ .col-md-pull-8 {
+ right: 66.66666667%;
+ }
+ .col-md-pull-7 {
+ right: 58.33333333%;
+ }
+ .col-md-pull-6 {
+ right: 50%;
+ }
+ .col-md-pull-5 {
+ right: 41.66666667%;
+ }
+ .col-md-pull-4 {
+ right: 33.33333333%;
+ }
+ .col-md-pull-3 {
+ right: 25%;
+ }
+ .col-md-pull-2 {
+ right: 16.66666667%;
+ }
+ .col-md-pull-1 {
+ right: 8.33333333%;
+ }
+ .col-md-pull-0 {
+ right: auto;
+ }
+ .col-md-push-12 {
+ left: 100%;
+ }
+ .col-md-push-11 {
+ left: 91.66666667%;
+ }
+ .col-md-push-10 {
+ left: 83.33333333%;
+ }
+ .col-md-push-9 {
+ left: 75%;
+ }
+ .col-md-push-8 {
+ left: 66.66666667%;
+ }
+ .col-md-push-7 {
+ left: 58.33333333%;
+ }
+ .col-md-push-6 {
+ left: 50%;
+ }
+ .col-md-push-5 {
+ left: 41.66666667%;
+ }
+ .col-md-push-4 {
+ left: 33.33333333%;
+ }
+ .col-md-push-3 {
+ left: 25%;
+ }
+ .col-md-push-2 {
+ left: 16.66666667%;
+ }
+ .col-md-push-1 {
+ left: 8.33333333%;
+ }
+ .col-md-push-0 {
+ left: auto;
+ }
+ .col-md-offset-12 {
+ margin-left: 100%;
+ }
+ .col-md-offset-11 {
+ margin-left: 91.66666667%;
+ }
+ .col-md-offset-10 {
+ margin-left: 83.33333333%;
+ }
+ .col-md-offset-9 {
+ margin-left: 75%;
+ }
+ .col-md-offset-8 {
+ margin-left: 66.66666667%;
+ }
+ .col-md-offset-7 {
+ margin-left: 58.33333333%;
+ }
+ .col-md-offset-6 {
+ margin-left: 50%;
+ }
+ .col-md-offset-5 {
+ margin-left: 41.66666667%;
+ }
+ .col-md-offset-4 {
+ margin-left: 33.33333333%;
+ }
+ .col-md-offset-3 {
+ margin-left: 25%;
+ }
+ .col-md-offset-2 {
+ margin-left: 16.66666667%;
+ }
+ .col-md-offset-1 {
+ margin-left: 8.33333333%;
+ }
+ .col-md-offset-0 {
+ margin-left: 0%;
+ }
+}
+@media (min-width: 1200px) {
+ .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12 {
+ float: left;
+ }
+ .col-lg-12 {
+ width: 100%;
+ }
+ .col-lg-11 {
+ width: 91.66666667%;
+ }
+ .col-lg-10 {
+ width: 83.33333333%;
+ }
+ .col-lg-9 {
+ width: 75%;
+ }
+ .col-lg-8 {
+ width: 66.66666667%;
+ }
+ .col-lg-7 {
+ width: 58.33333333%;
+ }
+ .col-lg-6 {
+ width: 50%;
+ }
+ .col-lg-5 {
+ width: 41.66666667%;
+ }
+ .col-lg-4 {
+ width: 33.33333333%;
+ }
+ .col-lg-3 {
+ width: 25%;
+ }
+ .col-lg-2 {
+ width: 16.66666667%;
+ }
+ .col-lg-1 {
+ width: 8.33333333%;
+ }
+ .col-lg-pull-12 {
+ right: 100%;
+ }
+ .col-lg-pull-11 {
+ right: 91.66666667%;
+ }
+ .col-lg-pull-10 {
+ right: 83.33333333%;
+ }
+ .col-lg-pull-9 {
+ right: 75%;
+ }
+ .col-lg-pull-8 {
+ right: 66.66666667%;
+ }
+ .col-lg-pull-7 {
+ right: 58.33333333%;
+ }
+ .col-lg-pull-6 {
+ right: 50%;
+ }
+ .col-lg-pull-5 {
+ right: 41.66666667%;
+ }
+ .col-lg-pull-4 {
+ right: 33.33333333%;
+ }
+ .col-lg-pull-3 {
+ right: 25%;
+ }
+ .col-lg-pull-2 {
+ right: 16.66666667%;
+ }
+ .col-lg-pull-1 {
+ right: 8.33333333%;
+ }
+ .col-lg-pull-0 {
+ right: auto;
+ }
+ .col-lg-push-12 {
+ left: 100%;
+ }
+ .col-lg-push-11 {
+ left: 91.66666667%;
+ }
+ .col-lg-push-10 {
+ left: 83.33333333%;
+ }
+ .col-lg-push-9 {
+ left: 75%;
+ }
+ .col-lg-push-8 {
+ left: 66.66666667%;
+ }
+ .col-lg-push-7 {
+ left: 58.33333333%;
+ }
+ .col-lg-push-6 {
+ left: 50%;
+ }
+ .col-lg-push-5 {
+ left: 41.66666667%;
+ }
+ .col-lg-push-4 {
+ left: 33.33333333%;
+ }
+ .col-lg-push-3 {
+ left: 25%;
+ }
+ .col-lg-push-2 {
+ left: 16.66666667%;
+ }
+ .col-lg-push-1 {
+ left: 8.33333333%;
+ }
+ .col-lg-push-0 {
+ left: auto;
+ }
+ .col-lg-offset-12 {
+ margin-left: 100%;
+ }
+ .col-lg-offset-11 {
+ margin-left: 91.66666667%;
+ }
+ .col-lg-offset-10 {
+ margin-left: 83.33333333%;
+ }
+ .col-lg-offset-9 {
+ margin-left: 75%;
+ }
+ .col-lg-offset-8 {
+ margin-left: 66.66666667%;
+ }
+ .col-lg-offset-7 {
+ margin-left: 58.33333333%;
+ }
+ .col-lg-offset-6 {
+ margin-left: 50%;
+ }
+ .col-lg-offset-5 {
+ margin-left: 41.66666667%;
+ }
+ .col-lg-offset-4 {
+ margin-left: 33.33333333%;
+ }
+ .col-lg-offset-3 {
+ margin-left: 25%;
+ }
+ .col-lg-offset-2 {
+ margin-left: 16.66666667%;
+ }
+ .col-lg-offset-1 {
+ margin-left: 8.33333333%;
+ }
+ .col-lg-offset-0 {
+ margin-left: 0%;
+ }
+}
+table {
+ background-color: transparent;
+}
+caption {
+ padding-top: 8px;
+ padding-bottom: 8px;
+ color: #999999;
+ text-align: left;
+}
+th {
+ text-align: left;
+}
+.table {
+ width: 100%;
+ max-width: 100%;
+ margin-bottom: 21px;
+}
+.table > thead > tr > th,
+.table > tbody > tr > th,
+.table > tfoot > tr > th,
+.table > thead > tr > td,
+.table > tbody > tr > td,
+.table > tfoot > tr > td {
+ padding: 8px;
+ line-height: 1.4;
+ vertical-align: top;
+ border-top: 1px solid #dddddd;
+}
+.table > thead > tr > th {
+ vertical-align: bottom;
+ border-bottom: 2px solid #dddddd;
+}
+.table > caption + thead > tr:first-child > th,
+.table > colgroup + thead > tr:first-child > th,
+.table > thead:first-child > tr:first-child > th,
+.table > caption + thead > tr:first-child > td,
+.table > colgroup + thead > tr:first-child > td,
+.table > thead:first-child > tr:first-child > td {
+ border-top: 0;
+}
+.table > tbody + tbody {
+ border-top: 2px solid #dddddd;
+}
+.table .table {
+ background-color: #ffffff;
+}
+.table-condensed > thead > tr > th,
+.table-condensed > tbody > tr > th,
+.table-condensed > tfoot > tr > th,
+.table-condensed > thead > tr > td,
+.table-condensed > tbody > tr > td,
+.table-condensed > tfoot > tr > td {
+ padding: 5px;
+}
+.table-bordered {
+ border: 1px solid #dddddd;
+}
+.table-bordered > thead > tr > th,
+.table-bordered > tbody > tr > th,
+.table-bordered > tfoot > tr > th,
+.table-bordered > thead > tr > td,
+.table-bordered > tbody > tr > td,
+.table-bordered > tfoot > tr > td {
+ border: 1px solid #dddddd;
+}
+.table-bordered > thead > tr > th,
+.table-bordered > thead > tr > td {
+ border-bottom-width: 2px;
+}
+.table-striped > tbody > tr:nth-of-type(odd) {
+ background-color: #f9f9f9;
+}
+.table-hover > tbody > tr:hover {
+ background-color: #f5f5f5;
+}
+table col[class*="col-"] {
+ position: static;
+ float: none;
+ display: table-column;
+}
+table td[class*="col-"],
+table th[class*="col-"] {
+ position: static;
+ float: none;
+ display: table-cell;
+}
+.table > thead > tr > td.active,
+.table > tbody > tr > td.active,
+.table > tfoot > tr > td.active,
+.table > thead > tr > th.active,
+.table > tbody > tr > th.active,
+.table > tfoot > tr > th.active,
+.table > thead > tr.active > td,
+.table > tbody > tr.active > td,
+.table > tfoot > tr.active > td,
+.table > thead > tr.active > th,
+.table > tbody > tr.active > th,
+.table > tfoot > tr.active > th {
+ background-color: #f5f5f5;
+}
+.table-hover > tbody > tr > td.active:hover,
+.table-hover > tbody > tr > th.active:hover,
+.table-hover > tbody > tr.active:hover > td,
+.table-hover > tbody > tr:hover > .active,
+.table-hover > tbody > tr.active:hover > th {
+ background-color: #e8e8e8;
+}
+.table > thead > tr > td.success,
+.table > tbody > tr > td.success,
+.table > tfoot > tr > td.success,
+.table > thead > tr > th.success,
+.table > tbody > tr > th.success,
+.table > tfoot > tr > th.success,
+.table > thead > tr.success > td,
+.table > tbody > tr.success > td,
+.table > tfoot > tr.success > td,
+.table > thead > tr.success > th,
+.table > tbody > tr.success > th,
+.table > tfoot > tr.success > th {
+ background-color: #dff0d8;
+}
+.table-hover > tbody > tr > td.success:hover,
+.table-hover > tbody > tr > th.success:hover,
+.table-hover > tbody > tr.success:hover > td,
+.table-hover > tbody > tr:hover > .success,
+.table-hover > tbody > tr.success:hover > th {
+ background-color: #d0e9c6;
+}
+.table > thead > tr > td.info,
+.table > tbody > tr > td.info,
+.table > tfoot > tr > td.info,
+.table > thead > tr > th.info,
+.table > tbody > tr > th.info,
+.table > tfoot > tr > th.info,
+.table > thead > tr.info > td,
+.table > tbody > tr.info > td,
+.table > tfoot > tr.info > td,
+.table > thead > tr.info > th,
+.table > tbody > tr.info > th,
+.table > tfoot > tr.info > th {
+ background-color: #d9edf7;
+}
+.table-hover > tbody > tr > td.info:hover,
+.table-hover > tbody > tr > th.info:hover,
+.table-hover > tbody > tr.info:hover > td,
+.table-hover > tbody > tr:hover > .info,
+.table-hover > tbody > tr.info:hover > th {
+ background-color: #c4e3f3;
+}
+.table > thead > tr > td.warning,
+.table > tbody > tr > td.warning,
+.table > tfoot > tr > td.warning,
+.table > thead > tr > th.warning,
+.table > tbody > tr > th.warning,
+.table > tfoot > tr > th.warning,
+.table > thead > tr.warning > td,
+.table > tbody > tr.warning > td,
+.table > tfoot > tr.warning > td,
+.table > thead > tr.warning > th,
+.table > tbody > tr.warning > th,
+.table > tfoot > tr.warning > th {
+ background-color: #fcf8e3;
+}
+.table-hover > tbody > tr > td.warning:hover,
+.table-hover > tbody > tr > th.warning:hover,
+.table-hover > tbody > tr.warning:hover > td,
+.table-hover > tbody > tr:hover > .warning,
+.table-hover > tbody > tr.warning:hover > th {
+ background-color: #faf2cc;
+}
+.table > thead > tr > td.danger,
+.table > tbody > tr > td.danger,
+.table > tfoot > tr > td.danger,
+.table > thead > tr > th.danger,
+.table > tbody > tr > th.danger,
+.table > tfoot > tr > th.danger,
+.table > thead > tr.danger > td,
+.table > tbody > tr.danger > td,
+.table > tfoot > tr.danger > td,
+.table > thead > tr.danger > th,
+.table > tbody > tr.danger > th,
+.table > tfoot > tr.danger > th {
+ background-color: #f2dede;
+}
+.table-hover > tbody > tr > td.danger:hover,
+.table-hover > tbody > tr > th.danger:hover,
+.table-hover > tbody > tr.danger:hover > td,
+.table-hover > tbody > tr:hover > .danger,
+.table-hover > tbody > tr.danger:hover > th {
+ background-color: #ebcccc;
+}
+.table-responsive {
+ overflow-x: auto;
+ min-height: 0.01%;
+}
+@media screen and (max-width: 767px) {
+ .table-responsive {
+ width: 100%;
+ margin-bottom: 15.75px;
+ overflow-y: hidden;
+ -ms-overflow-style: -ms-autohiding-scrollbar;
+ border: 1px solid #dddddd;
+ }
+ .table-responsive > .table {
+ margin-bottom: 0;
+ }
+ .table-responsive > .table > thead > tr > th,
+ .table-responsive > .table > tbody > tr > th,
+ .table-responsive > .table > tfoot > tr > th,
+ .table-responsive > .table > thead > tr > td,
+ .table-responsive > .table > tbody > tr > td,
+ .table-responsive > .table > tfoot > tr > td {
+ white-space: nowrap;
+ }
+ .table-responsive > .table-bordered {
+ border: 0;
+ }
+ .table-responsive > .table-bordered > thead > tr > th:first-child,
+ .table-responsive > .table-bordered > tbody > tr > th:first-child,
+ .table-responsive > .table-bordered > tfoot > tr > th:first-child,
+ .table-responsive > .table-bordered > thead > tr > td:first-child,
+ .table-responsive > .table-bordered > tbody > tr > td:first-child,
+ .table-responsive > .table-bordered > tfoot > tr > td:first-child {
+ border-left: 0;
+ }
+ .table-responsive > .table-bordered > thead > tr > th:last-child,
+ .table-responsive > .table-bordered > tbody > tr > th:last-child,
+ .table-responsive > .table-bordered > tfoot > tr > th:last-child,
+ .table-responsive > .table-bordered > thead > tr > td:last-child,
+ .table-responsive > .table-bordered > tbody > tr > td:last-child,
+ .table-responsive > .table-bordered > tfoot > tr > td:last-child {
+ border-right: 0;
+ }
+ .table-responsive > .table-bordered > tbody > tr:last-child > th,
+ .table-responsive > .table-bordered > tfoot > tr:last-child > th,
+ .table-responsive > .table-bordered > tbody > tr:last-child > td,
+ .table-responsive > .table-bordered > tfoot > tr:last-child > td {
+ border-bottom: 0;
+ }
+}
+fieldset {
+ padding: 0;
+ margin: 0;
+ border: 0;
+ min-width: 0;
+}
+legend {
+ display: block;
+ width: 100%;
+ padding: 0;
+ margin-bottom: 21px;
+ font-size: 22.5px;
+ line-height: inherit;
+ color: #333333;
+ border: 0;
+ border-bottom: 1px solid #e5e5e5;
+}
+label {
+ display: inline-block;
+ max-width: 100%;
+ margin-bottom: 5px;
+ font-weight: bold;
+}
+input[type="search"] {
+ -webkit-box-sizing: border-box;
+ -moz-box-sizing: border-box;
+ box-sizing: border-box;
+}
+input[type="radio"],
+input[type="checkbox"] {
+ margin: 4px 0 0;
+ margin-top: 1px \9;
+ line-height: normal;
+}
+input[type="file"] {
+ display: block;
+}
+input[type="range"] {
+ display: block;
+ width: 100%;
+}
+select[multiple],
+select[size] {
+ height: auto;
+}
+input[type="file"]:focus,
+input[type="radio"]:focus,
+input[type="checkbox"]:focus {
+ outline: 5px auto -webkit-focus-ring-color;
+ outline-offset: -2px;
+}
+output {
+ display: block;
+ padding-top: 9px;
+ font-size: 15px;
+ line-height: 1.4;
+ color: #6f6f6f;
+}
+.form-control {
+ display: block;
+ width: 100%;
+ height: 39px;
+ padding: 8px 12px;
+ font-size: 15px;
+ line-height: 1.4;
+ color: #6f6f6f;
+ background-color: #ffffff;
+ background-image: none;
+ border: 1px solid #cccccc;
+ border-radius: 0;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+ -webkit-transition: border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;
+ -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
+ transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
+}
+.form-control:focus {
+ border-color: #66afe9;
+ outline: 0;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
+ box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
+}
+.form-control::-moz-placeholder {
+ color: #999999;
+ opacity: 1;
+}
+.form-control:-ms-input-placeholder {
+ color: #999999;
+}
+.form-control::-webkit-input-placeholder {
+ color: #999999;
+}
+.form-control::-ms-expand {
+ border: 0;
+ background-color: transparent;
+}
+.form-control[disabled],
+.form-control[readonly],
+fieldset[disabled] .form-control {
+ background-color: #eeeeee;
+ opacity: 1;
+}
+.form-control[disabled],
+fieldset[disabled] .form-control {
+ cursor: not-allowed;
+}
+textarea.form-control {
+ height: auto;
+}
+input[type="search"] {
+ -webkit-appearance: none;
+}
+@media screen and (-webkit-min-device-pixel-ratio: 0) {
+ input[type="date"].form-control,
+ input[type="time"].form-control,
+ input[type="datetime-local"].form-control,
+ input[type="month"].form-control {
+ line-height: 39px;
+ }
+ input[type="date"].input-sm,
+ input[type="time"].input-sm,
+ input[type="datetime-local"].input-sm,
+ input[type="month"].input-sm,
+ .input-group-sm input[type="date"],
+ .input-group-sm input[type="time"],
+ .input-group-sm input[type="datetime-local"],
+ .input-group-sm input[type="month"] {
+ line-height: 36px;
+ }
+ input[type="date"].input-lg,
+ input[type="time"].input-lg,
+ input[type="datetime-local"].input-lg,
+ input[type="month"].input-lg,
+ .input-group-lg input[type="date"],
+ .input-group-lg input[type="time"],
+ .input-group-lg input[type="datetime-local"],
+ .input-group-lg input[type="month"] {
+ line-height: 60px;
+ }
+}
+.form-group {
+ margin-bottom: 15px;
+}
+.radio,
+.checkbox {
+ position: relative;
+ display: block;
+ margin-top: 10px;
+ margin-bottom: 10px;
+}
+.radio label,
+.checkbox label {
+ min-height: 21px;
+ padding-left: 20px;
+ margin-bottom: 0;
+ font-weight: normal;
+ cursor: pointer;
+}
+.radio input[type="radio"],
+.radio-inline input[type="radio"],
+.checkbox input[type="checkbox"],
+.checkbox-inline input[type="checkbox"] {
+ position: absolute;
+ margin-left: -20px;
+ margin-top: 4px \9;
+}
+.radio + .radio,
+.checkbox + .checkbox {
+ margin-top: -5px;
+}
+.radio-inline,
+.checkbox-inline {
+ position: relative;
+ display: inline-block;
+ padding-left: 20px;
+ margin-bottom: 0;
+ vertical-align: middle;
+ font-weight: normal;
+ cursor: pointer;
+}
+.radio-inline + .radio-inline,
+.checkbox-inline + .checkbox-inline {
+ margin-top: 0;
+ margin-left: 10px;
+}
+input[type="radio"][disabled],
+input[type="checkbox"][disabled],
+input[type="radio"].disabled,
+input[type="checkbox"].disabled,
+fieldset[disabled] input[type="radio"],
+fieldset[disabled] input[type="checkbox"] {
+ cursor: not-allowed;
+}
+.radio-inline.disabled,
+.checkbox-inline.disabled,
+fieldset[disabled] .radio-inline,
+fieldset[disabled] .checkbox-inline {
+ cursor: not-allowed;
+}
+.radio.disabled label,
+.checkbox.disabled label,
+fieldset[disabled] .radio label,
+fieldset[disabled] .checkbox label {
+ cursor: not-allowed;
+}
+.form-control-static {
+ padding-top: 9px;
+ padding-bottom: 9px;
+ margin-bottom: 0;
+ min-height: 36px;
+}
+.form-control-static.input-lg,
+.form-control-static.input-sm {
+ padding-left: 0;
+ padding-right: 0;
+}
+.input-sm {
+ height: 36px;
+ padding: 8px 12px;
+ font-size: 12px;
+ line-height: 1.5;
+ border-radius: 0;
+}
+select.input-sm {
+ height: 36px;
+ line-height: 36px;
+}
+textarea.input-sm,
+select[multiple].input-sm {
+ height: auto;
+}
+.form-group-sm .form-control {
+ height: 36px;
+ padding: 8px 12px;
+ font-size: 12px;
+ line-height: 1.5;
+ border-radius: 0;
+}
+.form-group-sm select.form-control {
+ height: 36px;
+ line-height: 36px;
+}
+.form-group-sm textarea.form-control,
+.form-group-sm select[multiple].form-control {
+ height: auto;
+}
+.form-group-sm .form-control-static {
+ height: 36px;
+ min-height: 33px;
+ padding: 9px 12px;
+ font-size: 12px;
+ line-height: 1.5;
+}
+.input-lg {
+ height: 60px;
+ padding: 16px 20px;
+ font-size: 19px;
+ line-height: 1.3333333;
+ border-radius: 0;
+}
+select.input-lg {
+ height: 60px;
+ line-height: 60px;
+}
+textarea.input-lg,
+select[multiple].input-lg {
+ height: auto;
+}
+.form-group-lg .form-control {
+ height: 60px;
+ padding: 16px 20px;
+ font-size: 19px;
+ line-height: 1.3333333;
+ border-radius: 0;
+}
+.form-group-lg select.form-control {
+ height: 60px;
+ line-height: 60px;
+}
+.form-group-lg textarea.form-control,
+.form-group-lg select[multiple].form-control {
+ height: auto;
+}
+.form-group-lg .form-control-static {
+ height: 60px;
+ min-height: 40px;
+ padding: 17px 20px;
+ font-size: 19px;
+ line-height: 1.3333333;
+}
+.has-feedback {
+ position: relative;
+}
+.has-feedback .form-control {
+ padding-right: 48.75px;
+}
+.form-control-feedback {
+ position: absolute;
+ top: 0;
+ right: 0;
+ z-index: 2;
+ display: block;
+ width: 39px;
+ height: 39px;
+ line-height: 39px;
+ text-align: center;
+ pointer-events: none;
+}
+.input-lg + .form-control-feedback,
+.input-group-lg + .form-control-feedback,
+.form-group-lg .form-control + .form-control-feedback {
+ width: 60px;
+ height: 60px;
+ line-height: 60px;
+}
+.input-sm + .form-control-feedback,
+.input-group-sm + .form-control-feedback,
+.form-group-sm .form-control + .form-control-feedback {
+ width: 36px;
+ height: 36px;
+ line-height: 36px;
+}
+.has-success .help-block,
+.has-success .control-label,
+.has-success .radio,
+.has-success .checkbox,
+.has-success .radio-inline,
+.has-success .checkbox-inline,
+.has-success.radio label,
+.has-success.checkbox label,
+.has-success.radio-inline label,
+.has-success.checkbox-inline label {
+ color: #43ac6a;
+}
+.has-success .form-control {
+ border-color: #43ac6a;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+}
+.has-success .form-control:focus {
+ border-color: #358753;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #85d0a1;
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #85d0a1;
+}
+.has-success .input-group-addon {
+ color: #43ac6a;
+ border-color: #43ac6a;
+ background-color: #dff0d8;
+}
+.has-success .form-control-feedback {
+ color: #43ac6a;
+}
+.has-warning .help-block,
+.has-warning .control-label,
+.has-warning .radio,
+.has-warning .checkbox,
+.has-warning .radio-inline,
+.has-warning .checkbox-inline,
+.has-warning.radio label,
+.has-warning.checkbox label,
+.has-warning.radio-inline label,
+.has-warning.checkbox-inline label {
+ color: #e99002;
+}
+.has-warning .form-control {
+ border-color: #e99002;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+}
+.has-warning .form-control:focus {
+ border-color: #b67102;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #febc53;
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #febc53;
+}
+.has-warning .input-group-addon {
+ color: #e99002;
+ border-color: #e99002;
+ background-color: #fcf8e3;
+}
+.has-warning .form-control-feedback {
+ color: #e99002;
+}
+.has-error .help-block,
+.has-error .control-label,
+.has-error .radio,
+.has-error .checkbox,
+.has-error .radio-inline,
+.has-error .checkbox-inline,
+.has-error.radio label,
+.has-error.checkbox label,
+.has-error.radio-inline label,
+.has-error.checkbox-inline label {
+ color: #f04124;
+}
+.has-error .form-control {
+ border-color: #f04124;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
+}
+.has-error .form-control:focus {
+ border-color: #d32a0e;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #f79483;
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #f79483;
+}
+.has-error .input-group-addon {
+ color: #f04124;
+ border-color: #f04124;
+ background-color: #f2dede;
+}
+.has-error .form-control-feedback {
+ color: #f04124;
+}
+.has-feedback label ~ .form-control-feedback {
+ top: 26px;
+}
+.has-feedback label.sr-only ~ .form-control-feedback {
+ top: 0;
+}
+.help-block {
+ display: block;
+ margin-top: 5px;
+ margin-bottom: 10px;
+ color: #626262;
+}
+@media (min-width: 768px) {
+ .form-inline .form-group {
+ display: inline-block;
+ margin-bottom: 0;
+ vertical-align: middle;
+ }
+ .form-inline .form-control {
+ display: inline-block;
+ width: auto;
+ vertical-align: middle;
+ }
+ .form-inline .form-control-static {
+ display: inline-block;
+ }
+ .form-inline .input-group {
+ display: inline-table;
+ vertical-align: middle;
+ }
+ .form-inline .input-group .input-group-addon,
+ .form-inline .input-group .input-group-btn,
+ .form-inline .input-group .form-control {
+ width: auto;
+ }
+ .form-inline .input-group > .form-control {
+ width: 100%;
+ }
+ .form-inline .control-label {
+ margin-bottom: 0;
+ vertical-align: middle;
+ }
+ .form-inline .radio,
+ .form-inline .checkbox {
+ display: inline-block;
+ margin-top: 0;
+ margin-bottom: 0;
+ vertical-align: middle;
+ }
+ .form-inline .radio label,
+ .form-inline .checkbox label {
+ padding-left: 0;
+ }
+ .form-inline .radio input[type="radio"],
+ .form-inline .checkbox input[type="checkbox"] {
+ position: relative;
+ margin-left: 0;
+ }
+ .form-inline .has-feedback .form-control-feedback {
+ top: 0;
+ }
+}
+.form-horizontal .radio,
+.form-horizontal .checkbox,
+.form-horizontal .radio-inline,
+.form-horizontal .checkbox-inline {
+ margin-top: 0;
+ margin-bottom: 0;
+ padding-top: 9px;
+}
+.form-horizontal .radio,
+.form-horizontal .checkbox {
+ min-height: 30px;
+}
+.form-horizontal .form-group {
+ margin-left: -15px;
+ margin-right: -15px;
+}
+@media (min-width: 768px) {
+ .form-horizontal .control-label {
+ text-align: right;
+ margin-bottom: 0;
+ padding-top: 9px;
+ }
+}
+.form-horizontal .has-feedback .form-control-feedback {
+ right: 15px;
+}
+@media (min-width: 768px) {
+ .form-horizontal .form-group-lg .control-label {
+ padding-top: 17px;
+ font-size: 19px;
+ }
+}
+@media (min-width: 768px) {
+ .form-horizontal .form-group-sm .control-label {
+ padding-top: 9px;
+ font-size: 12px;
+ }
+}
+.btn {
+ display: inline-block;
+ margin-bottom: 0;
+ font-weight: normal;
+ text-align: center;
+ vertical-align: middle;
+ -ms-touch-action: manipulation;
+ touch-action: manipulation;
+ cursor: pointer;
+ background-image: none;
+ border: 1px solid transparent;
+ white-space: nowrap;
+ padding: 8px 12px;
+ font-size: 15px;
+ line-height: 1.4;
+ border-radius: 0;
+ -webkit-user-select: none;
+ -moz-user-select: none;
+ -ms-user-select: none;
+ user-select: none;
+}
+.btn:focus,
+.btn:active:focus,
+.btn.active:focus,
+.btn.focus,
+.btn:active.focus,
+.btn.active.focus {
+ outline: 5px auto -webkit-focus-ring-color;
+ outline-offset: -2px;
+}
+.btn:hover,
+.btn:focus,
+.btn.focus {
+ color: #333333;
+ text-decoration: none;
+}
+.btn:active,
+.btn.active {
+ outline: 0;
+ background-image: none;
+ -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
+ box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
+}
+.btn.disabled,
+.btn[disabled],
+fieldset[disabled] .btn {
+ cursor: not-allowed;
+ opacity: 0.65;
+ filter: alpha(opacity=65);
+ -webkit-box-shadow: none;
+ box-shadow: none;
+}
+a.btn.disabled,
+fieldset[disabled] a.btn {
+ pointer-events: none;
+}
+.btn-default {
+ color: #333333;
+ background-color: #e7e7e7;
+ border-color: #cccccc;
+}
+.btn-default:focus,
+.btn-default.focus {
+ color: #333333;
+ background-color: #cecece;
+ border-color: #8c8c8c;
+}
+.btn-default:hover {
+ color: #333333;
+ background-color: #cecece;
+ border-color: #adadad;
+}
+.btn-default:active,
+.btn-default.active,
+.open > .dropdown-toggle.btn-default {
+ color: #333333;
+ background-color: #cecece;
+ border-color: #adadad;
+}
+.btn-default:active:hover,
+.btn-default.active:hover,
+.open > .dropdown-toggle.btn-default:hover,
+.btn-default:active:focus,
+.btn-default.active:focus,
+.open > .dropdown-toggle.btn-default:focus,
+.btn-default:active.focus,
+.btn-default.active.focus,
+.open > .dropdown-toggle.btn-default.focus {
+ color: #333333;
+ background-color: #bcbcbc;
+ border-color: #8c8c8c;
+}
+.btn-default:active,
+.btn-default.active,
+.open > .dropdown-toggle.btn-default {
+ background-image: none;
+}
+.btn-default.disabled:hover,
+.btn-default[disabled]:hover,
+fieldset[disabled] .btn-default:hover,
+.btn-default.disabled:focus,
+.btn-default[disabled]:focus,
+fieldset[disabled] .btn-default:focus,
+.btn-default.disabled.focus,
+.btn-default[disabled].focus,
+fieldset[disabled] .btn-default.focus {
+ background-color: #e7e7e7;
+ border-color: #cccccc;
+}
+.btn-default .badge {
+ color: #e7e7e7;
+ background-color: #333333;
+}
+.btn-primary {
+ color: #ffffff;
+ background-color: #008cba;
+ border-color: #0079a1;
+}
+.btn-primary:focus,
+.btn-primary.focus {
+ color: #ffffff;
+ background-color: #006687;
+ border-color: #001921;
+}
+.btn-primary:hover {
+ color: #ffffff;
+ background-color: #006687;
+ border-color: #004b63;
+}
+.btn-primary:active,
+.btn-primary.active,
+.open > .dropdown-toggle.btn-primary {
+ color: #ffffff;
+ background-color: #006687;
+ border-color: #004b63;
+}
+.btn-primary:active:hover,
+.btn-primary.active:hover,
+.open > .dropdown-toggle.btn-primary:hover,
+.btn-primary:active:focus,
+.btn-primary.active:focus,
+.open > .dropdown-toggle.btn-primary:focus,
+.btn-primary:active.focus,
+.btn-primary.active.focus,
+.open > .dropdown-toggle.btn-primary.focus {
+ color: #ffffff;
+ background-color: #004b63;
+ border-color: #001921;
+}
+.btn-primary:active,
+.btn-primary.active,
+.open > .dropdown-toggle.btn-primary {
+ background-image: none;
+}
+.btn-primary.disabled:hover,
+.btn-primary[disabled]:hover,
+fieldset[disabled] .btn-primary:hover,
+.btn-primary.disabled:focus,
+.btn-primary[disabled]:focus,
+fieldset[disabled] .btn-primary:focus,
+.btn-primary.disabled.focus,
+.btn-primary[disabled].focus,
+fieldset[disabled] .btn-primary.focus {
+ background-color: #008cba;
+ border-color: #0079a1;
+}
+.btn-primary .badge {
+ color: #008cba;
+ background-color: #ffffff;
+}
+.btn-success {
+ color: #ffffff;
+ background-color: #43ac6a;
+ border-color: #3c9a5f;
+}
+.btn-success:focus,
+.btn-success.focus {
+ color: #ffffff;
+ background-color: #358753;
+ border-color: #183e26;
+}
+.btn-success:hover {
+ color: #ffffff;
+ background-color: #358753;
+ border-color: #2b6e44;
+}
+.btn-success:active,
+.btn-success.active,
+.open > .dropdown-toggle.btn-success {
+ color: #ffffff;
+ background-color: #358753;
+ border-color: #2b6e44;
+}
+.btn-success:active:hover,
+.btn-success.active:hover,
+.open > .dropdown-toggle.btn-success:hover,
+.btn-success:active:focus,
+.btn-success.active:focus,
+.open > .dropdown-toggle.btn-success:focus,
+.btn-success:active.focus,
+.btn-success.active.focus,
+.open > .dropdown-toggle.btn-success.focus {
+ color: #ffffff;
+ background-color: #2b6e44;
+ border-color: #183e26;
+}
+.btn-success:active,
+.btn-success.active,
+.open > .dropdown-toggle.btn-success {
+ background-image: none;
+}
+.btn-success.disabled:hover,
+.btn-success[disabled]:hover,
+fieldset[disabled] .btn-success:hover,
+.btn-success.disabled:focus,
+.btn-success[disabled]:focus,
+fieldset[disabled] .btn-success:focus,
+.btn-success.disabled.focus,
+.btn-success[disabled].focus,
+fieldset[disabled] .btn-success.focus {
+ background-color: #43ac6a;
+ border-color: #3c9a5f;
+}
+.btn-success .badge {
+ color: #43ac6a;
+ background-color: #ffffff;
+}
+.btn-info {
+ color: #ffffff;
+ background-color: #5bc0de;
+ border-color: #46b8da;
+}
+.btn-info:focus,
+.btn-info.focus {
+ color: #ffffff;
+ background-color: #31b0d5;
+ border-color: #1b6d85;
+}
+.btn-info:hover {
+ color: #ffffff;
+ background-color: #31b0d5;
+ border-color: #269abc;
+}
+.btn-info:active,
+.btn-info.active,
+.open > .dropdown-toggle.btn-info {
+ color: #ffffff;
+ background-color: #31b0d5;
+ border-color: #269abc;
+}
+.btn-info:active:hover,
+.btn-info.active:hover,
+.open > .dropdown-toggle.btn-info:hover,
+.btn-info:active:focus,
+.btn-info.active:focus,
+.open > .dropdown-toggle.btn-info:focus,
+.btn-info:active.focus,
+.btn-info.active.focus,
+.open > .dropdown-toggle.btn-info.focus {
+ color: #ffffff;
+ background-color: #269abc;
+ border-color: #1b6d85;
+}
+.btn-info:active,
+.btn-info.active,
+.open > .dropdown-toggle.btn-info {
+ background-image: none;
+}
+.btn-info.disabled:hover,
+.btn-info[disabled]:hover,
+fieldset[disabled] .btn-info:hover,
+.btn-info.disabled:focus,
+.btn-info[disabled]:focus,
+fieldset[disabled] .btn-info:focus,
+.btn-info.disabled.focus,
+.btn-info[disabled].focus,
+fieldset[disabled] .btn-info.focus {
+ background-color: #5bc0de;
+ border-color: #46b8da;
+}
+.btn-info .badge {
+ color: #5bc0de;
+ background-color: #ffffff;
+}
+.btn-warning {
+ color: #ffffff;
+ background-color: #e99002;
+ border-color: #d08002;
+}
+.btn-warning:focus,
+.btn-warning.focus {
+ color: #ffffff;
+ background-color: #b67102;
+ border-color: #513201;
+}
+.btn-warning:hover {
+ color: #ffffff;
+ background-color: #b67102;
+ border-color: #935b01;
+}
+.btn-warning:active,
+.btn-warning.active,
+.open > .dropdown-toggle.btn-warning {
+ color: #ffffff;
+ background-color: #b67102;
+ border-color: #935b01;
+}
+.btn-warning:active:hover,
+.btn-warning.active:hover,
+.open > .dropdown-toggle.btn-warning:hover,
+.btn-warning:active:focus,
+.btn-warning.active:focus,
+.open > .dropdown-toggle.btn-warning:focus,
+.btn-warning:active.focus,
+.btn-warning.active.focus,
+.open > .dropdown-toggle.btn-warning.focus {
+ color: #ffffff;
+ background-color: #935b01;
+ border-color: #513201;
+}
+.btn-warning:active,
+.btn-warning.active,
+.open > .dropdown-toggle.btn-warning {
+ background-image: none;
+}
+.btn-warning.disabled:hover,
+.btn-warning[disabled]:hover,
+fieldset[disabled] .btn-warning:hover,
+.btn-warning.disabled:focus,
+.btn-warning[disabled]:focus,
+fieldset[disabled] .btn-warning:focus,
+.btn-warning.disabled.focus,
+.btn-warning[disabled].focus,
+fieldset[disabled] .btn-warning.focus {
+ background-color: #e99002;
+ border-color: #d08002;
+}
+.btn-warning .badge {
+ color: #e99002;
+ background-color: #ffffff;
+}
+.btn-danger {
+ color: #ffffff;
+ background-color: #f04124;
+ border-color: #ea2f10;
+}
+.btn-danger:focus,
+.btn-danger.focus {
+ color: #ffffff;
+ background-color: #d32a0e;
+ border-color: #731708;
+}
+.btn-danger:hover {
+ color: #ffffff;
+ background-color: #d32a0e;
+ border-color: #b1240c;
+}
+.btn-danger:active,
+.btn-danger.active,
+.open > .dropdown-toggle.btn-danger {
+ color: #ffffff;
+ background-color: #d32a0e;
+ border-color: #b1240c;
+}
+.btn-danger:active:hover,
+.btn-danger.active:hover,
+.open > .dropdown-toggle.btn-danger:hover,
+.btn-danger:active:focus,
+.btn-danger.active:focus,
+.open > .dropdown-toggle.btn-danger:focus,
+.btn-danger:active.focus,
+.btn-danger.active.focus,
+.open > .dropdown-toggle.btn-danger.focus {
+ color: #ffffff;
+ background-color: #b1240c;
+ border-color: #731708;
+}
+.btn-danger:active,
+.btn-danger.active,
+.open > .dropdown-toggle.btn-danger {
+ background-image: none;
+}
+.btn-danger.disabled:hover,
+.btn-danger[disabled]:hover,
+fieldset[disabled] .btn-danger:hover,
+.btn-danger.disabled:focus,
+.btn-danger[disabled]:focus,
+fieldset[disabled] .btn-danger:focus,
+.btn-danger.disabled.focus,
+.btn-danger[disabled].focus,
+fieldset[disabled] .btn-danger.focus {
+ background-color: #f04124;
+ border-color: #ea2f10;
+}
+.btn-danger .badge {
+ color: #f04124;
+ background-color: #ffffff;
+}
+.btn-link {
+ color: #008cba;
+ font-weight: normal;
+ border-radius: 0;
+}
+.btn-link,
+.btn-link:active,
+.btn-link.active,
+.btn-link[disabled],
+fieldset[disabled] .btn-link {
+ background-color: transparent;
+ -webkit-box-shadow: none;
+ box-shadow: none;
+}
+.btn-link,
+.btn-link:hover,
+.btn-link:focus,
+.btn-link:active {
+ border-color: transparent;
+}
+.btn-link:hover,
+.btn-link:focus {
+ color: #008cba;
+ text-decoration: underline;
+ background-color: transparent;
+}
+.btn-link[disabled]:hover,
+fieldset[disabled] .btn-link:hover,
+.btn-link[disabled]:focus,
+fieldset[disabled] .btn-link:focus {
+ color: #999999;
+ text-decoration: none;
+}
+.btn-lg,
+.btn-group-lg > .btn {
+ padding: 16px 20px;
+ font-size: 19px;
+ line-height: 1.3333333;
+ border-radius: 0;
+}
+.btn-sm,
+.btn-group-sm > .btn {
+ padding: 8px 12px;
+ font-size: 12px;
+ line-height: 1.5;
+ border-radius: 0;
+}
+.btn-xs,
+.btn-group-xs > .btn {
+ padding: 4px 6px;
+ font-size: 12px;
+ line-height: 1.5;
+ border-radius: 0;
+}
+.btn-block {
+ display: block;
+ width: 100%;
+}
+.btn-block + .btn-block {
+ margin-top: 5px;
+}
+input[type="submit"].btn-block,
+input[type="reset"].btn-block,
+input[type="button"].btn-block {
+ width: 100%;
+}
+.fade {
+ opacity: 0;
+ -webkit-transition: opacity 0.15s linear;
+ -o-transition: opacity 0.15s linear;
+ transition: opacity 0.15s linear;
+}
+.fade.in {
+ opacity: 1;
+}
+.collapse {
+ display: none;
+}
+.collapse.in {
+ display: block;
+}
+tr.collapse.in {
+ display: table-row;
+}
+tbody.collapse.in {
+ display: table-row-group;
+}
+.collapsing {
+ position: relative;
+ height: 0;
+ overflow: hidden;
+ -webkit-transition-property: height, visibility;
+ -o-transition-property: height, visibility;
+ transition-property: height, visibility;
+ -webkit-transition-duration: 0.35s;
+ -o-transition-duration: 0.35s;
+ transition-duration: 0.35s;
+ -webkit-transition-timing-function: ease;
+ -o-transition-timing-function: ease;
+ transition-timing-function: ease;
+}
+.caret {
+ display: inline-block;
+ width: 0;
+ height: 0;
+ margin-left: 2px;
+ vertical-align: middle;
+ border-top: 4px dashed;
+ border-top: 4px solid \9;
+ border-right: 4px solid transparent;
+ border-left: 4px solid transparent;
+}
+.dropup,
+.dropdown {
+ position: relative;
+}
+.dropdown-toggle:focus {
+ outline: 0;
+}
+.dropdown-menu {
+ position: absolute;
+ top: 100%;
+ left: 0;
+ z-index: 1000;
+ display: none;
+ float: left;
+ min-width: 160px;
+ padding: 5px 0;
+ margin: 2px 0 0;
+ list-style: none;
+ font-size: 15px;
+ text-align: left;
+ background-color: #ffffff;
+ border: 1px solid #cccccc;
+ border: 1px solid rgba(0, 0, 0, 0.15);
+ border-radius: 0;
+ -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);
+ box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);
+ -webkit-background-clip: padding-box;
+ background-clip: padding-box;
+}
+.dropdown-menu.pull-right {
+ right: 0;
+ left: auto;
+}
+.dropdown-menu .divider {
+ height: 1px;
+ margin: 9.5px 0;
+ overflow: hidden;
+ background-color: rgba(0, 0, 0, 0.2);
+}
+.dropdown-menu > li > a {
+ display: block;
+ padding: 3px 20px;
+ clear: both;
+ font-weight: normal;
+ line-height: 1.4;
+ color: #555555;
+ white-space: nowrap;
+}
+.dropdown-menu > li > a:hover,
+.dropdown-menu > li > a:focus {
+ text-decoration: none;
+ color: #262626;
+ background-color: #eeeeee;
+}
+.dropdown-menu > .active > a,
+.dropdown-menu > .active > a:hover,
+.dropdown-menu > .active > a:focus {
+ color: #ffffff;
+ text-decoration: none;
+ outline: 0;
+ background-color: #008cba;
+}
+.dropdown-menu > .disabled > a,
+.dropdown-menu > .disabled > a:hover,
+.dropdown-menu > .disabled > a:focus {
+ color: #999999;
+}
+.dropdown-menu > .disabled > a:hover,
+.dropdown-menu > .disabled > a:focus {
+ text-decoration: none;
+ background-color: transparent;
+ background-image: none;
+ filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
+ cursor: not-allowed;
+}
+.open > .dropdown-menu {
+ display: block;
+}
+.open > a {
+ outline: 0;
+}
+.dropdown-menu-right {
+ left: auto;
+ right: 0;
+}
+.dropdown-menu-left {
+ left: 0;
+ right: auto;
+}
+.dropdown-header {
+ display: block;
+ padding: 3px 20px;
+ font-size: 12px;
+ line-height: 1.4;
+ color: #999999;
+ white-space: nowrap;
+}
+.dropdown-backdrop {
+ position: fixed;
+ left: 0;
+ right: 0;
+ bottom: 0;
+ top: 0;
+ z-index: 990;
+}
+.pull-right > .dropdown-menu {
+ right: 0;
+ left: auto;
+}
+.dropup .caret,
+.navbar-fixed-bottom .dropdown .caret {
+ border-top: 0;
+ border-bottom: 4px dashed;
+ border-bottom: 4px solid \9;
+ content: "";
+}
+.dropup .dropdown-menu,
+.navbar-fixed-bottom .dropdown .dropdown-menu {
+ top: auto;
+ bottom: 100%;
+ margin-bottom: 2px;
+}
+@media (min-width: 768px) {
+ .navbar-right .dropdown-menu {
+ left: auto;
+ right: 0;
+ }
+ .navbar-right .dropdown-menu-left {
+ left: 0;
+ right: auto;
+ }
+}
+.btn-group,
+.btn-group-vertical {
+ position: relative;
+ display: inline-block;
+ vertical-align: middle;
+}
+.btn-group > .btn,
+.btn-group-vertical > .btn {
+ position: relative;
+ float: left;
+}
+.btn-group > .btn:hover,
+.btn-group-vertical > .btn:hover,
+.btn-group > .btn:focus,
+.btn-group-vertical > .btn:focus,
+.btn-group > .btn:active,
+.btn-group-vertical > .btn:active,
+.btn-group > .btn.active,
+.btn-group-vertical > .btn.active {
+ z-index: 2;
+}
+.btn-group .btn + .btn,
+.btn-group .btn + .btn-group,
+.btn-group .btn-group + .btn,
+.btn-group .btn-group + .btn-group {
+ margin-left: -1px;
+}
+.btn-toolbar {
+ margin-left: -5px;
+}
+.btn-toolbar .btn,
+.btn-toolbar .btn-group,
+.btn-toolbar .input-group {
+ float: left;
+}
+.btn-toolbar > .btn,
+.btn-toolbar > .btn-group,
+.btn-toolbar > .input-group {
+ margin-left: 5px;
+}
+.btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {
+ border-radius: 0;
+}
+.btn-group > .btn:first-child {
+ margin-left: 0;
+}
+.btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {
+ border-bottom-right-radius: 0;
+ border-top-right-radius: 0;
+}
+.btn-group > .btn:last-child:not(:first-child),
+.btn-group > .dropdown-toggle:not(:first-child) {
+ border-bottom-left-radius: 0;
+ border-top-left-radius: 0;
+}
+.btn-group > .btn-group {
+ float: left;
+}
+.btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {
+ border-radius: 0;
+}
+.btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,
+.btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {
+ border-bottom-right-radius: 0;
+ border-top-right-radius: 0;
+}
+.btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {
+ border-bottom-left-radius: 0;
+ border-top-left-radius: 0;
+}
+.btn-group .dropdown-toggle:active,
+.btn-group.open .dropdown-toggle {
+ outline: 0;
+}
+.btn-group > .btn + .dropdown-toggle {
+ padding-left: 8px;
+ padding-right: 8px;
+}
+.btn-group > .btn-lg + .dropdown-toggle {
+ padding-left: 12px;
+ padding-right: 12px;
+}
+.btn-group.open .dropdown-toggle {
+ -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
+ box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
+}
+.btn-group.open .dropdown-toggle.btn-link {
+ -webkit-box-shadow: none;
+ box-shadow: none;
+}
+.btn .caret {
+ margin-left: 0;
+}
+.btn-lg .caret {
+ border-width: 5px 5px 0;
+ border-bottom-width: 0;
+}
+.dropup .btn-lg .caret {
+ border-width: 0 5px 5px;
+}
+.btn-group-vertical > .btn,
+.btn-group-vertical > .btn-group,
+.btn-group-vertical > .btn-group > .btn {
+ display: block;
+ float: none;
+ width: 100%;
+ max-width: 100%;
+}
+.btn-group-vertical > .btn-group > .btn {
+ float: none;
+}
+.btn-group-vertical > .btn + .btn,
+.btn-group-vertical > .btn + .btn-group,
+.btn-group-vertical > .btn-group + .btn,
+.btn-group-vertical > .btn-group + .btn-group {
+ margin-top: -1px;
+ margin-left: 0;
+}
+.btn-group-vertical > .btn:not(:first-child):not(:last-child) {
+ border-radius: 0;
+}
+.btn-group-vertical > .btn:first-child:not(:last-child) {
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+ border-bottom-right-radius: 0;
+ border-bottom-left-radius: 0;
+}
+.btn-group-vertical > .btn:last-child:not(:first-child) {
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+ border-bottom-right-radius: 0;
+ border-bottom-left-radius: 0;
+}
+.btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {
+ border-radius: 0;
+}
+.btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,
+.btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {
+ border-bottom-right-radius: 0;
+ border-bottom-left-radius: 0;
+}
+.btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+}
+.btn-group-justified {
+ display: table;
+ width: 100%;
+ table-layout: fixed;
+ border-collapse: separate;
+}
+.btn-group-justified > .btn,
+.btn-group-justified > .btn-group {
+ float: none;
+ display: table-cell;
+ width: 1%;
+}
+.btn-group-justified > .btn-group .btn {
+ width: 100%;
+}
+.btn-group-justified > .btn-group .dropdown-menu {
+ left: auto;
+}
+[data-toggle="buttons"] > .btn input[type="radio"],
+[data-toggle="buttons"] > .btn-group > .btn input[type="radio"],
+[data-toggle="buttons"] > .btn input[type="checkbox"],
+[data-toggle="buttons"] > .btn-group > .btn input[type="checkbox"] {
+ position: absolute;
+ clip: rect(0, 0, 0, 0);
+ pointer-events: none;
+}
+.input-group {
+ position: relative;
+ display: table;
+ border-collapse: separate;
+}
+.input-group[class*="col-"] {
+ float: none;
+ padding-left: 0;
+ padding-right: 0;
+}
+.input-group .form-control {
+ position: relative;
+ z-index: 2;
+ float: left;
+ width: 100%;
+ margin-bottom: 0;
+}
+.input-group .form-control:focus {
+ z-index: 3;
+}
+.input-group-lg > .form-control,
+.input-group-lg > .input-group-addon,
+.input-group-lg > .input-group-btn > .btn {
+ height: 60px;
+ padding: 16px 20px;
+ font-size: 19px;
+ line-height: 1.3333333;
+ border-radius: 0;
+}
+select.input-group-lg > .form-control,
+select.input-group-lg > .input-group-addon,
+select.input-group-lg > .input-group-btn > .btn {
+ height: 60px;
+ line-height: 60px;
+}
+textarea.input-group-lg > .form-control,
+textarea.input-group-lg > .input-group-addon,
+textarea.input-group-lg > .input-group-btn > .btn,
+select[multiple].input-group-lg > .form-control,
+select[multiple].input-group-lg > .input-group-addon,
+select[multiple].input-group-lg > .input-group-btn > .btn {
+ height: auto;
+}
+.input-group-sm > .form-control,
+.input-group-sm > .input-group-addon,
+.input-group-sm > .input-group-btn > .btn {
+ height: 36px;
+ padding: 8px 12px;
+ font-size: 12px;
+ line-height: 1.5;
+ border-radius: 0;
+}
+select.input-group-sm > .form-control,
+select.input-group-sm > .input-group-addon,
+select.input-group-sm > .input-group-btn > .btn {
+ height: 36px;
+ line-height: 36px;
+}
+textarea.input-group-sm > .form-control,
+textarea.input-group-sm > .input-group-addon,
+textarea.input-group-sm > .input-group-btn > .btn,
+select[multiple].input-group-sm > .form-control,
+select[multiple].input-group-sm > .input-group-addon,
+select[multiple].input-group-sm > .input-group-btn > .btn {
+ height: auto;
+}
+.input-group-addon,
+.input-group-btn,
+.input-group .form-control {
+ display: table-cell;
+}
+.input-group-addon:not(:first-child):not(:last-child),
+.input-group-btn:not(:first-child):not(:last-child),
+.input-group .form-control:not(:first-child):not(:last-child) {
+ border-radius: 0;
+}
+.input-group-addon,
+.input-group-btn {
+ width: 1%;
+ white-space: nowrap;
+ vertical-align: middle;
+}
+.input-group-addon {
+ padding: 8px 12px;
+ font-size: 15px;
+ font-weight: normal;
+ line-height: 1;
+ color: #6f6f6f;
+ text-align: center;
+ background-color: #eeeeee;
+ border: 1px solid #cccccc;
+ border-radius: 0;
+}
+.input-group-addon.input-sm {
+ padding: 8px 12px;
+ font-size: 12px;
+ border-radius: 0;
+}
+.input-group-addon.input-lg {
+ padding: 16px 20px;
+ font-size: 19px;
+ border-radius: 0;
+}
+.input-group-addon input[type="radio"],
+.input-group-addon input[type="checkbox"] {
+ margin-top: 0;
+}
+.input-group .form-control:first-child,
+.input-group-addon:first-child,
+.input-group-btn:first-child > .btn,
+.input-group-btn:first-child > .btn-group > .btn,
+.input-group-btn:first-child > .dropdown-toggle,
+.input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),
+.input-group-btn:last-child > .btn-group:not(:last-child) > .btn {
+ border-bottom-right-radius: 0;
+ border-top-right-radius: 0;
+}
+.input-group-addon:first-child {
+ border-right: 0;
+}
+.input-group .form-control:last-child,
+.input-group-addon:last-child,
+.input-group-btn:last-child > .btn,
+.input-group-btn:last-child > .btn-group > .btn,
+.input-group-btn:last-child > .dropdown-toggle,
+.input-group-btn:first-child > .btn:not(:first-child),
+.input-group-btn:first-child > .btn-group:not(:first-child) > .btn {
+ border-bottom-left-radius: 0;
+ border-top-left-radius: 0;
+}
+.input-group-addon:last-child {
+ border-left: 0;
+}
+.input-group-btn {
+ position: relative;
+ font-size: 0;
+ white-space: nowrap;
+}
+.input-group-btn > .btn {
+ position: relative;
+}
+.input-group-btn > .btn + .btn {
+ margin-left: -1px;
+}
+.input-group-btn > .btn:hover,
+.input-group-btn > .btn:focus,
+.input-group-btn > .btn:active {
+ z-index: 2;
+}
+.input-group-btn:first-child > .btn,
+.input-group-btn:first-child > .btn-group {
+ margin-right: -1px;
+}
+.input-group-btn:last-child > .btn,
+.input-group-btn:last-child > .btn-group {
+ z-index: 2;
+ margin-left: -1px;
+}
+.nav {
+ margin-bottom: 0;
+ padding-left: 0;
+ list-style: none;
+}
+.nav > li {
+ position: relative;
+ display: block;
+}
+.nav > li > a {
+ position: relative;
+ display: block;
+ padding: 10px 15px;
+}
+.nav > li > a:hover,
+.nav > li > a:focus {
+ text-decoration: none;
+ background-color: #eeeeee;
+}
+.nav > li.disabled > a {
+ color: #999999;
+}
+.nav > li.disabled > a:hover,
+.nav > li.disabled > a:focus {
+ color: #999999;
+ text-decoration: none;
+ background-color: transparent;
+ cursor: not-allowed;
+}
+.nav .open > a,
+.nav .open > a:hover,
+.nav .open > a:focus {
+ background-color: #eeeeee;
+ border-color: #008cba;
+}
+.nav .nav-divider {
+ height: 1px;
+ margin: 9.5px 0;
+ overflow: hidden;
+ background-color: #e5e5e5;
+}
+.nav > li > a > img {
+ max-width: none;
+}
+.nav-tabs {
+ border-bottom: 1px solid #dddddd;
+}
+.nav-tabs > li {
+ float: left;
+ margin-bottom: -1px;
+}
+.nav-tabs > li > a {
+ margin-right: 2px;
+ line-height: 1.4;
+ border: 1px solid transparent;
+ border-radius: 0 0 0 0;
+}
+.nav-tabs > li > a:hover {
+ border-color: #eeeeee #eeeeee #dddddd;
+}
+.nav-tabs > li.active > a,
+.nav-tabs > li.active > a:hover,
+.nav-tabs > li.active > a:focus {
+ color: #6f6f6f;
+ background-color: #ffffff;
+ border: 1px solid #dddddd;
+ border-bottom-color: transparent;
+ cursor: default;
+}
+.nav-tabs.nav-justified {
+ width: 100%;
+ border-bottom: 0;
+}
+.nav-tabs.nav-justified > li {
+ float: none;
+}
+.nav-tabs.nav-justified > li > a {
+ text-align: center;
+ margin-bottom: 5px;
+}
+.nav-tabs.nav-justified > .dropdown .dropdown-menu {
+ top: auto;
+ left: auto;
+}
+@media (min-width: 768px) {
+ .nav-tabs.nav-justified > li {
+ display: table-cell;
+ width: 1%;
+ }
+ .nav-tabs.nav-justified > li > a {
+ margin-bottom: 0;
+ }
+}
+.nav-tabs.nav-justified > li > a {
+ margin-right: 0;
+ border-radius: 0;
+}
+.nav-tabs.nav-justified > .active > a,
+.nav-tabs.nav-justified > .active > a:hover,
+.nav-tabs.nav-justified > .active > a:focus {
+ border: 1px solid #dddddd;
+}
+@media (min-width: 768px) {
+ .nav-tabs.nav-justified > li > a {
+ border-bottom: 1px solid #dddddd;
+ border-radius: 0 0 0 0;
+ }
+ .nav-tabs.nav-justified > .active > a,
+ .nav-tabs.nav-justified > .active > a:hover,
+ .nav-tabs.nav-justified > .active > a:focus {
+ border-bottom-color: #ffffff;
+ }
+}
+.nav-pills > li {
+ float: left;
+}
+.nav-pills > li > a {
+ border-radius: 0;
+}
+.nav-pills > li + li {
+ margin-left: 2px;
+}
+.nav-pills > li.active > a,
+.nav-pills > li.active > a:hover,
+.nav-pills > li.active > a:focus {
+ color: #ffffff;
+ background-color: #008cba;
+}
+.nav-stacked > li {
+ float: none;
+}
+.nav-stacked > li + li {
+ margin-top: 2px;
+ margin-left: 0;
+}
+.nav-justified {
+ width: 100%;
+}
+.nav-justified > li {
+ float: none;
+}
+.nav-justified > li > a {
+ text-align: center;
+ margin-bottom: 5px;
+}
+.nav-justified > .dropdown .dropdown-menu {
+ top: auto;
+ left: auto;
+}
+@media (min-width: 768px) {
+ .nav-justified > li {
+ display: table-cell;
+ width: 1%;
+ }
+ .nav-justified > li > a {
+ margin-bottom: 0;
+ }
+}
+.nav-tabs-justified {
+ border-bottom: 0;
+}
+.nav-tabs-justified > li > a {
+ margin-right: 0;
+ border-radius: 0;
+}
+.nav-tabs-justified > .active > a,
+.nav-tabs-justified > .active > a:hover,
+.nav-tabs-justified > .active > a:focus {
+ border: 1px solid #dddddd;
+}
+@media (min-width: 768px) {
+ .nav-tabs-justified > li > a {
+ border-bottom: 1px solid #dddddd;
+ border-radius: 0 0 0 0;
+ }
+ .nav-tabs-justified > .active > a,
+ .nav-tabs-justified > .active > a:hover,
+ .nav-tabs-justified > .active > a:focus {
+ border-bottom-color: #ffffff;
+ }
+}
+.tab-content > .tab-pane {
+ display: none;
+}
+.tab-content > .active {
+ display: block;
+}
+.nav-tabs .dropdown-menu {
+ margin-top: -1px;
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+}
+.navbar {
+ position: relative;
+ min-height: 45px;
+ margin-bottom: 21px;
+ border: 1px solid transparent;
+}
+@media (min-width: 768px) {
+ .navbar {
+ border-radius: 0;
+ }
+}
+@media (min-width: 768px) {
+ .navbar-header {
+ float: left;
+ }
+}
+.navbar-collapse {
+ overflow-x: visible;
+ padding-right: 15px;
+ padding-left: 15px;
+ border-top: 1px solid transparent;
+ -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
+ box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
+ -webkit-overflow-scrolling: touch;
+}
+.navbar-collapse.in {
+ overflow-y: auto;
+}
+@media (min-width: 768px) {
+ .navbar-collapse {
+ width: auto;
+ border-top: 0;
+ -webkit-box-shadow: none;
+ box-shadow: none;
+ }
+ .navbar-collapse.collapse {
+ display: block !important;
+ height: auto !important;
+ padding-bottom: 0;
+ overflow: visible !important;
+ }
+ .navbar-collapse.in {
+ overflow-y: visible;
+ }
+ .navbar-fixed-top .navbar-collapse,
+ .navbar-static-top .navbar-collapse,
+ .navbar-fixed-bottom .navbar-collapse {
+ padding-left: 0;
+ padding-right: 0;
+ }
+}
+.navbar-fixed-top .navbar-collapse,
+.navbar-fixed-bottom .navbar-collapse {
+ max-height: 340px;
+}
+@media (max-device-width: 480px) and (orientation: landscape) {
+ .navbar-fixed-top .navbar-collapse,
+ .navbar-fixed-bottom .navbar-collapse {
+ max-height: 200px;
+ }
+}
+.container > .navbar-header,
+.container-fluid > .navbar-header,
+.container > .navbar-collapse,
+.container-fluid > .navbar-collapse {
+ margin-right: -15px;
+ margin-left: -15px;
+}
+@media (min-width: 768px) {
+ .container > .navbar-header,
+ .container-fluid > .navbar-header,
+ .container > .navbar-collapse,
+ .container-fluid > .navbar-collapse {
+ margin-right: 0;
+ margin-left: 0;
+ }
+}
+.navbar-static-top {
+ z-index: 1000;
+ border-width: 0 0 1px;
+}
+@media (min-width: 768px) {
+ .navbar-static-top {
+ border-radius: 0;
+ }
+}
+.navbar-fixed-top,
+.navbar-fixed-bottom {
+ position: fixed;
+ right: 0;
+ left: 0;
+ z-index: 1030;
+}
+@media (min-width: 768px) {
+ .navbar-fixed-top,
+ .navbar-fixed-bottom {
+ border-radius: 0;
+ }
+}
+.navbar-fixed-top {
+ top: 0;
+ border-width: 0 0 1px;
+}
+.navbar-fixed-bottom {
+ bottom: 0;
+ margin-bottom: 0;
+ border-width: 1px 0 0;
+}
+.navbar-brand {
+ float: left;
+ padding: 12px 15px;
+ font-size: 19px;
+ line-height: 21px;
+ height: 45px;
+}
+.navbar-brand:hover,
+.navbar-brand:focus {
+ text-decoration: none;
+}
+.navbar-brand > img {
+ display: block;
+}
+@media (min-width: 768px) {
+ .navbar > .container .navbar-brand,
+ .navbar > .container-fluid .navbar-brand {
+ margin-left: -15px;
+ }
+}
+.navbar-toggle {
+ position: relative;
+ float: right;
+ margin-right: 15px;
+ padding: 9px 10px;
+ margin-top: 5.5px;
+ margin-bottom: 5.5px;
+ background-color: transparent;
+ background-image: none;
+ border: 1px solid transparent;
+ border-radius: 0;
+}
+.navbar-toggle:focus {
+ outline: 0;
+}
+.navbar-toggle .icon-bar {
+ display: block;
+ width: 22px;
+ height: 2px;
+ border-radius: 1px;
+}
+.navbar-toggle .icon-bar + .icon-bar {
+ margin-top: 4px;
+}
+@media (min-width: 768px) {
+ .navbar-toggle {
+ display: none;
+ }
+}
+.navbar-nav {
+ margin: 6px -15px;
+}
+.navbar-nav > li > a {
+ padding-top: 10px;
+ padding-bottom: 10px;
+ line-height: 21px;
+}
+@media (max-width: 767px) {
+ .navbar-nav .open .dropdown-menu {
+ position: static;
+ float: none;
+ width: auto;
+ margin-top: 0;
+ background-color: transparent;
+ border: 0;
+ -webkit-box-shadow: none;
+ box-shadow: none;
+ }
+ .navbar-nav .open .dropdown-menu > li > a,
+ .navbar-nav .open .dropdown-menu .dropdown-header {
+ padding: 5px 15px 5px 25px;
+ }
+ .navbar-nav .open .dropdown-menu > li > a {
+ line-height: 21px;
+ }
+ .navbar-nav .open .dropdown-menu > li > a:hover,
+ .navbar-nav .open .dropdown-menu > li > a:focus {
+ background-image: none;
+ }
+}
+@media (min-width: 768px) {
+ .navbar-nav {
+ float: left;
+ margin: 0;
+ }
+ .navbar-nav > li {
+ float: left;
+ }
+ .navbar-nav > li > a {
+ padding-top: 12px;
+ padding-bottom: 12px;
+ }
+}
+.navbar-form {
+ margin-left: -15px;
+ margin-right: -15px;
+ padding: 10px 15px;
+ border-top: 1px solid transparent;
+ border-bottom: 1px solid transparent;
+ -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);
+ box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);
+ margin-top: 3px;
+ margin-bottom: 3px;
+}
+@media (min-width: 768px) {
+ .navbar-form .form-group {
+ display: inline-block;
+ margin-bottom: 0;
+ vertical-align: middle;
+ }
+ .navbar-form .form-control {
+ display: inline-block;
+ width: auto;
+ vertical-align: middle;
+ }
+ .navbar-form .form-control-static {
+ display: inline-block;
+ }
+ .navbar-form .input-group {
+ display: inline-table;
+ vertical-align: middle;
+ }
+ .navbar-form .input-group .input-group-addon,
+ .navbar-form .input-group .input-group-btn,
+ .navbar-form .input-group .form-control {
+ width: auto;
+ }
+ .navbar-form .input-group > .form-control {
+ width: 100%;
+ }
+ .navbar-form .control-label {
+ margin-bottom: 0;
+ vertical-align: middle;
+ }
+ .navbar-form .radio,
+ .navbar-form .checkbox {
+ display: inline-block;
+ margin-top: 0;
+ margin-bottom: 0;
+ vertical-align: middle;
+ }
+ .navbar-form .radio label,
+ .navbar-form .checkbox label {
+ padding-left: 0;
+ }
+ .navbar-form .radio input[type="radio"],
+ .navbar-form .checkbox input[type="checkbox"] {
+ position: relative;
+ margin-left: 0;
+ }
+ .navbar-form .has-feedback .form-control-feedback {
+ top: 0;
+ }
+}
+@media (max-width: 767px) {
+ .navbar-form .form-group {
+ margin-bottom: 5px;
+ }
+ .navbar-form .form-group:last-child {
+ margin-bottom: 0;
+ }
+}
+@media (min-width: 768px) {
+ .navbar-form {
+ width: auto;
+ border: 0;
+ margin-left: 0;
+ margin-right: 0;
+ padding-top: 0;
+ padding-bottom: 0;
+ -webkit-box-shadow: none;
+ box-shadow: none;
+ }
+}
+.navbar-nav > li > .dropdown-menu {
+ margin-top: 0;
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+}
+.navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {
+ margin-bottom: 0;
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+ border-bottom-right-radius: 0;
+ border-bottom-left-radius: 0;
+}
+.navbar-btn {
+ margin-top: 3px;
+ margin-bottom: 3px;
+}
+.navbar-btn.btn-sm {
+ margin-top: 4.5px;
+ margin-bottom: 4.5px;
+}
+.navbar-btn.btn-xs {
+ margin-top: 11.5px;
+ margin-bottom: 11.5px;
+}
+.navbar-text {
+ margin-top: 12px;
+ margin-bottom: 12px;
+}
+@media (min-width: 768px) {
+ .navbar-text {
+ float: left;
+ margin-left: 15px;
+ margin-right: 15px;
+ }
+}
+@media (min-width: 768px) {
+ .navbar-left {
+ float: left !important;
+ }
+ .navbar-right {
+ float: right !important;
+ margin-right: -15px;
+ }
+ .navbar-right ~ .navbar-right {
+ margin-right: 0;
+ }
+}
+.navbar-default {
+ background-color: #333333;
+ border-color: #222222;
+}
+.navbar-default .navbar-brand {
+ color: #ffffff;
+}
+.navbar-default .navbar-brand:hover,
+.navbar-default .navbar-brand:focus {
+ color: #ffffff;
+ background-color: transparent;
+}
+.navbar-default .navbar-text {
+ color: #ffffff;
+}
+.navbar-default .navbar-nav > li > a {
+ color: #ffffff;
+}
+.navbar-default .navbar-nav > li > a:hover,
+.navbar-default .navbar-nav > li > a:focus {
+ color: #ffffff;
+ background-color: #272727;
+}
+.navbar-default .navbar-nav > .active > a,
+.navbar-default .navbar-nav > .active > a:hover,
+.navbar-default .navbar-nav > .active > a:focus {
+ color: #ffffff;
+ background-color: #272727;
+}
+.navbar-default .navbar-nav > .disabled > a,
+.navbar-default .navbar-nav > .disabled > a:hover,
+.navbar-default .navbar-nav > .disabled > a:focus {
+ color: #cccccc;
+ background-color: transparent;
+}
+.navbar-default .navbar-toggle {
+ border-color: transparent;
+}
+.navbar-default .navbar-toggle:hover,
+.navbar-default .navbar-toggle:focus {
+ background-color: transparent;
+}
+.navbar-default .navbar-toggle .icon-bar {
+ background-color: #ffffff;
+}
+.navbar-default .navbar-collapse,
+.navbar-default .navbar-form {
+ border-color: #222222;
+}
+.navbar-default .navbar-nav > .open > a,
+.navbar-default .navbar-nav > .open > a:hover,
+.navbar-default .navbar-nav > .open > a:focus {
+ background-color: #272727;
+ color: #ffffff;
+}
+@media (max-width: 767px) {
+ .navbar-default .navbar-nav .open .dropdown-menu > li > a {
+ color: #ffffff;
+ }
+ .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover,
+ .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus {
+ color: #ffffff;
+ background-color: #272727;
+ }
+ .navbar-default .navbar-nav .open .dropdown-menu > .active > a,
+ .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover,
+ .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus {
+ color: #ffffff;
+ background-color: #272727;
+ }
+ .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a,
+ .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover,
+ .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus {
+ color: #cccccc;
+ background-color: transparent;
+ }
+}
+.navbar-default .navbar-link {
+ color: #ffffff;
+}
+.navbar-default .navbar-link:hover {
+ color: #ffffff;
+}
+.navbar-default .btn-link {
+ color: #ffffff;
+}
+.navbar-default .btn-link:hover,
+.navbar-default .btn-link:focus {
+ color: #ffffff;
+}
+.navbar-default .btn-link[disabled]:hover,
+fieldset[disabled] .navbar-default .btn-link:hover,
+.navbar-default .btn-link[disabled]:focus,
+fieldset[disabled] .navbar-default .btn-link:focus {
+ color: #cccccc;
+}
+.navbar-inverse {
+ background-color: #008cba;
+ border-color: #006687;
+}
+.navbar-inverse .navbar-brand {
+ color: #ffffff;
+}
+.navbar-inverse .navbar-brand:hover,
+.navbar-inverse .navbar-brand:focus {
+ color: #ffffff;
+ background-color: transparent;
+}
+.navbar-inverse .navbar-text {
+ color: #ffffff;
+}
+.navbar-inverse .navbar-nav > li > a {
+ color: #ffffff;
+}
+.navbar-inverse .navbar-nav > li > a:hover,
+.navbar-inverse .navbar-nav > li > a:focus {
+ color: #ffffff;
+ background-color: #006687;
+}
+.navbar-inverse .navbar-nav > .active > a,
+.navbar-inverse .navbar-nav > .active > a:hover,
+.navbar-inverse .navbar-nav > .active > a:focus {
+ color: #ffffff;
+ background-color: #006687;
+}
+.navbar-inverse .navbar-nav > .disabled > a,
+.navbar-inverse .navbar-nav > .disabled > a:hover,
+.navbar-inverse .navbar-nav > .disabled > a:focus {
+ color: #444444;
+ background-color: transparent;
+}
+.navbar-inverse .navbar-toggle {
+ border-color: transparent;
+}
+.navbar-inverse .navbar-toggle:hover,
+.navbar-inverse .navbar-toggle:focus {
+ background-color: transparent;
+}
+.navbar-inverse .navbar-toggle .icon-bar {
+ background-color: #ffffff;
+}
+.navbar-inverse .navbar-collapse,
+.navbar-inverse .navbar-form {
+ border-color: #007196;
+}
+.navbar-inverse .navbar-nav > .open > a,
+.navbar-inverse .navbar-nav > .open > a:hover,
+.navbar-inverse .navbar-nav > .open > a:focus {
+ background-color: #006687;
+ color: #ffffff;
+}
+@media (max-width: 767px) {
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header {
+ border-color: #006687;
+ }
+ .navbar-inverse .navbar-nav .open .dropdown-menu .divider {
+ background-color: #006687;
+ }
+ .navbar-inverse .navbar-nav .open .dropdown-menu > li > a {
+ color: #ffffff;
+ }
+ .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover,
+ .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus {
+ color: #ffffff;
+ background-color: #006687;
+ }
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a,
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover,
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus {
+ color: #ffffff;
+ background-color: #006687;
+ }
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a,
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover,
+ .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus {
+ color: #444444;
+ background-color: transparent;
+ }
+}
+.navbar-inverse .navbar-link {
+ color: #ffffff;
+}
+.navbar-inverse .navbar-link:hover {
+ color: #ffffff;
+}
+.navbar-inverse .btn-link {
+ color: #ffffff;
+}
+.navbar-inverse .btn-link:hover,
+.navbar-inverse .btn-link:focus {
+ color: #ffffff;
+}
+.navbar-inverse .btn-link[disabled]:hover,
+fieldset[disabled] .navbar-inverse .btn-link:hover,
+.navbar-inverse .btn-link[disabled]:focus,
+fieldset[disabled] .navbar-inverse .btn-link:focus {
+ color: #444444;
+}
+.breadcrumb {
+ padding: 8px 15px;
+ margin-bottom: 21px;
+ list-style: none;
+ background-color: #f5f5f5;
+ border-radius: 0;
+}
+.breadcrumb > li {
+ display: inline-block;
+}
+.breadcrumb > li + li:before {
+ content: "/\00a0";
+ padding: 0 5px;
+ color: #999999;
+}
+.breadcrumb > .active {
+ color: #333333;
+}
+.pagination {
+ display: inline-block;
+ padding-left: 0;
+ margin: 21px 0;
+ border-radius: 0;
+}
+.pagination > li {
+ display: inline;
+}
+.pagination > li > a,
+.pagination > li > span {
+ position: relative;
+ float: left;
+ padding: 8px 12px;
+ line-height: 1.4;
+ text-decoration: none;
+ color: #008cba;
+ background-color: transparent;
+ border: 1px solid transparent;
+ margin-left: -1px;
+}
+.pagination > li:first-child > a,
+.pagination > li:first-child > span {
+ margin-left: 0;
+ border-bottom-left-radius: 0;
+ border-top-left-radius: 0;
+}
+.pagination > li:last-child > a,
+.pagination > li:last-child > span {
+ border-bottom-right-radius: 0;
+ border-top-right-radius: 0;
+}
+.pagination > li > a:hover,
+.pagination > li > span:hover,
+.pagination > li > a:focus,
+.pagination > li > span:focus {
+ z-index: 2;
+ color: #008cba;
+ background-color: #eeeeee;
+ border-color: transparent;
+}
+.pagination > .active > a,
+.pagination > .active > span,
+.pagination > .active > a:hover,
+.pagination > .active > span:hover,
+.pagination > .active > a:focus,
+.pagination > .active > span:focus {
+ z-index: 3;
+ color: #ffffff;
+ background-color: #008cba;
+ border-color: transparent;
+ cursor: default;
+}
+.pagination > .disabled > span,
+.pagination > .disabled > span:hover,
+.pagination > .disabled > span:focus,
+.pagination > .disabled > a,
+.pagination > .disabled > a:hover,
+.pagination > .disabled > a:focus {
+ color: #999999;
+ background-color: #ffffff;
+ border-color: transparent;
+ cursor: not-allowed;
+}
+.pagination-lg > li > a,
+.pagination-lg > li > span {
+ padding: 16px 20px;
+ font-size: 19px;
+ line-height: 1.3333333;
+}
+.pagination-lg > li:first-child > a,
+.pagination-lg > li:first-child > span {
+ border-bottom-left-radius: 0;
+ border-top-left-radius: 0;
+}
+.pagination-lg > li:last-child > a,
+.pagination-lg > li:last-child > span {
+ border-bottom-right-radius: 0;
+ border-top-right-radius: 0;
+}
+.pagination-sm > li > a,
+.pagination-sm > li > span {
+ padding: 8px 12px;
+ font-size: 12px;
+ line-height: 1.5;
+}
+.pagination-sm > li:first-child > a,
+.pagination-sm > li:first-child > span {
+ border-bottom-left-radius: 0;
+ border-top-left-radius: 0;
+}
+.pagination-sm > li:last-child > a,
+.pagination-sm > li:last-child > span {
+ border-bottom-right-radius: 0;
+ border-top-right-radius: 0;
+}
+.pager {
+ padding-left: 0;
+ margin: 21px 0;
+ list-style: none;
+ text-align: center;
+}
+.pager li {
+ display: inline;
+}
+.pager li > a,
+.pager li > span {
+ display: inline-block;
+ padding: 5px 14px;
+ background-color: transparent;
+ border: 1px solid transparent;
+ border-radius: 3px;
+}
+.pager li > a:hover,
+.pager li > a:focus {
+ text-decoration: none;
+ background-color: #eeeeee;
+}
+.pager .next > a,
+.pager .next > span {
+ float: right;
+}
+.pager .previous > a,
+.pager .previous > span {
+ float: left;
+}
+.pager .disabled > a,
+.pager .disabled > a:hover,
+.pager .disabled > a:focus,
+.pager .disabled > span {
+ color: #999999;
+ background-color: transparent;
+ cursor: not-allowed;
+}
+.label {
+ display: inline;
+ padding: .2em .6em .3em;
+ font-size: 75%;
+ font-weight: bold;
+ line-height: 1;
+ color: #ffffff;
+ text-align: center;
+ white-space: nowrap;
+ vertical-align: baseline;
+ border-radius: .25em;
+}
+a.label:hover,
+a.label:focus {
+ color: #ffffff;
+ text-decoration: none;
+ cursor: pointer;
+}
+.label:empty {
+ display: none;
+}
+.btn .label {
+ position: relative;
+ top: -1px;
+}
+.label-default {
+ background-color: #999999;
+}
+.label-default[href]:hover,
+.label-default[href]:focus {
+ background-color: #808080;
+}
+.label-primary {
+ background-color: #008cba;
+}
+.label-primary[href]:hover,
+.label-primary[href]:focus {
+ background-color: #006687;
+}
+.label-success {
+ background-color: #43ac6a;
+}
+.label-success[href]:hover,
+.label-success[href]:focus {
+ background-color: #358753;
+}
+.label-info {
+ background-color: #5bc0de;
+}
+.label-info[href]:hover,
+.label-info[href]:focus {
+ background-color: #31b0d5;
+}
+.label-warning {
+ background-color: #e99002;
+}
+.label-warning[href]:hover,
+.label-warning[href]:focus {
+ background-color: #b67102;
+}
+.label-danger {
+ background-color: #f04124;
+}
+.label-danger[href]:hover,
+.label-danger[href]:focus {
+ background-color: #d32a0e;
+}
+.badge {
+ display: inline-block;
+ min-width: 10px;
+ padding: 3px 7px;
+ font-size: 12px;
+ font-weight: bold;
+ color: #ffffff;
+ line-height: 1;
+ vertical-align: middle;
+ white-space: nowrap;
+ text-align: center;
+ background-color: #008cba;
+ border-radius: 10px;
+}
+.badge:empty {
+ display: none;
+}
+.btn .badge {
+ position: relative;
+ top: -1px;
+}
+.btn-xs .badge,
+.btn-group-xs > .btn .badge {
+ top: 0;
+ padding: 1px 5px;
+}
+a.badge:hover,
+a.badge:focus {
+ color: #ffffff;
+ text-decoration: none;
+ cursor: pointer;
+}
+.list-group-item.active > .badge,
+.nav-pills > .active > a > .badge {
+ color: #008cba;
+ background-color: #ffffff;
+}
+.list-group-item > .badge {
+ float: right;
+}
+.list-group-item > .badge + .badge {
+ margin-right: 5px;
+}
+.nav-pills > li > a > .badge {
+ margin-left: 3px;
+}
+.jumbotron {
+ padding-top: 30px;
+ padding-bottom: 30px;
+ margin-bottom: 30px;
+ color: inherit;
+ background-color: #fafafa;
+}
+.jumbotron h1,
+.jumbotron .h1 {
+ color: inherit;
+}
+.jumbotron p {
+ margin-bottom: 15px;
+ font-size: 23px;
+ font-weight: 200;
+}
+.jumbotron > hr {
+ border-top-color: #e1e1e1;
+}
+.container .jumbotron,
+.container-fluid .jumbotron {
+ border-radius: 0;
+ padding-left: 15px;
+ padding-right: 15px;
+}
+.jumbotron .container {
+ max-width: 100%;
+}
+@media screen and (min-width: 768px) {
+ .jumbotron {
+ padding-top: 48px;
+ padding-bottom: 48px;
+ }
+ .container .jumbotron,
+ .container-fluid .jumbotron {
+ padding-left: 60px;
+ padding-right: 60px;
+ }
+ .jumbotron h1,
+ .jumbotron .h1 {
+ font-size: 68px;
+ }
+}
+.thumbnail {
+ display: block;
+ padding: 4px;
+ margin-bottom: 21px;
+ line-height: 1.4;
+ background-color: #ffffff;
+ border: 1px solid #dddddd;
+ border-radius: 0;
+ -webkit-transition: border 0.2s ease-in-out;
+ -o-transition: border 0.2s ease-in-out;
+ transition: border 0.2s ease-in-out;
+}
+.thumbnail > img,
+.thumbnail a > img {
+ margin-left: auto;
+ margin-right: auto;
+}
+a.thumbnail:hover,
+a.thumbnail:focus,
+a.thumbnail.active {
+ border-color: #008cba;
+}
+.thumbnail .caption {
+ padding: 9px;
+ color: #222222;
+}
+.alert {
+ padding: 15px;
+ margin-bottom: 21px;
+ border: 1px solid transparent;
+ border-radius: 0;
+}
+.alert h4 {
+ margin-top: 0;
+ color: inherit;
+}
+.alert .alert-link {
+ font-weight: bold;
+}
+.alert > p,
+.alert > ul {
+ margin-bottom: 0;
+}
+.alert > p + p {
+ margin-top: 5px;
+}
+.alert-dismissable,
+.alert-dismissible {
+ padding-right: 35px;
+}
+.alert-dismissable .close,
+.alert-dismissible .close {
+ position: relative;
+ top: -2px;
+ right: -21px;
+ color: inherit;
+}
+.alert-success {
+ background-color: #43ac6a;
+ border-color: #3c9a5f;
+ color: #ffffff;
+}
+.alert-success hr {
+ border-top-color: #358753;
+}
+.alert-success .alert-link {
+ color: #e6e6e6;
+}
+.alert-info {
+ background-color: #5bc0de;
+ border-color: #3db5d8;
+ color: #ffffff;
+}
+.alert-info hr {
+ border-top-color: #2aabd2;
+}
+.alert-info .alert-link {
+ color: #e6e6e6;
+}
+.alert-warning {
+ background-color: #e99002;
+ border-color: #d08002;
+ color: #ffffff;
+}
+.alert-warning hr {
+ border-top-color: #b67102;
+}
+.alert-warning .alert-link {
+ color: #e6e6e6;
+}
+.alert-danger {
+ background-color: #f04124;
+ border-color: #ea2f10;
+ color: #ffffff;
+}
+.alert-danger hr {
+ border-top-color: #d32a0e;
+}
+.alert-danger .alert-link {
+ color: #e6e6e6;
+}
+@-webkit-keyframes progress-bar-stripes {
+ from {
+ background-position: 40px 0;
+ }
+ to {
+ background-position: 0 0;
+ }
+}
+@-o-keyframes progress-bar-stripes {
+ from {
+ background-position: 40px 0;
+ }
+ to {
+ background-position: 0 0;
+ }
+}
+@keyframes progress-bar-stripes {
+ from {
+ background-position: 40px 0;
+ }
+ to {
+ background-position: 0 0;
+ }
+}
+.progress {
+ overflow: hidden;
+ height: 21px;
+ margin-bottom: 21px;
+ background-color: #f5f5f5;
+ border-radius: 0;
+ -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
+ box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
+}
+.progress-bar {
+ float: left;
+ width: 0%;
+ height: 100%;
+ font-size: 12px;
+ line-height: 21px;
+ color: #ffffff;
+ text-align: center;
+ background-color: #008cba;
+ -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
+ box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
+ -webkit-transition: width 0.6s ease;
+ -o-transition: width 0.6s ease;
+ transition: width 0.6s ease;
+}
+.progress-striped .progress-bar,
+.progress-bar-striped {
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ -webkit-background-size: 40px 40px;
+ background-size: 40px 40px;
+}
+.progress.active .progress-bar,
+.progress-bar.active {
+ -webkit-animation: progress-bar-stripes 2s linear infinite;
+ -o-animation: progress-bar-stripes 2s linear infinite;
+ animation: progress-bar-stripes 2s linear infinite;
+}
+.progress-bar-success {
+ background-color: #43ac6a;
+}
+.progress-striped .progress-bar-success {
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+}
+.progress-bar-info {
+ background-color: #5bc0de;
+}
+.progress-striped .progress-bar-info {
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+}
+.progress-bar-warning {
+ background-color: #e99002;
+}
+.progress-striped .progress-bar-warning {
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+}
+.progress-bar-danger {
+ background-color: #f04124;
+}
+.progress-striped .progress-bar-danger {
+ background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+ background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
+}
+.media {
+ margin-top: 15px;
+}
+.media:first-child {
+ margin-top: 0;
+}
+.media,
+.media-body {
+ zoom: 1;
+ overflow: hidden;
+}
+.media-body {
+ width: 10000px;
+}
+.media-object {
+ display: block;
+}
+.media-object.img-thumbnail {
+ max-width: none;
+}
+.media-right,
+.media > .pull-right {
+ padding-left: 10px;
+}
+.media-left,
+.media > .pull-left {
+ padding-right: 10px;
+}
+.media-left,
+.media-right,
+.media-body {
+ display: table-cell;
+ vertical-align: top;
+}
+.media-middle {
+ vertical-align: middle;
+}
+.media-bottom {
+ vertical-align: bottom;
+}
+.media-heading {
+ margin-top: 0;
+ margin-bottom: 5px;
+}
+.media-list {
+ padding-left: 0;
+ list-style: none;
+}
+.list-group {
+ margin-bottom: 20px;
+ padding-left: 0;
+}
+.list-group-item {
+ position: relative;
+ display: block;
+ padding: 10px 15px;
+ margin-bottom: -1px;
+ background-color: #ffffff;
+ border: 1px solid #dddddd;
+}
+.list-group-item:first-child {
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+}
+.list-group-item:last-child {
+ margin-bottom: 0;
+ border-bottom-right-radius: 0;
+ border-bottom-left-radius: 0;
+}
+a.list-group-item,
+button.list-group-item {
+ color: #555555;
+}
+a.list-group-item .list-group-item-heading,
+button.list-group-item .list-group-item-heading {
+ color: #333333;
+}
+a.list-group-item:hover,
+button.list-group-item:hover,
+a.list-group-item:focus,
+button.list-group-item:focus {
+ text-decoration: none;
+ color: #555555;
+ background-color: #f5f5f5;
+}
+button.list-group-item {
+ width: 100%;
+ text-align: left;
+}
+.list-group-item.disabled,
+.list-group-item.disabled:hover,
+.list-group-item.disabled:focus {
+ background-color: #eeeeee;
+ color: #999999;
+ cursor: not-allowed;
+}
+.list-group-item.disabled .list-group-item-heading,
+.list-group-item.disabled:hover .list-group-item-heading,
+.list-group-item.disabled:focus .list-group-item-heading {
+ color: inherit;
+}
+.list-group-item.disabled .list-group-item-text,
+.list-group-item.disabled:hover .list-group-item-text,
+.list-group-item.disabled:focus .list-group-item-text {
+ color: #999999;
+}
+.list-group-item.active,
+.list-group-item.active:hover,
+.list-group-item.active:focus {
+ z-index: 2;
+ color: #ffffff;
+ background-color: #008cba;
+ border-color: #008cba;
+}
+.list-group-item.active .list-group-item-heading,
+.list-group-item.active:hover .list-group-item-heading,
+.list-group-item.active:focus .list-group-item-heading,
+.list-group-item.active .list-group-item-heading > small,
+.list-group-item.active:hover .list-group-item-heading > small,
+.list-group-item.active:focus .list-group-item-heading > small,
+.list-group-item.active .list-group-item-heading > .small,
+.list-group-item.active:hover .list-group-item-heading > .small,
+.list-group-item.active:focus .list-group-item-heading > .small {
+ color: inherit;
+}
+.list-group-item.active .list-group-item-text,
+.list-group-item.active:hover .list-group-item-text,
+.list-group-item.active:focus .list-group-item-text {
+ color: #87e1ff;
+}
+.list-group-item-success {
+ color: #43ac6a;
+ background-color: #dff0d8;
+}
+a.list-group-item-success,
+button.list-group-item-success {
+ color: #43ac6a;
+}
+a.list-group-item-success .list-group-item-heading,
+button.list-group-item-success .list-group-item-heading {
+ color: inherit;
+}
+a.list-group-item-success:hover,
+button.list-group-item-success:hover,
+a.list-group-item-success:focus,
+button.list-group-item-success:focus {
+ color: #43ac6a;
+ background-color: #d0e9c6;
+}
+a.list-group-item-success.active,
+button.list-group-item-success.active,
+a.list-group-item-success.active:hover,
+button.list-group-item-success.active:hover,
+a.list-group-item-success.active:focus,
+button.list-group-item-success.active:focus {
+ color: #fff;
+ background-color: #43ac6a;
+ border-color: #43ac6a;
+}
+.list-group-item-info {
+ color: #5bc0de;
+ background-color: #d9edf7;
+}
+a.list-group-item-info,
+button.list-group-item-info {
+ color: #5bc0de;
+}
+a.list-group-item-info .list-group-item-heading,
+button.list-group-item-info .list-group-item-heading {
+ color: inherit;
+}
+a.list-group-item-info:hover,
+button.list-group-item-info:hover,
+a.list-group-item-info:focus,
+button.list-group-item-info:focus {
+ color: #5bc0de;
+ background-color: #c4e3f3;
+}
+a.list-group-item-info.active,
+button.list-group-item-info.active,
+a.list-group-item-info.active:hover,
+button.list-group-item-info.active:hover,
+a.list-group-item-info.active:focus,
+button.list-group-item-info.active:focus {
+ color: #fff;
+ background-color: #5bc0de;
+ border-color: #5bc0de;
+}
+.list-group-item-warning {
+ color: #e99002;
+ background-color: #fcf8e3;
+}
+a.list-group-item-warning,
+button.list-group-item-warning {
+ color: #e99002;
+}
+a.list-group-item-warning .list-group-item-heading,
+button.list-group-item-warning .list-group-item-heading {
+ color: inherit;
+}
+a.list-group-item-warning:hover,
+button.list-group-item-warning:hover,
+a.list-group-item-warning:focus,
+button.list-group-item-warning:focus {
+ color: #e99002;
+ background-color: #faf2cc;
+}
+a.list-group-item-warning.active,
+button.list-group-item-warning.active,
+a.list-group-item-warning.active:hover,
+button.list-group-item-warning.active:hover,
+a.list-group-item-warning.active:focus,
+button.list-group-item-warning.active:focus {
+ color: #fff;
+ background-color: #e99002;
+ border-color: #e99002;
+}
+.list-group-item-danger {
+ color: #f04124;
+ background-color: #f2dede;
+}
+a.list-group-item-danger,
+button.list-group-item-danger {
+ color: #f04124;
+}
+a.list-group-item-danger .list-group-item-heading,
+button.list-group-item-danger .list-group-item-heading {
+ color: inherit;
+}
+a.list-group-item-danger:hover,
+button.list-group-item-danger:hover,
+a.list-group-item-danger:focus,
+button.list-group-item-danger:focus {
+ color: #f04124;
+ background-color: #ebcccc;
+}
+a.list-group-item-danger.active,
+button.list-group-item-danger.active,
+a.list-group-item-danger.active:hover,
+button.list-group-item-danger.active:hover,
+a.list-group-item-danger.active:focus,
+button.list-group-item-danger.active:focus {
+ color: #fff;
+ background-color: #f04124;
+ border-color: #f04124;
+}
+.list-group-item-heading {
+ margin-top: 0;
+ margin-bottom: 5px;
+}
+.list-group-item-text {
+ margin-bottom: 0;
+ line-height: 1.3;
+}
+.panel {
+ margin-bottom: 21px;
+ background-color: #ffffff;
+ border: 1px solid transparent;
+ border-radius: 0;
+ -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);
+}
+.panel-body {
+ padding: 15px;
+}
+.panel-heading {
+ padding: 10px 15px;
+ border-bottom: 1px solid transparent;
+ border-top-right-radius: -1;
+ border-top-left-radius: -1;
+}
+.panel-heading > .dropdown .dropdown-toggle {
+ color: inherit;
+}
+.panel-title {
+ margin-top: 0;
+ margin-bottom: 0;
+ font-size: 17px;
+ color: inherit;
+}
+.panel-title > a,
+.panel-title > small,
+.panel-title > .small,
+.panel-title > small > a,
+.panel-title > .small > a {
+ color: inherit;
+}
+.panel-footer {
+ padding: 10px 15px;
+ background-color: #f5f5f5;
+ border-top: 1px solid #dddddd;
+ border-bottom-right-radius: -1;
+ border-bottom-left-radius: -1;
+}
+.panel > .list-group,
+.panel > .panel-collapse > .list-group {
+ margin-bottom: 0;
+}
+.panel > .list-group .list-group-item,
+.panel > .panel-collapse > .list-group .list-group-item {
+ border-width: 1px 0;
+ border-radius: 0;
+}
+.panel > .list-group:first-child .list-group-item:first-child,
+.panel > .panel-collapse > .list-group:first-child .list-group-item:first-child {
+ border-top: 0;
+ border-top-right-radius: -1;
+ border-top-left-radius: -1;
+}
+.panel > .list-group:last-child .list-group-item:last-child,
+.panel > .panel-collapse > .list-group:last-child .list-group-item:last-child {
+ border-bottom: 0;
+ border-bottom-right-radius: -1;
+ border-bottom-left-radius: -1;
+}
+.panel > .panel-heading + .panel-collapse > .list-group .list-group-item:first-child {
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+}
+.panel-heading + .list-group .list-group-item:first-child {
+ border-top-width: 0;
+}
+.list-group + .panel-footer {
+ border-top-width: 0;
+}
+.panel > .table,
+.panel > .table-responsive > .table,
+.panel > .panel-collapse > .table {
+ margin-bottom: 0;
+}
+.panel > .table caption,
+.panel > .table-responsive > .table caption,
+.panel > .panel-collapse > .table caption {
+ padding-left: 15px;
+ padding-right: 15px;
+}
+.panel > .table:first-child,
+.panel > .table-responsive:first-child > .table:first-child {
+ border-top-right-radius: -1;
+ border-top-left-radius: -1;
+}
+.panel > .table:first-child > thead:first-child > tr:first-child,
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child,
+.panel > .table:first-child > tbody:first-child > tr:first-child,
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child {
+ border-top-left-radius: -1;
+ border-top-right-radius: -1;
+}
+.panel > .table:first-child > thead:first-child > tr:first-child td:first-child,
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:first-child,
+.panel > .table:first-child > tbody:first-child > tr:first-child td:first-child,
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:first-child,
+.panel > .table:first-child > thead:first-child > tr:first-child th:first-child,
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:first-child,
+.panel > .table:first-child > tbody:first-child > tr:first-child th:first-child,
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:first-child {
+ border-top-left-radius: -1;
+}
+.panel > .table:first-child > thead:first-child > tr:first-child td:last-child,
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:last-child,
+.panel > .table:first-child > tbody:first-child > tr:first-child td:last-child,
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:last-child,
+.panel > .table:first-child > thead:first-child > tr:first-child th:last-child,
+.panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:last-child,
+.panel > .table:first-child > tbody:first-child > tr:first-child th:last-child,
+.panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:last-child {
+ border-top-right-radius: -1;
+}
+.panel > .table:last-child,
+.panel > .table-responsive:last-child > .table:last-child {
+ border-bottom-right-radius: -1;
+ border-bottom-left-radius: -1;
+}
+.panel > .table:last-child > tbody:last-child > tr:last-child,
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child,
+.panel > .table:last-child > tfoot:last-child > tr:last-child,
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child {
+ border-bottom-left-radius: -1;
+ border-bottom-right-radius: -1;
+}
+.panel > .table:last-child > tbody:last-child > tr:last-child td:first-child,
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:first-child,
+.panel > .table:last-child > tfoot:last-child > tr:last-child td:first-child,
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:first-child,
+.panel > .table:last-child > tbody:last-child > tr:last-child th:first-child,
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:first-child,
+.panel > .table:last-child > tfoot:last-child > tr:last-child th:first-child,
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:first-child {
+ border-bottom-left-radius: -1;
+}
+.panel > .table:last-child > tbody:last-child > tr:last-child td:last-child,
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:last-child,
+.panel > .table:last-child > tfoot:last-child > tr:last-child td:last-child,
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:last-child,
+.panel > .table:last-child > tbody:last-child > tr:last-child th:last-child,
+.panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:last-child,
+.panel > .table:last-child > tfoot:last-child > tr:last-child th:last-child,
+.panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:last-child {
+ border-bottom-right-radius: -1;
+}
+.panel > .panel-body + .table,
+.panel > .panel-body + .table-responsive,
+.panel > .table + .panel-body,
+.panel > .table-responsive + .panel-body {
+ border-top: 1px solid #dddddd;
+}
+.panel > .table > tbody:first-child > tr:first-child th,
+.panel > .table > tbody:first-child > tr:first-child td {
+ border-top: 0;
+}
+.panel > .table-bordered,
+.panel > .table-responsive > .table-bordered {
+ border: 0;
+}
+.panel > .table-bordered > thead > tr > th:first-child,
+.panel > .table-responsive > .table-bordered > thead > tr > th:first-child,
+.panel > .table-bordered > tbody > tr > th:first-child,
+.panel > .table-responsive > .table-bordered > tbody > tr > th:first-child,
+.panel > .table-bordered > tfoot > tr > th:first-child,
+.panel > .table-responsive > .table-bordered > tfoot > tr > th:first-child,
+.panel > .table-bordered > thead > tr > td:first-child,
+.panel > .table-responsive > .table-bordered > thead > tr > td:first-child,
+.panel > .table-bordered > tbody > tr > td:first-child,
+.panel > .table-responsive > .table-bordered > tbody > tr > td:first-child,
+.panel > .table-bordered > tfoot > tr > td:first-child,
+.panel > .table-responsive > .table-bordered > tfoot > tr > td:first-child {
+ border-left: 0;
+}
+.panel > .table-bordered > thead > tr > th:last-child,
+.panel > .table-responsive > .table-bordered > thead > tr > th:last-child,
+.panel > .table-bordered > tbody > tr > th:last-child,
+.panel > .table-responsive > .table-bordered > tbody > tr > th:last-child,
+.panel > .table-bordered > tfoot > tr > th:last-child,
+.panel > .table-responsive > .table-bordered > tfoot > tr > th:last-child,
+.panel > .table-bordered > thead > tr > td:last-child,
+.panel > .table-responsive > .table-bordered > thead > tr > td:last-child,
+.panel > .table-bordered > tbody > tr > td:last-child,
+.panel > .table-responsive > .table-bordered > tbody > tr > td:last-child,
+.panel > .table-bordered > tfoot > tr > td:last-child,
+.panel > .table-responsive > .table-bordered > tfoot > tr > td:last-child {
+ border-right: 0;
+}
+.panel > .table-bordered > thead > tr:first-child > td,
+.panel > .table-responsive > .table-bordered > thead > tr:first-child > td,
+.panel > .table-bordered > tbody > tr:first-child > td,
+.panel > .table-responsive > .table-bordered > tbody > tr:first-child > td,
+.panel > .table-bordered > thead > tr:first-child > th,
+.panel > .table-responsive > .table-bordered > thead > tr:first-child > th,
+.panel > .table-bordered > tbody > tr:first-child > th,
+.panel > .table-responsive > .table-bordered > tbody > tr:first-child > th {
+ border-bottom: 0;
+}
+.panel > .table-bordered > tbody > tr:last-child > td,
+.panel > .table-responsive > .table-bordered > tbody > tr:last-child > td,
+.panel > .table-bordered > tfoot > tr:last-child > td,
+.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > td,
+.panel > .table-bordered > tbody > tr:last-child > th,
+.panel > .table-responsive > .table-bordered > tbody > tr:last-child > th,
+.panel > .table-bordered > tfoot > tr:last-child > th,
+.panel > .table-responsive > .table-bordered > tfoot > tr:last-child > th {
+ border-bottom: 0;
+}
+.panel > .table-responsive {
+ border: 0;
+ margin-bottom: 0;
+}
+.panel-group {
+ margin-bottom: 21px;
+}
+.panel-group .panel {
+ margin-bottom: 0;
+ border-radius: 0;
+}
+.panel-group .panel + .panel {
+ margin-top: 5px;
+}
+.panel-group .panel-heading {
+ border-bottom: 0;
+}
+.panel-group .panel-heading + .panel-collapse > .panel-body,
+.panel-group .panel-heading + .panel-collapse > .list-group {
+ border-top: 1px solid #dddddd;
+}
+.panel-group .panel-footer {
+ border-top: 0;
+}
+.panel-group .panel-footer + .panel-collapse .panel-body {
+ border-bottom: 1px solid #dddddd;
+}
+.panel-default {
+ border-color: #dddddd;
+}
+.panel-default > .panel-heading {
+ color: #333333;
+ background-color: #f5f5f5;
+ border-color: #dddddd;
+}
+.panel-default > .panel-heading + .panel-collapse > .panel-body {
+ border-top-color: #dddddd;
+}
+.panel-default > .panel-heading .badge {
+ color: #f5f5f5;
+ background-color: #333333;
+}
+.panel-default > .panel-footer + .panel-collapse > .panel-body {
+ border-bottom-color: #dddddd;
+}
+.panel-primary {
+ border-color: #008cba;
+}
+.panel-primary > .panel-heading {
+ color: #ffffff;
+ background-color: #008cba;
+ border-color: #008cba;
+}
+.panel-primary > .panel-heading + .panel-collapse > .panel-body {
+ border-top-color: #008cba;
+}
+.panel-primary > .panel-heading .badge {
+ color: #008cba;
+ background-color: #ffffff;
+}
+.panel-primary > .panel-footer + .panel-collapse > .panel-body {
+ border-bottom-color: #008cba;
+}
+.panel-success {
+ border-color: #3c9a5f;
+}
+.panel-success > .panel-heading {
+ color: #ffffff;
+ background-color: #43ac6a;
+ border-color: #3c9a5f;
+}
+.panel-success > .panel-heading + .panel-collapse > .panel-body {
+ border-top-color: #3c9a5f;
+}
+.panel-success > .panel-heading .badge {
+ color: #43ac6a;
+ background-color: #ffffff;
+}
+.panel-success > .panel-footer + .panel-collapse > .panel-body {
+ border-bottom-color: #3c9a5f;
+}
+.panel-info {
+ border-color: #3db5d8;
+}
+.panel-info > .panel-heading {
+ color: #ffffff;
+ background-color: #5bc0de;
+ border-color: #3db5d8;
+}
+.panel-info > .panel-heading + .panel-collapse > .panel-body {
+ border-top-color: #3db5d8;
+}
+.panel-info > .panel-heading .badge {
+ color: #5bc0de;
+ background-color: #ffffff;
+}
+.panel-info > .panel-footer + .panel-collapse > .panel-body {
+ border-bottom-color: #3db5d8;
+}
+.panel-warning {
+ border-color: #d08002;
+}
+.panel-warning > .panel-heading {
+ color: #ffffff;
+ background-color: #e99002;
+ border-color: #d08002;
+}
+.panel-warning > .panel-heading + .panel-collapse > .panel-body {
+ border-top-color: #d08002;
+}
+.panel-warning > .panel-heading .badge {
+ color: #e99002;
+ background-color: #ffffff;
+}
+.panel-warning > .panel-footer + .panel-collapse > .panel-body {
+ border-bottom-color: #d08002;
+}
+.panel-danger {
+ border-color: #ea2f10;
+}
+.panel-danger > .panel-heading {
+ color: #ffffff;
+ background-color: #f04124;
+ border-color: #ea2f10;
+}
+.panel-danger > .panel-heading + .panel-collapse > .panel-body {
+ border-top-color: #ea2f10;
+}
+.panel-danger > .panel-heading .badge {
+ color: #f04124;
+ background-color: #ffffff;
+}
+.panel-danger > .panel-footer + .panel-collapse > .panel-body {
+ border-bottom-color: #ea2f10;
+}
+.embed-responsive {
+ position: relative;
+ display: block;
+ height: 0;
+ padding: 0;
+ overflow: hidden;
+}
+.embed-responsive .embed-responsive-item,
+.embed-responsive iframe,
+.embed-responsive embed,
+.embed-responsive object,
+.embed-responsive video {
+ position: absolute;
+ top: 0;
+ left: 0;
+ bottom: 0;
+ height: 100%;
+ width: 100%;
+ border: 0;
+}
+.embed-responsive-16by9 {
+ padding-bottom: 56.25%;
+}
+.embed-responsive-4by3 {
+ padding-bottom: 75%;
+}
+.well {
+ min-height: 20px;
+ padding: 19px;
+ margin-bottom: 20px;
+ background-color: #fafafa;
+ border: 1px solid #e8e8e8;
+ border-radius: 0;
+ -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);
+ box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);
+}
+.well blockquote {
+ border-color: #ddd;
+ border-color: rgba(0, 0, 0, 0.15);
+}
+.well-lg {
+ padding: 24px;
+ border-radius: 0;
+}
+.well-sm {
+ padding: 9px;
+ border-radius: 0;
+}
+.close {
+ float: right;
+ font-size: 22.5px;
+ font-weight: bold;
+ line-height: 1;
+ color: #ffffff;
+ text-shadow: 0 1px 0 #ffffff;
+ opacity: 0.2;
+ filter: alpha(opacity=20);
+}
+.close:hover,
+.close:focus {
+ color: #ffffff;
+ text-decoration: none;
+ cursor: pointer;
+ opacity: 0.5;
+ filter: alpha(opacity=50);
+}
+button.close {
+ padding: 0;
+ cursor: pointer;
+ background: transparent;
+ border: 0;
+ -webkit-appearance: none;
+}
+.modal-open {
+ overflow: hidden;
+}
+.modal {
+ display: none;
+ overflow: hidden;
+ position: fixed;
+ top: 0;
+ right: 0;
+ bottom: 0;
+ left: 0;
+ z-index: 1050;
+ -webkit-overflow-scrolling: touch;
+ outline: 0;
+}
+.modal.fade .modal-dialog {
+ -webkit-transform: translate(0, -25%);
+ -ms-transform: translate(0, -25%);
+ -o-transform: translate(0, -25%);
+ transform: translate(0, -25%);
+ -webkit-transition: -webkit-transform 0.3s ease-out;
+ -o-transition: -o-transform 0.3s ease-out;
+ transition: transform 0.3s ease-out;
+}
+.modal.in .modal-dialog {
+ -webkit-transform: translate(0, 0);
+ -ms-transform: translate(0, 0);
+ -o-transform: translate(0, 0);
+ transform: translate(0, 0);
+}
+.modal-open .modal {
+ overflow-x: hidden;
+ overflow-y: auto;
+}
+.modal-dialog {
+ position: relative;
+ width: auto;
+ margin: 10px;
+}
+.modal-content {
+ position: relative;
+ background-color: #ffffff;
+ border: 1px solid #999999;
+ border: 1px solid rgba(0, 0, 0, 0.2);
+ border-radius: 0;
+ -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);
+ box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);
+ -webkit-background-clip: padding-box;
+ background-clip: padding-box;
+ outline: 0;
+}
+.modal-backdrop {
+ position: fixed;
+ top: 0;
+ right: 0;
+ bottom: 0;
+ left: 0;
+ z-index: 1040;
+ background-color: #000000;
+}
+.modal-backdrop.fade {
+ opacity: 0;
+ filter: alpha(opacity=0);
+}
+.modal-backdrop.in {
+ opacity: 0.5;
+ filter: alpha(opacity=50);
+}
+.modal-header {
+ padding: 15px;
+ border-bottom: 1px solid #e5e5e5;
+}
+.modal-header .close {
+ margin-top: -2px;
+}
+.modal-title {
+ margin: 0;
+ line-height: 1.4;
+}
+.modal-body {
+ position: relative;
+ padding: 20px;
+}
+.modal-footer {
+ padding: 20px;
+ text-align: right;
+ border-top: 1px solid #e5e5e5;
+}
+.modal-footer .btn + .btn {
+ margin-left: 5px;
+ margin-bottom: 0;
+}
+.modal-footer .btn-group .btn + .btn {
+ margin-left: -1px;
+}
+.modal-footer .btn-block + .btn-block {
+ margin-left: 0;
+}
+.modal-scrollbar-measure {
+ position: absolute;
+ top: -9999px;
+ width: 50px;
+ height: 50px;
+ overflow: scroll;
+}
+@media (min-width: 768px) {
+ .modal-dialog {
+ width: 600px;
+ margin: 30px auto;
+ }
+ .modal-content {
+ -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);
+ box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);
+ }
+ .modal-sm {
+ width: 300px;
+ }
+}
+@media (min-width: 992px) {
+ .modal-lg {
+ width: 900px;
+ }
+}
+.tooltip {
+ position: absolute;
+ z-index: 1070;
+ display: block;
+ font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif;
+ font-style: normal;
+ font-weight: normal;
+ letter-spacing: normal;
+ line-break: auto;
+ line-height: 1.4;
+ text-align: left;
+ text-align: start;
+ text-decoration: none;
+ text-shadow: none;
+ text-transform: none;
+ white-space: normal;
+ word-break: normal;
+ word-spacing: normal;
+ word-wrap: normal;
+ font-size: 12px;
+ opacity: 0;
+ filter: alpha(opacity=0);
+}
+.tooltip.in {
+ opacity: 0.9;
+ filter: alpha(opacity=90);
+}
+.tooltip.top {
+ margin-top: -3px;
+ padding: 5px 0;
+}
+.tooltip.right {
+ margin-left: 3px;
+ padding: 0 5px;
+}
+.tooltip.bottom {
+ margin-top: 3px;
+ padding: 5px 0;
+}
+.tooltip.left {
+ margin-left: -3px;
+ padding: 0 5px;
+}
+.tooltip-inner {
+ max-width: 200px;
+ padding: 3px 8px;
+ color: #ffffff;
+ text-align: center;
+ background-color: #333333;
+ border-radius: 0;
+}
+.tooltip-arrow {
+ position: absolute;
+ width: 0;
+ height: 0;
+ border-color: transparent;
+ border-style: solid;
+}
+.tooltip.top .tooltip-arrow {
+ bottom: 0;
+ left: 50%;
+ margin-left: -5px;
+ border-width: 5px 5px 0;
+ border-top-color: #333333;
+}
+.tooltip.top-left .tooltip-arrow {
+ bottom: 0;
+ right: 5px;
+ margin-bottom: -5px;
+ border-width: 5px 5px 0;
+ border-top-color: #333333;
+}
+.tooltip.top-right .tooltip-arrow {
+ bottom: 0;
+ left: 5px;
+ margin-bottom: -5px;
+ border-width: 5px 5px 0;
+ border-top-color: #333333;
+}
+.tooltip.right .tooltip-arrow {
+ top: 50%;
+ left: 0;
+ margin-top: -5px;
+ border-width: 5px 5px 5px 0;
+ border-right-color: #333333;
+}
+.tooltip.left .tooltip-arrow {
+ top: 50%;
+ right: 0;
+ margin-top: -5px;
+ border-width: 5px 0 5px 5px;
+ border-left-color: #333333;
+}
+.tooltip.bottom .tooltip-arrow {
+ top: 0;
+ left: 50%;
+ margin-left: -5px;
+ border-width: 0 5px 5px;
+ border-bottom-color: #333333;
+}
+.tooltip.bottom-left .tooltip-arrow {
+ top: 0;
+ right: 5px;
+ margin-top: -5px;
+ border-width: 0 5px 5px;
+ border-bottom-color: #333333;
+}
+.tooltip.bottom-right .tooltip-arrow {
+ top: 0;
+ left: 5px;
+ margin-top: -5px;
+ border-width: 0 5px 5px;
+ border-bottom-color: #333333;
+}
+.popover {
+ position: absolute;
+ top: 0;
+ left: 0;
+ z-index: 1060;
+ display: none;
+ max-width: 276px;
+ padding: 1px;
+ font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif;
+ font-style: normal;
+ font-weight: normal;
+ letter-spacing: normal;
+ line-break: auto;
+ line-height: 1.4;
+ text-align: left;
+ text-align: start;
+ text-decoration: none;
+ text-shadow: none;
+ text-transform: none;
+ white-space: normal;
+ word-break: normal;
+ word-spacing: normal;
+ word-wrap: normal;
+ font-size: 15px;
+ background-color: #333333;
+ -webkit-background-clip: padding-box;
+ background-clip: padding-box;
+ border: 1px solid #333333;
+ border: 1px solid transparent;
+ border-radius: 0;
+ -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);
+ box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);
+}
+.popover.top {
+ margin-top: -10px;
+}
+.popover.right {
+ margin-left: 10px;
+}
+.popover.bottom {
+ margin-top: 10px;
+}
+.popover.left {
+ margin-left: -10px;
+}
+.popover-title {
+ margin: 0;
+ padding: 8px 14px;
+ font-size: 15px;
+ background-color: #333333;
+ border-bottom: 1px solid #262626;
+ border-radius: -1 -1 0 0;
+}
+.popover-content {
+ padding: 9px 14px;
+}
+.popover > .arrow,
+.popover > .arrow:after {
+ position: absolute;
+ display: block;
+ width: 0;
+ height: 0;
+ border-color: transparent;
+ border-style: solid;
+}
+.popover > .arrow {
+ border-width: 11px;
+}
+.popover > .arrow:after {
+ border-width: 10px;
+ content: "";
+}
+.popover.top > .arrow {
+ left: 50%;
+ margin-left: -11px;
+ border-bottom-width: 0;
+ border-top-color: #000000;
+ border-top-color: rgba(0, 0, 0, 0.05);
+ bottom: -11px;
+}
+.popover.top > .arrow:after {
+ content: " ";
+ bottom: 1px;
+ margin-left: -10px;
+ border-bottom-width: 0;
+ border-top-color: #333333;
+}
+.popover.right > .arrow {
+ top: 50%;
+ left: -11px;
+ margin-top: -11px;
+ border-left-width: 0;
+ border-right-color: #000000;
+ border-right-color: rgba(0, 0, 0, 0.05);
+}
+.popover.right > .arrow:after {
+ content: " ";
+ left: 1px;
+ bottom: -10px;
+ border-left-width: 0;
+ border-right-color: #333333;
+}
+.popover.bottom > .arrow {
+ left: 50%;
+ margin-left: -11px;
+ border-top-width: 0;
+ border-bottom-color: #000000;
+ border-bottom-color: rgba(0, 0, 0, 0.05);
+ top: -11px;
+}
+.popover.bottom > .arrow:after {
+ content: " ";
+ top: 1px;
+ margin-left: -10px;
+ border-top-width: 0;
+ border-bottom-color: #333333;
+}
+.popover.left > .arrow {
+ top: 50%;
+ right: -11px;
+ margin-top: -11px;
+ border-right-width: 0;
+ border-left-color: #000000;
+ border-left-color: rgba(0, 0, 0, 0.05);
+}
+.popover.left > .arrow:after {
+ content: " ";
+ right: 1px;
+ border-right-width: 0;
+ border-left-color: #333333;
+ bottom: -10px;
+}
+.carousel {
+ position: relative;
+}
+.carousel-inner {
+ position: relative;
+ overflow: hidden;
+ width: 100%;
+}
+.carousel-inner > .item {
+ display: none;
+ position: relative;
+ -webkit-transition: 0.6s ease-in-out left;
+ -o-transition: 0.6s ease-in-out left;
+ transition: 0.6s ease-in-out left;
+}
+.carousel-inner > .item > img,
+.carousel-inner > .item > a > img {
+ line-height: 1;
+}
+@media all and (transform-3d), (-webkit-transform-3d) {
+ .carousel-inner > .item {
+ -webkit-transition: -webkit-transform 0.6s ease-in-out;
+ -o-transition: -o-transform 0.6s ease-in-out;
+ transition: transform 0.6s ease-in-out;
+ -webkit-backface-visibility: hidden;
+ backface-visibility: hidden;
+ -webkit-perspective: 1000px;
+ perspective: 1000px;
+ }
+ .carousel-inner > .item.next,
+ .carousel-inner > .item.active.right {
+ -webkit-transform: translate3d(100%, 0, 0);
+ transform: translate3d(100%, 0, 0);
+ left: 0;
+ }
+ .carousel-inner > .item.prev,
+ .carousel-inner > .item.active.left {
+ -webkit-transform: translate3d(-100%, 0, 0);
+ transform: translate3d(-100%, 0, 0);
+ left: 0;
+ }
+ .carousel-inner > .item.next.left,
+ .carousel-inner > .item.prev.right,
+ .carousel-inner > .item.active {
+ -webkit-transform: translate3d(0, 0, 0);
+ transform: translate3d(0, 0, 0);
+ left: 0;
+ }
+}
+.carousel-inner > .active,
+.carousel-inner > .next,
+.carousel-inner > .prev {
+ display: block;
+}
+.carousel-inner > .active {
+ left: 0;
+}
+.carousel-inner > .next,
+.carousel-inner > .prev {
+ position: absolute;
+ top: 0;
+ width: 100%;
+}
+.carousel-inner > .next {
+ left: 100%;
+}
+.carousel-inner > .prev {
+ left: -100%;
+}
+.carousel-inner > .next.left,
+.carousel-inner > .prev.right {
+ left: 0;
+}
+.carousel-inner > .active.left {
+ left: -100%;
+}
+.carousel-inner > .active.right {
+ left: 100%;
+}
+.carousel-control {
+ position: absolute;
+ top: 0;
+ left: 0;
+ bottom: 0;
+ width: 15%;
+ opacity: 0.5;
+ filter: alpha(opacity=50);
+ font-size: 20px;
+ color: #ffffff;
+ text-align: center;
+ text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);
+ background-color: rgba(0, 0, 0, 0);
+}
+.carousel-control.left {
+ background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);
+ background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);
+ background-image: -webkit-gradient(linear, left top, right top, from(rgba(0, 0, 0, 0.5)), to(rgba(0, 0, 0, 0.0001)));
+ background-image: linear-gradient(to right, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);
+ background-repeat: repeat-x;
+ filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);
+}
+.carousel-control.right {
+ left: auto;
+ right: 0;
+ background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);
+ background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);
+ background-image: -webkit-gradient(linear, left top, right top, from(rgba(0, 0, 0, 0.0001)), to(rgba(0, 0, 0, 0.5)));
+ background-image: linear-gradient(to right, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);
+ background-repeat: repeat-x;
+ filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);
+}
+.carousel-control:hover,
+.carousel-control:focus {
+ outline: 0;
+ color: #ffffff;
+ text-decoration: none;
+ opacity: 0.9;
+ filter: alpha(opacity=90);
+}
+.carousel-control .icon-prev,
+.carousel-control .icon-next,
+.carousel-control .glyphicon-chevron-left,
+.carousel-control .glyphicon-chevron-right {
+ position: absolute;
+ top: 50%;
+ margin-top: -10px;
+ z-index: 5;
+ display: inline-block;
+}
+.carousel-control .icon-prev,
+.carousel-control .glyphicon-chevron-left {
+ left: 50%;
+ margin-left: -10px;
+}
+.carousel-control .icon-next,
+.carousel-control .glyphicon-chevron-right {
+ right: 50%;
+ margin-right: -10px;
+}
+.carousel-control .icon-prev,
+.carousel-control .icon-next {
+ width: 20px;
+ height: 20px;
+ line-height: 1;
+ font-family: serif;
+}
+.carousel-control .icon-prev:before {
+ content: '\2039';
+}
+.carousel-control .icon-next:before {
+ content: '\203a';
+}
+.carousel-indicators {
+ position: absolute;
+ bottom: 10px;
+ left: 50%;
+ z-index: 15;
+ width: 60%;
+ margin-left: -30%;
+ padding-left: 0;
+ list-style: none;
+ text-align: center;
+}
+.carousel-indicators li {
+ display: inline-block;
+ width: 10px;
+ height: 10px;
+ margin: 1px;
+ text-indent: -999px;
+ border: 1px solid #ffffff;
+ border-radius: 10px;
+ cursor: pointer;
+ background-color: #000 \9;
+ background-color: rgba(0, 0, 0, 0);
+}
+.carousel-indicators .active {
+ margin: 0;
+ width: 12px;
+ height: 12px;
+ background-color: #ffffff;
+}
+.carousel-caption {
+ position: absolute;
+ left: 15%;
+ right: 15%;
+ bottom: 20px;
+ z-index: 10;
+ padding-top: 20px;
+ padding-bottom: 20px;
+ color: #ffffff;
+ text-align: center;
+ text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);
+}
+.carousel-caption .btn {
+ text-shadow: none;
+}
+@media screen and (min-width: 768px) {
+ .carousel-control .glyphicon-chevron-left,
+ .carousel-control .glyphicon-chevron-right,
+ .carousel-control .icon-prev,
+ .carousel-control .icon-next {
+ width: 30px;
+ height: 30px;
+ margin-top: -10px;
+ font-size: 30px;
+ }
+ .carousel-control .glyphicon-chevron-left,
+ .carousel-control .icon-prev {
+ margin-left: -10px;
+ }
+ .carousel-control .glyphicon-chevron-right,
+ .carousel-control .icon-next {
+ margin-right: -10px;
+ }
+ .carousel-caption {
+ left: 20%;
+ right: 20%;
+ padding-bottom: 30px;
+ }
+ .carousel-indicators {
+ bottom: 20px;
+ }
+}
+.clearfix:before,
+.clearfix:after,
+.dl-horizontal dd:before,
+.dl-horizontal dd:after,
+.container:before,
+.container:after,
+.container-fluid:before,
+.container-fluid:after,
+.row:before,
+.row:after,
+.form-horizontal .form-group:before,
+.form-horizontal .form-group:after,
+.btn-toolbar:before,
+.btn-toolbar:after,
+.btn-group-vertical > .btn-group:before,
+.btn-group-vertical > .btn-group:after,
+.nav:before,
+.nav:after,
+.navbar:before,
+.navbar:after,
+.navbar-header:before,
+.navbar-header:after,
+.navbar-collapse:before,
+.navbar-collapse:after,
+.pager:before,
+.pager:after,
+.panel-body:before,
+.panel-body:after,
+.modal-header:before,
+.modal-header:after,
+.modal-footer:before,
+.modal-footer:after {
+ content: " ";
+ display: table;
+}
+.clearfix:after,
+.dl-horizontal dd:after,
+.container:after,
+.container-fluid:after,
+.row:after,
+.form-horizontal .form-group:after,
+.btn-toolbar:after,
+.btn-group-vertical > .btn-group:after,
+.nav:after,
+.navbar:after,
+.navbar-header:after,
+.navbar-collapse:after,
+.pager:after,
+.panel-body:after,
+.modal-header:after,
+.modal-footer:after {
+ clear: both;
+}
+.center-block {
+ display: block;
+ margin-left: auto;
+ margin-right: auto;
+}
+.pull-right {
+ float: right !important;
+}
+.pull-left {
+ float: left !important;
+}
+.hide {
+ display: none !important;
+}
+.show {
+ display: block !important;
+}
+.invisible {
+ visibility: hidden;
+}
+.text-hide {
+ font: 0/0 a;
+ color: transparent;
+ text-shadow: none;
+ background-color: transparent;
+ border: 0;
+}
+.hidden {
+ display: none !important;
+}
+.affix {
+ position: fixed;
+}
+@-ms-viewport {
+ width: device-width;
+}
+.visible-xs,
+.visible-sm,
+.visible-md,
+.visible-lg {
+ display: none !important;
+}
+.visible-xs-block,
+.visible-xs-inline,
+.visible-xs-inline-block,
+.visible-sm-block,
+.visible-sm-inline,
+.visible-sm-inline-block,
+.visible-md-block,
+.visible-md-inline,
+.visible-md-inline-block,
+.visible-lg-block,
+.visible-lg-inline,
+.visible-lg-inline-block {
+ display: none !important;
+}
+@media (max-width: 767px) {
+ .visible-xs {
+ display: block !important;
+ }
+ table.visible-xs {
+ display: table !important;
+ }
+ tr.visible-xs {
+ display: table-row !important;
+ }
+ th.visible-xs,
+ td.visible-xs {
+ display: table-cell !important;
+ }
+}
+@media (max-width: 767px) {
+ .visible-xs-block {
+ display: block !important;
+ }
+}
+@media (max-width: 767px) {
+ .visible-xs-inline {
+ display: inline !important;
+ }
+}
+@media (max-width: 767px) {
+ .visible-xs-inline-block {
+ display: inline-block !important;
+ }
+}
+@media (min-width: 768px) and (max-width: 991px) {
+ .visible-sm {
+ display: block !important;
+ }
+ table.visible-sm {
+ display: table !important;
+ }
+ tr.visible-sm {
+ display: table-row !important;
+ }
+ th.visible-sm,
+ td.visible-sm {
+ display: table-cell !important;
+ }
+}
+@media (min-width: 768px) and (max-width: 991px) {
+ .visible-sm-block {
+ display: block !important;
+ }
+}
+@media (min-width: 768px) and (max-width: 991px) {
+ .visible-sm-inline {
+ display: inline !important;
+ }
+}
+@media (min-width: 768px) and (max-width: 991px) {
+ .visible-sm-inline-block {
+ display: inline-block !important;
+ }
+}
+@media (min-width: 992px) and (max-width: 1199px) {
+ .visible-md {
+ display: block !important;
+ }
+ table.visible-md {
+ display: table !important;
+ }
+ tr.visible-md {
+ display: table-row !important;
+ }
+ th.visible-md,
+ td.visible-md {
+ display: table-cell !important;
+ }
+}
+@media (min-width: 992px) and (max-width: 1199px) {
+ .visible-md-block {
+ display: block !important;
+ }
+}
+@media (min-width: 992px) and (max-width: 1199px) {
+ .visible-md-inline {
+ display: inline !important;
+ }
+}
+@media (min-width: 992px) and (max-width: 1199px) {
+ .visible-md-inline-block {
+ display: inline-block !important;
+ }
+}
+@media (min-width: 1200px) {
+ .visible-lg {
+ display: block !important;
+ }
+ table.visible-lg {
+ display: table !important;
+ }
+ tr.visible-lg {
+ display: table-row !important;
+ }
+ th.visible-lg,
+ td.visible-lg {
+ display: table-cell !important;
+ }
+}
+@media (min-width: 1200px) {
+ .visible-lg-block {
+ display: block !important;
+ }
+}
+@media (min-width: 1200px) {
+ .visible-lg-inline {
+ display: inline !important;
+ }
+}
+@media (min-width: 1200px) {
+ .visible-lg-inline-block {
+ display: inline-block !important;
+ }
+}
+@media (max-width: 767px) {
+ .hidden-xs {
+ display: none !important;
+ }
+}
+@media (min-width: 768px) and (max-width: 991px) {
+ .hidden-sm {
+ display: none !important;
+ }
+}
+@media (min-width: 992px) and (max-width: 1199px) {
+ .hidden-md {
+ display: none !important;
+ }
+}
+@media (min-width: 1200px) {
+ .hidden-lg {
+ display: none !important;
+ }
+}
+.visible-print {
+ display: none !important;
+}
+@media print {
+ .visible-print {
+ display: block !important;
+ }
+ table.visible-print {
+ display: table !important;
+ }
+ tr.visible-print {
+ display: table-row !important;
+ }
+ th.visible-print,
+ td.visible-print {
+ display: table-cell !important;
+ }
+}
+.visible-print-block {
+ display: none !important;
+}
+@media print {
+ .visible-print-block {
+ display: block !important;
+ }
+}
+.visible-print-inline {
+ display: none !important;
+}
+@media print {
+ .visible-print-inline {
+ display: inline !important;
+ }
+}
+.visible-print-inline-block {
+ display: none !important;
+}
+@media print {
+ .visible-print-inline-block {
+ display: inline-block !important;
+ }
+}
+@media print {
+ .hidden-print {
+ display: none !important;
+ }
+}
+.navbar {
+ border: none;
+ font-size: 13px;
+ font-weight: 300;
+}
+.navbar .navbar-toggle:hover .icon-bar {
+ background-color: #b3b3b3;
+}
+.navbar-collapse {
+ border-top-color: rgba(0, 0, 0, 0.2);
+ -webkit-box-shadow: none;
+ box-shadow: none;
+}
+.navbar .btn {
+ padding-top: 6px;
+ padding-bottom: 6px;
+}
+.navbar-form {
+ margin-top: 7px;
+ margin-bottom: 5px;
+}
+.navbar-form .form-control {
+ height: auto;
+ padding: 4px 6px;
+}
+.navbar-text {
+ margin: 12px 15px;
+ line-height: 21px;
+}
+.navbar .dropdown-menu {
+ border: none;
+}
+.navbar .dropdown-menu > li > a,
+.navbar .dropdown-menu > li > a:focus {
+ background-color: transparent;
+ font-size: 13px;
+ font-weight: 300;
+}
+.navbar .dropdown-header {
+ color: rgba(255, 255, 255, 0.5);
+}
+.navbar-default .dropdown-menu {
+ background-color: #333333;
+}
+.navbar-default .dropdown-menu > li > a,
+.navbar-default .dropdown-menu > li > a:focus {
+ color: #ffffff;
+}
+.navbar-default .dropdown-menu > li > a:hover,
+.navbar-default .dropdown-menu > .active > a,
+.navbar-default .dropdown-menu > .active > a:hover {
+ background-color: #272727;
+}
+.navbar-inverse .dropdown-menu {
+ background-color: #008cba;
+}
+.navbar-inverse .dropdown-menu > li > a,
+.navbar-inverse .dropdown-menu > li > a:focus {
+ color: #ffffff;
+}
+.navbar-inverse .dropdown-menu > li > a:hover,
+.navbar-inverse .dropdown-menu > .active > a,
+.navbar-inverse .dropdown-menu > .active > a:hover {
+ background-color: #006687;
+}
+.btn {
+ padding: 8px 12px;
+}
+.btn-lg {
+ padding: 16px 20px;
+}
+.btn-sm {
+ padding: 8px 12px;
+}
+.btn-xs {
+ padding: 4px 6px;
+}
+.btn-group .btn ~ .dropdown-toggle {
+ padding-left: 16px;
+ padding-right: 16px;
+}
+.btn-group .dropdown-menu {
+ border-top-width: 0;
+}
+.btn-group.dropup .dropdown-menu {
+ border-top-width: 1px;
+ border-bottom-width: 0;
+ margin-bottom: 0;
+}
+.btn-group .dropdown-toggle.btn-default ~ .dropdown-menu {
+ background-color: #e7e7e7;
+ border-color: #cccccc;
+}
+.btn-group .dropdown-toggle.btn-default ~ .dropdown-menu > li > a {
+ color: #333333;
+}
+.btn-group .dropdown-toggle.btn-default ~ .dropdown-menu > li > a:hover {
+ background-color: #d3d3d3;
+}
+.btn-group .dropdown-toggle.btn-primary ~ .dropdown-menu {
+ background-color: #008cba;
+ border-color: #0079a1;
+}
+.btn-group .dropdown-toggle.btn-primary ~ .dropdown-menu > li > a {
+ color: #ffffff;
+}
+.btn-group .dropdown-toggle.btn-primary ~ .dropdown-menu > li > a:hover {
+ background-color: #006d91;
+}
+.btn-group .dropdown-toggle.btn-success ~ .dropdown-menu {
+ background-color: #43ac6a;
+ border-color: #3c9a5f;
+}
+.btn-group .dropdown-toggle.btn-success ~ .dropdown-menu > li > a {
+ color: #ffffff;
+}
+.btn-group .dropdown-toggle.btn-success ~ .dropdown-menu > li > a:hover {
+ background-color: #388f58;
+}
+.btn-group .dropdown-toggle.btn-info ~ .dropdown-menu {
+ background-color: #5bc0de;
+ border-color: #46b8da;
+}
+.btn-group .dropdown-toggle.btn-info ~ .dropdown-menu > li > a {
+ color: #ffffff;
+}
+.btn-group .dropdown-toggle.btn-info ~ .dropdown-menu > li > a:hover {
+ background-color: #39b3d7;
+}
+.btn-group .dropdown-toggle.btn-warning ~ .dropdown-menu {
+ background-color: #e99002;
+ border-color: #d08002;
+}
+.btn-group .dropdown-toggle.btn-warning ~ .dropdown-menu > li > a {
+ color: #ffffff;
+}
+.btn-group .dropdown-toggle.btn-warning ~ .dropdown-menu > li > a:hover {
+ background-color: #c17702;
+}
+.btn-group .dropdown-toggle.btn-danger ~ .dropdown-menu {
+ background-color: #f04124;
+ border-color: #ea2f10;
+}
+.btn-group .dropdown-toggle.btn-danger ~ .dropdown-menu > li > a {
+ color: #ffffff;
+}
+.btn-group .dropdown-toggle.btn-danger ~ .dropdown-menu > li > a:hover {
+ background-color: #dc2c0f;
+}
+.lead {
+ color: #6f6f6f;
+}
+cite {
+ font-style: italic;
+}
+blockquote {
+ border-left-width: 1px;
+ color: #6f6f6f;
+}
+blockquote.pull-right {
+ border-right-width: 1px;
+}
+blockquote small {
+ font-size: 12px;
+ font-weight: 300;
+}
+table {
+ font-size: 12px;
+}
+label,
+.control-label,
+.help-block,
+.checkbox,
+.radio {
+ font-size: 12px;
+ font-weight: normal;
+}
+input[type="radio"],
+input[type="checkbox"] {
+ margin-top: 1px;
+}
+.nav .open > a,
+.nav .open > a:hover,
+.nav .open > a:focus {
+ border-color: transparent;
+}
+.nav-tabs > li > a {
+ background-color: #e7e7e7;
+ color: #222222;
+}
+.nav-tabs .caret {
+ border-top-color: #222222;
+ border-bottom-color: #222222;
+}
+.nav-pills {
+ font-weight: 300;
+}
+.breadcrumb {
+ border: 1px solid #dddddd;
+ border-radius: 3px;
+ font-size: 10px;
+ font-weight: 300;
+ text-transform: uppercase;
+}
+.pagination {
+ font-size: 12px;
+ font-weight: 300;
+ color: #999999;
+}
+.pagination > li > a,
+.pagination > li > span {
+ margin-left: 4px;
+ color: #999999;
+}
+.pagination > .active > a,
+.pagination > .active > span {
+ color: #fff;
+}
+.pagination > li > a,
+.pagination > li:first-child > a,
+.pagination > li:last-child > a,
+.pagination > li > span,
+.pagination > li:first-child > span,
+.pagination > li:last-child > span {
+ border-radius: 3px;
+}
+.pagination-lg > li > a,
+.pagination-lg > li > span {
+ padding-left: 22px;
+ padding-right: 22px;
+}
+.pagination-sm > li > a,
+.pagination-sm > li > span {
+ padding: 0 5px;
+}
+.pager {
+ font-size: 12px;
+ font-weight: 300;
+ color: #999999;
+}
+.list-group {
+ font-size: 12px;
+ font-weight: 300;
+}
+.close {
+ opacity: 0.4;
+ text-decoration: none;
+ text-shadow: none;
+}
+.close:hover,
+.close:focus {
+ opacity: 1;
+}
+.alert {
+ font-size: 12px;
+ font-weight: 300;
+}
+.alert .alert-link {
+ font-weight: normal;
+ color: #fff;
+ text-decoration: underline;
+}
+.label {
+ padding-left: 1em;
+ padding-right: 1em;
+ border-radius: 0;
+ font-weight: 300;
+}
+.label-default {
+ background-color: #e7e7e7;
+ color: #333333;
+}
+.badge {
+ font-weight: 300;
+}
+.progress {
+ height: 22px;
+ padding: 2px;
+ background-color: #f6f6f6;
+ border: 1px solid #ccc;
+ -webkit-box-shadow: none;
+ box-shadow: none;
+}
+.dropdown-menu {
+ padding: 0;
+ margin-top: 0;
+ font-size: 12px;
+}
+.dropdown-menu > li > a {
+ padding: 12px 15px;
+}
+.dropdown-header {
+ padding-left: 15px;
+ padding-right: 15px;
+ font-size: 9px;
+ text-transform: uppercase;
+}
+.popover {
+ color: #fff;
+ font-size: 12px;
+ font-weight: 300;
+}
+.panel-heading,
+.panel-footer {
+ border-top-right-radius: 0;
+ border-top-left-radius: 0;
+}
+.panel-default .close {
+ color: #222222;
+}
+.modal .close {
+ color: #222222;
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/bootswatch/css/bootstrap_yeti.min.css b/src/LanBackup.WebApp/ClientApp/app/bootswatch/css/bootstrap_yeti.min.css
new file mode 100644
index 0000000..cda7d4a
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/bootswatch/css/bootstrap_yeti.min.css
@@ -0,0 +1,11 @@
+@import url("https://fonts.googleapis.com/css?family=Open+Sans:300italic,400italic,700italic,400,300,700");/*!
+ * bootswatch v3.3.7
+ * Homepage: http://bootswatch.com
+ * Copyright 2012-2016 Thomas Park
+ * Licensed under MIT
+ * Based on Bootstrap
+*//*!
+ * Bootstrap v3.3.7 (http://getbootstrap.com)
+ * Copyright 2011-2016 Twitter, Inc.
+ * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
+ *//*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */html{font-family:sans-serif;-ms-text-size-adjust:100%;-webkit-text-size-adjust:100%}body{margin:0}article,aside,details,figcaption,figure,footer,header,hgroup,main,menu,nav,section,summary{display:block}audio,canvas,progress,video{display:inline-block;vertical-align:baseline}audio:not([controls]){display:none;height:0}[hidden],template{display:none}a{background-color:transparent}a:active,a:hover{outline:0}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:bold}dfn{font-style:italic}h1{font-size:2em;margin:0.67em 0}mark{background:#ff0;color:#000}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sup{top:-0.5em}sub{bottom:-0.25em}img{border:0}svg:not(:root){overflow:hidden}figure{margin:1em 40px}hr{-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box;height:0}pre{overflow:auto}code,kbd,pre,samp{font-family:monospace, monospace;font-size:1em}button,input,optgroup,select,textarea{color:inherit;font:inherit;margin:0}button{overflow:visible}button,select{text-transform:none}button,html input[type="button"],input[type="reset"],input[type="submit"]{-webkit-appearance:button;cursor:pointer}button[disabled],html input[disabled]{cursor:default}button::-moz-focus-inner,input::-moz-focus-inner{border:0;padding:0}input{line-height:normal}input[type="checkbox"],input[type="radio"]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;padding:0}input[type="number"]::-webkit-inner-spin-button,input[type="number"]::-webkit-outer-spin-button{height:auto}input[type="search"]{-webkit-appearance:textfield;-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box}input[type="search"]::-webkit-search-cancel-button,input[type="search"]::-webkit-search-decoration{-webkit-appearance:none}fieldset{border:1px solid #c0c0c0;margin:0 2px;padding:0.35em 0.625em 0.75em}legend{border:0;padding:0}textarea{overflow:auto}optgroup{font-weight:bold}table{border-collapse:collapse;border-spacing:0}td,th{padding:0}/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */@media print{*,*:before,*:after{background:transparent !important;color:#000 !important;-webkit-box-shadow:none !important;box-shadow:none !important;text-shadow:none !important}a,a:visited{text-decoration:underline}a[href]:after{content:" (" attr(href) ")"}abbr[title]:after{content:" (" attr(title) ")"}a[href^="#"]:after,a[href^="javascript:"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}p,h2,h3{orphans:3;widows:3}h2,h3{page-break-after:avoid}.navbar{display:none}.btn>.caret,.dropup>.btn>.caret{border-top-color:#000 !important}.label{border:1px solid #000}.table{border-collapse:collapse !important}.table td,.table th{background-color:#fff !important}.table-bordered th,.table-bordered td{border:1px solid #ddd !important}}@font-face{font-family:'Glyphicons Halflings';src:url('../fonts/glyphicons-halflings-regular.eot');src:url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'),url('../fonts/glyphicons-halflings-regular.woff2') format('woff2'),url('../fonts/glyphicons-halflings-regular.woff') format('woff'),url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'),url('../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg')}.glyphicon{position:relative;top:1px;display:inline-block;font-family:'Glyphicons Halflings';font-style:normal;font-weight:normal;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.glyphicon-asterisk:before{content:"\002a"}.glyphicon-plus:before{content:"\002b"}.glyphicon-euro:before,.glyphicon-eur:before{content:"\20ac"}.glyphicon-minus:before{content:"\2212"}.glyphicon-cloud:before{content:"\2601"}.glyphicon-envelope:before{content:"\2709"}.glyphicon-pencil:before{content:"\270f"}.glyphicon-glass:before{content:"\e001"}.glyphicon-music:before{content:"\e002"}.glyphicon-search:before{content:"\e003"}.glyphicon-heart:before{content:"\e005"}.glyphicon-star:before{content:"\e006"}.glyphicon-star-empty:before{content:"\e007"}.glyphicon-user:before{content:"\e008"}.glyphicon-film:before{content:"\e009"}.glyphicon-th-large:before{content:"\e010"}.glyphicon-th:before{content:"\e011"}.glyphicon-th-list:before{content:"\e012"}.glyphicon-ok:before{content:"\e013"}.glyphicon-remove:before{content:"\e014"}.glyphicon-zoom-in:before{content:"\e015"}.glyphicon-zoom-out:before{content:"\e016"}.glyphicon-off:before{content:"\e017"}.glyphicon-signal:before{content:"\e018"}.glyphicon-cog:before{content:"\e019"}.glyphicon-trash:before{content:"\e020"}.glyphicon-home:before{content:"\e021"}.glyphicon-file:before{content:"\e022"}.glyphicon-time:before{content:"\e023"}.glyphicon-road:before{content:"\e024"}.glyphicon-download-alt:before{content:"\e025"}.glyphicon-download:before{content:"\e026"}.glyphicon-upload:before{content:"\e027"}.glyphicon-inbox:before{content:"\e028"}.glyphicon-play-circle:before{content:"\e029"}.glyphicon-repeat:before{content:"\e030"}.glyphicon-refresh:before{content:"\e031"}.glyphicon-list-alt:before{content:"\e032"}.glyphicon-lock:before{content:"\e033"}.glyphicon-flag:before{content:"\e034"}.glyphicon-headphones:before{content:"\e035"}.glyphicon-volume-off:before{content:"\e036"}.glyphicon-volume-down:before{content:"\e037"}.glyphicon-volume-up:before{content:"\e038"}.glyphicon-qrcode:before{content:"\e039"}.glyphicon-barcode:before{content:"\e040"}.glyphicon-tag:before{content:"\e041"}.glyphicon-tags:before{content:"\e042"}.glyphicon-book:before{content:"\e043"}.glyphicon-bookmark:before{content:"\e044"}.glyphicon-print:before{content:"\e045"}.glyphicon-camera:before{content:"\e046"}.glyphicon-font:before{content:"\e047"}.glyphicon-bold:before{content:"\e048"}.glyphicon-italic:before{content:"\e049"}.glyphicon-text-height:before{content:"\e050"}.glyphicon-text-width:before{content:"\e051"}.glyphicon-align-left:before{content:"\e052"}.glyphicon-align-center:before{content:"\e053"}.glyphicon-align-right:before{content:"\e054"}.glyphicon-align-justify:before{content:"\e055"}.glyphicon-list:before{content:"\e056"}.glyphicon-indent-left:before{content:"\e057"}.glyphicon-indent-right:before{content:"\e058"}.glyphicon-facetime-video:before{content:"\e059"}.glyphicon-picture:before{content:"\e060"}.glyphicon-map-marker:before{content:"\e062"}.glyphicon-adjust:before{content:"\e063"}.glyphicon-tint:before{content:"\e064"}.glyphicon-edit:before{content:"\e065"}.glyphicon-share:before{content:"\e066"}.glyphicon-check:before{content:"\e067"}.glyphicon-move:before{content:"\e068"}.glyphicon-step-backward:before{content:"\e069"}.glyphicon-fast-backward:before{content:"\e070"}.glyphicon-backward:before{content:"\e071"}.glyphicon-play:before{content:"\e072"}.glyphicon-pause:before{content:"\e073"}.glyphicon-stop:before{content:"\e074"}.glyphicon-forward:before{content:"\e075"}.glyphicon-fast-forward:before{content:"\e076"}.glyphicon-step-forward:before{content:"\e077"}.glyphicon-eject:before{content:"\e078"}.glyphicon-chevron-left:before{content:"\e079"}.glyphicon-chevron-right:before{content:"\e080"}.glyphicon-plus-sign:before{content:"\e081"}.glyphicon-minus-sign:before{content:"\e082"}.glyphicon-remove-sign:before{content:"\e083"}.glyphicon-ok-sign:before{content:"\e084"}.glyphicon-question-sign:before{content:"\e085"}.glyphicon-info-sign:before{content:"\e086"}.glyphicon-screenshot:before{content:"\e087"}.glyphicon-remove-circle:before{content:"\e088"}.glyphicon-ok-circle:before{content:"\e089"}.glyphicon-ban-circle:before{content:"\e090"}.glyphicon-arrow-left:before{content:"\e091"}.glyphicon-arrow-right:before{content:"\e092"}.glyphicon-arrow-up:before{content:"\e093"}.glyphicon-arrow-down:before{content:"\e094"}.glyphicon-share-alt:before{content:"\e095"}.glyphicon-resize-full:before{content:"\e096"}.glyphicon-resize-small:before{content:"\e097"}.glyphicon-exclamation-sign:before{content:"\e101"}.glyphicon-gift:before{content:"\e102"}.glyphicon-leaf:before{content:"\e103"}.glyphicon-fire:before{content:"\e104"}.glyphicon-eye-open:before{content:"\e105"}.glyphicon-eye-close:before{content:"\e106"}.glyphicon-warning-sign:before{content:"\e107"}.glyphicon-plane:before{content:"\e108"}.glyphicon-calendar:before{content:"\e109"}.glyphicon-random:before{content:"\e110"}.glyphicon-comment:before{content:"\e111"}.glyphicon-magnet:before{content:"\e112"}.glyphicon-chevron-up:before{content:"\e113"}.glyphicon-chevron-down:before{content:"\e114"}.glyphicon-retweet:before{content:"\e115"}.glyphicon-shopping-cart:before{content:"\e116"}.glyphicon-folder-close:before{content:"\e117"}.glyphicon-folder-open:before{content:"\e118"}.glyphicon-resize-vertical:before{content:"\e119"}.glyphicon-resize-horizontal:before{content:"\e120"}.glyphicon-hdd:before{content:"\e121"}.glyphicon-bullhorn:before{content:"\e122"}.glyphicon-bell:before{content:"\e123"}.glyphicon-certificate:before{content:"\e124"}.glyphicon-thumbs-up:before{content:"\e125"}.glyphicon-thumbs-down:before{content:"\e126"}.glyphicon-hand-right:before{content:"\e127"}.glyphicon-hand-left:before{content:"\e128"}.glyphicon-hand-up:before{content:"\e129"}.glyphicon-hand-down:before{content:"\e130"}.glyphicon-circle-arrow-right:before{content:"\e131"}.glyphicon-circle-arrow-left:before{content:"\e132"}.glyphicon-circle-arrow-up:before{content:"\e133"}.glyphicon-circle-arrow-down:before{content:"\e134"}.glyphicon-globe:before{content:"\e135"}.glyphicon-wrench:before{content:"\e136"}.glyphicon-tasks:before{content:"\e137"}.glyphicon-filter:before{content:"\e138"}.glyphicon-briefcase:before{content:"\e139"}.glyphicon-fullscreen:before{content:"\e140"}.glyphicon-dashboard:before{content:"\e141"}.glyphicon-paperclip:before{content:"\e142"}.glyphicon-heart-empty:before{content:"\e143"}.glyphicon-link:before{content:"\e144"}.glyphicon-phone:before{content:"\e145"}.glyphicon-pushpin:before{content:"\e146"}.glyphicon-usd:before{content:"\e148"}.glyphicon-gbp:before{content:"\e149"}.glyphicon-sort:before{content:"\e150"}.glyphicon-sort-by-alphabet:before{content:"\e151"}.glyphicon-sort-by-alphabet-alt:before{content:"\e152"}.glyphicon-sort-by-order:before{content:"\e153"}.glyphicon-sort-by-order-alt:before{content:"\e154"}.glyphicon-sort-by-attributes:before{content:"\e155"}.glyphicon-sort-by-attributes-alt:before{content:"\e156"}.glyphicon-unchecked:before{content:"\e157"}.glyphicon-expand:before{content:"\e158"}.glyphicon-collapse-down:before{content:"\e159"}.glyphicon-collapse-up:before{content:"\e160"}.glyphicon-log-in:before{content:"\e161"}.glyphicon-flash:before{content:"\e162"}.glyphicon-log-out:before{content:"\e163"}.glyphicon-new-window:before{content:"\e164"}.glyphicon-record:before{content:"\e165"}.glyphicon-save:before{content:"\e166"}.glyphicon-open:before{content:"\e167"}.glyphicon-saved:before{content:"\e168"}.glyphicon-import:before{content:"\e169"}.glyphicon-export:before{content:"\e170"}.glyphicon-send:before{content:"\e171"}.glyphicon-floppy-disk:before{content:"\e172"}.glyphicon-floppy-saved:before{content:"\e173"}.glyphicon-floppy-remove:before{content:"\e174"}.glyphicon-floppy-save:before{content:"\e175"}.glyphicon-floppy-open:before{content:"\e176"}.glyphicon-credit-card:before{content:"\e177"}.glyphicon-transfer:before{content:"\e178"}.glyphicon-cutlery:before{content:"\e179"}.glyphicon-header:before{content:"\e180"}.glyphicon-compressed:before{content:"\e181"}.glyphicon-earphone:before{content:"\e182"}.glyphicon-phone-alt:before{content:"\e183"}.glyphicon-tower:before{content:"\e184"}.glyphicon-stats:before{content:"\e185"}.glyphicon-sd-video:before{content:"\e186"}.glyphicon-hd-video:before{content:"\e187"}.glyphicon-subtitles:before{content:"\e188"}.glyphicon-sound-stereo:before{content:"\e189"}.glyphicon-sound-dolby:before{content:"\e190"}.glyphicon-sound-5-1:before{content:"\e191"}.glyphicon-sound-6-1:before{content:"\e192"}.glyphicon-sound-7-1:before{content:"\e193"}.glyphicon-copyright-mark:before{content:"\e194"}.glyphicon-registration-mark:before{content:"\e195"}.glyphicon-cloud-download:before{content:"\e197"}.glyphicon-cloud-upload:before{content:"\e198"}.glyphicon-tree-conifer:before{content:"\e199"}.glyphicon-tree-deciduous:before{content:"\e200"}.glyphicon-cd:before{content:"\e201"}.glyphicon-save-file:before{content:"\e202"}.glyphicon-open-file:before{content:"\e203"}.glyphicon-level-up:before{content:"\e204"}.glyphicon-copy:before{content:"\e205"}.glyphicon-paste:before{content:"\e206"}.glyphicon-alert:before{content:"\e209"}.glyphicon-equalizer:before{content:"\e210"}.glyphicon-king:before{content:"\e211"}.glyphicon-queen:before{content:"\e212"}.glyphicon-pawn:before{content:"\e213"}.glyphicon-bishop:before{content:"\e214"}.glyphicon-knight:before{content:"\e215"}.glyphicon-baby-formula:before{content:"\e216"}.glyphicon-tent:before{content:"\26fa"}.glyphicon-blackboard:before{content:"\e218"}.glyphicon-bed:before{content:"\e219"}.glyphicon-apple:before{content:"\f8ff"}.glyphicon-erase:before{content:"\e221"}.glyphicon-hourglass:before{content:"\231b"}.glyphicon-lamp:before{content:"\e223"}.glyphicon-duplicate:before{content:"\e224"}.glyphicon-piggy-bank:before{content:"\e225"}.glyphicon-scissors:before{content:"\e226"}.glyphicon-bitcoin:before{content:"\e227"}.glyphicon-btc:before{content:"\e227"}.glyphicon-xbt:before{content:"\e227"}.glyphicon-yen:before{content:"\00a5"}.glyphicon-jpy:before{content:"\00a5"}.glyphicon-ruble:before{content:"\20bd"}.glyphicon-rub:before{content:"\20bd"}.glyphicon-scale:before{content:"\e230"}.glyphicon-ice-lolly:before{content:"\e231"}.glyphicon-ice-lolly-tasted:before{content:"\e232"}.glyphicon-education:before{content:"\e233"}.glyphicon-option-horizontal:before{content:"\e234"}.glyphicon-option-vertical:before{content:"\e235"}.glyphicon-menu-hamburger:before{content:"\e236"}.glyphicon-modal-window:before{content:"\e237"}.glyphicon-oil:before{content:"\e238"}.glyphicon-grain:before{content:"\e239"}.glyphicon-sunglasses:before{content:"\e240"}.glyphicon-text-size:before{content:"\e241"}.glyphicon-text-color:before{content:"\e242"}.glyphicon-text-background:before{content:"\e243"}.glyphicon-object-align-top:before{content:"\e244"}.glyphicon-object-align-bottom:before{content:"\e245"}.glyphicon-object-align-horizontal:before{content:"\e246"}.glyphicon-object-align-left:before{content:"\e247"}.glyphicon-object-align-vertical:before{content:"\e248"}.glyphicon-object-align-right:before{content:"\e249"}.glyphicon-triangle-right:before{content:"\e250"}.glyphicon-triangle-left:before{content:"\e251"}.glyphicon-triangle-bottom:before{content:"\e252"}.glyphicon-triangle-top:before{content:"\e253"}.glyphicon-console:before{content:"\e254"}.glyphicon-superscript:before{content:"\e255"}.glyphicon-subscript:before{content:"\e256"}.glyphicon-menu-left:before{content:"\e257"}.glyphicon-menu-right:before{content:"\e258"}.glyphicon-menu-down:before{content:"\e259"}.glyphicon-menu-up:before{content:"\e260"}*{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}*:before,*:after{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}html{font-size:10px;-webkit-tap-highlight-color:rgba(0,0,0,0)}body{font-family:"Open Sans","Helvetica Neue",Helvetica,Arial,sans-serif;font-size:15px;line-height:1.4;color:#222222;background-color:#ffffff}input,button,select,textarea{font-family:inherit;font-size:inherit;line-height:inherit}a{color:#008cba;text-decoration:none}a:hover,a:focus{color:#008cba;text-decoration:underline}a:focus{outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}figure{margin:0}img{vertical-align:middle}.img-responsive,.thumbnail>img,.thumbnail a>img,.carousel-inner>.item>img,.carousel-inner>.item>a>img{display:block;max-width:100%;height:auto}.img-rounded{border-radius:0}.img-thumbnail{padding:4px;line-height:1.4;background-color:#ffffff;border:1px solid #dddddd;border-radius:0;-webkit-transition:all .2s ease-in-out;-o-transition:all .2s ease-in-out;transition:all .2s ease-in-out;display:inline-block;max-width:100%;height:auto}.img-circle{border-radius:50%}hr{margin-top:21px;margin-bottom:21px;border:0;border-top:1px solid #dddddd}.sr-only{position:absolute;width:1px;height:1px;margin:-1px;padding:0;overflow:hidden;clip:rect(0, 0, 0, 0);border:0}.sr-only-focusable:active,.sr-only-focusable:focus{position:static;width:auto;height:auto;margin:0;overflow:visible;clip:auto}[role="button"]{cursor:pointer}h1,h2,h3,h4,h5,h6,.h1,.h2,.h3,.h4,.h5,.h6{font-family:"Open Sans","Helvetica Neue",Helvetica,Arial,sans-serif;font-weight:300;line-height:1.1;color:inherit}h1 small,h2 small,h3 small,h4 small,h5 small,h6 small,.h1 small,.h2 small,.h3 small,.h4 small,.h5 small,.h6 small,h1 .small,h2 .small,h3 .small,h4 .small,h5 .small,h6 .small,.h1 .small,.h2 .small,.h3 .small,.h4 .small,.h5 .small,.h6 .small{font-weight:normal;line-height:1;color:#999999}h1,.h1,h2,.h2,h3,.h3{margin-top:21px;margin-bottom:10.5px}h1 small,.h1 small,h2 small,.h2 small,h3 small,.h3 small,h1 .small,.h1 .small,h2 .small,.h2 .small,h3 .small,.h3 .small{font-size:65%}h4,.h4,h5,.h5,h6,.h6{margin-top:10.5px;margin-bottom:10.5px}h4 small,.h4 small,h5 small,.h5 small,h6 small,.h6 small,h4 .small,.h4 .small,h5 .small,.h5 .small,h6 .small,.h6 .small{font-size:75%}h1,.h1{font-size:39px}h2,.h2{font-size:32px}h3,.h3{font-size:26px}h4,.h4{font-size:19px}h5,.h5{font-size:15px}h6,.h6{font-size:13px}p{margin:0 0 10.5px}.lead{margin-bottom:21px;font-size:17px;font-weight:300;line-height:1.4}@media (min-width:768px){.lead{font-size:22.5px}}small,.small{font-size:80%}mark,.mark{background-color:#fcf8e3;padding:.2em}.text-left{text-align:left}.text-right{text-align:right}.text-center{text-align:center}.text-justify{text-align:justify}.text-nowrap{white-space:nowrap}.text-lowercase{text-transform:lowercase}.text-uppercase{text-transform:uppercase}.text-capitalize{text-transform:capitalize}.text-muted{color:#999999}.text-primary{color:#008cba}a.text-primary:hover,a.text-primary:focus{color:#006687}.text-success{color:#43ac6a}a.text-success:hover,a.text-success:focus{color:#358753}.text-info{color:#5bc0de}a.text-info:hover,a.text-info:focus{color:#31b0d5}.text-warning{color:#e99002}a.text-warning:hover,a.text-warning:focus{color:#b67102}.text-danger{color:#f04124}a.text-danger:hover,a.text-danger:focus{color:#d32a0e}.bg-primary{color:#fff;background-color:#008cba}a.bg-primary:hover,a.bg-primary:focus{background-color:#006687}.bg-success{background-color:#dff0d8}a.bg-success:hover,a.bg-success:focus{background-color:#c1e2b3}.bg-info{background-color:#d9edf7}a.bg-info:hover,a.bg-info:focus{background-color:#afd9ee}.bg-warning{background-color:#fcf8e3}a.bg-warning:hover,a.bg-warning:focus{background-color:#f7ecb5}.bg-danger{background-color:#f2dede}a.bg-danger:hover,a.bg-danger:focus{background-color:#e4b9b9}.page-header{padding-bottom:9.5px;margin:42px 0 21px;border-bottom:1px solid #dddddd}ul,ol{margin-top:0;margin-bottom:10.5px}ul ul,ol ul,ul ol,ol ol{margin-bottom:0}.list-unstyled{padding-left:0;list-style:none}.list-inline{padding-left:0;list-style:none;margin-left:-5px}.list-inline>li{display:inline-block;padding-left:5px;padding-right:5px}dl{margin-top:0;margin-bottom:21px}dt,dd{line-height:1.4}dt{font-weight:bold}dd{margin-left:0}@media (min-width:768px){.dl-horizontal dt{float:left;width:160px;clear:left;text-align:right;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.dl-horizontal dd{margin-left:180px}}abbr[title],abbr[data-original-title]{cursor:help;border-bottom:1px dotted #999999}.initialism{font-size:90%;text-transform:uppercase}blockquote{padding:10.5px 21px;margin:0 0 21px;font-size:18.75px;border-left:5px solid #dddddd}blockquote p:last-child,blockquote ul:last-child,blockquote ol:last-child{margin-bottom:0}blockquote footer,blockquote small,blockquote .small{display:block;font-size:80%;line-height:1.4;color:#6f6f6f}blockquote footer:before,blockquote small:before,blockquote .small:before{content:'\2014 \00A0'}.blockquote-reverse,blockquote.pull-right{padding-right:15px;padding-left:0;border-right:5px solid #dddddd;border-left:0;text-align:right}.blockquote-reverse footer:before,blockquote.pull-right footer:before,.blockquote-reverse small:before,blockquote.pull-right small:before,.blockquote-reverse .small:before,blockquote.pull-right .small:before{content:''}.blockquote-reverse footer:after,blockquote.pull-right footer:after,.blockquote-reverse small:after,blockquote.pull-right small:after,.blockquote-reverse .small:after,blockquote.pull-right .small:after{content:'\00A0 \2014'}address{margin-bottom:21px;font-style:normal;line-height:1.4}code,kbd,pre,samp{font-family:Menlo,Monaco,Consolas,"Courier New",monospace}code{padding:2px 4px;font-size:90%;color:#c7254e;background-color:#f9f2f4;border-radius:0}kbd{padding:2px 4px;font-size:90%;color:#ffffff;background-color:#333333;border-radius:0;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,0.25);box-shadow:inset 0 -1px 0 rgba(0,0,0,0.25)}kbd kbd{padding:0;font-size:100%;font-weight:bold;-webkit-box-shadow:none;box-shadow:none}pre{display:block;padding:10px;margin:0 0 10.5px;font-size:14px;line-height:1.4;word-break:break-all;word-wrap:break-word;color:#333333;background-color:#f5f5f5;border:1px solid #cccccc;border-radius:0}pre code{padding:0;font-size:inherit;color:inherit;white-space:pre-wrap;background-color:transparent;border-radius:0}.pre-scrollable{max-height:340px;overflow-y:scroll}.container{margin-right:auto;margin-left:auto;padding-left:15px;padding-right:15px}@media (min-width:768px){.container{width:750px}}@media (min-width:992px){.container{width:970px}}@media (min-width:1200px){.container{width:1170px}}.container-fluid{margin-right:auto;margin-left:auto;padding-left:15px;padding-right:15px}.row{margin-left:-15px;margin-right:-15px}.col-xs-1,.col-sm-1,.col-md-1,.col-lg-1,.col-xs-2,.col-sm-2,.col-md-2,.col-lg-2,.col-xs-3,.col-sm-3,.col-md-3,.col-lg-3,.col-xs-4,.col-sm-4,.col-md-4,.col-lg-4,.col-xs-5,.col-sm-5,.col-md-5,.col-lg-5,.col-xs-6,.col-sm-6,.col-md-6,.col-lg-6,.col-xs-7,.col-sm-7,.col-md-7,.col-lg-7,.col-xs-8,.col-sm-8,.col-md-8,.col-lg-8,.col-xs-9,.col-sm-9,.col-md-9,.col-lg-9,.col-xs-10,.col-sm-10,.col-md-10,.col-lg-10,.col-xs-11,.col-sm-11,.col-md-11,.col-lg-11,.col-xs-12,.col-sm-12,.col-md-12,.col-lg-12{position:relative;min-height:1px;padding-left:15px;padding-right:15px}.col-xs-1,.col-xs-2,.col-xs-3,.col-xs-4,.col-xs-5,.col-xs-6,.col-xs-7,.col-xs-8,.col-xs-9,.col-xs-10,.col-xs-11,.col-xs-12{float:left}.col-xs-12{width:100%}.col-xs-11{width:91.66666667%}.col-xs-10{width:83.33333333%}.col-xs-9{width:75%}.col-xs-8{width:66.66666667%}.col-xs-7{width:58.33333333%}.col-xs-6{width:50%}.col-xs-5{width:41.66666667%}.col-xs-4{width:33.33333333%}.col-xs-3{width:25%}.col-xs-2{width:16.66666667%}.col-xs-1{width:8.33333333%}.col-xs-pull-12{right:100%}.col-xs-pull-11{right:91.66666667%}.col-xs-pull-10{right:83.33333333%}.col-xs-pull-9{right:75%}.col-xs-pull-8{right:66.66666667%}.col-xs-pull-7{right:58.33333333%}.col-xs-pull-6{right:50%}.col-xs-pull-5{right:41.66666667%}.col-xs-pull-4{right:33.33333333%}.col-xs-pull-3{right:25%}.col-xs-pull-2{right:16.66666667%}.col-xs-pull-1{right:8.33333333%}.col-xs-pull-0{right:auto}.col-xs-push-12{left:100%}.col-xs-push-11{left:91.66666667%}.col-xs-push-10{left:83.33333333%}.col-xs-push-9{left:75%}.col-xs-push-8{left:66.66666667%}.col-xs-push-7{left:58.33333333%}.col-xs-push-6{left:50%}.col-xs-push-5{left:41.66666667%}.col-xs-push-4{left:33.33333333%}.col-xs-push-3{left:25%}.col-xs-push-2{left:16.66666667%}.col-xs-push-1{left:8.33333333%}.col-xs-push-0{left:auto}.col-xs-offset-12{margin-left:100%}.col-xs-offset-11{margin-left:91.66666667%}.col-xs-offset-10{margin-left:83.33333333%}.col-xs-offset-9{margin-left:75%}.col-xs-offset-8{margin-left:66.66666667%}.col-xs-offset-7{margin-left:58.33333333%}.col-xs-offset-6{margin-left:50%}.col-xs-offset-5{margin-left:41.66666667%}.col-xs-offset-4{margin-left:33.33333333%}.col-xs-offset-3{margin-left:25%}.col-xs-offset-2{margin-left:16.66666667%}.col-xs-offset-1{margin-left:8.33333333%}.col-xs-offset-0{margin-left:0%}@media (min-width:768px){.col-sm-1,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9,.col-sm-10,.col-sm-11,.col-sm-12{float:left}.col-sm-12{width:100%}.col-sm-11{width:91.66666667%}.col-sm-10{width:83.33333333%}.col-sm-9{width:75%}.col-sm-8{width:66.66666667%}.col-sm-7{width:58.33333333%}.col-sm-6{width:50%}.col-sm-5{width:41.66666667%}.col-sm-4{width:33.33333333%}.col-sm-3{width:25%}.col-sm-2{width:16.66666667%}.col-sm-1{width:8.33333333%}.col-sm-pull-12{right:100%}.col-sm-pull-11{right:91.66666667%}.col-sm-pull-10{right:83.33333333%}.col-sm-pull-9{right:75%}.col-sm-pull-8{right:66.66666667%}.col-sm-pull-7{right:58.33333333%}.col-sm-pull-6{right:50%}.col-sm-pull-5{right:41.66666667%}.col-sm-pull-4{right:33.33333333%}.col-sm-pull-3{right:25%}.col-sm-pull-2{right:16.66666667%}.col-sm-pull-1{right:8.33333333%}.col-sm-pull-0{right:auto}.col-sm-push-12{left:100%}.col-sm-push-11{left:91.66666667%}.col-sm-push-10{left:83.33333333%}.col-sm-push-9{left:75%}.col-sm-push-8{left:66.66666667%}.col-sm-push-7{left:58.33333333%}.col-sm-push-6{left:50%}.col-sm-push-5{left:41.66666667%}.col-sm-push-4{left:33.33333333%}.col-sm-push-3{left:25%}.col-sm-push-2{left:16.66666667%}.col-sm-push-1{left:8.33333333%}.col-sm-push-0{left:auto}.col-sm-offset-12{margin-left:100%}.col-sm-offset-11{margin-left:91.66666667%}.col-sm-offset-10{margin-left:83.33333333%}.col-sm-offset-9{margin-left:75%}.col-sm-offset-8{margin-left:66.66666667%}.col-sm-offset-7{margin-left:58.33333333%}.col-sm-offset-6{margin-left:50%}.col-sm-offset-5{margin-left:41.66666667%}.col-sm-offset-4{margin-left:33.33333333%}.col-sm-offset-3{margin-left:25%}.col-sm-offset-2{margin-left:16.66666667%}.col-sm-offset-1{margin-left:8.33333333%}.col-sm-offset-0{margin-left:0%}}@media (min-width:992px){.col-md-1,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9,.col-md-10,.col-md-11,.col-md-12{float:left}.col-md-12{width:100%}.col-md-11{width:91.66666667%}.col-md-10{width:83.33333333%}.col-md-9{width:75%}.col-md-8{width:66.66666667%}.col-md-7{width:58.33333333%}.col-md-6{width:50%}.col-md-5{width:41.66666667%}.col-md-4{width:33.33333333%}.col-md-3{width:25%}.col-md-2{width:16.66666667%}.col-md-1{width:8.33333333%}.col-md-pull-12{right:100%}.col-md-pull-11{right:91.66666667%}.col-md-pull-10{right:83.33333333%}.col-md-pull-9{right:75%}.col-md-pull-8{right:66.66666667%}.col-md-pull-7{right:58.33333333%}.col-md-pull-6{right:50%}.col-md-pull-5{right:41.66666667%}.col-md-pull-4{right:33.33333333%}.col-md-pull-3{right:25%}.col-md-pull-2{right:16.66666667%}.col-md-pull-1{right:8.33333333%}.col-md-pull-0{right:auto}.col-md-push-12{left:100%}.col-md-push-11{left:91.66666667%}.col-md-push-10{left:83.33333333%}.col-md-push-9{left:75%}.col-md-push-8{left:66.66666667%}.col-md-push-7{left:58.33333333%}.col-md-push-6{left:50%}.col-md-push-5{left:41.66666667%}.col-md-push-4{left:33.33333333%}.col-md-push-3{left:25%}.col-md-push-2{left:16.66666667%}.col-md-push-1{left:8.33333333%}.col-md-push-0{left:auto}.col-md-offset-12{margin-left:100%}.col-md-offset-11{margin-left:91.66666667%}.col-md-offset-10{margin-left:83.33333333%}.col-md-offset-9{margin-left:75%}.col-md-offset-8{margin-left:66.66666667%}.col-md-offset-7{margin-left:58.33333333%}.col-md-offset-6{margin-left:50%}.col-md-offset-5{margin-left:41.66666667%}.col-md-offset-4{margin-left:33.33333333%}.col-md-offset-3{margin-left:25%}.col-md-offset-2{margin-left:16.66666667%}.col-md-offset-1{margin-left:8.33333333%}.col-md-offset-0{margin-left:0%}}@media (min-width:1200px){.col-lg-1,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9,.col-lg-10,.col-lg-11,.col-lg-12{float:left}.col-lg-12{width:100%}.col-lg-11{width:91.66666667%}.col-lg-10{width:83.33333333%}.col-lg-9{width:75%}.col-lg-8{width:66.66666667%}.col-lg-7{width:58.33333333%}.col-lg-6{width:50%}.col-lg-5{width:41.66666667%}.col-lg-4{width:33.33333333%}.col-lg-3{width:25%}.col-lg-2{width:16.66666667%}.col-lg-1{width:8.33333333%}.col-lg-pull-12{right:100%}.col-lg-pull-11{right:91.66666667%}.col-lg-pull-10{right:83.33333333%}.col-lg-pull-9{right:75%}.col-lg-pull-8{right:66.66666667%}.col-lg-pull-7{right:58.33333333%}.col-lg-pull-6{right:50%}.col-lg-pull-5{right:41.66666667%}.col-lg-pull-4{right:33.33333333%}.col-lg-pull-3{right:25%}.col-lg-pull-2{right:16.66666667%}.col-lg-pull-1{right:8.33333333%}.col-lg-pull-0{right:auto}.col-lg-push-12{left:100%}.col-lg-push-11{left:91.66666667%}.col-lg-push-10{left:83.33333333%}.col-lg-push-9{left:75%}.col-lg-push-8{left:66.66666667%}.col-lg-push-7{left:58.33333333%}.col-lg-push-6{left:50%}.col-lg-push-5{left:41.66666667%}.col-lg-push-4{left:33.33333333%}.col-lg-push-3{left:25%}.col-lg-push-2{left:16.66666667%}.col-lg-push-1{left:8.33333333%}.col-lg-push-0{left:auto}.col-lg-offset-12{margin-left:100%}.col-lg-offset-11{margin-left:91.66666667%}.col-lg-offset-10{margin-left:83.33333333%}.col-lg-offset-9{margin-left:75%}.col-lg-offset-8{margin-left:66.66666667%}.col-lg-offset-7{margin-left:58.33333333%}.col-lg-offset-6{margin-left:50%}.col-lg-offset-5{margin-left:41.66666667%}.col-lg-offset-4{margin-left:33.33333333%}.col-lg-offset-3{margin-left:25%}.col-lg-offset-2{margin-left:16.66666667%}.col-lg-offset-1{margin-left:8.33333333%}.col-lg-offset-0{margin-left:0%}}table{background-color:transparent}caption{padding-top:8px;padding-bottom:8px;color:#999999;text-align:left}th{text-align:left}.table{width:100%;max-width:100%;margin-bottom:21px}.table>thead>tr>th,.table>tbody>tr>th,.table>tfoot>tr>th,.table>thead>tr>td,.table>tbody>tr>td,.table>tfoot>tr>td{padding:8px;line-height:1.4;vertical-align:top;border-top:1px solid #dddddd}.table>thead>tr>th{vertical-align:bottom;border-bottom:2px solid #dddddd}.table>caption+thead>tr:first-child>th,.table>colgroup+thead>tr:first-child>th,.table>thead:first-child>tr:first-child>th,.table>caption+thead>tr:first-child>td,.table>colgroup+thead>tr:first-child>td,.table>thead:first-child>tr:first-child>td{border-top:0}.table>tbody+tbody{border-top:2px solid #dddddd}.table .table{background-color:#ffffff}.table-condensed>thead>tr>th,.table-condensed>tbody>tr>th,.table-condensed>tfoot>tr>th,.table-condensed>thead>tr>td,.table-condensed>tbody>tr>td,.table-condensed>tfoot>tr>td{padding:5px}.table-bordered{border:1px solid #dddddd}.table-bordered>thead>tr>th,.table-bordered>tbody>tr>th,.table-bordered>tfoot>tr>th,.table-bordered>thead>tr>td,.table-bordered>tbody>tr>td,.table-bordered>tfoot>tr>td{border:1px solid #dddddd}.table-bordered>thead>tr>th,.table-bordered>thead>tr>td{border-bottom-width:2px}.table-striped>tbody>tr:nth-of-type(odd){background-color:#f9f9f9}.table-hover>tbody>tr:hover{background-color:#f5f5f5}table col[class*="col-"]{position:static;float:none;display:table-column}table td[class*="col-"],table th[class*="col-"]{position:static;float:none;display:table-cell}.table>thead>tr>td.active,.table>tbody>tr>td.active,.table>tfoot>tr>td.active,.table>thead>tr>th.active,.table>tbody>tr>th.active,.table>tfoot>tr>th.active,.table>thead>tr.active>td,.table>tbody>tr.active>td,.table>tfoot>tr.active>td,.table>thead>tr.active>th,.table>tbody>tr.active>th,.table>tfoot>tr.active>th{background-color:#f5f5f5}.table-hover>tbody>tr>td.active:hover,.table-hover>tbody>tr>th.active:hover,.table-hover>tbody>tr.active:hover>td,.table-hover>tbody>tr:hover>.active,.table-hover>tbody>tr.active:hover>th{background-color:#e8e8e8}.table>thead>tr>td.success,.table>tbody>tr>td.success,.table>tfoot>tr>td.success,.table>thead>tr>th.success,.table>tbody>tr>th.success,.table>tfoot>tr>th.success,.table>thead>tr.success>td,.table>tbody>tr.success>td,.table>tfoot>tr.success>td,.table>thead>tr.success>th,.table>tbody>tr.success>th,.table>tfoot>tr.success>th{background-color:#dff0d8}.table-hover>tbody>tr>td.success:hover,.table-hover>tbody>tr>th.success:hover,.table-hover>tbody>tr.success:hover>td,.table-hover>tbody>tr:hover>.success,.table-hover>tbody>tr.success:hover>th{background-color:#d0e9c6}.table>thead>tr>td.info,.table>tbody>tr>td.info,.table>tfoot>tr>td.info,.table>thead>tr>th.info,.table>tbody>tr>th.info,.table>tfoot>tr>th.info,.table>thead>tr.info>td,.table>tbody>tr.info>td,.table>tfoot>tr.info>td,.table>thead>tr.info>th,.table>tbody>tr.info>th,.table>tfoot>tr.info>th{background-color:#d9edf7}.table-hover>tbody>tr>td.info:hover,.table-hover>tbody>tr>th.info:hover,.table-hover>tbody>tr.info:hover>td,.table-hover>tbody>tr:hover>.info,.table-hover>tbody>tr.info:hover>th{background-color:#c4e3f3}.table>thead>tr>td.warning,.table>tbody>tr>td.warning,.table>tfoot>tr>td.warning,.table>thead>tr>th.warning,.table>tbody>tr>th.warning,.table>tfoot>tr>th.warning,.table>thead>tr.warning>td,.table>tbody>tr.warning>td,.table>tfoot>tr.warning>td,.table>thead>tr.warning>th,.table>tbody>tr.warning>th,.table>tfoot>tr.warning>th{background-color:#fcf8e3}.table-hover>tbody>tr>td.warning:hover,.table-hover>tbody>tr>th.warning:hover,.table-hover>tbody>tr.warning:hover>td,.table-hover>tbody>tr:hover>.warning,.table-hover>tbody>tr.warning:hover>th{background-color:#faf2cc}.table>thead>tr>td.danger,.table>tbody>tr>td.danger,.table>tfoot>tr>td.danger,.table>thead>tr>th.danger,.table>tbody>tr>th.danger,.table>tfoot>tr>th.danger,.table>thead>tr.danger>td,.table>tbody>tr.danger>td,.table>tfoot>tr.danger>td,.table>thead>tr.danger>th,.table>tbody>tr.danger>th,.table>tfoot>tr.danger>th{background-color:#f2dede}.table-hover>tbody>tr>td.danger:hover,.table-hover>tbody>tr>th.danger:hover,.table-hover>tbody>tr.danger:hover>td,.table-hover>tbody>tr:hover>.danger,.table-hover>tbody>tr.danger:hover>th{background-color:#ebcccc}.table-responsive{overflow-x:auto;min-height:0.01%}@media screen and (max-width:767px){.table-responsive{width:100%;margin-bottom:15.75px;overflow-y:hidden;-ms-overflow-style:-ms-autohiding-scrollbar;border:1px solid #dddddd}.table-responsive>.table{margin-bottom:0}.table-responsive>.table>thead>tr>th,.table-responsive>.table>tbody>tr>th,.table-responsive>.table>tfoot>tr>th,.table-responsive>.table>thead>tr>td,.table-responsive>.table>tbody>tr>td,.table-responsive>.table>tfoot>tr>td{white-space:nowrap}.table-responsive>.table-bordered{border:0}.table-responsive>.table-bordered>thead>tr>th:first-child,.table-responsive>.table-bordered>tbody>tr>th:first-child,.table-responsive>.table-bordered>tfoot>tr>th:first-child,.table-responsive>.table-bordered>thead>tr>td:first-child,.table-responsive>.table-bordered>tbody>tr>td:first-child,.table-responsive>.table-bordered>tfoot>tr>td:first-child{border-left:0}.table-responsive>.table-bordered>thead>tr>th:last-child,.table-responsive>.table-bordered>tbody>tr>th:last-child,.table-responsive>.table-bordered>tfoot>tr>th:last-child,.table-responsive>.table-bordered>thead>tr>td:last-child,.table-responsive>.table-bordered>tbody>tr>td:last-child,.table-responsive>.table-bordered>tfoot>tr>td:last-child{border-right:0}.table-responsive>.table-bordered>tbody>tr:last-child>th,.table-responsive>.table-bordered>tfoot>tr:last-child>th,.table-responsive>.table-bordered>tbody>tr:last-child>td,.table-responsive>.table-bordered>tfoot>tr:last-child>td{border-bottom:0}}fieldset{padding:0;margin:0;border:0;min-width:0}legend{display:block;width:100%;padding:0;margin-bottom:21px;font-size:22.5px;line-height:inherit;color:#333333;border:0;border-bottom:1px solid #e5e5e5}label{display:inline-block;max-width:100%;margin-bottom:5px;font-weight:bold}input[type="search"]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}input[type="radio"],input[type="checkbox"]{margin:4px 0 0;margin-top:1px \9;line-height:normal}input[type="file"]{display:block}input[type="range"]{display:block;width:100%}select[multiple],select[size]{height:auto}input[type="file"]:focus,input[type="radio"]:focus,input[type="checkbox"]:focus{outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}output{display:block;padding-top:9px;font-size:15px;line-height:1.4;color:#6f6f6f}.form-control{display:block;width:100%;height:39px;padding:8px 12px;font-size:15px;line-height:1.4;color:#6f6f6f;background-color:#ffffff;background-image:none;border:1px solid #cccccc;border-radius:0;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);-webkit-transition:border-color ease-in-out .15s,-webkit-box-shadow ease-in-out .15s;-o-transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s;transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s}.form-control:focus{border-color:#66afe9;outline:0;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 8px rgba(102,175,233,0.6);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 8px rgba(102,175,233,0.6)}.form-control::-moz-placeholder{color:#999999;opacity:1}.form-control:-ms-input-placeholder{color:#999999}.form-control::-webkit-input-placeholder{color:#999999}.form-control::-ms-expand{border:0;background-color:transparent}.form-control[disabled],.form-control[readonly],fieldset[disabled] .form-control{background-color:#eeeeee;opacity:1}.form-control[disabled],fieldset[disabled] .form-control{cursor:not-allowed}textarea.form-control{height:auto}input[type="search"]{-webkit-appearance:none}@media screen and (-webkit-min-device-pixel-ratio:0){input[type="date"].form-control,input[type="time"].form-control,input[type="datetime-local"].form-control,input[type="month"].form-control{line-height:39px}input[type="date"].input-sm,input[type="time"].input-sm,input[type="datetime-local"].input-sm,input[type="month"].input-sm,.input-group-sm input[type="date"],.input-group-sm input[type="time"],.input-group-sm input[type="datetime-local"],.input-group-sm input[type="month"]{line-height:36px}input[type="date"].input-lg,input[type="time"].input-lg,input[type="datetime-local"].input-lg,input[type="month"].input-lg,.input-group-lg input[type="date"],.input-group-lg input[type="time"],.input-group-lg input[type="datetime-local"],.input-group-lg input[type="month"]{line-height:60px}}.form-group{margin-bottom:15px}.radio,.checkbox{position:relative;display:block;margin-top:10px;margin-bottom:10px}.radio label,.checkbox label{min-height:21px;padding-left:20px;margin-bottom:0;font-weight:normal;cursor:pointer}.radio input[type="radio"],.radio-inline input[type="radio"],.checkbox input[type="checkbox"],.checkbox-inline input[type="checkbox"]{position:absolute;margin-left:-20px;margin-top:4px \9}.radio+.radio,.checkbox+.checkbox{margin-top:-5px}.radio-inline,.checkbox-inline{position:relative;display:inline-block;padding-left:20px;margin-bottom:0;vertical-align:middle;font-weight:normal;cursor:pointer}.radio-inline+.radio-inline,.checkbox-inline+.checkbox-inline{margin-top:0;margin-left:10px}input[type="radio"][disabled],input[type="checkbox"][disabled],input[type="radio"].disabled,input[type="checkbox"].disabled,fieldset[disabled] input[type="radio"],fieldset[disabled] input[type="checkbox"]{cursor:not-allowed}.radio-inline.disabled,.checkbox-inline.disabled,fieldset[disabled] .radio-inline,fieldset[disabled] .checkbox-inline{cursor:not-allowed}.radio.disabled label,.checkbox.disabled label,fieldset[disabled] .radio label,fieldset[disabled] .checkbox label{cursor:not-allowed}.form-control-static{padding-top:9px;padding-bottom:9px;margin-bottom:0;min-height:36px}.form-control-static.input-lg,.form-control-static.input-sm{padding-left:0;padding-right:0}.input-sm{height:36px;padding:8px 12px;font-size:12px;line-height:1.5;border-radius:0}select.input-sm{height:36px;line-height:36px}textarea.input-sm,select[multiple].input-sm{height:auto}.form-group-sm .form-control{height:36px;padding:8px 12px;font-size:12px;line-height:1.5;border-radius:0}.form-group-sm select.form-control{height:36px;line-height:36px}.form-group-sm textarea.form-control,.form-group-sm select[multiple].form-control{height:auto}.form-group-sm .form-control-static{height:36px;min-height:33px;padding:9px 12px;font-size:12px;line-height:1.5}.input-lg{height:60px;padding:16px 20px;font-size:19px;line-height:1.3333333;border-radius:0}select.input-lg{height:60px;line-height:60px}textarea.input-lg,select[multiple].input-lg{height:auto}.form-group-lg .form-control{height:60px;padding:16px 20px;font-size:19px;line-height:1.3333333;border-radius:0}.form-group-lg select.form-control{height:60px;line-height:60px}.form-group-lg textarea.form-control,.form-group-lg select[multiple].form-control{height:auto}.form-group-lg .form-control-static{height:60px;min-height:40px;padding:17px 20px;font-size:19px;line-height:1.3333333}.has-feedback{position:relative}.has-feedback .form-control{padding-right:48.75px}.form-control-feedback{position:absolute;top:0;right:0;z-index:2;display:block;width:39px;height:39px;line-height:39px;text-align:center;pointer-events:none}.input-lg+.form-control-feedback,.input-group-lg+.form-control-feedback,.form-group-lg .form-control+.form-control-feedback{width:60px;height:60px;line-height:60px}.input-sm+.form-control-feedback,.input-group-sm+.form-control-feedback,.form-group-sm .form-control+.form-control-feedback{width:36px;height:36px;line-height:36px}.has-success .help-block,.has-success .control-label,.has-success .radio,.has-success .checkbox,.has-success .radio-inline,.has-success .checkbox-inline,.has-success.radio label,.has-success.checkbox label,.has-success.radio-inline label,.has-success.checkbox-inline label{color:#43ac6a}.has-success .form-control{border-color:#43ac6a;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-success .form-control:focus{border-color:#358753;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #85d0a1;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #85d0a1}.has-success .input-group-addon{color:#43ac6a;border-color:#43ac6a;background-color:#dff0d8}.has-success .form-control-feedback{color:#43ac6a}.has-warning .help-block,.has-warning .control-label,.has-warning .radio,.has-warning .checkbox,.has-warning .radio-inline,.has-warning .checkbox-inline,.has-warning.radio label,.has-warning.checkbox label,.has-warning.radio-inline label,.has-warning.checkbox-inline label{color:#e99002}.has-warning .form-control{border-color:#e99002;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-warning .form-control:focus{border-color:#b67102;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #febc53;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #febc53}.has-warning .input-group-addon{color:#e99002;border-color:#e99002;background-color:#fcf8e3}.has-warning .form-control-feedback{color:#e99002}.has-error .help-block,.has-error .control-label,.has-error .radio,.has-error .checkbox,.has-error .radio-inline,.has-error .checkbox-inline,.has-error.radio label,.has-error.checkbox label,.has-error.radio-inline label,.has-error.checkbox-inline label{color:#f04124}.has-error .form-control{border-color:#f04124;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-error .form-control:focus{border-color:#d32a0e;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #f79483;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #f79483}.has-error .input-group-addon{color:#f04124;border-color:#f04124;background-color:#f2dede}.has-error .form-control-feedback{color:#f04124}.has-feedback label~.form-control-feedback{top:26px}.has-feedback label.sr-only~.form-control-feedback{top:0}.help-block{display:block;margin-top:5px;margin-bottom:10px;color:#626262}@media (min-width:768px){.form-inline .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.form-inline .form-control{display:inline-block;width:auto;vertical-align:middle}.form-inline .form-control-static{display:inline-block}.form-inline .input-group{display:inline-table;vertical-align:middle}.form-inline .input-group .input-group-addon,.form-inline .input-group .input-group-btn,.form-inline .input-group .form-control{width:auto}.form-inline .input-group>.form-control{width:100%}.form-inline .control-label{margin-bottom:0;vertical-align:middle}.form-inline .radio,.form-inline .checkbox{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.form-inline .radio label,.form-inline .checkbox label{padding-left:0}.form-inline .radio input[type="radio"],.form-inline .checkbox input[type="checkbox"]{position:relative;margin-left:0}.form-inline .has-feedback .form-control-feedback{top:0}}.form-horizontal .radio,.form-horizontal .checkbox,.form-horizontal .radio-inline,.form-horizontal .checkbox-inline{margin-top:0;margin-bottom:0;padding-top:9px}.form-horizontal .radio,.form-horizontal .checkbox{min-height:30px}.form-horizontal .form-group{margin-left:-15px;margin-right:-15px}@media (min-width:768px){.form-horizontal .control-label{text-align:right;margin-bottom:0;padding-top:9px}}.form-horizontal .has-feedback .form-control-feedback{right:15px}@media (min-width:768px){.form-horizontal .form-group-lg .control-label{padding-top:17px;font-size:19px}}@media (min-width:768px){.form-horizontal .form-group-sm .control-label{padding-top:9px;font-size:12px}}.btn{display:inline-block;margin-bottom:0;font-weight:normal;text-align:center;vertical-align:middle;-ms-touch-action:manipulation;touch-action:manipulation;cursor:pointer;background-image:none;border:1px solid transparent;white-space:nowrap;padding:8px 12px;font-size:15px;line-height:1.4;border-radius:0;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.btn:focus,.btn:active:focus,.btn.active:focus,.btn.focus,.btn:active.focus,.btn.active.focus{outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}.btn:hover,.btn:focus,.btn.focus{color:#333333;text-decoration:none}.btn:active,.btn.active{outline:0;background-image:none;-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,0.125);box-shadow:inset 0 3px 5px rgba(0,0,0,0.125)}.btn.disabled,.btn[disabled],fieldset[disabled] .btn{cursor:not-allowed;opacity:0.65;filter:alpha(opacity=65);-webkit-box-shadow:none;box-shadow:none}a.btn.disabled,fieldset[disabled] a.btn{pointer-events:none}.btn-default{color:#333333;background-color:#e7e7e7;border-color:#cccccc}.btn-default:focus,.btn-default.focus{color:#333333;background-color:#cecece;border-color:#8c8c8c}.btn-default:hover{color:#333333;background-color:#cecece;border-color:#adadad}.btn-default:active,.btn-default.active,.open>.dropdown-toggle.btn-default{color:#333333;background-color:#cecece;border-color:#adadad}.btn-default:active:hover,.btn-default.active:hover,.open>.dropdown-toggle.btn-default:hover,.btn-default:active:focus,.btn-default.active:focus,.open>.dropdown-toggle.btn-default:focus,.btn-default:active.focus,.btn-default.active.focus,.open>.dropdown-toggle.btn-default.focus{color:#333333;background-color:#bcbcbc;border-color:#8c8c8c}.btn-default:active,.btn-default.active,.open>.dropdown-toggle.btn-default{background-image:none}.btn-default.disabled:hover,.btn-default[disabled]:hover,fieldset[disabled] .btn-default:hover,.btn-default.disabled:focus,.btn-default[disabled]:focus,fieldset[disabled] .btn-default:focus,.btn-default.disabled.focus,.btn-default[disabled].focus,fieldset[disabled] .btn-default.focus{background-color:#e7e7e7;border-color:#cccccc}.btn-default .badge{color:#e7e7e7;background-color:#333333}.btn-primary{color:#ffffff;background-color:#008cba;border-color:#0079a1}.btn-primary:focus,.btn-primary.focus{color:#ffffff;background-color:#006687;border-color:#001921}.btn-primary:hover{color:#ffffff;background-color:#006687;border-color:#004b63}.btn-primary:active,.btn-primary.active,.open>.dropdown-toggle.btn-primary{color:#ffffff;background-color:#006687;border-color:#004b63}.btn-primary:active:hover,.btn-primary.active:hover,.open>.dropdown-toggle.btn-primary:hover,.btn-primary:active:focus,.btn-primary.active:focus,.open>.dropdown-toggle.btn-primary:focus,.btn-primary:active.focus,.btn-primary.active.focus,.open>.dropdown-toggle.btn-primary.focus{color:#ffffff;background-color:#004b63;border-color:#001921}.btn-primary:active,.btn-primary.active,.open>.dropdown-toggle.btn-primary{background-image:none}.btn-primary.disabled:hover,.btn-primary[disabled]:hover,fieldset[disabled] .btn-primary:hover,.btn-primary.disabled:focus,.btn-primary[disabled]:focus,fieldset[disabled] .btn-primary:focus,.btn-primary.disabled.focus,.btn-primary[disabled].focus,fieldset[disabled] .btn-primary.focus{background-color:#008cba;border-color:#0079a1}.btn-primary .badge{color:#008cba;background-color:#ffffff}.btn-success{color:#ffffff;background-color:#43ac6a;border-color:#3c9a5f}.btn-success:focus,.btn-success.focus{color:#ffffff;background-color:#358753;border-color:#183e26}.btn-success:hover{color:#ffffff;background-color:#358753;border-color:#2b6e44}.btn-success:active,.btn-success.active,.open>.dropdown-toggle.btn-success{color:#ffffff;background-color:#358753;border-color:#2b6e44}.btn-success:active:hover,.btn-success.active:hover,.open>.dropdown-toggle.btn-success:hover,.btn-success:active:focus,.btn-success.active:focus,.open>.dropdown-toggle.btn-success:focus,.btn-success:active.focus,.btn-success.active.focus,.open>.dropdown-toggle.btn-success.focus{color:#ffffff;background-color:#2b6e44;border-color:#183e26}.btn-success:active,.btn-success.active,.open>.dropdown-toggle.btn-success{background-image:none}.btn-success.disabled:hover,.btn-success[disabled]:hover,fieldset[disabled] .btn-success:hover,.btn-success.disabled:focus,.btn-success[disabled]:focus,fieldset[disabled] .btn-success:focus,.btn-success.disabled.focus,.btn-success[disabled].focus,fieldset[disabled] .btn-success.focus{background-color:#43ac6a;border-color:#3c9a5f}.btn-success .badge{color:#43ac6a;background-color:#ffffff}.btn-info{color:#ffffff;background-color:#5bc0de;border-color:#46b8da}.btn-info:focus,.btn-info.focus{color:#ffffff;background-color:#31b0d5;border-color:#1b6d85}.btn-info:hover{color:#ffffff;background-color:#31b0d5;border-color:#269abc}.btn-info:active,.btn-info.active,.open>.dropdown-toggle.btn-info{color:#ffffff;background-color:#31b0d5;border-color:#269abc}.btn-info:active:hover,.btn-info.active:hover,.open>.dropdown-toggle.btn-info:hover,.btn-info:active:focus,.btn-info.active:focus,.open>.dropdown-toggle.btn-info:focus,.btn-info:active.focus,.btn-info.active.focus,.open>.dropdown-toggle.btn-info.focus{color:#ffffff;background-color:#269abc;border-color:#1b6d85}.btn-info:active,.btn-info.active,.open>.dropdown-toggle.btn-info{background-image:none}.btn-info.disabled:hover,.btn-info[disabled]:hover,fieldset[disabled] .btn-info:hover,.btn-info.disabled:focus,.btn-info[disabled]:focus,fieldset[disabled] .btn-info:focus,.btn-info.disabled.focus,.btn-info[disabled].focus,fieldset[disabled] .btn-info.focus{background-color:#5bc0de;border-color:#46b8da}.btn-info .badge{color:#5bc0de;background-color:#ffffff}.btn-warning{color:#ffffff;background-color:#e99002;border-color:#d08002}.btn-warning:focus,.btn-warning.focus{color:#ffffff;background-color:#b67102;border-color:#513201}.btn-warning:hover{color:#ffffff;background-color:#b67102;border-color:#935b01}.btn-warning:active,.btn-warning.active,.open>.dropdown-toggle.btn-warning{color:#ffffff;background-color:#b67102;border-color:#935b01}.btn-warning:active:hover,.btn-warning.active:hover,.open>.dropdown-toggle.btn-warning:hover,.btn-warning:active:focus,.btn-warning.active:focus,.open>.dropdown-toggle.btn-warning:focus,.btn-warning:active.focus,.btn-warning.active.focus,.open>.dropdown-toggle.btn-warning.focus{color:#ffffff;background-color:#935b01;border-color:#513201}.btn-warning:active,.btn-warning.active,.open>.dropdown-toggle.btn-warning{background-image:none}.btn-warning.disabled:hover,.btn-warning[disabled]:hover,fieldset[disabled] .btn-warning:hover,.btn-warning.disabled:focus,.btn-warning[disabled]:focus,fieldset[disabled] .btn-warning:focus,.btn-warning.disabled.focus,.btn-warning[disabled].focus,fieldset[disabled] .btn-warning.focus{background-color:#e99002;border-color:#d08002}.btn-warning .badge{color:#e99002;background-color:#ffffff}.btn-danger{color:#ffffff;background-color:#f04124;border-color:#ea2f10}.btn-danger:focus,.btn-danger.focus{color:#ffffff;background-color:#d32a0e;border-color:#731708}.btn-danger:hover{color:#ffffff;background-color:#d32a0e;border-color:#b1240c}.btn-danger:active,.btn-danger.active,.open>.dropdown-toggle.btn-danger{color:#ffffff;background-color:#d32a0e;border-color:#b1240c}.btn-danger:active:hover,.btn-danger.active:hover,.open>.dropdown-toggle.btn-danger:hover,.btn-danger:active:focus,.btn-danger.active:focus,.open>.dropdown-toggle.btn-danger:focus,.btn-danger:active.focus,.btn-danger.active.focus,.open>.dropdown-toggle.btn-danger.focus{color:#ffffff;background-color:#b1240c;border-color:#731708}.btn-danger:active,.btn-danger.active,.open>.dropdown-toggle.btn-danger{background-image:none}.btn-danger.disabled:hover,.btn-danger[disabled]:hover,fieldset[disabled] .btn-danger:hover,.btn-danger.disabled:focus,.btn-danger[disabled]:focus,fieldset[disabled] .btn-danger:focus,.btn-danger.disabled.focus,.btn-danger[disabled].focus,fieldset[disabled] .btn-danger.focus{background-color:#f04124;border-color:#ea2f10}.btn-danger .badge{color:#f04124;background-color:#ffffff}.btn-link{color:#008cba;font-weight:normal;border-radius:0}.btn-link,.btn-link:active,.btn-link.active,.btn-link[disabled],fieldset[disabled] .btn-link{background-color:transparent;-webkit-box-shadow:none;box-shadow:none}.btn-link,.btn-link:hover,.btn-link:focus,.btn-link:active{border-color:transparent}.btn-link:hover,.btn-link:focus{color:#008cba;text-decoration:underline;background-color:transparent}.btn-link[disabled]:hover,fieldset[disabled] .btn-link:hover,.btn-link[disabled]:focus,fieldset[disabled] .btn-link:focus{color:#999999;text-decoration:none}.btn-lg,.btn-group-lg>.btn{padding:16px 20px;font-size:19px;line-height:1.3333333;border-radius:0}.btn-sm,.btn-group-sm>.btn{padding:8px 12px;font-size:12px;line-height:1.5;border-radius:0}.btn-xs,.btn-group-xs>.btn{padding:4px 6px;font-size:12px;line-height:1.5;border-radius:0}.btn-block{display:block;width:100%}.btn-block+.btn-block{margin-top:5px}input[type="submit"].btn-block,input[type="reset"].btn-block,input[type="button"].btn-block{width:100%}.fade{opacity:0;-webkit-transition:opacity 0.15s linear;-o-transition:opacity 0.15s linear;transition:opacity 0.15s linear}.fade.in{opacity:1}.collapse{display:none}.collapse.in{display:block}tr.collapse.in{display:table-row}tbody.collapse.in{display:table-row-group}.collapsing{position:relative;height:0;overflow:hidden;-webkit-transition-property:height, visibility;-o-transition-property:height, visibility;transition-property:height, visibility;-webkit-transition-duration:0.35s;-o-transition-duration:0.35s;transition-duration:0.35s;-webkit-transition-timing-function:ease;-o-transition-timing-function:ease;transition-timing-function:ease}.caret{display:inline-block;width:0;height:0;margin-left:2px;vertical-align:middle;border-top:4px dashed;border-top:4px solid \9;border-right:4px solid transparent;border-left:4px solid transparent}.dropup,.dropdown{position:relative}.dropdown-toggle:focus{outline:0}.dropdown-menu{position:absolute;top:100%;left:0;z-index:1000;display:none;float:left;min-width:160px;padding:5px 0;margin:2px 0 0;list-style:none;font-size:15px;text-align:left;background-color:#ffffff;border:1px solid #cccccc;border:1px solid rgba(0,0,0,0.15);border-radius:0;-webkit-box-shadow:0 6px 12px rgba(0,0,0,0.175);box-shadow:0 6px 12px rgba(0,0,0,0.175);-webkit-background-clip:padding-box;background-clip:padding-box}.dropdown-menu.pull-right{right:0;left:auto}.dropdown-menu .divider{height:1px;margin:9.5px 0;overflow:hidden;background-color:rgba(0,0,0,0.2)}.dropdown-menu>li>a{display:block;padding:3px 20px;clear:both;font-weight:normal;line-height:1.4;color:#555555;white-space:nowrap}.dropdown-menu>li>a:hover,.dropdown-menu>li>a:focus{text-decoration:none;color:#262626;background-color:#eeeeee}.dropdown-menu>.active>a,.dropdown-menu>.active>a:hover,.dropdown-menu>.active>a:focus{color:#ffffff;text-decoration:none;outline:0;background-color:#008cba}.dropdown-menu>.disabled>a,.dropdown-menu>.disabled>a:hover,.dropdown-menu>.disabled>a:focus{color:#999999}.dropdown-menu>.disabled>a:hover,.dropdown-menu>.disabled>a:focus{text-decoration:none;background-color:transparent;background-image:none;filter:progid:DXImageTransform.Microsoft.gradient(enabled=false);cursor:not-allowed}.open>.dropdown-menu{display:block}.open>a{outline:0}.dropdown-menu-right{left:auto;right:0}.dropdown-menu-left{left:0;right:auto}.dropdown-header{display:block;padding:3px 20px;font-size:12px;line-height:1.4;color:#999999;white-space:nowrap}.dropdown-backdrop{position:fixed;left:0;right:0;bottom:0;top:0;z-index:990}.pull-right>.dropdown-menu{right:0;left:auto}.dropup .caret,.navbar-fixed-bottom .dropdown .caret{border-top:0;border-bottom:4px dashed;border-bottom:4px solid \9;content:""}.dropup .dropdown-menu,.navbar-fixed-bottom .dropdown .dropdown-menu{top:auto;bottom:100%;margin-bottom:2px}@media (min-width:768px){.navbar-right .dropdown-menu{left:auto;right:0}.navbar-right .dropdown-menu-left{left:0;right:auto}}.btn-group,.btn-group-vertical{position:relative;display:inline-block;vertical-align:middle}.btn-group>.btn,.btn-group-vertical>.btn{position:relative;float:left}.btn-group>.btn:hover,.btn-group-vertical>.btn:hover,.btn-group>.btn:focus,.btn-group-vertical>.btn:focus,.btn-group>.btn:active,.btn-group-vertical>.btn:active,.btn-group>.btn.active,.btn-group-vertical>.btn.active{z-index:2}.btn-group .btn+.btn,.btn-group .btn+.btn-group,.btn-group .btn-group+.btn,.btn-group .btn-group+.btn-group{margin-left:-1px}.btn-toolbar{margin-left:-5px}.btn-toolbar .btn,.btn-toolbar .btn-group,.btn-toolbar .input-group{float:left}.btn-toolbar>.btn,.btn-toolbar>.btn-group,.btn-toolbar>.input-group{margin-left:5px}.btn-group>.btn:not(:first-child):not(:last-child):not(.dropdown-toggle){border-radius:0}.btn-group>.btn:first-child{margin-left:0}.btn-group>.btn:first-child:not(:last-child):not(.dropdown-toggle){border-bottom-right-radius:0;border-top-right-radius:0}.btn-group>.btn:last-child:not(:first-child),.btn-group>.dropdown-toggle:not(:first-child){border-bottom-left-radius:0;border-top-left-radius:0}.btn-group>.btn-group{float:left}.btn-group>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-bottom-right-radius:0;border-top-right-radius:0}.btn-group>.btn-group:last-child:not(:first-child)>.btn:first-child{border-bottom-left-radius:0;border-top-left-radius:0}.btn-group .dropdown-toggle:active,.btn-group.open .dropdown-toggle{outline:0}.btn-group>.btn+.dropdown-toggle{padding-left:8px;padding-right:8px}.btn-group>.btn-lg+.dropdown-toggle{padding-left:12px;padding-right:12px}.btn-group.open .dropdown-toggle{-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,0.125);box-shadow:inset 0 3px 5px rgba(0,0,0,0.125)}.btn-group.open .dropdown-toggle.btn-link{-webkit-box-shadow:none;box-shadow:none}.btn .caret{margin-left:0}.btn-lg .caret{border-width:5px 5px 0;border-bottom-width:0}.dropup .btn-lg .caret{border-width:0 5px 5px}.btn-group-vertical>.btn,.btn-group-vertical>.btn-group,.btn-group-vertical>.btn-group>.btn{display:block;float:none;width:100%;max-width:100%}.btn-group-vertical>.btn-group>.btn{float:none}.btn-group-vertical>.btn+.btn,.btn-group-vertical>.btn+.btn-group,.btn-group-vertical>.btn-group+.btn,.btn-group-vertical>.btn-group+.btn-group{margin-top:-1px;margin-left:0}.btn-group-vertical>.btn:not(:first-child):not(:last-child){border-radius:0}.btn-group-vertical>.btn:first-child:not(:last-child){border-top-right-radius:0;border-top-left-radius:0;border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn:last-child:not(:first-child){border-top-right-radius:0;border-top-left-radius:0;border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group-vertical>.btn-group:first-child:not(:last-child)>.btn:last-child,.btn-group-vertical>.btn-group:first-child:not(:last-child)>.dropdown-toggle{border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn-group:last-child:not(:first-child)>.btn:first-child{border-top-right-radius:0;border-top-left-radius:0}.btn-group-justified{display:table;width:100%;table-layout:fixed;border-collapse:separate}.btn-group-justified>.btn,.btn-group-justified>.btn-group{float:none;display:table-cell;width:1%}.btn-group-justified>.btn-group .btn{width:100%}.btn-group-justified>.btn-group .dropdown-menu{left:auto}[data-toggle="buttons"]>.btn input[type="radio"],[data-toggle="buttons"]>.btn-group>.btn input[type="radio"],[data-toggle="buttons"]>.btn input[type="checkbox"],[data-toggle="buttons"]>.btn-group>.btn input[type="checkbox"]{position:absolute;clip:rect(0, 0, 0, 0);pointer-events:none}.input-group{position:relative;display:table;border-collapse:separate}.input-group[class*="col-"]{float:none;padding-left:0;padding-right:0}.input-group .form-control{position:relative;z-index:2;float:left;width:100%;margin-bottom:0}.input-group .form-control:focus{z-index:3}.input-group-lg>.form-control,.input-group-lg>.input-group-addon,.input-group-lg>.input-group-btn>.btn{height:60px;padding:16px 20px;font-size:19px;line-height:1.3333333;border-radius:0}select.input-group-lg>.form-control,select.input-group-lg>.input-group-addon,select.input-group-lg>.input-group-btn>.btn{height:60px;line-height:60px}textarea.input-group-lg>.form-control,textarea.input-group-lg>.input-group-addon,textarea.input-group-lg>.input-group-btn>.btn,select[multiple].input-group-lg>.form-control,select[multiple].input-group-lg>.input-group-addon,select[multiple].input-group-lg>.input-group-btn>.btn{height:auto}.input-group-sm>.form-control,.input-group-sm>.input-group-addon,.input-group-sm>.input-group-btn>.btn{height:36px;padding:8px 12px;font-size:12px;line-height:1.5;border-radius:0}select.input-group-sm>.form-control,select.input-group-sm>.input-group-addon,select.input-group-sm>.input-group-btn>.btn{height:36px;line-height:36px}textarea.input-group-sm>.form-control,textarea.input-group-sm>.input-group-addon,textarea.input-group-sm>.input-group-btn>.btn,select[multiple].input-group-sm>.form-control,select[multiple].input-group-sm>.input-group-addon,select[multiple].input-group-sm>.input-group-btn>.btn{height:auto}.input-group-addon,.input-group-btn,.input-group .form-control{display:table-cell}.input-group-addon:not(:first-child):not(:last-child),.input-group-btn:not(:first-child):not(:last-child),.input-group .form-control:not(:first-child):not(:last-child){border-radius:0}.input-group-addon,.input-group-btn{width:1%;white-space:nowrap;vertical-align:middle}.input-group-addon{padding:8px 12px;font-size:15px;font-weight:normal;line-height:1;color:#6f6f6f;text-align:center;background-color:#eeeeee;border:1px solid #cccccc;border-radius:0}.input-group-addon.input-sm{padding:8px 12px;font-size:12px;border-radius:0}.input-group-addon.input-lg{padding:16px 20px;font-size:19px;border-radius:0}.input-group-addon input[type="radio"],.input-group-addon input[type="checkbox"]{margin-top:0}.input-group .form-control:first-child,.input-group-addon:first-child,.input-group-btn:first-child>.btn,.input-group-btn:first-child>.btn-group>.btn,.input-group-btn:first-child>.dropdown-toggle,.input-group-btn:last-child>.btn:not(:last-child):not(.dropdown-toggle),.input-group-btn:last-child>.btn-group:not(:last-child)>.btn{border-bottom-right-radius:0;border-top-right-radius:0}.input-group-addon:first-child{border-right:0}.input-group .form-control:last-child,.input-group-addon:last-child,.input-group-btn:last-child>.btn,.input-group-btn:last-child>.btn-group>.btn,.input-group-btn:last-child>.dropdown-toggle,.input-group-btn:first-child>.btn:not(:first-child),.input-group-btn:first-child>.btn-group:not(:first-child)>.btn{border-bottom-left-radius:0;border-top-left-radius:0}.input-group-addon:last-child{border-left:0}.input-group-btn{position:relative;font-size:0;white-space:nowrap}.input-group-btn>.btn{position:relative}.input-group-btn>.btn+.btn{margin-left:-1px}.input-group-btn>.btn:hover,.input-group-btn>.btn:focus,.input-group-btn>.btn:active{z-index:2}.input-group-btn:first-child>.btn,.input-group-btn:first-child>.btn-group{margin-right:-1px}.input-group-btn:last-child>.btn,.input-group-btn:last-child>.btn-group{z-index:2;margin-left:-1px}.nav{margin-bottom:0;padding-left:0;list-style:none}.nav>li{position:relative;display:block}.nav>li>a{position:relative;display:block;padding:10px 15px}.nav>li>a:hover,.nav>li>a:focus{text-decoration:none;background-color:#eeeeee}.nav>li.disabled>a{color:#999999}.nav>li.disabled>a:hover,.nav>li.disabled>a:focus{color:#999999;text-decoration:none;background-color:transparent;cursor:not-allowed}.nav .open>a,.nav .open>a:hover,.nav .open>a:focus{background-color:#eeeeee;border-color:#008cba}.nav .nav-divider{height:1px;margin:9.5px 0;overflow:hidden;background-color:#e5e5e5}.nav>li>a>img{max-width:none}.nav-tabs{border-bottom:1px solid #dddddd}.nav-tabs>li{float:left;margin-bottom:-1px}.nav-tabs>li>a{margin-right:2px;line-height:1.4;border:1px solid transparent;border-radius:0 0 0 0}.nav-tabs>li>a:hover{border-color:#eeeeee #eeeeee #dddddd}.nav-tabs>li.active>a,.nav-tabs>li.active>a:hover,.nav-tabs>li.active>a:focus{color:#6f6f6f;background-color:#ffffff;border:1px solid #dddddd;border-bottom-color:transparent;cursor:default}.nav-tabs.nav-justified{width:100%;border-bottom:0}.nav-tabs.nav-justified>li{float:none}.nav-tabs.nav-justified>li>a{text-align:center;margin-bottom:5px}.nav-tabs.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-tabs.nav-justified>li{display:table-cell;width:1%}.nav-tabs.nav-justified>li>a{margin-bottom:0}}.nav-tabs.nav-justified>li>a{margin-right:0;border-radius:0}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:hover,.nav-tabs.nav-justified>.active>a:focus{border:1px solid #dddddd}@media (min-width:768px){.nav-tabs.nav-justified>li>a{border-bottom:1px solid #dddddd;border-radius:0 0 0 0}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:hover,.nav-tabs.nav-justified>.active>a:focus{border-bottom-color:#ffffff}}.nav-pills>li{float:left}.nav-pills>li>a{border-radius:0}.nav-pills>li+li{margin-left:2px}.nav-pills>li.active>a,.nav-pills>li.active>a:hover,.nav-pills>li.active>a:focus{color:#ffffff;background-color:#008cba}.nav-stacked>li{float:none}.nav-stacked>li+li{margin-top:2px;margin-left:0}.nav-justified{width:100%}.nav-justified>li{float:none}.nav-justified>li>a{text-align:center;margin-bottom:5px}.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-justified>li{display:table-cell;width:1%}.nav-justified>li>a{margin-bottom:0}}.nav-tabs-justified{border-bottom:0}.nav-tabs-justified>li>a{margin-right:0;border-radius:0}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:hover,.nav-tabs-justified>.active>a:focus{border:1px solid #dddddd}@media (min-width:768px){.nav-tabs-justified>li>a{border-bottom:1px solid #dddddd;border-radius:0 0 0 0}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:hover,.nav-tabs-justified>.active>a:focus{border-bottom-color:#ffffff}}.tab-content>.tab-pane{display:none}.tab-content>.active{display:block}.nav-tabs .dropdown-menu{margin-top:-1px;border-top-right-radius:0;border-top-left-radius:0}.navbar{position:relative;min-height:45px;margin-bottom:21px;border:1px solid transparent}@media (min-width:768px){.navbar{border-radius:0}}@media (min-width:768px){.navbar-header{float:left}}.navbar-collapse{overflow-x:visible;padding-right:15px;padding-left:15px;border-top:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,0.1);box-shadow:inset 0 1px 0 rgba(255,255,255,0.1);-webkit-overflow-scrolling:touch}.navbar-collapse.in{overflow-y:auto}@media (min-width:768px){.navbar-collapse{width:auto;border-top:0;-webkit-box-shadow:none;box-shadow:none}.navbar-collapse.collapse{display:block !important;height:auto !important;padding-bottom:0;overflow:visible !important}.navbar-collapse.in{overflow-y:visible}.navbar-fixed-top .navbar-collapse,.navbar-static-top .navbar-collapse,.navbar-fixed-bottom .navbar-collapse{padding-left:0;padding-right:0}}.navbar-fixed-top .navbar-collapse,.navbar-fixed-bottom .navbar-collapse{max-height:340px}@media (max-device-width:480px) and (orientation:landscape){.navbar-fixed-top .navbar-collapse,.navbar-fixed-bottom .navbar-collapse{max-height:200px}}.container>.navbar-header,.container-fluid>.navbar-header,.container>.navbar-collapse,.container-fluid>.navbar-collapse{margin-right:-15px;margin-left:-15px}@media (min-width:768px){.container>.navbar-header,.container-fluid>.navbar-header,.container>.navbar-collapse,.container-fluid>.navbar-collapse{margin-right:0;margin-left:0}}.navbar-static-top{z-index:1000;border-width:0 0 1px}@media (min-width:768px){.navbar-static-top{border-radius:0}}.navbar-fixed-top,.navbar-fixed-bottom{position:fixed;right:0;left:0;z-index:1030}@media (min-width:768px){.navbar-fixed-top,.navbar-fixed-bottom{border-radius:0}}.navbar-fixed-top{top:0;border-width:0 0 1px}.navbar-fixed-bottom{bottom:0;margin-bottom:0;border-width:1px 0 0}.navbar-brand{float:left;padding:12px 15px;font-size:19px;line-height:21px;height:45px}.navbar-brand:hover,.navbar-brand:focus{text-decoration:none}.navbar-brand>img{display:block}@media (min-width:768px){.navbar>.container .navbar-brand,.navbar>.container-fluid .navbar-brand{margin-left:-15px}}.navbar-toggle{position:relative;float:right;margin-right:15px;padding:9px 10px;margin-top:5.5px;margin-bottom:5.5px;background-color:transparent;background-image:none;border:1px solid transparent;border-radius:0}.navbar-toggle:focus{outline:0}.navbar-toggle .icon-bar{display:block;width:22px;height:2px;border-radius:1px}.navbar-toggle .icon-bar+.icon-bar{margin-top:4px}@media (min-width:768px){.navbar-toggle{display:none}}.navbar-nav{margin:6px -15px}.navbar-nav>li>a{padding-top:10px;padding-bottom:10px;line-height:21px}@media (max-width:767px){.navbar-nav .open .dropdown-menu{position:static;float:none;width:auto;margin-top:0;background-color:transparent;border:0;-webkit-box-shadow:none;box-shadow:none}.navbar-nav .open .dropdown-menu>li>a,.navbar-nav .open .dropdown-menu .dropdown-header{padding:5px 15px 5px 25px}.navbar-nav .open .dropdown-menu>li>a{line-height:21px}.navbar-nav .open .dropdown-menu>li>a:hover,.navbar-nav .open .dropdown-menu>li>a:focus{background-image:none}}@media (min-width:768px){.navbar-nav{float:left;margin:0}.navbar-nav>li{float:left}.navbar-nav>li>a{padding-top:12px;padding-bottom:12px}}.navbar-form{margin-left:-15px;margin-right:-15px;padding:10px 15px;border-top:1px solid transparent;border-bottom:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1);box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1);margin-top:3px;margin-bottom:3px}@media (min-width:768px){.navbar-form .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.navbar-form .form-control{display:inline-block;width:auto;vertical-align:middle}.navbar-form .form-control-static{display:inline-block}.navbar-form .input-group{display:inline-table;vertical-align:middle}.navbar-form .input-group .input-group-addon,.navbar-form .input-group .input-group-btn,.navbar-form .input-group .form-control{width:auto}.navbar-form .input-group>.form-control{width:100%}.navbar-form .control-label{margin-bottom:0;vertical-align:middle}.navbar-form .radio,.navbar-form .checkbox{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.navbar-form .radio label,.navbar-form .checkbox label{padding-left:0}.navbar-form .radio input[type="radio"],.navbar-form .checkbox input[type="checkbox"]{position:relative;margin-left:0}.navbar-form .has-feedback .form-control-feedback{top:0}}@media (max-width:767px){.navbar-form .form-group{margin-bottom:5px}.navbar-form .form-group:last-child{margin-bottom:0}}@media (min-width:768px){.navbar-form{width:auto;border:0;margin-left:0;margin-right:0;padding-top:0;padding-bottom:0;-webkit-box-shadow:none;box-shadow:none}}.navbar-nav>li>.dropdown-menu{margin-top:0;border-top-right-radius:0;border-top-left-radius:0}.navbar-fixed-bottom .navbar-nav>li>.dropdown-menu{margin-bottom:0;border-top-right-radius:0;border-top-left-radius:0;border-bottom-right-radius:0;border-bottom-left-radius:0}.navbar-btn{margin-top:3px;margin-bottom:3px}.navbar-btn.btn-sm{margin-top:4.5px;margin-bottom:4.5px}.navbar-btn.btn-xs{margin-top:11.5px;margin-bottom:11.5px}.navbar-text{margin-top:12px;margin-bottom:12px}@media (min-width:768px){.navbar-text{float:left;margin-left:15px;margin-right:15px}}@media (min-width:768px){.navbar-left{float:left !important}.navbar-right{float:right !important;margin-right:-15px}.navbar-right~.navbar-right{margin-right:0}}.navbar-default{background-color:#333333;border-color:#222222}.navbar-default .navbar-brand{color:#ffffff}.navbar-default .navbar-brand:hover,.navbar-default .navbar-brand:focus{color:#ffffff;background-color:transparent}.navbar-default .navbar-text{color:#ffffff}.navbar-default .navbar-nav>li>a{color:#ffffff}.navbar-default .navbar-nav>li>a:hover,.navbar-default .navbar-nav>li>a:focus{color:#ffffff;background-color:#272727}.navbar-default .navbar-nav>.active>a,.navbar-default .navbar-nav>.active>a:hover,.navbar-default .navbar-nav>.active>a:focus{color:#ffffff;background-color:#272727}.navbar-default .navbar-nav>.disabled>a,.navbar-default .navbar-nav>.disabled>a:hover,.navbar-default .navbar-nav>.disabled>a:focus{color:#cccccc;background-color:transparent}.navbar-default .navbar-toggle{border-color:transparent}.navbar-default .navbar-toggle:hover,.navbar-default .navbar-toggle:focus{background-color:transparent}.navbar-default .navbar-toggle .icon-bar{background-color:#ffffff}.navbar-default .navbar-collapse,.navbar-default .navbar-form{border-color:#222222}.navbar-default .navbar-nav>.open>a,.navbar-default .navbar-nav>.open>a:hover,.navbar-default .navbar-nav>.open>a:focus{background-color:#272727;color:#ffffff}@media (max-width:767px){.navbar-default .navbar-nav .open .dropdown-menu>li>a{color:#ffffff}.navbar-default .navbar-nav .open .dropdown-menu>li>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>li>a:focus{color:#ffffff;background-color:#272727}.navbar-default .navbar-nav .open .dropdown-menu>.active>a,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:focus{color:#ffffff;background-color:#272727}.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:focus{color:#cccccc;background-color:transparent}}.navbar-default .navbar-link{color:#ffffff}.navbar-default .navbar-link:hover{color:#ffffff}.navbar-default .btn-link{color:#ffffff}.navbar-default .btn-link:hover,.navbar-default .btn-link:focus{color:#ffffff}.navbar-default .btn-link[disabled]:hover,fieldset[disabled] .navbar-default .btn-link:hover,.navbar-default .btn-link[disabled]:focus,fieldset[disabled] .navbar-default .btn-link:focus{color:#cccccc}.navbar-inverse{background-color:#008cba;border-color:#006687}.navbar-inverse .navbar-brand{color:#ffffff}.navbar-inverse .navbar-brand:hover,.navbar-inverse .navbar-brand:focus{color:#ffffff;background-color:transparent}.navbar-inverse .navbar-text{color:#ffffff}.navbar-inverse .navbar-nav>li>a{color:#ffffff}.navbar-inverse .navbar-nav>li>a:hover,.navbar-inverse .navbar-nav>li>a:focus{color:#ffffff;background-color:#006687}.navbar-inverse .navbar-nav>.active>a,.navbar-inverse .navbar-nav>.active>a:hover,.navbar-inverse .navbar-nav>.active>a:focus{color:#ffffff;background-color:#006687}.navbar-inverse .navbar-nav>.disabled>a,.navbar-inverse .navbar-nav>.disabled>a:hover,.navbar-inverse .navbar-nav>.disabled>a:focus{color:#444444;background-color:transparent}.navbar-inverse .navbar-toggle{border-color:transparent}.navbar-inverse .navbar-toggle:hover,.navbar-inverse .navbar-toggle:focus{background-color:transparent}.navbar-inverse .navbar-toggle .icon-bar{background-color:#ffffff}.navbar-inverse .navbar-collapse,.navbar-inverse .navbar-form{border-color:#007196}.navbar-inverse .navbar-nav>.open>a,.navbar-inverse .navbar-nav>.open>a:hover,.navbar-inverse .navbar-nav>.open>a:focus{background-color:#006687;color:#ffffff}@media (max-width:767px){.navbar-inverse .navbar-nav .open .dropdown-menu>.dropdown-header{border-color:#006687}.navbar-inverse .navbar-nav .open .dropdown-menu .divider{background-color:#006687}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a{color:#ffffff}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:focus{color:#ffffff;background-color:#006687}.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:focus{color:#ffffff;background-color:#006687}.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:focus{color:#444444;background-color:transparent}}.navbar-inverse .navbar-link{color:#ffffff}.navbar-inverse .navbar-link:hover{color:#ffffff}.navbar-inverse .btn-link{color:#ffffff}.navbar-inverse .btn-link:hover,.navbar-inverse .btn-link:focus{color:#ffffff}.navbar-inverse .btn-link[disabled]:hover,fieldset[disabled] .navbar-inverse .btn-link:hover,.navbar-inverse .btn-link[disabled]:focus,fieldset[disabled] .navbar-inverse .btn-link:focus{color:#444444}.breadcrumb{padding:8px 15px;margin-bottom:21px;list-style:none;background-color:#f5f5f5;border-radius:0}.breadcrumb>li{display:inline-block}.breadcrumb>li+li:before{content:"/\00a0";padding:0 5px;color:#999999}.breadcrumb>.active{color:#333333}.pagination{display:inline-block;padding-left:0;margin:21px 0;border-radius:0}.pagination>li{display:inline}.pagination>li>a,.pagination>li>span{position:relative;float:left;padding:8px 12px;line-height:1.4;text-decoration:none;color:#008cba;background-color:transparent;border:1px solid transparent;margin-left:-1px}.pagination>li:first-child>a,.pagination>li:first-child>span{margin-left:0;border-bottom-left-radius:0;border-top-left-radius:0}.pagination>li:last-child>a,.pagination>li:last-child>span{border-bottom-right-radius:0;border-top-right-radius:0}.pagination>li>a:hover,.pagination>li>span:hover,.pagination>li>a:focus,.pagination>li>span:focus{z-index:2;color:#008cba;background-color:#eeeeee;border-color:transparent}.pagination>.active>a,.pagination>.active>span,.pagination>.active>a:hover,.pagination>.active>span:hover,.pagination>.active>a:focus,.pagination>.active>span:focus{z-index:3;color:#ffffff;background-color:#008cba;border-color:transparent;cursor:default}.pagination>.disabled>span,.pagination>.disabled>span:hover,.pagination>.disabled>span:focus,.pagination>.disabled>a,.pagination>.disabled>a:hover,.pagination>.disabled>a:focus{color:#999999;background-color:#ffffff;border-color:transparent;cursor:not-allowed}.pagination-lg>li>a,.pagination-lg>li>span{padding:16px 20px;font-size:19px;line-height:1.3333333}.pagination-lg>li:first-child>a,.pagination-lg>li:first-child>span{border-bottom-left-radius:0;border-top-left-radius:0}.pagination-lg>li:last-child>a,.pagination-lg>li:last-child>span{border-bottom-right-radius:0;border-top-right-radius:0}.pagination-sm>li>a,.pagination-sm>li>span{padding:8px 12px;font-size:12px;line-height:1.5}.pagination-sm>li:first-child>a,.pagination-sm>li:first-child>span{border-bottom-left-radius:0;border-top-left-radius:0}.pagination-sm>li:last-child>a,.pagination-sm>li:last-child>span{border-bottom-right-radius:0;border-top-right-radius:0}.pager{padding-left:0;margin:21px 0;list-style:none;text-align:center}.pager li{display:inline}.pager li>a,.pager li>span{display:inline-block;padding:5px 14px;background-color:transparent;border:1px solid transparent;border-radius:3px}.pager li>a:hover,.pager li>a:focus{text-decoration:none;background-color:#eeeeee}.pager .next>a,.pager .next>span{float:right}.pager .previous>a,.pager .previous>span{float:left}.pager .disabled>a,.pager .disabled>a:hover,.pager .disabled>a:focus,.pager .disabled>span{color:#999999;background-color:transparent;cursor:not-allowed}.label{display:inline;padding:.2em .6em .3em;font-size:75%;font-weight:bold;line-height:1;color:#ffffff;text-align:center;white-space:nowrap;vertical-align:baseline;border-radius:.25em}a.label:hover,a.label:focus{color:#ffffff;text-decoration:none;cursor:pointer}.label:empty{display:none}.btn .label{position:relative;top:-1px}.label-default{background-color:#999999}.label-default[href]:hover,.label-default[href]:focus{background-color:#808080}.label-primary{background-color:#008cba}.label-primary[href]:hover,.label-primary[href]:focus{background-color:#006687}.label-success{background-color:#43ac6a}.label-success[href]:hover,.label-success[href]:focus{background-color:#358753}.label-info{background-color:#5bc0de}.label-info[href]:hover,.label-info[href]:focus{background-color:#31b0d5}.label-warning{background-color:#e99002}.label-warning[href]:hover,.label-warning[href]:focus{background-color:#b67102}.label-danger{background-color:#f04124}.label-danger[href]:hover,.label-danger[href]:focus{background-color:#d32a0e}.badge{display:inline-block;min-width:10px;padding:3px 7px;font-size:12px;font-weight:bold;color:#ffffff;line-height:1;vertical-align:middle;white-space:nowrap;text-align:center;background-color:#008cba;border-radius:10px}.badge:empty{display:none}.btn .badge{position:relative;top:-1px}.btn-xs .badge,.btn-group-xs>.btn .badge{top:0;padding:1px 5px}a.badge:hover,a.badge:focus{color:#ffffff;text-decoration:none;cursor:pointer}.list-group-item.active>.badge,.nav-pills>.active>a>.badge{color:#008cba;background-color:#ffffff}.list-group-item>.badge{float:right}.list-group-item>.badge+.badge{margin-right:5px}.nav-pills>li>a>.badge{margin-left:3px}.jumbotron{padding-top:30px;padding-bottom:30px;margin-bottom:30px;color:inherit;background-color:#fafafa}.jumbotron h1,.jumbotron .h1{color:inherit}.jumbotron p{margin-bottom:15px;font-size:23px;font-weight:200}.jumbotron>hr{border-top-color:#e1e1e1}.container .jumbotron,.container-fluid .jumbotron{border-radius:0;padding-left:15px;padding-right:15px}.jumbotron .container{max-width:100%}@media screen and (min-width:768px){.jumbotron{padding-top:48px;padding-bottom:48px}.container .jumbotron,.container-fluid .jumbotron{padding-left:60px;padding-right:60px}.jumbotron h1,.jumbotron .h1{font-size:68px}}.thumbnail{display:block;padding:4px;margin-bottom:21px;line-height:1.4;background-color:#ffffff;border:1px solid #dddddd;border-radius:0;-webkit-transition:border .2s ease-in-out;-o-transition:border .2s ease-in-out;transition:border .2s ease-in-out}.thumbnail>img,.thumbnail a>img{margin-left:auto;margin-right:auto}a.thumbnail:hover,a.thumbnail:focus,a.thumbnail.active{border-color:#008cba}.thumbnail .caption{padding:9px;color:#222222}.alert{padding:15px;margin-bottom:21px;border:1px solid transparent;border-radius:0}.alert h4{margin-top:0;color:inherit}.alert .alert-link{font-weight:bold}.alert>p,.alert>ul{margin-bottom:0}.alert>p+p{margin-top:5px}.alert-dismissable,.alert-dismissible{padding-right:35px}.alert-dismissable .close,.alert-dismissible .close{position:relative;top:-2px;right:-21px;color:inherit}.alert-success{background-color:#43ac6a;border-color:#3c9a5f;color:#ffffff}.alert-success hr{border-top-color:#358753}.alert-success .alert-link{color:#e6e6e6}.alert-info{background-color:#5bc0de;border-color:#3db5d8;color:#ffffff}.alert-info hr{border-top-color:#2aabd2}.alert-info .alert-link{color:#e6e6e6}.alert-warning{background-color:#e99002;border-color:#d08002;color:#ffffff}.alert-warning hr{border-top-color:#b67102}.alert-warning .alert-link{color:#e6e6e6}.alert-danger{background-color:#f04124;border-color:#ea2f10;color:#ffffff}.alert-danger hr{border-top-color:#d32a0e}.alert-danger .alert-link{color:#e6e6e6}@-webkit-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@-o-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}.progress{overflow:hidden;height:21px;margin-bottom:21px;background-color:#f5f5f5;border-radius:0;-webkit-box-shadow:inset 0 1px 2px rgba(0,0,0,0.1);box-shadow:inset 0 1px 2px rgba(0,0,0,0.1)}.progress-bar{float:left;width:0%;height:100%;font-size:12px;line-height:21px;color:#ffffff;text-align:center;background-color:#008cba;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,0.15);box-shadow:inset 0 -1px 0 rgba(0,0,0,0.15);-webkit-transition:width 0.6s ease;-o-transition:width 0.6s ease;transition:width 0.6s ease}.progress-striped .progress-bar,.progress-bar-striped{background-image:-webkit-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);-webkit-background-size:40px 40px;background-size:40px 40px}.progress.active .progress-bar,.progress-bar.active{-webkit-animation:progress-bar-stripes 2s linear infinite;-o-animation:progress-bar-stripes 2s linear infinite;animation:progress-bar-stripes 2s linear infinite}.progress-bar-success{background-color:#43ac6a}.progress-striped .progress-bar-success{background-image:-webkit-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent)}.progress-bar-info{background-color:#5bc0de}.progress-striped .progress-bar-info{background-image:-webkit-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent)}.progress-bar-warning{background-color:#e99002}.progress-striped .progress-bar-warning{background-image:-webkit-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent)}.progress-bar-danger{background-color:#f04124}.progress-striped .progress-bar-danger{background-image:-webkit-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:-o-linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent);background-image:linear-gradient(45deg, rgba(255,255,255,0.15) 25%, transparent 25%, transparent 50%, rgba(255,255,255,0.15) 50%, rgba(255,255,255,0.15) 75%, transparent 75%, transparent)}.media{margin-top:15px}.media:first-child{margin-top:0}.media,.media-body{zoom:1;overflow:hidden}.media-body{width:10000px}.media-object{display:block}.media-object.img-thumbnail{max-width:none}.media-right,.media>.pull-right{padding-left:10px}.media-left,.media>.pull-left{padding-right:10px}.media-left,.media-right,.media-body{display:table-cell;vertical-align:top}.media-middle{vertical-align:middle}.media-bottom{vertical-align:bottom}.media-heading{margin-top:0;margin-bottom:5px}.media-list{padding-left:0;list-style:none}.list-group{margin-bottom:20px;padding-left:0}.list-group-item{position:relative;display:block;padding:10px 15px;margin-bottom:-1px;background-color:#ffffff;border:1px solid #dddddd}.list-group-item:first-child{border-top-right-radius:0;border-top-left-radius:0}.list-group-item:last-child{margin-bottom:0;border-bottom-right-radius:0;border-bottom-left-radius:0}a.list-group-item,button.list-group-item{color:#555555}a.list-group-item .list-group-item-heading,button.list-group-item .list-group-item-heading{color:#333333}a.list-group-item:hover,button.list-group-item:hover,a.list-group-item:focus,button.list-group-item:focus{text-decoration:none;color:#555555;background-color:#f5f5f5}button.list-group-item{width:100%;text-align:left}.list-group-item.disabled,.list-group-item.disabled:hover,.list-group-item.disabled:focus{background-color:#eeeeee;color:#999999;cursor:not-allowed}.list-group-item.disabled .list-group-item-heading,.list-group-item.disabled:hover .list-group-item-heading,.list-group-item.disabled:focus .list-group-item-heading{color:inherit}.list-group-item.disabled .list-group-item-text,.list-group-item.disabled:hover .list-group-item-text,.list-group-item.disabled:focus .list-group-item-text{color:#999999}.list-group-item.active,.list-group-item.active:hover,.list-group-item.active:focus{z-index:2;color:#ffffff;background-color:#008cba;border-color:#008cba}.list-group-item.active .list-group-item-heading,.list-group-item.active:hover .list-group-item-heading,.list-group-item.active:focus .list-group-item-heading,.list-group-item.active .list-group-item-heading>small,.list-group-item.active:hover .list-group-item-heading>small,.list-group-item.active:focus .list-group-item-heading>small,.list-group-item.active .list-group-item-heading>.small,.list-group-item.active:hover .list-group-item-heading>.small,.list-group-item.active:focus .list-group-item-heading>.small{color:inherit}.list-group-item.active .list-group-item-text,.list-group-item.active:hover .list-group-item-text,.list-group-item.active:focus .list-group-item-text{color:#87e1ff}.list-group-item-success{color:#43ac6a;background-color:#dff0d8}a.list-group-item-success,button.list-group-item-success{color:#43ac6a}a.list-group-item-success .list-group-item-heading,button.list-group-item-success .list-group-item-heading{color:inherit}a.list-group-item-success:hover,button.list-group-item-success:hover,a.list-group-item-success:focus,button.list-group-item-success:focus{color:#43ac6a;background-color:#d0e9c6}a.list-group-item-success.active,button.list-group-item-success.active,a.list-group-item-success.active:hover,button.list-group-item-success.active:hover,a.list-group-item-success.active:focus,button.list-group-item-success.active:focus{color:#fff;background-color:#43ac6a;border-color:#43ac6a}.list-group-item-info{color:#5bc0de;background-color:#d9edf7}a.list-group-item-info,button.list-group-item-info{color:#5bc0de}a.list-group-item-info .list-group-item-heading,button.list-group-item-info .list-group-item-heading{color:inherit}a.list-group-item-info:hover,button.list-group-item-info:hover,a.list-group-item-info:focus,button.list-group-item-info:focus{color:#5bc0de;background-color:#c4e3f3}a.list-group-item-info.active,button.list-group-item-info.active,a.list-group-item-info.active:hover,button.list-group-item-info.active:hover,a.list-group-item-info.active:focus,button.list-group-item-info.active:focus{color:#fff;background-color:#5bc0de;border-color:#5bc0de}.list-group-item-warning{color:#e99002;background-color:#fcf8e3}a.list-group-item-warning,button.list-group-item-warning{color:#e99002}a.list-group-item-warning .list-group-item-heading,button.list-group-item-warning .list-group-item-heading{color:inherit}a.list-group-item-warning:hover,button.list-group-item-warning:hover,a.list-group-item-warning:focus,button.list-group-item-warning:focus{color:#e99002;background-color:#faf2cc}a.list-group-item-warning.active,button.list-group-item-warning.active,a.list-group-item-warning.active:hover,button.list-group-item-warning.active:hover,a.list-group-item-warning.active:focus,button.list-group-item-warning.active:focus{color:#fff;background-color:#e99002;border-color:#e99002}.list-group-item-danger{color:#f04124;background-color:#f2dede}a.list-group-item-danger,button.list-group-item-danger{color:#f04124}a.list-group-item-danger .list-group-item-heading,button.list-group-item-danger .list-group-item-heading{color:inherit}a.list-group-item-danger:hover,button.list-group-item-danger:hover,a.list-group-item-danger:focus,button.list-group-item-danger:focus{color:#f04124;background-color:#ebcccc}a.list-group-item-danger.active,button.list-group-item-danger.active,a.list-group-item-danger.active:hover,button.list-group-item-danger.active:hover,a.list-group-item-danger.active:focus,button.list-group-item-danger.active:focus{color:#fff;background-color:#f04124;border-color:#f04124}.list-group-item-heading{margin-top:0;margin-bottom:5px}.list-group-item-text{margin-bottom:0;line-height:1.3}.panel{margin-bottom:21px;background-color:#ffffff;border:1px solid transparent;border-radius:0;-webkit-box-shadow:0 1px 1px rgba(0,0,0,0.05);box-shadow:0 1px 1px rgba(0,0,0,0.05)}.panel-body{padding:15px}.panel-heading{padding:10px 15px;border-bottom:1px solid transparent;border-top-right-radius:-1;border-top-left-radius:-1}.panel-heading>.dropdown .dropdown-toggle{color:inherit}.panel-title{margin-top:0;margin-bottom:0;font-size:17px;color:inherit}.panel-title>a,.panel-title>small,.panel-title>.small,.panel-title>small>a,.panel-title>.small>a{color:inherit}.panel-footer{padding:10px 15px;background-color:#f5f5f5;border-top:1px solid #dddddd;border-bottom-right-radius:-1;border-bottom-left-radius:-1}.panel>.list-group,.panel>.panel-collapse>.list-group{margin-bottom:0}.panel>.list-group .list-group-item,.panel>.panel-collapse>.list-group .list-group-item{border-width:1px 0;border-radius:0}.panel>.list-group:first-child .list-group-item:first-child,.panel>.panel-collapse>.list-group:first-child .list-group-item:first-child{border-top:0;border-top-right-radius:-1;border-top-left-radius:-1}.panel>.list-group:last-child .list-group-item:last-child,.panel>.panel-collapse>.list-group:last-child .list-group-item:last-child{border-bottom:0;border-bottom-right-radius:-1;border-bottom-left-radius:-1}.panel>.panel-heading+.panel-collapse>.list-group .list-group-item:first-child{border-top-right-radius:0;border-top-left-radius:0}.panel-heading+.list-group .list-group-item:first-child{border-top-width:0}.list-group+.panel-footer{border-top-width:0}.panel>.table,.panel>.table-responsive>.table,.panel>.panel-collapse>.table{margin-bottom:0}.panel>.table caption,.panel>.table-responsive>.table caption,.panel>.panel-collapse>.table caption{padding-left:15px;padding-right:15px}.panel>.table:first-child,.panel>.table-responsive:first-child>.table:first-child{border-top-right-radius:-1;border-top-left-radius:-1}.panel>.table:first-child>thead:first-child>tr:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child{border-top-left-radius:-1;border-top-right-radius:-1}.panel>.table:first-child>thead:first-child>tr:first-child td:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child td:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child td:first-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child td:first-child,.panel>.table:first-child>thead:first-child>tr:first-child th:first-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child th:first-child,.panel>.table:first-child>tbody:first-child>tr:first-child th:first-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child th:first-child{border-top-left-radius:-1}.panel>.table:first-child>thead:first-child>tr:first-child td:last-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child td:last-child,.panel>.table:first-child>tbody:first-child>tr:first-child td:last-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child td:last-child,.panel>.table:first-child>thead:first-child>tr:first-child th:last-child,.panel>.table-responsive:first-child>.table:first-child>thead:first-child>tr:first-child th:last-child,.panel>.table:first-child>tbody:first-child>tr:first-child th:last-child,.panel>.table-responsive:first-child>.table:first-child>tbody:first-child>tr:first-child th:last-child{border-top-right-radius:-1}.panel>.table:last-child,.panel>.table-responsive:last-child>.table:last-child{border-bottom-right-radius:-1;border-bottom-left-radius:-1}.panel>.table:last-child>tbody:last-child>tr:last-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child{border-bottom-left-radius:-1;border-bottom-right-radius:-1}.panel>.table:last-child>tbody:last-child>tr:last-child td:first-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child td:first-child,.panel>.table:last-child>tfoot:last-child>tr:last-child td:first-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child td:first-child,.panel>.table:last-child>tbody:last-child>tr:last-child th:first-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child th:first-child,.panel>.table:last-child>tfoot:last-child>tr:last-child th:first-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child th:first-child{border-bottom-left-radius:-1}.panel>.table:last-child>tbody:last-child>tr:last-child td:last-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child td:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child td:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child td:last-child,.panel>.table:last-child>tbody:last-child>tr:last-child th:last-child,.panel>.table-responsive:last-child>.table:last-child>tbody:last-child>tr:last-child th:last-child,.panel>.table:last-child>tfoot:last-child>tr:last-child th:last-child,.panel>.table-responsive:last-child>.table:last-child>tfoot:last-child>tr:last-child th:last-child{border-bottom-right-radius:-1}.panel>.panel-body+.table,.panel>.panel-body+.table-responsive,.panel>.table+.panel-body,.panel>.table-responsive+.panel-body{border-top:1px solid #dddddd}.panel>.table>tbody:first-child>tr:first-child th,.panel>.table>tbody:first-child>tr:first-child td{border-top:0}.panel>.table-bordered,.panel>.table-responsive>.table-bordered{border:0}.panel>.table-bordered>thead>tr>th:first-child,.panel>.table-responsive>.table-bordered>thead>tr>th:first-child,.panel>.table-bordered>tbody>tr>th:first-child,.panel>.table-responsive>.table-bordered>tbody>tr>th:first-child,.panel>.table-bordered>tfoot>tr>th:first-child,.panel>.table-responsive>.table-bordered>tfoot>tr>th:first-child,.panel>.table-bordered>thead>tr>td:first-child,.panel>.table-responsive>.table-bordered>thead>tr>td:first-child,.panel>.table-bordered>tbody>tr>td:first-child,.panel>.table-responsive>.table-bordered>tbody>tr>td:first-child,.panel>.table-bordered>tfoot>tr>td:first-child,.panel>.table-responsive>.table-bordered>tfoot>tr>td:first-child{border-left:0}.panel>.table-bordered>thead>tr>th:last-child,.panel>.table-responsive>.table-bordered>thead>tr>th:last-child,.panel>.table-bordered>tbody>tr>th:last-child,.panel>.table-responsive>.table-bordered>tbody>tr>th:last-child,.panel>.table-bordered>tfoot>tr>th:last-child,.panel>.table-responsive>.table-bordered>tfoot>tr>th:last-child,.panel>.table-bordered>thead>tr>td:last-child,.panel>.table-responsive>.table-bordered>thead>tr>td:last-child,.panel>.table-bordered>tbody>tr>td:last-child,.panel>.table-responsive>.table-bordered>tbody>tr>td:last-child,.panel>.table-bordered>tfoot>tr>td:last-child,.panel>.table-responsive>.table-bordered>tfoot>tr>td:last-child{border-right:0}.panel>.table-bordered>thead>tr:first-child>td,.panel>.table-responsive>.table-bordered>thead>tr:first-child>td,.panel>.table-bordered>tbody>tr:first-child>td,.panel>.table-responsive>.table-bordered>tbody>tr:first-child>td,.panel>.table-bordered>thead>tr:first-child>th,.panel>.table-responsive>.table-bordered>thead>tr:first-child>th,.panel>.table-bordered>tbody>tr:first-child>th,.panel>.table-responsive>.table-bordered>tbody>tr:first-child>th{border-bottom:0}.panel>.table-bordered>tbody>tr:last-child>td,.panel>.table-responsive>.table-bordered>tbody>tr:last-child>td,.panel>.table-bordered>tfoot>tr:last-child>td,.panel>.table-responsive>.table-bordered>tfoot>tr:last-child>td,.panel>.table-bordered>tbody>tr:last-child>th,.panel>.table-responsive>.table-bordered>tbody>tr:last-child>th,.panel>.table-bordered>tfoot>tr:last-child>th,.panel>.table-responsive>.table-bordered>tfoot>tr:last-child>th{border-bottom:0}.panel>.table-responsive{border:0;margin-bottom:0}.panel-group{margin-bottom:21px}.panel-group .panel{margin-bottom:0;border-radius:0}.panel-group .panel+.panel{margin-top:5px}.panel-group .panel-heading{border-bottom:0}.panel-group .panel-heading+.panel-collapse>.panel-body,.panel-group .panel-heading+.panel-collapse>.list-group{border-top:1px solid #dddddd}.panel-group .panel-footer{border-top:0}.panel-group .panel-footer+.panel-collapse .panel-body{border-bottom:1px solid #dddddd}.panel-default{border-color:#dddddd}.panel-default>.panel-heading{color:#333333;background-color:#f5f5f5;border-color:#dddddd}.panel-default>.panel-heading+.panel-collapse>.panel-body{border-top-color:#dddddd}.panel-default>.panel-heading .badge{color:#f5f5f5;background-color:#333333}.panel-default>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#dddddd}.panel-primary{border-color:#008cba}.panel-primary>.panel-heading{color:#ffffff;background-color:#008cba;border-color:#008cba}.panel-primary>.panel-heading+.panel-collapse>.panel-body{border-top-color:#008cba}.panel-primary>.panel-heading .badge{color:#008cba;background-color:#ffffff}.panel-primary>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#008cba}.panel-success{border-color:#3c9a5f}.panel-success>.panel-heading{color:#ffffff;background-color:#43ac6a;border-color:#3c9a5f}.panel-success>.panel-heading+.panel-collapse>.panel-body{border-top-color:#3c9a5f}.panel-success>.panel-heading .badge{color:#43ac6a;background-color:#ffffff}.panel-success>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#3c9a5f}.panel-info{border-color:#3db5d8}.panel-info>.panel-heading{color:#ffffff;background-color:#5bc0de;border-color:#3db5d8}.panel-info>.panel-heading+.panel-collapse>.panel-body{border-top-color:#3db5d8}.panel-info>.panel-heading .badge{color:#5bc0de;background-color:#ffffff}.panel-info>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#3db5d8}.panel-warning{border-color:#d08002}.panel-warning>.panel-heading{color:#ffffff;background-color:#e99002;border-color:#d08002}.panel-warning>.panel-heading+.panel-collapse>.panel-body{border-top-color:#d08002}.panel-warning>.panel-heading .badge{color:#e99002;background-color:#ffffff}.panel-warning>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#d08002}.panel-danger{border-color:#ea2f10}.panel-danger>.panel-heading{color:#ffffff;background-color:#f04124;border-color:#ea2f10}.panel-danger>.panel-heading+.panel-collapse>.panel-body{border-top-color:#ea2f10}.panel-danger>.panel-heading .badge{color:#f04124;background-color:#ffffff}.panel-danger>.panel-footer+.panel-collapse>.panel-body{border-bottom-color:#ea2f10}.embed-responsive{position:relative;display:block;height:0;padding:0;overflow:hidden}.embed-responsive .embed-responsive-item,.embed-responsive iframe,.embed-responsive embed,.embed-responsive object,.embed-responsive video{position:absolute;top:0;left:0;bottom:0;height:100%;width:100%;border:0}.embed-responsive-16by9{padding-bottom:56.25%}.embed-responsive-4by3{padding-bottom:75%}.well{min-height:20px;padding:19px;margin-bottom:20px;background-color:#fafafa;border:1px solid #e8e8e8;border-radius:0;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.05);box-shadow:inset 0 1px 1px rgba(0,0,0,0.05)}.well blockquote{border-color:#ddd;border-color:rgba(0,0,0,0.15)}.well-lg{padding:24px;border-radius:0}.well-sm{padding:9px;border-radius:0}.close{float:right;font-size:22.5px;font-weight:bold;line-height:1;color:#ffffff;text-shadow:0 1px 0 #ffffff;opacity:0.2;filter:alpha(opacity=20)}.close:hover,.close:focus{color:#ffffff;text-decoration:none;cursor:pointer;opacity:0.5;filter:alpha(opacity=50)}button.close{padding:0;cursor:pointer;background:transparent;border:0;-webkit-appearance:none}.modal-open{overflow:hidden}.modal{display:none;overflow:hidden;position:fixed;top:0;right:0;bottom:0;left:0;z-index:1050;-webkit-overflow-scrolling:touch;outline:0}.modal.fade .modal-dialog{-webkit-transform:translate(0, -25%);-ms-transform:translate(0, -25%);-o-transform:translate(0, -25%);transform:translate(0, -25%);-webkit-transition:-webkit-transform .3s ease-out;-o-transition:-o-transform .3s ease-out;transition:transform .3s ease-out}.modal.in .modal-dialog{-webkit-transform:translate(0, 0);-ms-transform:translate(0, 0);-o-transform:translate(0, 0);transform:translate(0, 0)}.modal-open .modal{overflow-x:hidden;overflow-y:auto}.modal-dialog{position:relative;width:auto;margin:10px}.modal-content{position:relative;background-color:#ffffff;border:1px solid #999999;border:1px solid rgba(0,0,0,0.2);border-radius:0;-webkit-box-shadow:0 3px 9px rgba(0,0,0,0.5);box-shadow:0 3px 9px rgba(0,0,0,0.5);-webkit-background-clip:padding-box;background-clip:padding-box;outline:0}.modal-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1040;background-color:#000000}.modal-backdrop.fade{opacity:0;filter:alpha(opacity=0)}.modal-backdrop.in{opacity:0.5;filter:alpha(opacity=50)}.modal-header{padding:15px;border-bottom:1px solid #e5e5e5}.modal-header .close{margin-top:-2px}.modal-title{margin:0;line-height:1.4}.modal-body{position:relative;padding:20px}.modal-footer{padding:20px;text-align:right;border-top:1px solid #e5e5e5}.modal-footer .btn+.btn{margin-left:5px;margin-bottom:0}.modal-footer .btn-group .btn+.btn{margin-left:-1px}.modal-footer .btn-block+.btn-block{margin-left:0}.modal-scrollbar-measure{position:absolute;top:-9999px;width:50px;height:50px;overflow:scroll}@media (min-width:768px){.modal-dialog{width:600px;margin:30px auto}.modal-content{-webkit-box-shadow:0 5px 15px rgba(0,0,0,0.5);box-shadow:0 5px 15px rgba(0,0,0,0.5)}.modal-sm{width:300px}}@media (min-width:992px){.modal-lg{width:900px}}.tooltip{position:absolute;z-index:1070;display:block;font-family:"Open Sans","Helvetica Neue",Helvetica,Arial,sans-serif;font-style:normal;font-weight:normal;letter-spacing:normal;line-break:auto;line-height:1.4;text-align:left;text-align:start;text-decoration:none;text-shadow:none;text-transform:none;white-space:normal;word-break:normal;word-spacing:normal;word-wrap:normal;font-size:12px;opacity:0;filter:alpha(opacity=0)}.tooltip.in{opacity:0.9;filter:alpha(opacity=90)}.tooltip.top{margin-top:-3px;padding:5px 0}.tooltip.right{margin-left:3px;padding:0 5px}.tooltip.bottom{margin-top:3px;padding:5px 0}.tooltip.left{margin-left:-3px;padding:0 5px}.tooltip-inner{max-width:200px;padding:3px 8px;color:#ffffff;text-align:center;background-color:#333333;border-radius:0}.tooltip-arrow{position:absolute;width:0;height:0;border-color:transparent;border-style:solid}.tooltip.top .tooltip-arrow{bottom:0;left:50%;margin-left:-5px;border-width:5px 5px 0;border-top-color:#333333}.tooltip.top-left .tooltip-arrow{bottom:0;right:5px;margin-bottom:-5px;border-width:5px 5px 0;border-top-color:#333333}.tooltip.top-right .tooltip-arrow{bottom:0;left:5px;margin-bottom:-5px;border-width:5px 5px 0;border-top-color:#333333}.tooltip.right .tooltip-arrow{top:50%;left:0;margin-top:-5px;border-width:5px 5px 5px 0;border-right-color:#333333}.tooltip.left .tooltip-arrow{top:50%;right:0;margin-top:-5px;border-width:5px 0 5px 5px;border-left-color:#333333}.tooltip.bottom .tooltip-arrow{top:0;left:50%;margin-left:-5px;border-width:0 5px 5px;border-bottom-color:#333333}.tooltip.bottom-left .tooltip-arrow{top:0;right:5px;margin-top:-5px;border-width:0 5px 5px;border-bottom-color:#333333}.tooltip.bottom-right .tooltip-arrow{top:0;left:5px;margin-top:-5px;border-width:0 5px 5px;border-bottom-color:#333333}.popover{position:absolute;top:0;left:0;z-index:1060;display:none;max-width:276px;padding:1px;font-family:"Open Sans","Helvetica Neue",Helvetica,Arial,sans-serif;font-style:normal;font-weight:normal;letter-spacing:normal;line-break:auto;line-height:1.4;text-align:left;text-align:start;text-decoration:none;text-shadow:none;text-transform:none;white-space:normal;word-break:normal;word-spacing:normal;word-wrap:normal;font-size:15px;background-color:#333333;-webkit-background-clip:padding-box;background-clip:padding-box;border:1px solid #333333;border:1px solid transparent;border-radius:0;-webkit-box-shadow:0 5px 10px rgba(0,0,0,0.2);box-shadow:0 5px 10px rgba(0,0,0,0.2)}.popover.top{margin-top:-10px}.popover.right{margin-left:10px}.popover.bottom{margin-top:10px}.popover.left{margin-left:-10px}.popover-title{margin:0;padding:8px 14px;font-size:15px;background-color:#333333;border-bottom:1px solid #262626;border-radius:-1 -1 0 0}.popover-content{padding:9px 14px}.popover>.arrow,.popover>.arrow:after{position:absolute;display:block;width:0;height:0;border-color:transparent;border-style:solid}.popover>.arrow{border-width:11px}.popover>.arrow:after{border-width:10px;content:""}.popover.top>.arrow{left:50%;margin-left:-11px;border-bottom-width:0;border-top-color:#000000;border-top-color:rgba(0,0,0,0.05);bottom:-11px}.popover.top>.arrow:after{content:" ";bottom:1px;margin-left:-10px;border-bottom-width:0;border-top-color:#333333}.popover.right>.arrow{top:50%;left:-11px;margin-top:-11px;border-left-width:0;border-right-color:#000000;border-right-color:rgba(0,0,0,0.05)}.popover.right>.arrow:after{content:" ";left:1px;bottom:-10px;border-left-width:0;border-right-color:#333333}.popover.bottom>.arrow{left:50%;margin-left:-11px;border-top-width:0;border-bottom-color:#000000;border-bottom-color:rgba(0,0,0,0.05);top:-11px}.popover.bottom>.arrow:after{content:" ";top:1px;margin-left:-10px;border-top-width:0;border-bottom-color:#333333}.popover.left>.arrow{top:50%;right:-11px;margin-top:-11px;border-right-width:0;border-left-color:#000000;border-left-color:rgba(0,0,0,0.05)}.popover.left>.arrow:after{content:" ";right:1px;border-right-width:0;border-left-color:#333333;bottom:-10px}.carousel{position:relative}.carousel-inner{position:relative;overflow:hidden;width:100%}.carousel-inner>.item{display:none;position:relative;-webkit-transition:.6s ease-in-out left;-o-transition:.6s ease-in-out left;transition:.6s ease-in-out left}.carousel-inner>.item>img,.carousel-inner>.item>a>img{line-height:1}@media all and (transform-3d),(-webkit-transform-3d){.carousel-inner>.item{-webkit-transition:-webkit-transform .6s ease-in-out;-o-transition:-o-transform .6s ease-in-out;transition:transform .6s ease-in-out;-webkit-backface-visibility:hidden;backface-visibility:hidden;-webkit-perspective:1000px;perspective:1000px}.carousel-inner>.item.next,.carousel-inner>.item.active.right{-webkit-transform:translate3d(100%, 0, 0);transform:translate3d(100%, 0, 0);left:0}.carousel-inner>.item.prev,.carousel-inner>.item.active.left{-webkit-transform:translate3d(-100%, 0, 0);transform:translate3d(-100%, 0, 0);left:0}.carousel-inner>.item.next.left,.carousel-inner>.item.prev.right,.carousel-inner>.item.active{-webkit-transform:translate3d(0, 0, 0);transform:translate3d(0, 0, 0);left:0}}.carousel-inner>.active,.carousel-inner>.next,.carousel-inner>.prev{display:block}.carousel-inner>.active{left:0}.carousel-inner>.next,.carousel-inner>.prev{position:absolute;top:0;width:100%}.carousel-inner>.next{left:100%}.carousel-inner>.prev{left:-100%}.carousel-inner>.next.left,.carousel-inner>.prev.right{left:0}.carousel-inner>.active.left{left:-100%}.carousel-inner>.active.right{left:100%}.carousel-control{position:absolute;top:0;left:0;bottom:0;width:15%;opacity:0.5;filter:alpha(opacity=50);font-size:20px;color:#ffffff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,0.6);background-color:rgba(0,0,0,0)}.carousel-control.left{background-image:-webkit-linear-gradient(left, rgba(0,0,0,0.5) 0, rgba(0,0,0,0.0001) 100%);background-image:-o-linear-gradient(left, rgba(0,0,0,0.5) 0, rgba(0,0,0,0.0001) 100%);background-image:-webkit-gradient(linear, left top, right top, from(rgba(0,0,0,0.5)), to(rgba(0,0,0,0.0001)));background-image:linear-gradient(to right, rgba(0,0,0,0.5) 0, rgba(0,0,0,0.0001) 100%);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1)}.carousel-control.right{left:auto;right:0;background-image:-webkit-linear-gradient(left, rgba(0,0,0,0.0001) 0, rgba(0,0,0,0.5) 100%);background-image:-o-linear-gradient(left, rgba(0,0,0,0.0001) 0, rgba(0,0,0,0.5) 100%);background-image:-webkit-gradient(linear, left top, right top, from(rgba(0,0,0,0.0001)), to(rgba(0,0,0,0.5)));background-image:linear-gradient(to right, rgba(0,0,0,0.0001) 0, rgba(0,0,0,0.5) 100%);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1)}.carousel-control:hover,.carousel-control:focus{outline:0;color:#ffffff;text-decoration:none;opacity:0.9;filter:alpha(opacity=90)}.carousel-control .icon-prev,.carousel-control .icon-next,.carousel-control .glyphicon-chevron-left,.carousel-control .glyphicon-chevron-right{position:absolute;top:50%;margin-top:-10px;z-index:5;display:inline-block}.carousel-control .icon-prev,.carousel-control .glyphicon-chevron-left{left:50%;margin-left:-10px}.carousel-control .icon-next,.carousel-control .glyphicon-chevron-right{right:50%;margin-right:-10px}.carousel-control .icon-prev,.carousel-control .icon-next{width:20px;height:20px;line-height:1;font-family:serif}.carousel-control .icon-prev:before{content:'\2039'}.carousel-control .icon-next:before{content:'\203a'}.carousel-indicators{position:absolute;bottom:10px;left:50%;z-index:15;width:60%;margin-left:-30%;padding-left:0;list-style:none;text-align:center}.carousel-indicators li{display:inline-block;width:10px;height:10px;margin:1px;text-indent:-999px;border:1px solid #ffffff;border-radius:10px;cursor:pointer;background-color:#000 \9;background-color:rgba(0,0,0,0)}.carousel-indicators .active{margin:0;width:12px;height:12px;background-color:#ffffff}.carousel-caption{position:absolute;left:15%;right:15%;bottom:20px;z-index:10;padding-top:20px;padding-bottom:20px;color:#ffffff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,0.6)}.carousel-caption .btn{text-shadow:none}@media screen and (min-width:768px){.carousel-control .glyphicon-chevron-left,.carousel-control .glyphicon-chevron-right,.carousel-control .icon-prev,.carousel-control .icon-next{width:30px;height:30px;margin-top:-10px;font-size:30px}.carousel-control .glyphicon-chevron-left,.carousel-control .icon-prev{margin-left:-10px}.carousel-control .glyphicon-chevron-right,.carousel-control .icon-next{margin-right:-10px}.carousel-caption{left:20%;right:20%;padding-bottom:30px}.carousel-indicators{bottom:20px}}.clearfix:before,.clearfix:after,.dl-horizontal dd:before,.dl-horizontal dd:after,.container:before,.container:after,.container-fluid:before,.container-fluid:after,.row:before,.row:after,.form-horizontal .form-group:before,.form-horizontal .form-group:after,.btn-toolbar:before,.btn-toolbar:after,.btn-group-vertical>.btn-group:before,.btn-group-vertical>.btn-group:after,.nav:before,.nav:after,.navbar:before,.navbar:after,.navbar-header:before,.navbar-header:after,.navbar-collapse:before,.navbar-collapse:after,.pager:before,.pager:after,.panel-body:before,.panel-body:after,.modal-header:before,.modal-header:after,.modal-footer:before,.modal-footer:after{content:" ";display:table}.clearfix:after,.dl-horizontal dd:after,.container:after,.container-fluid:after,.row:after,.form-horizontal .form-group:after,.btn-toolbar:after,.btn-group-vertical>.btn-group:after,.nav:after,.navbar:after,.navbar-header:after,.navbar-collapse:after,.pager:after,.panel-body:after,.modal-header:after,.modal-footer:after{clear:both}.center-block{display:block;margin-left:auto;margin-right:auto}.pull-right{float:right !important}.pull-left{float:left !important}.hide{display:none !important}.show{display:block !important}.invisible{visibility:hidden}.text-hide{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0}.hidden{display:none !important}.affix{position:fixed}@-ms-viewport{width:device-width}.visible-xs,.visible-sm,.visible-md,.visible-lg{display:none !important}.visible-xs-block,.visible-xs-inline,.visible-xs-inline-block,.visible-sm-block,.visible-sm-inline,.visible-sm-inline-block,.visible-md-block,.visible-md-inline,.visible-md-inline-block,.visible-lg-block,.visible-lg-inline,.visible-lg-inline-block{display:none !important}@media (max-width:767px){.visible-xs{display:block !important}table.visible-xs{display:table !important}tr.visible-xs{display:table-row !important}th.visible-xs,td.visible-xs{display:table-cell !important}}@media (max-width:767px){.visible-xs-block{display:block !important}}@media (max-width:767px){.visible-xs-inline{display:inline !important}}@media (max-width:767px){.visible-xs-inline-block{display:inline-block !important}}@media (min-width:768px) and (max-width:991px){.visible-sm{display:block !important}table.visible-sm{display:table !important}tr.visible-sm{display:table-row !important}th.visible-sm,td.visible-sm{display:table-cell !important}}@media (min-width:768px) and (max-width:991px){.visible-sm-block{display:block !important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline{display:inline !important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline-block{display:inline-block !important}}@media (min-width:992px) and (max-width:1199px){.visible-md{display:block !important}table.visible-md{display:table !important}tr.visible-md{display:table-row !important}th.visible-md,td.visible-md{display:table-cell !important}}@media (min-width:992px) and (max-width:1199px){.visible-md-block{display:block !important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline{display:inline !important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline-block{display:inline-block !important}}@media (min-width:1200px){.visible-lg{display:block !important}table.visible-lg{display:table !important}tr.visible-lg{display:table-row !important}th.visible-lg,td.visible-lg{display:table-cell !important}}@media (min-width:1200px){.visible-lg-block{display:block !important}}@media (min-width:1200px){.visible-lg-inline{display:inline !important}}@media (min-width:1200px){.visible-lg-inline-block{display:inline-block !important}}@media (max-width:767px){.hidden-xs{display:none !important}}@media (min-width:768px) and (max-width:991px){.hidden-sm{display:none !important}}@media (min-width:992px) and (max-width:1199px){.hidden-md{display:none !important}}@media (min-width:1200px){.hidden-lg{display:none !important}}.visible-print{display:none !important}@media print{.visible-print{display:block !important}table.visible-print{display:table !important}tr.visible-print{display:table-row !important}th.visible-print,td.visible-print{display:table-cell !important}}.visible-print-block{display:none !important}@media print{.visible-print-block{display:block !important}}.visible-print-inline{display:none !important}@media print{.visible-print-inline{display:inline !important}}.visible-print-inline-block{display:none !important}@media print{.visible-print-inline-block{display:inline-block !important}}@media print{.hidden-print{display:none !important}}.navbar{border:none;font-size:13px;font-weight:300}.navbar .navbar-toggle:hover .icon-bar{background-color:#b3b3b3}.navbar-collapse{border-top-color:rgba(0,0,0,0.2);-webkit-box-shadow:none;box-shadow:none}.navbar .btn{padding-top:6px;padding-bottom:6px}.navbar-form{margin-top:7px;margin-bottom:5px}.navbar-form .form-control{height:auto;padding:4px 6px}.navbar-text{margin:12px 15px;line-height:21px}.navbar .dropdown-menu{border:none}.navbar .dropdown-menu>li>a,.navbar .dropdown-menu>li>a:focus{background-color:transparent;font-size:13px;font-weight:300}.navbar .dropdown-header{color:rgba(255,255,255,0.5)}.navbar-default .dropdown-menu{background-color:#333333}.navbar-default .dropdown-menu>li>a,.navbar-default .dropdown-menu>li>a:focus{color:#ffffff}.navbar-default .dropdown-menu>li>a:hover,.navbar-default .dropdown-menu>.active>a,.navbar-default .dropdown-menu>.active>a:hover{background-color:#272727}.navbar-inverse .dropdown-menu{background-color:#008cba}.navbar-inverse .dropdown-menu>li>a,.navbar-inverse .dropdown-menu>li>a:focus{color:#ffffff}.navbar-inverse .dropdown-menu>li>a:hover,.navbar-inverse .dropdown-menu>.active>a,.navbar-inverse .dropdown-menu>.active>a:hover{background-color:#006687}.btn{padding:8px 12px}.btn-lg{padding:16px 20px}.btn-sm{padding:8px 12px}.btn-xs{padding:4px 6px}.btn-group .btn~.dropdown-toggle{padding-left:16px;padding-right:16px}.btn-group .dropdown-menu{border-top-width:0}.btn-group.dropup .dropdown-menu{border-top-width:1px;border-bottom-width:0;margin-bottom:0}.btn-group .dropdown-toggle.btn-default~.dropdown-menu{background-color:#e7e7e7;border-color:#cccccc}.btn-group .dropdown-toggle.btn-default~.dropdown-menu>li>a{color:#333333}.btn-group .dropdown-toggle.btn-default~.dropdown-menu>li>a:hover{background-color:#d3d3d3}.btn-group .dropdown-toggle.btn-primary~.dropdown-menu{background-color:#008cba;border-color:#0079a1}.btn-group .dropdown-toggle.btn-primary~.dropdown-menu>li>a{color:#ffffff}.btn-group .dropdown-toggle.btn-primary~.dropdown-menu>li>a:hover{background-color:#006d91}.btn-group .dropdown-toggle.btn-success~.dropdown-menu{background-color:#43ac6a;border-color:#3c9a5f}.btn-group .dropdown-toggle.btn-success~.dropdown-menu>li>a{color:#ffffff}.btn-group .dropdown-toggle.btn-success~.dropdown-menu>li>a:hover{background-color:#388f58}.btn-group .dropdown-toggle.btn-info~.dropdown-menu{background-color:#5bc0de;border-color:#46b8da}.btn-group .dropdown-toggle.btn-info~.dropdown-menu>li>a{color:#ffffff}.btn-group .dropdown-toggle.btn-info~.dropdown-menu>li>a:hover{background-color:#39b3d7}.btn-group .dropdown-toggle.btn-warning~.dropdown-menu{background-color:#e99002;border-color:#d08002}.btn-group .dropdown-toggle.btn-warning~.dropdown-menu>li>a{color:#ffffff}.btn-group .dropdown-toggle.btn-warning~.dropdown-menu>li>a:hover{background-color:#c17702}.btn-group .dropdown-toggle.btn-danger~.dropdown-menu{background-color:#f04124;border-color:#ea2f10}.btn-group .dropdown-toggle.btn-danger~.dropdown-menu>li>a{color:#ffffff}.btn-group .dropdown-toggle.btn-danger~.dropdown-menu>li>a:hover{background-color:#dc2c0f}.lead{color:#6f6f6f}cite{font-style:italic}blockquote{border-left-width:1px;color:#6f6f6f}blockquote.pull-right{border-right-width:1px}blockquote small{font-size:12px;font-weight:300}table{font-size:12px}label,.control-label,.help-block,.checkbox,.radio{font-size:12px;font-weight:normal}input[type="radio"],input[type="checkbox"]{margin-top:1px}.nav .open>a,.nav .open>a:hover,.nav .open>a:focus{border-color:transparent}.nav-tabs>li>a{background-color:#e7e7e7;color:#222222}.nav-tabs .caret{border-top-color:#222222;border-bottom-color:#222222}.nav-pills{font-weight:300}.breadcrumb{border:1px solid #dddddd;border-radius:3px;font-size:10px;font-weight:300;text-transform:uppercase}.pagination{font-size:12px;font-weight:300;color:#999999}.pagination>li>a,.pagination>li>span{margin-left:4px;color:#999999}.pagination>.active>a,.pagination>.active>span{color:#fff}.pagination>li>a,.pagination>li:first-child>a,.pagination>li:last-child>a,.pagination>li>span,.pagination>li:first-child>span,.pagination>li:last-child>span{border-radius:3px}.pagination-lg>li>a,.pagination-lg>li>span{padding-left:22px;padding-right:22px}.pagination-sm>li>a,.pagination-sm>li>span{padding:0 5px}.pager{font-size:12px;font-weight:300;color:#999999}.list-group{font-size:12px;font-weight:300}.close{opacity:0.4;text-decoration:none;text-shadow:none}.close:hover,.close:focus{opacity:1}.alert{font-size:12px;font-weight:300}.alert .alert-link{font-weight:normal;color:#fff;text-decoration:underline}.label{padding-left:1em;padding-right:1em;border-radius:0;font-weight:300}.label-default{background-color:#e7e7e7;color:#333333}.badge{font-weight:300}.progress{height:22px;padding:2px;background-color:#f6f6f6;border:1px solid #ccc;-webkit-box-shadow:none;box-shadow:none}.dropdown-menu{padding:0;margin-top:0;font-size:12px}.dropdown-menu>li>a{padding:12px 15px}.dropdown-header{padding-left:15px;padding-right:15px;font-size:9px;text-transform:uppercase}.popover{color:#fff;font-size:12px;font-weight:300}.panel-heading,.panel-footer{border-top-right-radius:0;border-top-left-radius:0}.panel-default .close{color:#222222}.modal .close{color:#222222}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.eot b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.eot
new file mode 100644
index 0000000..b93a495
Binary files /dev/null and b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.eot differ
diff --git a/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.svg b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.svg
new file mode 100644
index 0000000..94fb549
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.svg
@@ -0,0 +1,288 @@
+
+
+
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.ttf b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.ttf
new file mode 100644
index 0000000..1413fc6
Binary files /dev/null and b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.ttf differ
diff --git a/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.woff b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.woff
new file mode 100644
index 0000000..9e61285
Binary files /dev/null and b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.woff differ
diff --git a/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.woff2 b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.woff2
new file mode 100644
index 0000000..64539b5
Binary files /dev/null and b/src/LanBackup.WebApp/ClientApp/app/bootswatch/fonts/glyphicons-halflings-regular.woff2 differ
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.css b/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.css
new file mode 100644
index 0000000..48b2036
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.css
@@ -0,0 +1,73 @@
+body {
+ padding-top: 50px;
+}
+
+
+/*override pagination styles*/
+.pagination {
+ margin: 10px 5px 5px 10px;
+}
+
+ .pagination > li {
+ cursor: pointer;
+ }
+
+
+
+/*switch adjust*/
+.switchAdjust {
+ margin-top: 2px;
+}
+
+
+.mypointerlink {
+ cursor: pointer;
+}
+
+.nounderline:hover {
+ text-decoration: none;
+}
+
+
+.progress {
+ margin: 0px;
+ padding: 0px;
+}
+
+.tabledesc {
+ padding-top: 5px;
+ padding-bottom: 15px;
+}
+
+
+
+
+.navbar-default {
+ z-index: 1030;
+}
+
+
+.anyLoadingTable {
+ float: left
+}
+.spinnercontainer{
+ float: none;
+ background-color: rgba(0, 0, 0, 0.10);
+ margin: 0;
+ height: 100%;
+ width: 100%;
+ text-align: center;
+ position: relative;
+}
+.myspinnerback {
+ height:100%;
+ min-height:100%;
+ width:100%;
+ float:left;
+ position:absolute;
+}
+
+.myspinner {
+ top:45%;
+ position:relative;
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.html b/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.html
new file mode 100644
index 0000000..60f40ef
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.html
@@ -0,0 +1,7 @@
+
+
+
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.ts b/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.ts
new file mode 100644
index 0000000..cd50162
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/app/app.component.ts
@@ -0,0 +1,52 @@
+import { Component, OnInit, ViewEncapsulation } from '@angular/core';
+import { AuthenticationService } from '../../services/authentication.service';
+import { Observable } from 'rxjs/Observable';
+
+import { MessageService, Messages } from '../../services/message.service';
+import { NotificationsService } from '../../services/notifications.service';
+import { LoggerService, Level } from '../../services/logger.service';
+import { AgentsService } from '../../services/agents.service';
+import { AppInsightsService } from 'ng2-appinsights';
+
+import { GlobalRef } from '../../shared/global/global-ref';
+
+@Component({
+ selector: 'app',
+ templateUrl: './app.component.html',
+ styleUrls: [
+ "../../../../node_modules/ng2-toasty/style-material.css"
+ , '../../bootswatch/css/bootstrap_yeti.min.css'
+ ,'./app.component.css' //THIS SHOULD BE LATS TO OVERRIDE OTHER GLOBAL STYLES
+ ],
+ encapsulation: ViewEncapsulation.None
+})
+export class AppComponent implements OnInit {
+
+
+ instrumentationEnabled: boolean;
+ instrumentationKey: string;
+
+ constructor(
+ private authService: AuthenticationService,
+ private _service: NotificationsService,
+ private messageService: MessageService,
+ private log: LoggerService,
+ private agentsService: AgentsService,
+ private appinsightsService: AppInsightsService,
+ private _global: GlobalRef
+ ) {
+ this.instrumentationEnabled = _global.nativeGlobal.clientSettings.instrumentationEnabled;
+ this.instrumentationKey = _global.nativeGlobal.clientSettings.instrumentationKey;
+ log.level = Level.DEBUG;
+ if (this.instrumentationEnabled) {
+ this.appinsightsService.Init({
+ instrumentationKey: this.instrumentationKey // key obtained from clientSettings
+ });
+ }
+ }
+
+ ngOnInit() {
+ this.agentsService.refreshAgents();
+ }
+
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.css b/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.css
new file mode 100644
index 0000000..5f28270
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.css
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.html b/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.html
new file mode 100644
index 0000000..ad33faa
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.html
@@ -0,0 +1,77 @@
+
+
+
+ LanBackup Agents activity board
+
+
+
+
+
+
+
+
+
+
+ Here you can monitor registered backup agents.
+
+
+
+
+
+
+
+
+
+ | Computer IP |
+ Config ID |
+ |
+ Status |
+ Progress |
+ Last Report |
+
+
+
+
+
+ | {{agent.ip}} |
+ {{agent.configurationId ? agent.configurationId : '---'}} |
+ {{agent.statusType}} |
+ {{agent.statusDescription}} |
+
+
+ {{agent.statusPercent}}%
+ |
+ {{agent.statusDateTime | date: 'hh:mm:ss dd/MM/yyyy'}} |
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.ts b/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.ts
new file mode 100644
index 0000000..ec38bd8
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/dashboard/dashboard.component.ts
@@ -0,0 +1,81 @@
+import { Component, OnInit, Input, ViewChild, ChangeDetectorRef } from '@angular/core';
+import { StatusReportInfo } from '../../model/StatusReportInfo';
+import { SaveResult } from '../../model/SaveResult';
+import { PaginatedList } from '../../model/PaginatedList';
+import { WebApiService } from '../../services/webapi.service';
+import { Observable } from 'rxjs/Observable';
+import { AuthenticationService } from '../../services/authentication.service';
+import { ModalComponent } from '../../shared/modal/modal.component';
+
+import { LoggerService } from '../../services/logger.service';
+import { ToastNotification, ToastType } from '../../services/notifications.service';
+import { MessageService, Messages } from '../../services/message.service';
+import { AgentsService } from '../../services/agents.service';
+import { Subscription } from 'rxjs/Subscription';
+
+
+@Component({
+ selector: 'dashboard',
+ templateUrl: './dashboard.component.html',
+ styleUrls: ['./dashboard.component.css'
+ ]
+})
+export class DashboardComponent implements OnInit {
+
+
+ private list: StatusReportInfo[] = []; // PaginatedList = new PaginatedList(null);
+
+ type = 'info';//can be success, info, warning, danger
+ currentPage: number = 1;
+ pageSize: number = 5;
+ totalPages: number;
+ public isloading = false;
+
+ private subscription: Subscription;
+
+
+ constructor(
+ private webApi: WebApiService,
+ private _service: AuthenticationService,
+ private messageService: MessageService,
+ private log: LoggerService,
+ private agentsService: AgentsService,
+ private changeDetectionRef: ChangeDetectorRef
+ ) {
+ this.subscription = this.messageService.subscribe(Messages.MESSAGE_REFRESHAGENTS, (payload) => {
+ //this.log.debug(payload);
+ this.list = payload as StatusReportInfo[];
+ //trigger change detection
+ setTimeout(() =>
+ //mark for detection change and refresh
+ this.changeDetectionRef.detectChanges()
+ , 10);
+
+ this.isloading = false;
+ });
+ }
+
+
+ showToast(toast: ToastNotification) {
+ this.messageService.broadcast(Messages.MESSAGE_NOTIFY, toast);
+ }
+
+
+ ngOnInit(): void {
+ this.list = this.agentsService.getAgents();
+ }
+
+
+ doRefresh() {
+ this.isloading = true;
+ //force service refresh
+ this.agentsService.refreshAgents();
+ }
+
+ getPage(page: number) {
+ this.currentPage = page
+ this.totalPages = this.list.length;
+ }
+
+
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.css b/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.css
new file mode 100644
index 0000000..dde6ea1
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.css
@@ -0,0 +1,47 @@
+body {
+ padding-top: 50px;
+}
+.pagetemplate {
+ padding: 50px 0px 15px;
+ text-align: left;
+}
+.panel-default {
+ margin-top:20px;
+}
+
+
+
+
+
+.newbackup{
+ float: right;
+ clear: both;
+}
+
+.table-footer{
+ padding: 0px;
+}
+
+.pagination{
+ margin: 5px 0px 0px;
+}
+
+.tabledesc{
+ margin: 10px 10px 25PX;
+}
+
+
+
+.mytitle{
+ padding-left: 20px;
+}
+
+#myTabContent {
+ margin-top: 20px;
+}
+
+
+.form-horizontal .form-group{
+ margin-left: 0px;
+ margin-right: 0px;
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.html b/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.html
new file mode 100644
index 0000000..62d8fbb
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.html
@@ -0,0 +1,89 @@
+
+
+
+
+
+
+
Have an Account?
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
{{errorMsg}}
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.ts b/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.ts
new file mode 100644
index 0000000..87445e8
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/login/login.component.ts
@@ -0,0 +1,97 @@
+import { Component, OnInit, Input } from '@angular/core';
+import { Observable } from 'rxjs/Observable';
+import { Router } from '@angular/router';
+import { AuthenticationService, User } from '../../services/authentication.service';
+
+import { LoggerService } from '../../services/logger.service';
+import { ToastNotification, ToastType } from '../../services/notifications.service';
+import { MessageService, Messages } from '../../services/message.service';
+
+
+@Component({
+ selector: 'login',
+ templateUrl: './login.component.html',
+ styleUrls: ['./login.component.css']
+})
+export class LoginComponent implements OnInit {
+
+
+ public user = new User({ email: '', password: '', isAdmin: false });
+ public errorMsg = '';
+ public repassword = '';
+
+ constructor(
+ private _service: AuthenticationService,
+ private _router: Router,
+ private messageService: MessageService,
+ private log: LoggerService
+ ) {
+ }
+
+
+
+ showToast(toast: ToastNotification) {
+ this.messageService.broadcast(Messages.MESSAGE_NOTIFY, toast);
+ }
+
+
+ ngOnInit(): void {
+ if (this._service.checkIsLoggedIn()) {
+ this.log.debug('oninit() navigate to root');
+ this._router.navigate(['/']);
+ }
+ }
+
+
+ doLogin() {
+ this.log.debug("doLogin()");
+ if (this.user.password.length > 0 &&
+ this.user.email.length > 0) {
+ //
+ this._service.login(this.user, () => {
+ //data
+ }, err => {
+ this.showToast({
+ title: "Login error",
+ body: err,
+ type: ToastType.error
+ });
+ });
+ }
+ }
+
+ doRegister() {
+ this.log.debug("doRegister()");
+ if (this.repassword.length > 0 && this.repassword == this.user.password &&
+ this.user.email.length > 0) {
+ this._service.registerUser(this.user, () => {
+ //is registered
+ this.showToast({
+ title: "Register success",
+ body: "The user has been created",
+ type: ToastType.success
+ });
+ //navigate default to root
+ this._router.navigate(['/']);//to default or last url
+ },
+ (err) => {
+ this.showToast({
+ title: "Register error",
+ body: err.text(),
+ type: ToastType.error
+ });
+ this.log.error(err);
+ });
+ }
+ else {
+ this.showToast({
+ title: "Invalid data",
+ body: "Some data not OK!",
+ type: ToastType.error
+ });
+ }
+ }
+
+
+}
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.css b/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.css
new file mode 100644
index 0000000..5f28270
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.css
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.html b/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.html
new file mode 100644
index 0000000..5e3b179
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.html
@@ -0,0 +1,70 @@
+
+
+
+
+
+
+
+
+
+
+ Here are all agents and operations logs.
+
+
+
+
+
+
+
+
+
+ | DateTime |
+ Computer IP |
+ Description |
+ Error |
+ Status |
+
+
+
+
+ | {{logItem.dateTime | date: 'yyyy/MM/dd hh:mm:ss'}} |
+ {{logItem.clientIP}} |
+ {{logItem.description}} |
+ {{logItem.logError}} |
+ {{logItem.status}} |
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.ts b/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.ts
new file mode 100644
index 0000000..555bf71
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/logs/logs.component.ts
@@ -0,0 +1,67 @@
+import { Component, OnInit, Input, ViewChild } from '@angular/core';
+import { BackupConfiguration } from '../../model/BackupConfiguration';
+import { PaginatedList } from '../../model/PaginatedList';
+import { WebApiService } from '../../services/webapi.service';
+import { Observable } from 'rxjs/Observable';
+import { AuthenticationService } from '../../services/authentication.service';
+import { ModalComponent } from '../../shared/modal/modal.component';
+import { BackupLog } from '../../model/BackupLog';
+
+import { LoggerService } from '../../services/logger.service';
+import { ToastNotification, ToastType } from '../../services/notifications.service';
+import { MessageService, Messages } from '../../services/message.service';
+
+
+@Component({
+ selector: 'logs',
+ templateUrl: './logs.component.html',
+ styleUrls: ['./logs.component.css']
+})
+export class LogsComponent implements OnInit {
+
+
+ public list: PaginatedList = new PaginatedList(null);
+
+
+ currentPage: number = 1;
+ pageSize: number = 10;
+ totalPages: number;
+ isloading: boolean;
+
+
+ constructor(
+ private webApi: WebApiService,
+ private _service: AuthenticationService,
+ private messageService: MessageService,
+ private log: LoggerService
+ ) { }
+
+
+ ngOnInit(): void {
+ this.doRefresh();
+ }
+
+
+ doRefresh() {
+ this.getPage(this.currentPage);
+ }
+
+
+ getPage(page: number) {
+ //this.log.debug('getting page: ' + page);
+ this.isloading = true;
+ this.webApi.getLogsPage(page, this.pageSize).subscribe(
+ (data) => {
+ setTimeout(() => {
+ this.list = data;
+ this.currentPage = page
+ this.totalPages = data.tp * this.pageSize;
+ this.isloading = false;
+ }, 400);//induced delay
+ },
+ err => this.log.error(err)
+ );
+ }
+
+
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.css b/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.css
new file mode 100644
index 0000000..ec3acae
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.css
@@ -0,0 +1,34 @@
+body {
+ padding-top: 50px;
+}
+.pagetemplate {
+ padding: 15px 50px 15px;
+ text-align: left;
+}
+
+
+.newbackup{
+ float: right;
+ clear: both;
+}
+
+.table-footer{
+ padding: 0px;
+}
+
+.pagination{
+ margin: 5px 0px 0px;
+}
+
+.tabledesc{
+ margin: 10px 10px 25PX;
+}
+
+
+
+@media (max-width: 767px) {
+ /* On small screens, the nav menu spans the full width of the screen. Leave a space for it. */
+ .body-content {
+ padding-top: 50px;
+ }
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.html b/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.html
new file mode 100644
index 0000000..2c18174
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.html
@@ -0,0 +1,27 @@
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.ts b/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.ts
new file mode 100644
index 0000000..bb3f7b6
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/navmenu/navmenu.component.ts
@@ -0,0 +1,45 @@
+import { Component, ChangeDetectorRef } from '@angular/core';
+import { AuthenticationService, User } from '../../services/authentication.service';
+import { MessageService, Messages } from '../../services/message.service';
+//import { AgentsService } from '../../services/agents.service';
+import { Subscription } from 'rxjs/Subscription';
+import { StatusReportInfo } from '../../model/StatusReportInfo';
+
+
+@Component({
+ selector: 'nav-menu',
+ templateUrl: './navmenu.component.html',
+ styleUrls: ['./navmenu.component.css'],
+ //providers: [AuthenticationService]
+})
+export class NavMenuComponent {
+
+ private subscription: Subscription;
+ private agentsCount: number = 0;
+
+ constructor(
+ private _authService: AuthenticationService,
+ //private agentsService: AgentsService,
+ private messageService: MessageService,
+ private changeDetectionRef: ChangeDetectorRef
+ ) {
+ this.subscription = this.messageService.subscribe(Messages.MESSAGE_REFRESHAGENTS, (payload) => {
+ let list = payload as StatusReportInfo[];
+ this.agentsCount = list.length;
+
+ setTimeout(() =>
+ this.changeDetectionRef.detectChanges()
+ , 10);
+ });
+ }
+
+
+ isLoggedIn() {
+ return this._authService.checkIsLoggedIn();
+ }
+
+ logOut() {
+ this._authService.logout();
+ }
+
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.css b/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.css
new file mode 100644
index 0000000..b413937
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.css
@@ -0,0 +1,46 @@
+body {
+ padding-top: 50px;
+}
+.pagetemplate {
+ padding: 50px 0px 15px;
+ text-align: left;
+}
+.panel-default {
+ margin-top:20px;
+}
+
+
+
+
+.newbackup{
+ float: right;
+ clear: both;
+}
+
+.table-footer{
+ padding: 0px;
+}
+
+.pagination{
+ margin: 5px 0px 0px;
+}
+
+.tabledesc{
+ margin: 10px 10px 25PX;
+}
+
+
+
+.mytitle{
+ padding-left: 20px;
+}
+
+#myTabContent {
+ margin-top: 20px;
+}
+
+
+.form-horizontal .form-group{
+ margin-left: 0px;
+ margin-right: 0px;
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.html b/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.html
new file mode 100644
index 0000000..873ba39
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.html
@@ -0,0 +1,52 @@
+
+
+
+
+
+
+
Your profile - {{user.email}} {{isAdmin() ? " - (Admin)" : ''}}
+
+
+
+
+
+
+
+
+ Here you can change your password
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
{{errorMsg}}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.ts b/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.ts
new file mode 100644
index 0000000..00a149a
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/profile/profile.component.ts
@@ -0,0 +1,85 @@
+import { Component, OnInit, Input } from '@angular/core';
+import { Observable } from 'rxjs/Observable';
+import { Router } from '@angular/router';
+import { AuthenticationService, User } from '../../services/authentication.service';
+import { WebApiService } from '../../services/webapi.service';
+
+import { LoggerService } from '../../services/logger.service';
+import { ToastNotification, ToastType } from '../../services/notifications.service';
+import { MessageService, Messages } from '../../services/message.service';
+
+
+@Component({
+ selector: 'profile',
+ templateUrl: './profile.component.html',
+ styleUrls: ['./profile.component.css']
+})
+export class ProfileComponent implements OnInit {
+
+
+ public user : User;
+ public errorMsg = '';
+ public password: string = '';
+ public repassword: string = '';
+
+ constructor(
+ private _service: AuthenticationService,
+ private _router: Router,
+ private _webApi: WebApiService,
+ private messageService: MessageService,
+ private log: LoggerService
+ ) {
+ }
+
+ ngOnInit(): void {
+ this.user = this._service.getLoggedUser();
+ }
+
+ showToast(toast: ToastNotification) {
+ this.messageService.broadcast(Messages.MESSAGE_NOTIFY, toast);
+ }
+
+ isAdmin() {
+ return this._service.checkIsAdmin();
+ }
+
+ doChangePassword() {
+ this.password = this.password.trim();
+ this.repassword = this.repassword.trim();
+
+ let mpass = this.password.trim();
+ let mrepass = this.repassword.trim();
+
+ if (this.user && this.user.email &&
+ mpass.length > 0 &&
+ mpass == mrepass) {
+ this.user.newpassword = mpass;
+ this._webApi.changePassword(this.user).subscribe((data) => {
+ if (data.succeeded) {
+ //notify pwd changed
+ this.showToast({ title: "Password change success", body: "Password has been changed!", type: ToastType.success });
+ }
+ else {
+ //notify something not OK
+ this.showToast({ title: "Password change error", body: data.errors, type: ToastType.error });
+ }
+ }, err => {
+ this.log.error(err);
+ //notify err
+ this.showToast({ title: "Password change error", body: err.text(), type: ToastType.error });
+ });
+ }
+ else if (mpass.length == 0) {
+ this.errorMsg = 'Password cannot be empty!';
+ this.showToast({ title: "Error", body: this.errorMsg, type: ToastType.error });
+ }
+ else {
+ this.errorMsg = 'Passwords does not match!';
+ this.showToast({ title: "Error", body: this.errorMsg, type: ToastType.error });
+ }
+ }
+
+
+
+}
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.css b/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.css
new file mode 100644
index 0000000..5f28270
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.css
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.html b/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.html
new file mode 100644
index 0000000..9faeb8f
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.html
@@ -0,0 +1,54 @@
+
+
Manage Admin Users
+
+
+
+
+
+
+
+ Here an Admin user can grant or revoke "Admin" role for other users.
+
+
+
+
+
+
+
+
+
+ | User name |
+ Is Admin |
+
+
+
+
+ | {{userItem.email}} |
+
+
+
+
+
+ |
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.ts b/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.ts
new file mode 100644
index 0000000..9491e21
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/components/users/users.component.ts
@@ -0,0 +1,101 @@
+import { Component, OnInit, Input, ViewChild } from '@angular/core';
+import { BackupConfiguration } from '../../model/BackupConfiguration';
+import { PaginatedList } from '../../model/PaginatedList';
+import { WebApiService } from '../../services/webapi.service';
+import { Observable } from 'rxjs/Observable';
+import { AuthenticationService } from '../../services/authentication.service';
+
+import { User } from '../../services/authentication.service';
+
+import { LoggerService } from '../../services/logger.service';
+import { ToastNotification, ToastType } from '../../services/notifications.service';
+import { MessageService, Messages } from '../../services/message.service';
+
+
+@Component({
+ selector: 'logs',
+ templateUrl: './users.component.html',
+ styleUrls: ['./users.component.css']
+})
+export class UsersComponent implements OnInit {
+
+
+ public list: User[] = new Array();
+ currentPage: number = 1;
+ pageSize: number = 10;
+ totalPages: number;
+ loading: boolean;
+
+
+ constructor(
+ private webApi: WebApiService,
+ private _service: AuthenticationService,
+ private messageService: MessageService,
+ private log: LoggerService
+ ) { }
+
+
+ ngOnInit(): void {
+ this.getPage();
+ }
+
+
+ showToast(toast: ToastNotification) {
+ this.messageService.broadcast(Messages.MESSAGE_NOTIFY, toast);
+ }
+
+
+ getPage() {
+ //this.log.debug('getting page: ' + page);
+ this.loading = true;
+ this.webApi.getAllUsers().subscribe(
+ (data) => {
+ //this.log.debug('data: ' + JSON.stringify(data));
+ this.list = data;
+
+ this.totalPages = data.length;// data.tp * this.pageSize;
+ this.loading = false;
+ },
+ err => this.log.error(err)
+ );
+ }
+
+
+ toggleAdmin(user: User) {
+ let prevValue = user.isAdmin;
+ user.isAdmin = user.isAdmin ? false : true;
+ this.log.debug('Make user admin - ' + user.isAdmin);
+ return this.webApi.changeAdminRole(user).subscribe((data) => {
+ //
+ if (data.succeeded) {
+ this.showToast({ title: "User change success", body: `User ${user.email} has been ${user.isAdmin ? "promoted" : "revoked"}`, type: ToastType.success });
+ }
+ else {
+ user.isAdmin = prevValue;
+ this.log.debug(data);
+ this.showToast({ title: "User change error", body: `The user ${user.email} cannot be changed!`, type: ToastType.error });
+ }
+ }, err => {
+ this.log.error(err);
+ user.isAdmin = prevValue;
+ this.showToast({ title: "User change error", body: err, type: ToastType.error });
+ });
+ }
+
+ isAllowedToChange(user: User) {
+ let isAdmin = this._service.checkIsAdmin();
+ if (isAdmin) {
+ let currentUser = this._service.getLoggedUser();
+ if (currentUser) {
+ if (currentUser.email == user.email) {
+ //not allowed to change your own password
+ return false;
+ } else {
+ return true;//only case to allow editing
+ }
+ }
+ }
+ return false;
+ }
+
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/model/BackupConfiguration.ts b/src/LanBackup.WebApp/ClientApp/app/model/BackupConfiguration.ts
new file mode 100644
index 0000000..958c504
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/model/BackupConfiguration.ts
@@ -0,0 +1,17 @@
+export class BackupConfiguration {
+ id: string;
+ clientIP: string;
+ srcFolder: string;
+ srcUser: string;
+ srcPass: string;
+ destLanFolder: string;
+ destUser: string;
+ destPass: string;
+ crontab: string;
+ isActive: boolean;
+ rowVersion: string;
+
+ constructor(data) {
+ Object.assign(this, data);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/model/BackupLog.ts b/src/LanBackup.WebApp/ClientApp/app/model/BackupLog.ts
new file mode 100644
index 0000000..c343035
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/model/BackupLog.ts
@@ -0,0 +1,13 @@
+export class BackupLog {
+ iD: string;
+ clientIP: string;
+ configurationID: string;
+ description: string;
+ logError: string;
+ status: string;
+ dateTime: Date;
+
+ constructor(data) {
+ Object.assign(this, data);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/model/PaginatedList.ts b/src/LanBackup.WebApp/ClientApp/app/model/PaginatedList.ts
new file mode 100644
index 0000000..c7d2f59
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/model/PaginatedList.ts
@@ -0,0 +1,11 @@
+export class PaginatedList {
+ pi: number;
+ tp: number;
+ recs: T[];
+ hp: boolean;
+ hn: boolean;
+
+ constructor(data) {
+ Object.assign(this, data);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/model/SaveResult.ts b/src/LanBackup.WebApp/ClientApp/app/model/SaveResult.ts
new file mode 100644
index 0000000..723d417
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/model/SaveResult.ts
@@ -0,0 +1,10 @@
+export class SaveResult {
+ _body: T;
+ status: string;
+ ok: string;
+ statusText: string;
+
+ constructor(data) {
+ Object.assign(this, data);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/model/SignInResult.ts b/src/LanBackup.WebApp/ClientApp/app/model/SignInResult.ts
new file mode 100644
index 0000000..28f535d
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/model/SignInResult.ts
@@ -0,0 +1,10 @@
+export class SignInResult {
+ succeeded: boolean;
+ isLockedOut: boolean;
+ isNotAllowed: boolean;
+ requiresTwoFactor: boolean;
+
+ constructor(data) {
+ Object.assign(this, data);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/model/StatusReportInfo.ts b/src/LanBackup.WebApp/ClientApp/app/model/StatusReportInfo.ts
new file mode 100644
index 0000000..c4aa1bd
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/model/StatusReportInfo.ts
@@ -0,0 +1,13 @@
+export class StatusReportInfo {
+
+ iP: string;
+ configurationId: string;
+ statusType: number;
+ statusDescription: string;
+ statusPercent: number;
+ statusDateTime: Date;
+
+ constructor(data) {
+ Object.assign(this, data);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/AuthGuard.ts b/src/LanBackup.WebApp/ClientApp/app/services/AuthGuard.ts
new file mode 100644
index 0000000..5fc2602
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/AuthGuard.ts
@@ -0,0 +1,26 @@
+import { Injectable, Inject } from '@angular/core';
+import { CanActivate } from '@angular/router';
+import { Router } from '@angular/router';
+import { AuthenticationService } from './authentication.service';
+
+
+@Injectable()
+export class AuthGuard implements CanActivate {
+
+ auth: any = {};
+
+ constructor(private authService: AuthenticationService, private router: Router) {
+
+ }
+
+ canActivate() {
+ if (this.authService.checkIsLoggedIn()) {
+ //this.router.navigate(['/']);
+ return true;
+ }
+ else {
+ this.router.navigate(['/login']);
+ }
+ return false;
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/agents.service.ts b/src/LanBackup.WebApp/ClientApp/app/services/agents.service.ts
new file mode 100644
index 0000000..8364e03
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/agents.service.ts
@@ -0,0 +1,60 @@
+import { Injectable } from '@angular/core';
+import { WebApiService } from '../services/webapi.service';
+import { LoggerService } from './logger.service';
+import { StatusReportInfo } from '../model/StatusReportInfo';
+import { MessageService, Messages } from './message.service';
+import { Observable } from 'rxjs/Observable';
+
+
+@Injectable()
+export class AgentsService {
+
+ isLoaded: boolean;
+ agents: StatusReportInfo[] = [];
+ connectionState$: Observable;
+
+
+ constructor(
+ private webApi: WebApiService,
+ private messageService: MessageService,
+ private log: LoggerService,
+
+ ) {
+ //wiring signalr
+
+ this.log.debug('connecting to signalr');
+
+ let service = this;
+ let connection = $["hubConnection"](); // $.hubConnection();
+ let contosoChatHubProxy = connection.createHubProxy('backupslan');
+ //hook on client methos 'agentsRefresh'
+ contosoChatHubProxy.on('agentsRefresh', function (newagents) {
+ service.agents = newagents as StatusReportInfo[];
+ service.messageService.broadcast(Messages.MESSAGE_REFRESHAGENTS, service.agents);
+ });
+ connection.start().done(function () {
+ //service.log.debug('SignalR connected');
+ });
+
+ }
+
+
+
+ getAgents() {
+ if (!this.isLoaded) {
+ this.refreshAgents();
+ }
+ return this.agents;
+ }
+
+ refreshAgents() {
+ this.isLoaded = false;
+ this.webApi.getAgentsAll()
+ .subscribe(data => {
+ this.agents = data;
+ this.isLoaded = true;
+ this.messageService.broadcast(Messages.MESSAGE_REFRESHAGENTS, this.agents);
+ });
+ }
+
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/authentication.service.ts b/src/LanBackup.WebApp/ClientApp/app/services/authentication.service.ts
new file mode 100644
index 0000000..3a6b511
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/authentication.service.ts
@@ -0,0 +1,136 @@
+import { Injectable, Inject } from '@angular/core';
+import { Router } from '@angular/router';
+import { Location } from '@angular/common';
+import { isBrowser } from 'angular2-universal';
+import { Observable } from 'rxjs/Observable';
+import { RequestOptions, Request, RequestMethod } from '@angular/http';
+import { WebApiService } from './webapi.service';
+
+import { LoggerService } from './logger.service';
+
+
+export class User {
+
+ email: string;
+ password: string;
+ newpassword: string;
+ isAdmin: boolean;
+ succeeded: boolean;
+ isLockedOut: boolean;
+ errors: any;
+
+ constructor(data) {
+ Object.assign(this, data);
+ }
+}
+
+
+@Injectable()
+export class AuthenticationService {
+
+ constructor(
+ private _router: Router,
+ private location: Location,
+ private webApi: WebApiService,
+ private log: LoggerService
+ ) { }
+
+
+
+
+ logout() {
+ localStorage.removeItem("user");
+ this._router.navigate(['login']);
+ }
+
+ login(user: User, success, error) {
+
+ return this.webApi.loginUser(user)
+ .subscribe(data => {
+ if (data.succeeded) {
+ localStorage.setItem("user", btoa(JSON.stringify(data)));
+ this._router.navigate(['/']);//to default or last url
+ success(data);
+ }
+ else {
+ //clear
+ localStorage.removeItem("user");
+ error(data.errors.map(err=>err.description));
+ }
+ }, err => {
+ error(err);
+ });
+ }
+
+ registerUser(user: User, success, error) {
+ return this.webApi.registerUser(user)
+ .subscribe(data => {
+ if (data.succeeded) {
+ localStorage.setItem("user", btoa(JSON.stringify(data)));
+ //created and logged in
+ success();
+ }
+ else {
+ //could not create
+ localStorage.removeItem("user");
+ }
+ }, err => {
+ error(err);
+ })
+ ;
+ }
+
+
+
+
+
+ getLoggedUser(): User {
+ if (isBrowser) {
+ if (localStorage.getItem("user") === null) {
+ return null;
+ }
+ let _user: User = JSON.parse(atob(localStorage.getItem("user")));
+ return _user;
+ }
+ return null;
+ }
+
+ checkCredentials() {
+ if (isBrowser) {
+ if (localStorage.getItem("user") === null) {
+ this._router.navigate(['login']);
+ }
+ return true;
+ }
+ return false;
+ }
+
+ checkIsAdmin() {
+ if (isBrowser) {
+ if (localStorage.getItem("user") != null) {
+ let _user: User = JSON.parse(atob(localStorage.getItem("user")));
+ return _user && _user.isAdmin;
+ }
+ return false;
+ }
+ return false;
+ }
+
+ checkIsLoggedIn() {
+ if (isBrowser) {
+ try {
+ if (localStorage.getItem("user") === null) {
+ return false;
+ }
+ return true;
+ }
+ catch (e) {
+ this.log.error('e: ' + e);
+ }
+ return false;
+ }
+ return false;
+ }
+
+
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/channel.service.ts b/src/LanBackup.WebApp/ClientApp/app/services/channel.service.ts
new file mode 100644
index 0000000..9ae8817
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/channel.service.ts
@@ -0,0 +1,256 @@
+import { Injectable, Inject } from "@angular/core";
+import { Subject } from "rxjs/Subject";
+import { Observable } from "rxjs/Observable";
+import * as $ from 'jquery'
+
+/**
+ * When SignalR runs it will add functions to the global $ variable
+ * that you use to create connections to the hub. However, in this
+ * class we won't want to depend on any global variables, so this
+ * class provides an abstraction away from using $ directly in here.
+ */
+export class SignalrWindow extends Window {
+ $: any;
+}
+
+export enum ConnectionState {
+ Connecting = 1,
+ Connected = 2,
+ Reconnecting = 3,
+ Disconnected = 4
+}
+
+export class ChannelConfig {
+ url: string;
+ hubName: string;
+ channel: string;
+}
+
+export class ChannelEvent {
+ Name: string;
+ ChannelName: string;
+ Timestamp: Date;
+ Data: any;
+ Json: string;
+
+ constructor() {
+ this.Timestamp = new Date();
+ }
+}
+
+class ChannelSubject {
+ channel: string;
+ subject: Subject;
+}
+
+/**
+ * ChannelService is a wrapper around the functionality that SignalR
+ * provides to expose the ideas of channels and events. With this service
+ * you can subscribe to specific channels (or groups in signalr speak) and
+ * use observables to react to specific events sent out on those channels.
+ */
+@Injectable()
+export class ChannelService {
+ /**
+ * starting$ is an observable available to know if the signalr
+ * connection is ready or not. On a successful connection this
+ * stream will emit a value.
+ */
+ starting$: Observable;
+
+ /**
+ * connectionState$ provides the current state of the underlying
+ * connection as an observable stream.
+ */
+ connectionState$: Observable;
+
+ /**
+ * error$ provides a stream of any error messages that occur on the
+ * SignalR connection
+ */
+ error$: Observable;
+
+ // These are used to feed the public observables
+ //
+ private connectionStateSubject = new Subject();
+ private startingSubject = new Subject();
+ private errorSubject = new Subject();
+
+ // These are used to track the internal SignalR state
+ //
+ private hubConnection: any;
+ private hubProxy: any;
+
+ // An internal array to track what channel subscriptions exist
+ //
+ private subjects = new Array();
+
+ constructor(
+ @Inject(SignalrWindow) private window: SignalrWindow,
+ @Inject("channel.config") private channelConfig: ChannelConfig
+ ) {
+ if (this.window.$ === undefined || this.window.$.hubConnection === undefined) {
+ throw new Error("The variable '$' or the .hubConnection() function are not defined...please check the SignalR scripts have been loaded properly");
+ }
+
+ // Set up our observables
+ //
+ this.connectionState$ = this.connectionStateSubject.asObservable();
+ this.error$ = this.errorSubject.asObservable();
+ this.starting$ = this.startingSubject.asObservable();
+
+ this.hubConnection = this.window.$.hubConnection();
+ this.hubConnection.url = channelConfig.url;
+ this.hubProxy = this.hubConnection.createHubProxy(channelConfig.hubName);
+
+ // Define handlers for the connection state events
+ //
+ this.hubConnection.stateChanged((state: any) => {
+ //console.log(state);
+ let newState = ConnectionState.Connecting;
+
+ switch (state.newState) {
+ case this.window.$.signalR.connectionState.connecting:
+ newState = ConnectionState.Connecting;
+ break;
+ case this.window.$.signalR.connectionState.connected:
+ newState = ConnectionState.Connected;
+ break;
+ case this.window.$.signalR.connectionState.reconnecting:
+ newState = ConnectionState.Reconnecting;
+ break;
+ case this.window.$.signalR.connectionState.disconnected:
+ newState = ConnectionState.Disconnected;
+ break;
+ }
+
+ // Push the new state on our subject
+ //
+ this.connectionStateSubject.next(newState);
+ });
+
+ // Define handlers for any errors
+ //
+ this.hubConnection.error((error: any) => {
+ // Push the error on our subject
+ //
+ this.errorSubject.next(error);
+ });
+
+ this.hubProxy.on("onEvent", (channel: string, ev: ChannelEvent) => {
+ console.log(`onEvent - ${channel} channel`, ev);
+
+ // This method acts like a broker for incoming messages. We
+ // check the interal array of subjects to see if one exists
+ // for the channel this came in on, and then emit the event
+ // on it. Otherwise we ignore the message.
+ //
+ let channelSub = this.subjects.find((x: ChannelSubject) => {
+ return x.channel === channel;
+ }) as ChannelSubject;
+
+ // If we found a subject then emit the event on it
+ //
+ if (channelSub !== undefined) {
+ return channelSub.subject.next(ev);
+ }
+ });
+ }
+
+ /**
+ * Start the SignalR connection. The starting$ stream will emit an
+ * event if the connection is established, otherwise it will emit an
+ * error.
+ */
+ start(): void {
+ // Now we only want the connection started once, so we have a special
+ // starting$ observable that clients can subscribe to know know if
+ // if the startup sequence is done.
+ //
+ // If we just mapped the start() promise to an observable, then any time
+ // a client subscried to it the start sequence would be triggered
+ // again since it's a cold observable.
+ //
+ this.hubConnection.start()
+ .done(() => {
+ this.startingSubject.next();
+ })
+ .fail((error: any) => {
+ this.startingSubject.error(error);
+ });
+ }
+
+ /**
+ * Get an observable that will contain the data associated with a specific
+ * channel
+ * */
+ sub(channel: string): Observable {
+
+ // Try to find an observable that we already created for the requested
+ // channel
+ //
+ let channelSub = this.subjects.find((x: ChannelSubject) => {
+ return x.channel === channel;
+ }) as ChannelSubject;
+
+ // If we already have one for this event, then just return it
+ //
+ if (channelSub !== undefined) {
+ console.log(`Found existing observable for ${channel} channel`)
+ return channelSub.subject.asObservable();
+ }
+
+ //
+ // If we're here then we don't already have the observable to provide the
+ // caller, so we need to call the server method to join the channel
+ // and then create an observable that the caller can use to received
+ // messages.
+ //
+
+ // Now we just create our internal object so we can track this subject
+ // in case someone else wants it too
+ //
+ channelSub = new ChannelSubject();
+ channelSub.channel = channel;
+ channelSub.subject = new Subject();
+ this.subjects.push(channelSub);
+
+ // Now SignalR is asynchronous, so we need to ensure the connection is
+ // established before we call any server methods. So we'll subscribe to
+ // the starting$ stream since that won't emit a value until the connection
+ // is ready
+ //
+ this.starting$.subscribe(() => {
+ this.hubProxy.invoke("Subscribe", channel)
+ .done(() => {
+ console.log(`Successfully subscribed to ${channel} channel`);
+ })
+ .fail((error: any) => {
+ channelSub.subject.error(error);
+ });
+ },
+ (error: any) => {
+ channelSub.subject.error(error);
+ });
+
+ return channelSub.subject.asObservable();
+ }
+
+ // Not quite sure how to handle this (if at all) since there could be
+ // more than 1 caller subscribed to an observable we created
+ //
+ // unsubscribe(channel: string): Rx.Observable {
+ // this.observables = this.observables.filter((x: ChannelObservable) => {
+ // return x.channel === channel;
+ // });
+ // }
+
+ /** publish provides a way for calles to emit events on any channel. In a
+ * production app the server would ensure that only authorized clients can
+ * actually emit the message, but here we're not concerned about that.
+ */
+ publish(ev: ChannelEvent): void {
+ this.hubProxy.invoke("Publish", ev);
+ }
+
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/logger.service.ts b/src/LanBackup.WebApp/ClientApp/app/services/logger.service.ts
new file mode 100644
index 0000000..e09b927
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/logger.service.ts
@@ -0,0 +1,54 @@
+//inspired from
+//https://github.com/code-chunks/angular2-logger/blob/master/app/core/logger.ts
+import { Injectable } from '@angular/core';
+
+const CONSOLE_DEBUG_METHOD = console["debug"] ? "debug" : "log";
+
+//logging here
+@Injectable()
+export class LoggerService {
+
+ constructor() {
+ this._level = Level.WARN;
+ }
+
+
+ error(message?: any, ...optionalParams: any[]) {
+ this.isErrorEnabled() && console.error.apply(console, arguments);
+ }
+
+ warn(message?: any, ...optionalParams: any[]) {
+ this.isWarnEnabled() && console.warn.apply(console, arguments);
+ }
+
+ info(message?: any, ...optionalParams: any[]) {
+ this.isInfoEnabled() && console.info.apply(console, arguments);
+ }
+
+ debug(message?: any, ...optionalParams: any[]) {
+ this.isDebugEnabled() && (console)[CONSOLE_DEBUG_METHOD].apply(console, arguments);
+ }
+
+ log(message?: any, ...optionalParams: any[]) {
+ this.isLogEnabled() && console.log.apply(console, arguments);
+ }
+
+
+ private _level: Level;
+ public Level: any = Level;
+
+ get level(): Level { return this._level; }
+
+ set level(level: Level) {
+ this._level = level;
+ }
+
+ isErrorEnabled = (): boolean => this._level >= Level.ERROR;
+ isWarnEnabled = (): boolean => this._level >= Level.WARN;
+ isInfoEnabled = (): boolean => this._level >= Level.INFO;
+ isDebugEnabled = (): boolean => this._level >= Level.DEBUG;
+ isLogEnabled = (): boolean => this._level >= Level.LOG;
+
+}
+
+export enum Level { OFF = 0, ERROR = 1, WARN = 2, INFO = 3, DEBUG = 4, LOG = 5 }
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/message.service.ts b/src/LanBackup.WebApp/ClientApp/app/services/message.service.ts
new file mode 100644
index 0000000..ffd9c2f
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/message.service.ts
@@ -0,0 +1,36 @@
+import { Injectable } from '@angular/core';
+import { Subject } from 'rxjs/Subject';
+import { Subscription } from 'rxjs/Subscription';
+import 'rxjs/add/operator/filter'
+import 'rxjs/add/operator/map'
+
+
+type MessageCallback = (payload: any) => void;
+
+@Injectable()
+export class MessageService {
+ private handler = new Subject();
+
+ broadcast(type: string, payload: any) {
+ this.handler.next({ type, payload });
+ }
+
+ subscribe(type: string, callback: MessageCallback): Subscription {
+ return this.handler
+ .filter(message => message.type === type)
+ .map(message => message.payload)
+ .subscribe(callback);
+ }
+}
+
+
+interface Message {
+ type: string;
+ payload: any;
+}
+
+export class Messages {
+ static readonly MESSAGE_NOTIFY: string = 'notify';
+ static readonly MESSAGE_REFRESHAGENTS: string = 'refreshagents';
+
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/notifications.service.ts b/src/LanBackup.WebApp/ClientApp/app/services/notifications.service.ts
new file mode 100644
index 0000000..c342b4a
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/notifications.service.ts
@@ -0,0 +1,80 @@
+import { Injectable, EventEmitter } from "@angular/core"
+import { Observable } from "rxjs"
+import { MessageService, Messages } from './message.service';
+import { Subscription } from 'rxjs/Subscription';
+import { LoggerService } from './logger.service';
+import {
+ ToastyService,
+ ToastOptions, ToastData, ToastyConfig
+} from 'ng2-toasty';
+
+
+
+@Injectable()
+export class NotificationsService {
+
+ private subscription: Subscription;
+
+ constructor(
+ private messageService: MessageService,
+ private toastyService: ToastyService,
+ private toastConfig: ToastyConfig,
+ private log: LoggerService
+ ) {
+ toastConfig.theme = 'material';
+ this.subscription = this.messageService.subscribe(Messages.MESSAGE_NOTIFY, (payload) => {
+ this.addToast(payload as ToastNotification);
+ });
+ }
+
+
+ addToast(toastnotification: ToastNotification) {
+ var toastOptions: ToastOptions = {
+ title: toastnotification.title,
+ msg: toastnotification.body,
+ showClose: true,
+ timeout: 5000,
+ onAdd: (toast: ToastData) => {
+ this.log.debug('Toast ' + toast.id + ' has been added!');
+ },
+ onRemove: (toast: ToastData) => {
+ this.log.debug('Toast ' + toast.id + ' has been removed!');
+ }
+ };
+ //create notification
+ switch (toastnotification.type) {
+ case ToastType.success:
+ this.toastyService.success(toastOptions);
+ break;
+ case ToastType.error:
+ this.toastyService.error(toastOptions);
+ break;
+ case ToastType.warning:
+ this.toastyService.warning(toastOptions);
+ break;
+ case ToastType.info:
+ this.toastyService.info(toastOptions);
+ break;
+ default:
+ this.toastyService.default(toastOptions);
+ break;
+ }
+ }
+}
+
+
+//notification dto
+export interface ToastNotification {
+ title: string
+ body: string
+ type: ToastType
+}
+
+//notification type enumeration
+export enum ToastType {
+ normal,
+ success,
+ warning,
+ error,
+ info
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/services/webapi.service.ts b/src/LanBackup.WebApp/ClientApp/app/services/webapi.service.ts
new file mode 100644
index 0000000..a3fbf19
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/services/webapi.service.ts
@@ -0,0 +1,204 @@
+import { Injectable } from '@angular/core';
+import { Http, Headers, RequestOptions, Response } from '@angular/http';
+import { Observable } from 'rxjs/Rx';
+import 'rxjs/add/operator/toPromise';
+//models
+import { BackupConfiguration } from '../model/BackupConfiguration';
+import { BackupLog } from '../model/BackupLog';
+import { StatusReportInfo } from '../model/StatusReportInfo';
+import { User } from '../services/authentication.service';
+import { SaveResult } from '../model/SaveResult';
+import { SignInResult } from '../model/SignInResult';
+
+
+import { PaginatedList } from '../model/PaginatedList';
+import { LoggerService } from './logger.service';
+
+
+
+@Injectable()
+export class WebApiService {
+ public list: BackupConfiguration[];
+
+ constructor(
+ private http: Http,
+ private log: LoggerService
+ ) {
+ }
+
+
+ // ### REGION BACKUPS ///
+
+ getBackupsAll(): Promise {
+ return this.http
+ .get('/api/backupconfig/')
+ .toPromise()
+ .then(response => response.json())
+ .then(backups => Array.from(backups, b => new BackupConfiguration(b)))
+ .catch(error => this.log.error(error));
+ }
+
+
+ getBackupsPage(idx: number, siz: number): Observable> {
+ let headers = new Headers({
+ 'Content-Type': 'application/json',
+ 'idx': idx,
+ 'siz': siz
+ });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .get('/api/backupconfig', options)
+ .map((res: Response) => res.json())
+ .catch(error => Observable.throw(error.text() || 'Server error'));
+ }
+
+
+ saveBackup(toSave: BackupConfiguration, isNew: boolean): Observable {
+ let headers = new Headers({ 'Content-Type': 'application/json' });
+ let options = new RequestOptions({ headers: headers });
+ if (isNew)//create
+ return this.http
+ .post('/api/backupconfig', toSave, options)
+ .map((res: Response) => res.json())
+ .catch(error => Observable.throw(error.text() || 'Server error'));
+ else//update
+ return this.http
+ .put(`/api/backupconfig/${toSave.id}`, toSave, options)
+ .map((res: Response) => res.json())
+ .catch(error => Observable.throw(error.text() || 'Server error')
+ );
+ }
+
+
+ deleteBackup(toDelete: BackupConfiguration): Observable {
+ let headers = new Headers({ 'Content-Type': 'application/json' });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .delete(`/api/backupconfig/${toDelete.id}`, options)
+ .map((res: Response) => res.json())
+ .catch(error => Observable.throw(error.text() || 'Server error'));
+ }
+
+
+ // ### END REGION BACKUPS ///
+
+
+
+
+
+
+ // ### REGION LOGS ///
+
+ getLogsPage(idx: number, siz: number): Observable> {
+ let headers = new Headers({
+ 'Content-Type': 'application/json',
+ 'idx': idx,
+ 'siz': siz
+ });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .get('/api/logs', options)
+ .map((res: Response) => res.json())
+ .catch(error => Observable.throw(error.text() || 'Server error'));
+ }
+
+ // ### END REGION LOGS ///
+
+
+
+
+
+
+ // ### REGION USER ///
+
+
+ loginUser(user: User): Observable {
+ let headers = new Headers({
+ 'Content-Type': 'application/json'
+ });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .post('/api/users/login', user, options)
+ .map((res: Response) => res.json())
+ .catch(error => {
+ this.log.error(error);
+ return Observable.throw(error || 'Server error')
+ }
+ );
+ }
+
+ registerUser(user: User): Observable {
+ let headers = new Headers({
+ 'Content-Type': 'application/json'
+ });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .post('/api/users/register', user, options)
+ .map((res: Response) => res.json())
+ .catch(error => {
+ this.log.error(error);
+ return Observable.throw(error || 'Server error')
+ }
+ );
+ }
+
+ changePassword(user: User): Observable {
+ let headers = new Headers({
+ 'Content-Type': 'application/json'
+ });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .post('/api/users/pwchange', user, options)
+ .map((res: Response) => res.json())
+ .catch(error => Observable.throw(error || 'Server error'));
+ }
+
+
+ getAllUsers(): Observable {
+ let headers = new Headers({
+ 'Content-Type': 'application/json'
+ });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .get('/api/users/list', options)
+ .map((res: Response) => res.json())
+ .catch(error => Observable.throw(error.text() || 'Server error'));
+ }
+
+
+ changeAdminRole(user: User): Observable {
+ let headers = new Headers({
+ 'Content-Type': 'application/json'
+ });
+ let options = new RequestOptions({ headers: headers });
+ return this.http
+ .post('/api/users/list', user, options)
+ .map((res: Response) => res.json())
+ .catch(error => {
+ this.log.error(error);
+ return Observable.throw(error || 'Server error')
+ }
+ );
+ }
+
+
+ // ### END REGION USER ///
+
+
+
+ // ### REGION SIGNALR ///
+
+ getAgentsAll(): Observable {
+ return this.http
+ .get('/api/lanagents/')
+ .map((res: Response) => res.json())
+ .catch(error => {
+ this.log.error(error);
+ return Observable.throw(error || 'Server error')
+ });
+ }
+
+ // ### ENDREGION SIGNALR ///
+
+}
+
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/global/SharedModule.ts b/src/LanBackup.WebApp/ClientApp/app/shared/global/SharedModule.ts
new file mode 100644
index 0000000..44b8527
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/global/SharedModule.ts
@@ -0,0 +1,24 @@
+
+import { NgModule, ModuleWithProviders } from '@angular/core';
+import { GlobalRef, BrowserGlobalRef, NodeGlobalRef } from './global-ref';
+@NgModule({})
+export class SharedModule {
+
+ static forBrowser(): ModuleWithProviders {
+ return {
+ ngModule: SharedModule,
+ providers: [
+ { provide: GlobalRef, useClass: BrowserGlobalRef }
+ ]
+ };
+ }
+
+ static forNode(): ModuleWithProviders {
+ return {
+ ngModule: SharedModule,
+ providers: [
+ { provide: GlobalRef, useClass: NodeGlobalRef }
+ ]
+ };
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/global/global-ref.ts b/src/LanBackup.WebApp/ClientApp/app/shared/global/global-ref.ts
new file mode 100644
index 0000000..a0079a8
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/global/global-ref.ts
@@ -0,0 +1,19 @@
+export interface MyGlobal {
+ clientSettings: {
+ admin_email: string,
+ instrumentationEnabled: boolean,
+ instrumentationKey: string
+ };
+}
+
+export abstract class GlobalRef {
+ abstract get nativeGlobal(): MyGlobal;
+}
+
+export class BrowserGlobalRef extends GlobalRef {
+ get nativeGlobal(): MyGlobal { return window as MyGlobal; }
+}
+
+export class NodeGlobalRef extends GlobalRef {
+ get nativeGlobal(): MyGlobal { return global as MyGlobal; }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/modal/modal.component.css b/src/LanBackup.WebApp/ClientApp/app/shared/modal/modal.component.css
new file mode 100644
index 0000000..ef6632c
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/modal/modal.component.css
@@ -0,0 +1,39 @@
+.vertical-alignment-helper {
+ display:table;
+ height: 100%;
+ width: 100%;
+ pointer-events:none;
+}
+.vertical-align-center {
+ /* To center vertically */
+ display: table-cell;
+ vertical-align: middle;
+ pointer-events:none;
+}
+.modal-content {
+ /* Bootstrap sets the size of the modal in the modal-dialog class, we need to inherit it */
+ width:inherit;
+ height:inherit;
+ /* To center horizontally */
+ margin: 0 auto;
+ pointer-events:all;
+}
+
+
+.fade-scale {
+ transform: scale(0.6);
+ opacity: 0;
+ -webkit-transition: all .25s linear;
+ -o-transition: all .25s linear;
+ transition: all .25s linear;
+}
+
+.fade-scale.in {
+ opacity: 1;
+ transform: scale(1);
+}
+
+
+.modal{
+ background: rgba(0,0,0,0.6);
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/modal/modal.component.ts b/src/LanBackup.WebApp/ClientApp/app/shared/modal/modal.component.ts
new file mode 100644
index 0000000..7e0e078
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/modal/modal.component.ts
@@ -0,0 +1,41 @@
+import { Component } from '@angular/core';
+
+@Component({
+ selector: 'app-modal',
+ template: `
+
+ `,
+ styleUrls: ['./modal.component.css']
+})
+export class ModalComponent {
+
+ public visible = false;
+ private visibleAnimate = false;
+
+ public show(): void {
+ this.visible = true;
+ setTimeout(() => this.visibleAnimate = true);
+ }
+
+ public hide(): void {
+ this.visibleAnimate = false;
+ setTimeout(() => this.visible = false, 300);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/ng2-pagination.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/ng2-pagination.ts
new file mode 100644
index 0000000..b3dcfc6
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/ng2-pagination.ts
@@ -0,0 +1,24 @@
+import {NgModule} from '@angular/core';
+import {CommonModule} from '@angular/common';
+import {PaginatePipe} from './paginate.pipe';
+import {PaginationService} from './pagination.service';
+import {PaginationControlsComponent} from './pagination-controls.component';
+import {PaginationControlsDirective} from './pagination-controls.directive';
+
+export {PaginationInstance} from './pagination-instance';
+export {PaginationService} from './pagination.service';
+export {PaginationControlsComponent} from './pagination-controls.component';
+export {PaginationControlsDirective} from './pagination-controls.directive';
+export {PaginatePipe} from './paginate.pipe';
+
+@NgModule({
+ imports: [CommonModule],
+ declarations: [
+ PaginatePipe,
+ PaginationControlsComponent,
+ PaginationControlsDirective
+ ],
+ providers: [PaginationService],
+ exports: [PaginatePipe, PaginationControlsComponent, PaginationControlsDirective]
+})
+export class Ng2PaginationModule { }
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/paginate.pipe.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/paginate.pipe.ts
new file mode 100644
index 0000000..d41b962
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/paginate.pipe.ts
@@ -0,0 +1,137 @@
+import {Pipe} from "@angular/core";
+import {PaginationService} from "./pagination.service";
+import {PaginationInstance} from './pagination-instance';
+
+const LARGE_NUMBER = Number.MAX_SAFE_INTEGER;
+
+interface PipeState {
+ collection: any[];
+ size: number;
+ start: number;
+ end: number;
+ slice: any[];
+}
+
+@Pipe({
+ name: 'paginate',
+ pure: false
+})
+export class PaginatePipe {
+
+ // store the values from the last time the pipe was invoked
+ private state: { [id: string]: PipeState } = {};
+
+ constructor(private service: PaginationService) {
+ }
+
+ public transform(collection: any[], args: any): any {
+
+ // When an observable is passed through the AsyncPipe, it will output
+ // `null` until the subscription resolves. In this case, we want to
+ // use the cached data from the `state` object to prevent the NgFor
+ // from flashing empty until the real values arrive.
+ if (args instanceof Array) {
+ // compatible with angular2 before beta16
+ args = args[0];
+ }
+ if (!(collection instanceof Array)) {
+ let _id = args.id || this.service.defaultId;
+ if (this.state[_id]) {
+ return this.state[_id].slice;
+ } else {
+ return collection;
+ }
+ }
+
+ let serverSideMode = args.totalItems !== undefined;
+ let instance = this.createInstance(collection, args);
+ let id = instance.id;
+ let start, end;
+ let perPage = instance.itemsPerPage;
+
+ this.service.register(instance);
+
+ if (!serverSideMode && collection instanceof Array) {
+ perPage = +perPage || LARGE_NUMBER;
+ start = (instance.currentPage - 1) * perPage;
+ end = start + perPage;
+
+ let isIdentical = this.stateIsIdentical(id, collection, start, end);
+ if (isIdentical) {
+ return this.state[id].slice;
+ } else {
+ let slice = collection.slice(start, end);
+ this.saveState(id, collection, slice, start, end);
+ this.service.change.emit(id);
+ return slice;
+ }
+ }
+
+ // save the state for server-side collection to avoid null
+ // flash as new data loads.
+ this.saveState(id, collection, collection, start, end);
+ return collection;
+ }
+
+ /**
+ * Create an PaginationInstance object, using defaults for any optional properties not supplied.
+ */
+ private createInstance(collection: any[], args: any): PaginationInstance {
+ let config = args;
+ this.checkConfig(config);
+
+ return {
+ id: config.id || this.service.defaultId(),
+ itemsPerPage: config.itemsPerPage || 0,
+ currentPage: config.currentPage || 1,
+ totalItems: config.totalItems || collection.length
+ };
+ }
+
+ /**
+ * Ensure the argument passed to the filter contains the required properties.
+ */
+ private checkConfig(config: any): void {
+ const required = ['itemsPerPage', 'currentPage'];
+
+ const missing = required.filter(prop => !config.hasOwnProperty(prop));
+ if (0 < missing.length) {
+ throw new Error(`PaginatePipe: Argument is missing the following required properties: ${missing.join(', ')}`);
+ }
+ }
+
+ /**
+ * To avoid returning a brand new array each time the pipe is run, we store the state of the sliced
+ * array for a given id. This means that the next time the pipe is run on this collection & id, we just
+ * need to check that the collection, start and end points are all identical, and if so, return the
+ * last sliced array.
+ */
+ private saveState(id: string, collection: any[], slice: any[], start: number, end: number) {
+ this.state[id] = {
+ collection,
+ size: collection.length,
+ slice,
+ start,
+ end
+ };
+ }
+
+ /**
+ * For a given id, returns true if the collection, size, start and end values are identical.
+ */
+ private stateIsIdentical(id: string, collection: any[], start: number, end: number): boolean {
+ let state = this.state[id];
+ if (!state) {
+ return false;
+ }
+ let isMetaDataIdentical = state.size === collection.length &&
+ state.start === start &&
+ state.end === end;
+
+ if(!isMetaDataIdentical) {
+ return false;
+ }
+
+ return state.slice.every((element, index) => element === collection[start + index]);
+ }
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-controls.component.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-controls.component.ts
new file mode 100644
index 0000000..9c1a7ed
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-controls.component.ts
@@ -0,0 +1,41 @@
+import {Component, Input, Output, EventEmitter, ChangeDetectionStrategy, ViewEncapsulation} from '@angular/core'
+import {DEFAULT_TEMPLATE, DEFAULT_STYLES} from './template';
+
+/**
+ * The default pagination controls component. Actually just a default implementation of a custom template.
+ */
+@Component({
+ selector: 'pagination-controls',
+ template: DEFAULT_TEMPLATE,
+ styles: [DEFAULT_STYLES],
+ changeDetection: ChangeDetectionStrategy.OnPush,
+ encapsulation: ViewEncapsulation.None
+})
+export class PaginationControlsComponent {
+
+ @Input() id: string;
+ @Input() maxSize: number = 7;
+ @Input()
+ get directionLinks(): boolean {
+ return this._directionLinks;
+ }
+ set directionLinks(value: boolean) {
+ this._directionLinks = !!value && value !== 'false';
+ }
+ @Input()
+ get autoHide(): boolean {
+ return this._autoHide;
+ }
+ set autoHide(value: boolean) {
+ this._autoHide = !!value && value !== 'false';
+ }
+ @Input() previousLabel: string = 'Previous';
+ @Input() nextLabel: string = 'Next';
+ @Input() screenReaderPaginationLabel: string = 'Pagination';
+ @Input() screenReaderPageLabel: string = 'page';
+ @Input() screenReaderCurrentLabel: string = `You're on page`;
+ @Output() pageChange: EventEmitter = new EventEmitter();
+
+ private _directionLinks: boolean = true;
+ private _autoHide: boolean = false;
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-controls.directive.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-controls.directive.ts
new file mode 100644
index 0000000..09f0e0d
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-controls.directive.ts
@@ -0,0 +1,209 @@
+import {ChangeDetectorRef, Directive, EventEmitter, Input, Output} from '@angular/core';
+import {Subscription} from 'rxjs';
+
+import {PaginationService} from './pagination.service';
+import {PaginationInstance} from './pagination-instance';
+
+export interface Page {
+ label: string;
+ value: any;
+}
+
+/**
+ * This directive is what powers all pagination controls components, including the default one.
+ * It exposes an API which is hooked up to the PaginationService to keep the PaginatePipe in sync
+ * with the pagination controls.
+ */
+@Directive({
+ selector: 'pagination-template,[pagination-template]',
+ exportAs: 'paginationApi'
+})
+export class PaginationControlsDirective {
+ @Input() id: string;
+ @Input() maxSize: number = 7;
+ @Output() pageChange: EventEmitter = new EventEmitter();
+ pages: Page[] = [];
+
+ private changeSub: Subscription;
+
+ constructor(private service: PaginationService,
+ private changeDetectorRef: ChangeDetectorRef) {
+ this.changeSub = this.service.change
+ .subscribe(id => {
+ if (this.id === id) {
+ this.updatePageLinks();
+ this.changeDetectorRef.markForCheck();
+ this.changeDetectorRef.detectChanges();
+ }
+ });
+ }
+
+ ngOnInit() {
+ if (this.id === undefined) {
+ this.id = this.service.defaultId();
+ }
+ this.updatePageLinks();
+ }
+
+ ngOnChanges(changes: any) {
+ this.updatePageLinks();
+ }
+
+ ngOnDestroy() {
+ this.changeSub.unsubscribe();
+ }
+
+ /**
+ * Go to the previous page
+ */
+ previous() {
+ if (this.getCurrent() - 1 > 0) {
+ this.setCurrent(this.getCurrent() - 1);
+ }
+ }
+
+ /**
+ * Go to the next page
+ */
+ next() {
+ if (this.getCurrent() < this.getLastPage()) {
+ this.setCurrent(this.getCurrent() + 1);
+ }
+ }
+
+ /**
+ * Returns true if current page is first page
+ */
+ isFirstPage(): boolean {
+ return this.getCurrent() === 1;
+ }
+
+ /**
+ * Returns true if current page is last page
+ */
+ isLastPage(): boolean {
+ return this.getLastPage() === this.getCurrent();
+ }
+
+ /**
+ * Set the current page number.
+ */
+ setCurrent(page: number) {
+ if (this.getCurrent() != page) {
+ this.pageChange.emit(page);
+ }
+ }
+
+ /**
+ * Get the current page number.
+ */
+ getCurrent(): number {
+ return this.service.getCurrentPage(this.id);
+ }
+
+ /**
+ * Returns the last page number
+ */
+ getLastPage(): number {
+ let inst = this.service.getInstance(this.id);
+ if (inst.totalItems < 1) {
+ // when there are 0 or fewer (an error case) items, there are no "pages" as such,
+ // but it makes sense to consider a single, empty page as the last page.
+ return 1;
+ }
+ return Math.ceil(inst.totalItems / inst.itemsPerPage);
+ }
+
+ /**
+ * Updates the page links and checks that the current page is valid. Should run whenever the
+ * PaginationService.change stream emits a value matching the current ID, or when any of the
+ * input values changes.
+ */
+ private updatePageLinks() {
+ let inst = this.service.getInstance(this.id);
+ const correctedCurrentPage = this.outOfBoundCorrection(inst);
+
+ if (correctedCurrentPage !== inst.currentPage) {
+ setTimeout(() => {
+ this.setCurrent(correctedCurrentPage);
+ this.pages = this.createPageArray(inst.currentPage, inst.itemsPerPage, inst.totalItems, this.maxSize);
+ });
+ } else {
+ this.pages = this.createPageArray(inst.currentPage, inst.itemsPerPage, inst.totalItems, this.maxSize);
+ }
+ }
+
+ /**
+ * Checks that the instance.currentPage property is within bounds for the current page range.
+ * If not, return a correct value for currentPage, or the current value if OK.
+ */
+ private outOfBoundCorrection(instance: PaginationInstance): number {
+ const totalPages = Math.ceil(instance.totalItems / instance.itemsPerPage);
+ if (totalPages < instance.currentPage && 0 < totalPages) {
+ return totalPages;
+ } else if (instance.currentPage < 1) {
+ return 1;
+ }
+
+ return instance.currentPage;
+ }
+
+ /**
+ * Returns an array of Page objects to use in the pagination controls.
+ */
+ private createPageArray(currentPage: number, itemsPerPage: number, totalItems: number, paginationRange: number): Page[] {
+ // paginationRange could be a string if passed from attribute, so cast to number.
+ paginationRange = +paginationRange;
+ let pages = [];
+ const totalPages = Math.ceil(totalItems / itemsPerPage);
+ const halfWay = Math.ceil(paginationRange / 2);
+
+ const isStart = currentPage <= halfWay;
+ const isEnd = totalPages - halfWay < currentPage;
+ const isMiddle = !isStart && !isEnd;
+
+ let ellipsesNeeded = paginationRange < totalPages;
+ let i = 1;
+
+ while (i <= totalPages && i <= paginationRange) {
+ let label;
+ let pageNumber = this.calculatePageNumber(i, currentPage, paginationRange, totalPages);
+ let openingEllipsesNeeded = (i === 2 && (isMiddle || isEnd));
+ let closingEllipsesNeeded = (i === paginationRange - 1 && (isMiddle || isStart));
+ if (ellipsesNeeded && (openingEllipsesNeeded || closingEllipsesNeeded)) {
+ label = '...';
+ } else {
+ label = pageNumber;
+ }
+ pages.push({
+ label: label,
+ value: pageNumber
+ });
+ i ++;
+ }
+ return pages;
+ }
+
+ /**
+ * Given the position in the sequence of pagination links [i],
+ * figure out what page number corresponds to that position.
+ */
+ private calculatePageNumber(i: number, currentPage: number, paginationRange: number, totalPages: number) {
+ let halfWay = Math.ceil(paginationRange / 2);
+ if (i === paginationRange) {
+ return totalPages;
+ } else if (i === 1) {
+ return i;
+ } else if (paginationRange < totalPages) {
+ if (totalPages - halfWay < currentPage) {
+ return totalPages - paginationRange + i;
+ } else if (halfWay < currentPage) {
+ return currentPage - halfWay + i;
+ } else {
+ return i;
+ }
+ } else {
+ return i;
+ }
+ }
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-instance.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-instance.ts
new file mode 100644
index 0000000..b200ea9
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination-instance.ts
@@ -0,0 +1,24 @@
+export interface PaginationInstance {
+ /**
+ * An optional ID for the pagination instance. Only useful if you wish to
+ * have more than once instance at a time in a given component.
+ */
+ id?: string;
+ /**
+ * The number of items per paginated page.
+ */
+ itemsPerPage: number;
+ /**
+ * The current (active) page.
+ */
+ currentPage: number;
+ /**
+ * The total number of items in the collection. Only useful when
+ * doing server-side paging, where the collection size is limited
+ * to a single page returned by the server API.
+ *
+ * For in-memory paging, this property should not be set, as it
+ * will be automatically set to the value of collection.length.
+ */
+ totalItems?: number;
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination.service.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination.service.ts
new file mode 100644
index 0000000..5641efe
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/pagination.service.ts
@@ -0,0 +1,111 @@
+import {EventEmitter} from '@angular/core'
+import {PaginationInstance} from './pagination-instance';
+
+export class PaginationService {
+
+ public change: EventEmitter = new EventEmitter();
+
+ private instances: { [id: string]: PaginationInstance } = {};
+ private DEFAULT_ID = 'DEFAULT_PAGINATION_ID';
+
+ public defaultId(): string { return this.DEFAULT_ID }
+
+ public register(instance: PaginationInstance) {
+ if (!instance.id) {
+ instance.id = this.DEFAULT_ID;
+ }
+
+ if (!this.instances[instance.id]) {
+ this.instances[instance.id] = instance;
+ this.change.emit(instance.id);
+ } else {
+ let changed = this.updateInstance(instance);
+ if (changed) {
+ this.change.emit(instance.id);
+ }
+ }
+ }
+
+ /**
+ * Check each property of the instance and update any that have changed. Return
+ * true if any changes were made, else return false.
+ */
+ private updateInstance(instance: PaginationInstance): boolean {
+ let changed = false;
+ for (let prop in this.instances[instance.id]) {
+ if (instance[prop] !== this.instances[instance.id][prop]) {
+ this.instances[instance.id][prop] = instance[prop];
+ changed = true;
+ }
+ }
+ return changed;
+ }
+
+ /**
+ * Returns the current page number.
+ */
+ public getCurrentPage(id: string): number {
+ if (this.instances[id]) {
+ return this.instances[id].currentPage;
+ }
+ }
+
+ /**
+ * Sets the current page number.
+ */
+ public setCurrentPage(id: string, page: number) {
+ if (this.instances[id]) {
+ let instance = this.instances[id];
+ let maxPage = Math.ceil(instance.totalItems / instance.itemsPerPage);
+ if (page <= maxPage && 1 <= page) {
+ this.instances[id].currentPage = page;
+ this.change.emit(id);
+ }
+ }
+ }
+
+ /**
+ * Sets the value of instance.totalItems
+ */
+ public setTotalItems(id: string, totalItems: number) {
+ if (this.instances[id] && 0 <= totalItems) {
+ this.instances[id].totalItems = totalItems;
+ this.change.emit(id);
+ }
+ }
+
+ /**
+ * Sets the value of instance.itemsPerPage.
+ */
+ public setItemsPerPage(id: string, itemsPerPage: number) {
+ if (this.instances[id]) {
+ this.instances[id].itemsPerPage = itemsPerPage;
+ this.change.emit(id);
+ }
+ }
+
+ /**
+ * Returns a clone of the pagination instance object matching the id. If no
+ * id specified, returns the instance corresponding to the default id.
+ */
+ public getInstance(id: string = this.DEFAULT_ID): PaginationInstance {
+ if (this.instances[id]) {
+ return this.clone(this.instances[id]);
+ }
+ return {};
+ }
+
+ /**
+ * Perform a shallow clone of an object.
+ */
+ private clone(obj: any): any {
+ var target = {};
+ for (var i in obj) {
+ if (obj.hasOwnProperty(i)) {
+ target[i] = obj[i];
+ }
+ }
+ return target;
+ }
+
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/template.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/template.ts
new file mode 100644
index 0000000..74b85a2
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-pagination/template.ts
@@ -0,0 +1,99 @@
+/**
+ * The default template and styles for the pagination links are borrowed directly
+ * from Zurb Foundation 6: http://foundation.zurb.com/sites/docs/pagination.html
+ */
+
+export const DEFAULT_TEMPLATE = `
+
+
+
+ `;
+
+export const DEFAULT_STYLES = `
+.ng2-pagination {
+ margin-left: 0;
+ margin-bottom: 1rem; }
+ .ng2-pagination::before, .ng2-pagination::after {
+ content: ' ';
+ display: table; }
+ .ng2-pagination::after {
+ clear: both; }
+ .ng2-pagination li {
+ -moz-user-select: none;
+ -webkit-user-select: none;
+ -ms-user-select: none;
+ margin-right: 0.0625rem;
+ cursor: pointer;
+ border-radius: 0; }
+ .ng2-pagination li {
+ cursor: pointer;
+ display: inline-block; }
+ .ng2-pagination a,
+ .ng2-pagination button {
+ color: #0a0a0a;
+ display: block;
+ padding: 0.1875rem 0.625rem;
+ border-radius: 0; }
+ .ng2-pagination a:hover,
+ .ng2-pagination button:hover {
+ background: #e6e6e6; }
+ .ng2-pagination .current {
+ padding: 0.1875rem 0.625rem;
+ background: #2199e8;
+ color: #fefefe;
+ cursor: default; }
+ .ng2-pagination .disabled {
+ padding: 0.1875rem 0.625rem;
+ color: #cacaca;
+ cursor: default; }
+ .ng2-pagination .disabled:hover {
+ background: transparent; }
+ .ng2-pagination .ellipsis::after {
+ content: '…';
+ padding: 0.1875rem 0.625rem;
+ color: #0a0a0a; }
+
+.ng2-pagination .pagination-previous a::before,
+.ng2-pagination .pagination-previous.disabled::before {
+ content: '«';
+ display: inline-block;
+ margin-right: 0.5rem; }
+
+.ng2-pagination .pagination-next a::after,
+.ng2-pagination .pagination-next.disabled::after {
+ content: '»';
+ display: inline-block;
+ margin-left: 0.5rem; }
+
+.ng2-pagination .show-for-sr {
+ position: absolute !important;
+ width: 1px;
+ height: 1px;
+ overflow: hidden;
+ clip: rect(0, 0, 0, 0); }`;
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/ng2-switch/ng2-switch.ts b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-switch/ng2-switch.ts
new file mode 100644
index 0000000..d5a04ae
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/ng2-switch/ng2-switch.ts
@@ -0,0 +1,185 @@
+//https://github.com/yuyang041060120/angular2-ui-switch
+//
+import { Component, Input, Output, EventEmitter, HostListener, forwardRef } from '@angular/core';
+import { NG_VALUE_ACCESSOR, ControlValueAccessor } from '@angular/forms';
+
+const UI_SWITCH_CONTROL_VALUE_ACCESSOR: any = {
+ provide: NG_VALUE_ACCESSOR,
+ useExisting: forwardRef(() => Ng2SwitchComponent),
+ multi: true
+};
+
+@Component({
+ selector: 'ngSwitch',
+ template: `
+
+
+
+
+ `,
+ styles: [`
+ .switch {
+ background: #f00;
+ border: 1px solid #dfdfdf;
+ position: relative;
+ display: inline-block;
+ box-sizing: content-box;
+ overflow: visible;
+ padding: 0;
+ margin: 0;
+ cursor: pointer;
+ box-shadow: rgb(223, 223, 223) 0 0 0 0 inset;
+ transition: 0.3s ease-out all;
+ -webkit-transition: 0.3s ease-out all;
+ }
+
+ small {
+ border-radius: 10%;
+ box-shadow: 0 1px 3px rgba(0, 0, 0, 0.4);
+ position: absolute;
+ top: 0;
+ left: 0;
+ transition: 0.3s ease-out all;
+ -webkit-transition: 0.3s ease-out all;
+ }
+
+ .switch-large {
+ width: 66px;
+ height: 40px;
+ border-radius: 4px;
+ }
+
+ .switch-large small {
+ width: 40px;
+ height: 40px;
+ }
+
+ .switch-medium {
+ width: 50px;
+ height: 30px;
+ border-radius: 3px;
+ }
+
+ .switch-medium small {
+ width: 30px;
+ height: 30px;
+ }
+
+ .switch-small {
+ width: 33px;
+ height: 20px;
+ border-radius: 2px;
+ }
+
+ .switch-small small {
+ width: 20px;
+ height: 20px;
+ }
+
+ .checked {
+ background: rgb(100, 189, 99);
+ border-color: rgb(100, 189, 99);
+ }
+
+ .switch-large.checked small {
+ left: 26px;
+ }
+
+ .switch-medium.checked small {
+ left: 20px;
+ }
+
+ .switch-small.checked small {
+ left: 13px;
+ }
+
+ .disabled {
+ opacity: .50;
+ cursor: not-allowed;
+ }
+ `],
+ providers: [UI_SWITCH_CONTROL_VALUE_ACCESSOR]
+})
+export class Ng2SwitchComponent implements ControlValueAccessor {
+ private onTouchedCallback = (v: any) => {
+ };
+ private onChangeCallback = (v: any) => {
+ };
+
+ private _checked: boolean;
+ private _disabled: boolean;
+ private _reverse: boolean;
+
+ @Input() set checked(v: boolean) {
+ this._checked = v !== false;
+ }
+
+ get checked() {
+ return this._checked;
+ }
+
+ @Input() set disabled(v: boolean) {
+ this._disabled = v !== false;
+ };
+
+ get disabled() {
+ return this._disabled;
+ }
+
+ @Input() set reverse(v: boolean) {
+ this._reverse = v !== false;
+ };
+
+ get reverse() {
+ return this._reverse;
+ }
+
+ @Input() size: string = 'medium';
+ @Output() change = new EventEmitter();
+ @Input() color: string = 'rgb(100, 189, 99)';
+ @Input() switchOffColor: string = '';
+ @Input() switchColor: string = '#fff';
+ defaultBgColor: string = '#fff';
+ defaultBoColor: string = '#dfdfdf';
+
+ getColor(flag) {
+ if (flag === 'borderColor') return this.defaultBoColor;
+ if (flag === 'switchColor') {
+ if (this.reverse) return !this.checked ? this.switchColor : this.switchOffColor || this.switchColor;
+ return this.checked ? this.switchColor : this.switchOffColor || this.switchColor;
+ }
+ if (this.reverse) return !this.checked ? this.color : this.defaultBgColor;
+ return this.checked ? this.color : this.defaultBgColor;
+ }
+
+ @HostListener('click')
+ onToggle() {
+ if (this.disabled) return;
+ this.checked = !this.checked;
+ this.change.emit(this.checked);
+ this.onChangeCallback(this.checked);
+ this.onTouchedCallback(this.checked);
+ }
+
+ writeValue(obj: any): void {
+ if (obj !== this.checked) {
+ this.checked = !!obj;
+ }
+ }
+
+ registerOnChange(fn: any) {
+ this.onChangeCallback = fn;
+ }
+
+ registerOnTouched(fn: any) {
+ this.onTouchedCallback = fn;
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/bar.ts b/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/bar.ts
new file mode 100644
index 0000000..fc07f43
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/bar.ts
@@ -0,0 +1,64 @@
+import { Component, OnInit, OnDestroy, Input, Host } from '@angular/core';
+//import { NgClass, NgStyle } from '@angular/common';
+
+import { Progress } from './progress';
+
+@Component({
+ selector: 'bar, [bar]',
+ //directives: [NgClass, NgStyle],
+ template: `
+
+`
+})
+export class Bar implements OnInit, OnDestroy {
+ @Input() public type: string;
+
+ @Input() public get value(): number {
+ return this._value;
+ }
+
+ public set value(v: number) {
+ if (!v && v !== 0) {
+ return;
+ }
+ this._value = v;
+ this.recalculatePercentage();
+ }
+
+ public percent: number = 0;
+ public transition: string;
+
+ private _value: number;
+
+ constructor( @Host() public progress: Progress) {
+ }
+
+ ngOnInit() {
+ this.progress.addBar(this);
+ }
+
+ ngOnDestroy() {
+ this.progress.removeBar(this);
+ }
+
+ public recalculatePercentage() {
+ this.percent = +(100 * this.value / this.progress.max).toFixed(2);
+
+ let totalPercentage = this.progress.bars.reduce(function (total, bar) {
+ return total + bar.percent;
+ }, 0);
+
+ if (totalPercentage > 100) {
+ this.percent -= totalPercentage - 100;
+ }
+ }
+}
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/progress.ts b/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/progress.ts
new file mode 100644
index 0000000..a3c489f
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/progress.ts
@@ -0,0 +1,50 @@
+import { Directive, OnInit, Input, HostBinding } from '@angular/core';
+import { Bar } from './bar';
+
+const progressConfig = {
+ animate: true,
+ max: 100
+};
+
+@Directive({ selector: 'bs-progress, [progress]' })
+export class Progress implements OnInit {
+ @Input() public animate: boolean;
+
+ @HostBinding('attr.max')
+ @Input() public get max(): number {
+ return this._max;
+ }
+
+ @HostBinding('class') private addClass = 'progress';
+
+ public set max(v: number) {
+ this._max = v;
+ this.bars.forEach((bar: Bar) => {
+ bar.recalculatePercentage();
+ });
+ }
+
+ public bars: Array = [];
+
+ private _max: number;
+
+ constructor() {
+ }
+
+ ngOnInit() {
+ this.animate = this.animate !== false;
+ this.max = typeof this.max === 'number' ? this.max : progressConfig.max;
+ }
+
+
+ public addBar(bar: Bar) {
+ if (!this.animate) {
+ bar.transition = 'none';
+ }
+ this.bars.push(bar);
+ }
+
+ public removeBar(bar: Bar) {
+ this.bars.splice(this.bars.indexOf(bar), 1);
+ }
+}
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/progressbar.ts b/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/progressbar.ts
new file mode 100644
index 0000000..7e36081
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/app/shared/progressbar/progressbar.ts
@@ -0,0 +1,23 @@
+import { Component, Input } from '@angular/core';
+//import { NgClass, NgStyle } from '@angular/common';
+
+import { Progress } from './progress';
+import { Bar } from './bar';
+
+@Component({
+ selector: 'progressbar, [progressbar]',
+ //directives: [Progress, Bar],
+ template: `
+
+
+
+
+
+ `
+})
+export class Progressbar {
+ @Input() private animate: boolean;
+ @Input() private max: number;
+ @Input() private type: string;
+ @Input() private value: number;
+}
diff --git a/src/LanBackup.WebApp/ClientApp/boot-client.ts b/src/LanBackup.WebApp/ClientApp/boot-client.ts
new file mode 100644
index 0000000..b34b923
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/boot-client.ts
@@ -0,0 +1,30 @@
+import 'angular2-universal-polyfills/browser';
+import { enableProdMode } from '@angular/core';
+import { platformUniversalDynamic } from 'angular2-universal';
+import { AppModule } from './app/app.module';
+
+import * as $ from 'jquery';
+import 'bootstrap';
+//import { AppInsightsModule, AppInsightsService } from 'ng2-appinsights';
+
+// Enable either Hot Module Reloading or production mode
+if (module['hot']) {
+ module['hot'].accept();
+ module['hot'].dispose(() => { platform.destroy(); });
+} else {
+ enableProdMode();
+}
+
+// Boot the application, either now or when the DOM content is loaded
+const platform = platformUniversalDynamic();
+const bootApplication = () => { platform.bootstrapModule(AppModule); };
+if (document.readyState === 'complete') {
+ bootApplication();
+} else {
+ document.addEventListener('DOMContentLoaded', bootApplication);
+}
+
+//var appIns: AppInsightsService = new AppInsightsService('');
+//appIns.Init({
+// instrumentationKey: '9f667285-ff2c-4626-a8da-1db518593323' //TODO - MOVE INTO A CONFIG FILE THAT SHOULD NOT BE COMMITED
+//});
\ No newline at end of file
diff --git a/src/LanBackup.WebApp/ClientApp/boot-server.ts b/src/LanBackup.WebApp/ClientApp/boot-server.ts
new file mode 100644
index 0000000..c29916f
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/boot-server.ts
@@ -0,0 +1,33 @@
+import 'angular2-universal-polyfills';
+import 'zone.js';
+import { createServerRenderer, RenderResult } from 'aspnet-prerendering';
+import { enableProdMode } from '@angular/core';
+import { platformNodeDynamic } from 'angular2-universal';
+import { AppModule } from './app/app.module';
+
+enableProdMode();
+const platform = platformNodeDynamic();
+
+export default createServerRenderer(params => {
+ return new Promise((resolve, reject) => {
+ const requestZone = Zone.current.fork({
+ name: 'angular-universal request',
+ properties: {
+ baseUrl: '/',
+ requestUrl: params.url,
+ originUrl: params.origin,
+ preboot: false,
+ document: ''
+ },
+ onHandleError: (parentZone, currentZone, targetZone, error) => {
+ // If any error occurs while rendering the module, reject the whole operation
+ reject(error);
+ return true;
+ }
+ });
+
+ return requestZone.run>(() => platform.serializeModule(AppModule)).then(html => {
+ resolve({ html: html });
+ }, reject);
+ });
+});
diff --git a/src/LanBackup.WebApp/ClientApp/dist/_placeholder.txt b/src/LanBackup.WebApp/ClientApp/dist/_placeholder.txt
new file mode 100644
index 0000000..b22cc15
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/dist/_placeholder.txt
@@ -0,0 +1,9 @@
+------------------------------------------------------------------
+Don't delete this file. Do include it in your source control repo.
+------------------------------------------------------------------
+
+This file exists as a workaround for https://github.com/dotnet/cli/issues/1396
+('dotnet publish' does not publish any directories that didn't exist or were
+empty before the publish script started).
+
+Hopefully, this can be removed after the move to the new MSBuild.
diff --git a/src/LanBackup.WebApp/ClientApp/test/boot-tests.ts b/src/LanBackup.WebApp/ClientApp/test/boot-tests.ts
new file mode 100644
index 0000000..6121b04
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/test/boot-tests.ts
@@ -0,0 +1,32 @@
+// Load required polyfills and testing libraries
+import 'angular2-universal-polyfills';
+import 'zone.js/dist/long-stack-trace-zone';
+import 'zone.js/dist/proxy.js';
+import 'zone.js/dist/sync-test';
+import 'zone.js/dist/jasmine-patch';
+import 'zone.js/dist/async-test';
+import 'zone.js/dist/fake-async-test';
+import * as testing from '@angular/core/testing';
+import * as testingBrowser from '@angular/platform-browser-dynamic/testing';
+
+// There's no typing for the `__karma__` variable. Just declare it as any
+declare var __karma__: any;
+declare var require: any;
+
+// Prevent Karma from running prematurely
+__karma__.loaded = function () {};
+
+// First, initialize the Angular testing environment
+testing.getTestBed().initTestEnvironment(
+ testingBrowser.BrowserDynamicTestingModule,
+ testingBrowser.platformBrowserDynamicTesting()
+);
+
+// Then we find all the tests
+const context = require.context('../', true, /\.spec\.ts$/);
+
+// And load the modules
+context.keys().map(context);
+
+// Finally, start Karma to run the tests
+__karma__.start();
diff --git a/src/LanBackup.WebApp/ClientApp/test/karma.conf.js b/src/LanBackup.WebApp/ClientApp/test/karma.conf.js
new file mode 100644
index 0000000..e8162c4
--- /dev/null
+++ b/src/LanBackup.WebApp/ClientApp/test/karma.conf.js
@@ -0,0 +1,25 @@
+// Karma configuration file, see link for more information
+// https://karma-runner.github.io/0.13/config/configuration-file.html
+
+module.exports = function (config) {
+ config.set({
+ basePath: '.',
+ frameworks: ['jasmine'],
+ files: [
+ '../../wwwroot/dist/vendor.js',
+ './boot-tests.ts'
+ ],
+ preprocessors: {
+ './boot-tests.ts': ['webpack']
+ },
+ reporters: ['progress'],
+ port: 9876,
+ colors: true,
+ logLevel: config.LOG_INFO,
+ autoWatch: true,
+ browsers: ['Chrome'],
+ singleRun: false,
+ webpack: require('../../webpack.config.js').filter(config => config.target !== 'node'), // Test against client bundle, because tests run in a browser
+ webpackMiddleware: { stats: 'errors-only' }
+ });
+};
diff --git a/src/LanBackup.WebApp/Controllers/API/BackupConfigController.cs b/src/LanBackup.WebApp/Controllers/API/BackupConfigController.cs
new file mode 100644
index 0000000..00b3419
--- /dev/null
+++ b/src/LanBackup.WebApp/Controllers/API/BackupConfigController.cs
@@ -0,0 +1,220 @@
+using System.Collections.Generic;
+using System.Linq;
+using Microsoft.AspNetCore.Mvc;
+using LanBackup.ModelsCore;
+using LanBackup.DataCore;
+using Microsoft.AspNetCore.Authorization;
+using System.Threading.Tasks;
+using System;
+using AutoMapper;
+using LanBackup.WebApp.Models.DTO;
+using AutoMapper.QueryableExtensions;
+using LanBackup.WebApp.Models.Telemetry;
+
+namespace LanBackup.WebApp.Controllers
+{
+
+ ///
+ /// BackupConfig REST Web api controller for handling backup configurations
+ ///
+ [Authorize]
+ [Produces("application/json")]
+ [Route("api/[controller]")]
+ public class BackupConfigController : Controller
+ {
+
+ private readonly IMapper mapper;
+ private BackupsContext _context;
+ private ITelemetryLogger telemetry;
+
+ public BackupConfigController(IMapper mapper, BackupsContext context, ITelemetryLogger telemetry)
+ {
+ this.mapper = mapper;
+ this._context = context;
+ this.telemetry = telemetry;
+ }
+
+
+ ///
+ /// retrieve all backup configurations
+ ///
+ ///
+ [AllowAnonymous]
+ [HttpGet]
+ [ProducesResponseType(typeof(IEnumerable), 200)]
+ [ProducesResponseType(typeof(PaginatedList), 200)]
+ public async Task Get([FromHeader] string idx, [FromHeader] string siz)
+ //public IEnumerable Get()
+ {
+ //return new DatabaseManager(_context).GetBackupConfigs();
+ if (!string.IsNullOrEmpty(idx) && !string.IsNullOrEmpty(siz))
+ {
+ return new OkObjectResult(
+ (await PaginatedList.CreateAsync(_context.Backups, Convert.ToInt32(idx), Convert.ToInt32(siz), o=>o.ClientIP, this.mapper))
+ );
+ }
+ return new OkObjectResult(_context.Backups.ProjectTo().ToList());
+ }
+
+ ///
+ /// retrieve backup configuration by ID
+ ///
+ ///
+ ///
+ [AllowAnonymous]
+ [HttpGet("{id}")]
+ [ProducesResponseType(typeof(BackupConfigurationDTO), 200)]
+ [ProducesResponseType(typeof(BackupConfigurationDTO), 404)]
+ public IActionResult Get(string id)
+ {
+ var res = new DatabaseManager(_context).GetBackupConfig(id);
+ if (res == null)
+ {
+ return NotFound();
+ }
+ var mapped = mapper.Map(res);
+ return new ObjectResult(mapped);
+ }
+
+ ///
+ /// retrieve backup configuration by ID
+ ///
+ ///
+ ///
+ [AllowAnonymous]
+ [HttpGet("client/{clientid}")]
+ [ProducesResponseType(typeof(IEnumerable), 200)]
+ [ProducesResponseType(typeof(IEnumerable), 404)]
+ public IActionResult GetByCient(string clientid)
+ {
+ var results = new DatabaseManager(_context).GetBackupConfigByClient(clientid);
+ if (results == null || results.Count() == 0)
+ return NotFound();
+ var mapped = mapper.Map, IEnumerable>(results);
+ return new ObjectResult(mapped);
+ }
+
+
+ ///
+ /// create backup configuration
+ ///
+ ///
+ //[Authorize(Roles = "Admin")]
+ [AllowAnonymous]
+ [HttpPost]
+ [ProducesResponseType(typeof(BackupConfigurationDTO), 200)]
+ [ProducesResponseType(typeof(BackupConfigurationDTO), 400)]
+ public async Task Create([FromBody]BackupConfigurationDTO backupDTO)
+ {
+ if (ModelState.IsValid)
+ {
+ try
+ {
+ var backup = mapper.Map(backupDTO);
+ _context.Add(backup);
+ var res = await _context.SaveChangesAsync();
+ if (res > 0)
+ {
+ var mapped = mapper.Map(backup);
+ return new ObjectResult(mapped);
+ }
+ }
+ catch (Exception ex)
+ {
+ this.telemetry.TrackException(ex);
+ return BadRequest(
+ new { message = ex.Message }
+ );
+ }
+ }
+ else
+ {
+ string msg = string.Join("|", ModelState.Values.SelectMany(e => e.Errors).Select(s => s.ErrorMessage));
+ return BadRequest(msg);
+ }
+ return BadRequest();
+ }
+
+
+ ///
+ /// Update backup configuration
+ ///
+ ///
+ ///
+ /// affected records
+ //[Authorize(Roles = "Admin")]
+ [AllowAnonymous]
+ [HttpPut("{id}")]
+ [ProducesResponseType(typeof(BackupConfigurationDTO), 200)]
+ [ProducesResponseType(typeof(BackupConfigurationDTO), 400)]
+ public async Task Update(string id, [FromBody]BackupConfigurationDTO backupDTO)
+ {
+ if (id != backupDTO.ID)
+ {
+ return BadRequest("Ids do not match");
+ }
+ if (ModelState.IsValid)
+ {
+ var backup = mapper.Map(backupDTO);
+ _context.Update(backup);
+ try
+ {
+ var res = await _context.SaveChangesAsync();
+ if (res > 0)
+ {
+ var mapped = mapper.Map(backup);
+ return new ObjectResult(mapped);//retun back the updated object
+ }
+ }
+ catch (Exception ex)
+ {
+ this.telemetry.TrackException(ex);
+ return BadRequest(
+ new { message = ex.Message }
+ );
+
+ }
+ }
+ else
+ {
+ string msg = string.Join("|", ModelState.Values.SelectMany(e => e.Errors).Select(s => s.ErrorMessage));
+ return BadRequest(msg);
+ }
+ return BadRequest();
+ }
+
+ ///
+ /// delete backup configuration by id
+ ///
+ ///
+ ///
+ //[Authorize(Roles = "Admin")]
+ [AllowAnonymous]
+ [HttpDelete("{id}")]
+ [ProducesResponseType(typeof(string), 200)]
+ [ProducesResponseType(typeof(string), 404)]
+ public async Task Delete(string id)
+ {
+ try
+ {
+ BackupConfiguration backup = _context.Backups.Find(id);
+ _context.Backups.Remove(backup);
+ var res = await _context.SaveChangesAsync();
+ if (res > 0)
+ {
+ var mapped = mapper.Map(backup);
+ return new ObjectResult(mapped);//retun back old Object
+ }
+ return NotFound(id);
+ }
+ catch (Exception ex)
+ {
+ this.telemetry.TrackException(ex);
+ return BadRequest(
+ new { message = ex.Message }
+ );
+ }
+ return NotFound(id);
+ }
+ }
+}
diff --git a/src/LanBackup.WebApp/Controllers/API/LogsController.cs b/src/LanBackup.WebApp/Controllers/API/LogsController.cs
new file mode 100644
index 0000000..f720e54
--- /dev/null
+++ b/src/LanBackup.WebApp/Controllers/API/LogsController.cs
@@ -0,0 +1,168 @@
+using System.Collections.Generic;
+using System.Linq;
+using Microsoft.AspNetCore.Mvc;
+using LanBackup.ModelsCore;
+using LanBackup.DataCore;
+using Microsoft.AspNetCore.Authorization;
+using System.Threading.Tasks;
+using System;
+using LanBackup.WebApp.Models.DTO;
+using AutoMapper;
+using AutoMapper.QueryableExtensions;
+using LanBackup.WebApp.Models.Telemetry;
+
+namespace LanBackup.WebApp.Controllers
+{
+
+ ///
+ /// BackupLogs REST Web api controller for handling logs
+ ///
+ [Authorize]
+ [Produces("application/json")]
+ [Route("api/[controller]")]
+ public class LogsController : Controller
+ {
+ private readonly IMapper mapper;
+ private BackupsContext _context;
+ private ITelemetryLogger telemetry;
+
+
+ public LogsController(IMapper mapper, BackupsContext context, ITelemetryLogger telemetry)
+ {
+ this.mapper = mapper;
+ this._context = context;
+ this.telemetry = telemetry;
+ }
+
+
+ /////
+ ///// retrieves all logs from DB
+ /////
+ /////
+ //[AllowAnonymous]
+ //[HttpGet]
+ //[ProducesResponseType(typeof(IEnumerable), 200)]
+ //public IActionResult Get()
+ //{
+ // return new OkObjectResult(_context.Logs.ToList());
+ // //return new ObjectResult(_context.Logs.ToList());
+ //}
+
+
+ ///
+ /// retrieves paginated logs from DB
+ ///
+ /// page index
+ /// page size
+ ///
+ [AllowAnonymous]
+ [HttpGet]
+ //[HttpGet("{pageIndex}/{pageSize}")]
+ [ProducesResponseType(typeof(IEnumerable), 200)]
+ [ProducesResponseType(typeof(PaginatedList), 200)]
+ public async Task Get([FromHeader] string idx, [FromHeader] string siz)
+ {
+ //StringValues val1, val2;
+ //HttpContext.Request.Headers.TryGetValue("idx", out val1) &&
+ //HttpContext.Request.Headers.TryGetValue("siz", out val2)
+ if (!string.IsNullOrEmpty(idx) && !string.IsNullOrEmpty(siz))
+ {
+ return new OkObjectResult(
+ (await PaginatedList.CreateAsync(_context.Logs, Convert.ToInt32(idx), Convert.ToInt32(siz), (or)=> or.DateTime, this.mapper))
+ );
+ }
+ return new OkObjectResult(_context.Logs.ProjectTo().ToList());
+ }
+
+
+ ///
+ /// retrieves alog record by ID
+ ///
+ ///
+ ///
+ [AllowAnonymous]
+ [HttpGet("{id}")]
+ [ProducesResponseType(typeof(BackupLogDTO), 200)]
+ [ProducesResponseType(typeof(BackupLogDTO), 404)]
+ public IActionResult Get(int id)
+ {
+ var result = _context.Logs.SingleOrDefault(p => p.ID == id);
+ if (result == null)
+ {
+ return NotFound();
+ }
+ var mapped = mapper.Map(result);
+ return new OkObjectResult(mapped);
+ }
+
+
+ ///
+ /// retrieve all logs of a clientIP
+ ///
+ ///
+ ///
+ [AllowAnonymous]
+ [HttpGet("client/{clientid}")]
+ [ProducesResponseType(typeof(IEnumerable), 200)]
+ [ProducesResponseType(typeof(IEnumerable), 404)]
+ public IActionResult GetByCientID(string clientid)
+ {
+ var results = _context.Logs.Where(p => p.ClientIP == clientid).OrderByDescending(o => o.DateTime);
+ if (results == null || results.Count() == 0)
+ return NotFound();
+ var mapped = mapper.Map, IEnumerable>(results);
+ return new OkObjectResult(mapped);
+ }
+
+
+ ///
+ /// retrieves all logs of a specific configuration
+ ///
+ ///
+ ///
+ [AllowAnonymous]
+ [HttpGet("config/{configurationid}")]
+ [ProducesResponseType(typeof(IEnumerable), 200)]
+ [ProducesResponseType(typeof(IEnumerable), 404)]
+ public IActionResult GetByConfigurationID(string configurationid)
+ {
+ var results = _context.Logs.Where(p => p.ConfigurationID == configurationid).OrderByDescending(o => o.DateTime);
+ if (results == null || results.Count() == 0)
+ return NotFound();
+ var mapped = mapper.Map, IEnumerable>(results);
+ return new ObjectResult(mapped);
+ }
+
+
+
+ //[EnableCors("AllowSpecificOrigin")]
+ ///
+ /// Create an entry in the logs
+ ///
+ ///
+ ///
+ [AllowAnonymous]//[Authorize(Roles = "Admin")]
+ [HttpPost]
+ [ProducesResponseType(typeof(int), 200)]
+ [ProducesResponseType(typeof(int), 400)]
+ public async Task Create([FromBody]BackupLog log)
+ {
+ if (ModelState.IsValid)
+ {
+ _context.Logs.Add(log);
+ var res = await _context.SaveChangesAsync();
+ if (res >0 )
+ return new ObjectResult(log.ID);//retun back the new ID
+ }
+ else
+ {
+ string msg = string.Join("|", ModelState.Values.SelectMany(e => e.Errors).Select(s => s.ErrorMessage));
+ return BadRequest(msg);
+ }
+ return BadRequest();
+ }
+
+
+
+ }
+}
diff --git a/src/LanBackup.WebApp/Controllers/API/UsersController.cs b/src/LanBackup.WebApp/Controllers/API/UsersController.cs
new file mode 100644
index 0000000..c9807b7
--- /dev/null
+++ b/src/LanBackup.WebApp/Controllers/API/UsersController.cs
@@ -0,0 +1,246 @@
+using LanBackup.WebApp.Data;
+using LanBackup.WebApp.Models;
+using Microsoft.AspNetCore.Authorization;
+using Microsoft.AspNetCore.Identity;
+using Microsoft.AspNetCore.Identity.EntityFrameworkCore;
+using Microsoft.AspNetCore.Mvc;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Threading.Tasks;
+using LanBackup.WebApp.Models.Telemetry;
+using System.Net;
+
+namespace LanBackup.WebApp.Controllers
+{
+ ///
+ /// BackupConfig REST Web api controller for handling users
+ ///
+ [Authorize]
+ [Produces("application/json")]
+ [Route("api/[controller]")]
+ public class UsersController : Controller
+ {
+
+
+ private readonly UserManager _userManager;
+ private readonly SignInManager _signInManager;
+ private readonly ApplicationDbContext _appDbContext;
+ private ITelemetryLogger telemetry;
+
+
+ public UsersController(
+ ApplicationDbContext appDbContex,
+ UserManager userManager,
+ SignInManager signInManager,
+ ITelemetryLogger telemetry
+ )
+ {
+ this.telemetry = telemetry;
+ _userManager = userManager;
+ _signInManager = signInManager;
+ _appDbContext = appDbContex;
+ }
+
+
+
+
+ [HttpPost("register")]
+ [AllowAnonymous]
+ [ProducesResponseType(typeof(IdentityResult), 200)]
+ [ProducesResponseType(typeof(IdentityResult), 400)]
+ public async Task Register([FromBody]User dtouser)
+ {
+ try
+ {
+
+ dtouser.IsAdmin = false;
+
+ var user = new ApplicationUser { UserName = dtouser.Email, Email = dtouser.Email };
+ var result = await _userManager.CreateAsync(user, dtouser.Password);
+ if (result.Succeeded)
+ {
+
+ //update is Admin
+ var adminRole = _appDbContext.Roles.FirstOrDefault(r => r.NormalizedName == "ADMIN");
+ var iuser = _appDbContext.Users.FirstOrDefault(u => u.Email == dtouser.Email);
+ dtouser.IsAdmin = _appDbContext.UserRoles.FirstOrDefault(u => u.RoleId == adminRole.Id && u.UserId == iuser.Id) != null;
+
+ await _signInManager.SignInAsync(user, isPersistent: false);
+ dtouser.Succeeded = true;
+ this.telemetry.TrackEvent("NewRegistration");
+ return new ObjectResult(dtouser);
+ }
+ else
+ {
+ string msg = string.Join("|", result.Errors.Select(e => e.Description));
+ return BadRequest(msg);
+ }
+ }
+ catch (Exception ex)
+ {
+ this.telemetry.TrackException(ex);
+ return BadRequest(ex.Message);
+ }
+ return BadRequest();
+ }
+
+
+
+
+ [HttpPost("login")]
+ [AllowAnonymous]
+ [ProducesResponseType(typeof(User), 200)]
+ [ProducesResponseType(typeof(User), 400)]
+ public async Task Login([FromBody]User dtouser)
+ {
+ try
+ {
+ dtouser.Succeeded = false;
+ // This doesn't count login failures towards account lockout
+ // To enable password failures to trigger account lockout, set lockoutOnFailure: true
+ var result = await _signInManager.PasswordSignInAsync(dtouser.Email, dtouser.Password, isPersistent: false, lockoutOnFailure: false);
+ if (result.Succeeded)
+ {
+ dtouser.Succeeded = result.Succeeded;
+ dtouser.IsLockedOut = result.IsLockedOut;
+
+ //update is Admin
+ var adminRole = _appDbContext.Roles.FirstOrDefault(r => r.NormalizedName == "ADMIN");
+ var iuser = _appDbContext.Users.FirstOrDefault(u => u.Email == dtouser.Email);
+ dtouser.IsAdmin = _appDbContext.UserRoles.FirstOrDefault(u => u.RoleId == adminRole.Id && u.UserId == iuser.Id) != null;
+
+ var user = new ApplicationUser { UserName = dtouser.Email, Email = dtouser.Email };
+
+ this.telemetry.TrackEvent("LoginSuccess");
+ return Ok(dtouser);
+ }
+ else
+ {
+ this.telemetry.TrackEvent("LoginFailure");
+ dtouser.Errors = new IdentityError[] { new IdentityError { Description = "Login failed" } };
+ }
+ return Ok(dtouser);
+ }
+ catch (Exception ex)
+ {
+ this.telemetry.TrackException(ex);
+ return BadRequest(ex.Message);
+ }
+ }
+
+
+
+
+
+ [HttpPost("pwchange")]
+ [AllowAnonymous] //TODO - allow only authenticated users to do the update
+ [ProducesResponseType(typeof(User), 200)]
+ [ProducesResponseType(typeof(string), 400)]
+ [ProducesResponseType(typeof(string), 401)]
+ public async Task ChangePasssword([FromBody]User dtouser)
+ {
+ try
+ {
+ var user = await _userManager.GetUserAsync(HttpContext.User);
+ if (user != null)
+ {
+ dtouser.Succeeded = false;
+ var result = await _userManager.ChangePasswordAsync(user, dtouser.Password, dtouser.NewPassword);
+ if (result.Succeeded)
+ {
+ dtouser.Succeeded = result.Succeeded;
+ dtouser.Errors = result.Errors.ToArray();
+ await _signInManager.SignInAsync(user, isPersistent: false);
+ this.telemetry.TrackEvent("ChangePasswordSuccess");
+ return Ok(dtouser);
+ }
+ else
+ {
+ this.telemetry.TrackEvent("ChangePasswordFailure");
+ string msg = string.Join("|", result.Errors.Select(e => e.Description));
+ return BadRequest(msg);
+ }
+ }
+ return StatusCode((int)HttpStatusCode.Unauthorized, "User not logged in");// Unauthorized();
+ }
+ catch (Exception ex)
+ {
+ this.telemetry.TrackException(ex);
+ return BadRequest(ex.Message);
+ }
+ }
+
+
+
+
+
+ [HttpGet("list")]
+ [AllowAnonymous]
+ [ProducesResponseType(typeof(IEnumerable), 200)]
+ public async Task Users()
+ {
+ var adminRole = _appDbContext.Roles.FirstOrDefault(r => r.NormalizedName == "ADMIN");
+ List allusers = new List