diff --git a/.gitignore b/.gitignore index f5a1f07..99cacd5 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,5 @@ node_modules/ bundle.js factorio-server-manager +auth.level-db *.exe diff --git a/app/index.html b/app/index.html index 797eaac..e60cc66 100644 --- a/app/index.html +++ b/app/index.html @@ -35,6 +35,6 @@ - + diff --git a/auth.go b/auth.go index 29eee34..53b0b01 100644 --- a/auth.go +++ b/auth.go @@ -2,6 +2,7 @@ package main import ( "log" + "os" "github.com/apexskier/httpauth" ) @@ -11,10 +12,29 @@ type AuthHTTP struct { aaa httpauth.Authorizer } +type User struct { + Username string + Password string + Role string +} + func initAuth() *AuthHTTP { return &AuthHTTP{} } +func (auth *AuthHTTP) createAuthDb(backendFile string) error { + var err error + os.Mkdir(backendFile, 0755) + + auth.backend, err = httpauth.NewLeveldbAuthBackend(backendFile) + if err != nil { + log.Printf("Error creating Auth backend: %s", err) + return err + } + + return nil +} + func (auth *AuthHTTP) createRoles() { var err error roles := make(map[string]httpauth.Role) @@ -27,7 +47,7 @@ func (auth *AuthHTTP) createRoles() { } } -func (auth *AuthHTTP) createUser(username, role, password, email string) error { +func (auth *AuthHTTP) createUser(username, password, role, email string) error { user := httpauth.UserData{Username: username, Role: role, Email: email} err := auth.backend.SaveUser(user) if err != nil { diff --git a/auth.leveldb/000004.ldb b/auth.leveldb/000004.ldb new file mode 100644 index 0000000..213380f Binary files /dev/null and b/auth.leveldb/000004.ldb differ diff --git a/auth.leveldb/000007.ldb b/auth.leveldb/000007.ldb new file mode 100644 index 0000000..6558f66 Binary files /dev/null and b/auth.leveldb/000007.ldb differ diff --git a/auth.leveldb/000012.ldb b/auth.leveldb/000012.ldb new file mode 100644 index 0000000..837cc55 Binary files /dev/null and b/auth.leveldb/000012.ldb differ diff --git a/auth.leveldb/000015.ldb b/auth.leveldb/000015.ldb new file mode 100644 index 0000000..a0bac4b Binary files /dev/null and b/auth.leveldb/000015.ldb differ diff --git a/auth.leveldb/000020.ldb b/auth.leveldb/000020.ldb new file mode 100644 index 0000000..136270f Binary files /dev/null and b/auth.leveldb/000020.ldb differ diff --git a/auth.leveldb/000023.ldb b/auth.leveldb/000023.ldb new file mode 100644 index 0000000..e1d883e Binary files /dev/null and b/auth.leveldb/000023.ldb differ diff --git a/auth.leveldb/000028.ldb b/auth.leveldb/000028.ldb new file mode 100644 index 0000000..dda807c Binary files /dev/null and b/auth.leveldb/000028.ldb differ diff --git a/auth.leveldb/000029.log b/auth.leveldb/000029.log new file mode 100644 index 0000000..eea5cff Binary files /dev/null and b/auth.leveldb/000029.log differ diff --git a/auth.leveldb/CURRENT b/auth.leveldb/CURRENT new file mode 100644 index 0000000..caa721a --- /dev/null +++ b/auth.leveldb/CURRENT @@ -0,0 +1 @@ +MANIFEST-000030 diff --git a/auth.leveldb/LOCK b/auth.leveldb/LOCK new file mode 100644 index 0000000..e69de29 diff --git a/auth.leveldb/LOG b/auth.leveldb/LOG new file mode 100644 index 0000000..7811350 --- /dev/null +++ b/auth.leveldb/LOG @@ -0,0 +1,149 @@ +=============== Apr 29, 2016 (EDT) =============== +23:19:38.770534 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:19:38.771110 db@open opening +23:19:38.775638 version@stat F·[] S·0B[] Sc·[] +23:19:38.783797 db@janitor F·2 G·0 +23:19:38.783861 db@open done T·12.719123ms +23:19:38.783898 db@close closing +23:19:38.783970 db@close done T·67.905µs +=============== Apr 29, 2016 (EDT) =============== +23:19:38.784076 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:19:38.784282 version@stat F·[] S·0B[] Sc·[] +23:19:38.784309 db@open opening +23:19:38.784395 journal@recovery F·1 +23:19:38.784714 journal@recovery recovering @1 +23:19:38.786680 version@stat F·[] S·0B[] Sc·[] +23:19:38.789225 db@janitor F·2 G·0 +23:19:38.789262 db@open done T·4.934329ms +23:19:38.789423 db@close closing +23:19:38.789522 db@close done T·96.606µs +=============== Apr 29, 2016 (EDT) =============== +23:19:38.926567 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:19:38.926753 version@stat F·[] S·0B[] Sc·[] +23:19:38.926771 db@open opening +23:19:38.926820 journal@recovery F·1 +23:19:38.929753 journal@recovery recovering @2 +23:19:38.933599 memdb@flush created L0@4 N·1 S·190B "htt..ata,v1":"htt..ata,v1" +23:19:38.936658 version@stat F·[1] S·190B[190B] Sc·[0.25] +23:19:38.937105 db@janitor F·3 G·0 +23:19:38.937125 db@open done T·10.343223ms +23:19:38.937228 db@close closing +23:19:38.937260 db@close done T·71.925µs +=============== Apr 29, 2016 (EDT) =============== +23:36:25.541425 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:36:25.542263 version@stat F·[1] S·190B[190B] Sc·[0.25] +23:36:25.542306 db@open opening +23:36:25.542467 journal@recovery F·1 +23:36:25.543972 journal@recovery recovering @5 +23:36:25.556094 memdb@flush created L0@7 N·1 S·272B "htt..ata,v3":"htt..ata,v3" +23:36:25.557698 version@stat F·[2] S·462B[462B] Sc·[0.50] +23:36:25.560241 db@janitor F·4 G·0 +23:36:25.560352 db@open done T·18.008692ms +23:36:25.560779 db@close closing +23:36:25.560989 db@close done T·192.676µs +=============== Apr 29, 2016 (EDT) =============== +23:36:25.561205 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:36:25.561634 version@stat F·[2] S·462B[462B] Sc·[0.50] +23:36:25.561696 db@open opening +23:36:25.561902 journal@recovery F·1 +23:36:25.564982 journal@recovery recovering @8 +23:36:25.568373 version@stat F·[2] S·462B[462B] Sc·[0.50] +23:36:25.569870 db@janitor F·4 G·0 +23:36:25.569935 db@open done T·8.212765ms +23:36:25.570088 db@close closing +23:36:25.570208 db@close done T·110.318µs +=============== Apr 29, 2016 (EDT) =============== +23:36:25.752860 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:36:25.753038 version@stat F·[2] S·462B[462B] Sc·[0.50] +23:36:25.753053 db@open opening +23:36:25.753114 journal@recovery F·1 +23:36:25.754012 journal@recovery recovering @10 +23:36:25.757428 memdb@flush created L0@12 N·1 S·190B "htt..ata,v5":"htt..ata,v5" +23:36:25.760126 version@stat F·[3] S·652B[652B] Sc·[0.75] +23:36:25.761194 db@janitor F·5 G·0 +23:36:25.761232 db@open done T·8.167192ms +23:36:25.761337 db@close closing +23:36:25.761419 db@close done T·80.195µs +=============== Apr 29, 2016 (EDT) =============== +23:43:57.915266 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:43:57.915962 version@stat F·[3] S·652B[652B] Sc·[0.75] +23:43:57.916007 db@open opening +23:43:57.916225 journal@recovery F·1 +23:43:57.917459 journal@recovery recovering @13 +23:43:57.924923 memdb@flush created L0@15 N·1 S·272B "htt..ata,v7":"htt..ata,v7" +23:43:57.925592 version@stat F·[4] S·924B[924B] Sc·[1.00] +23:43:57.928233 db@janitor F·6 G·0 +23:43:57.928308 db@open done T·12.260507ms +23:43:57.928497 table@compaction L0·4 -> L1·0 S·924B Q·8 +23:43:57.928727 db@close closing +23:43:57.928863 db@close done T·131.622µs +=============== Apr 29, 2016 (EDT) =============== +23:43:57.928972 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:43:57.929207 version@stat F·[4] S·924B[924B] Sc·[1.00] +23:43:57.929238 db@open opening +23:43:57.929370 journal@recovery F·1 +23:43:57.932077 journal@recovery recovering @16 +23:43:57.935691 version@stat F·[4] S·924B[924B] Sc·[1.00] +23:43:57.937241 db@janitor F·6 G·0 +23:43:57.937297 db@open done T·8.038595ms +23:43:57.937455 table@compaction L0·4 -> L1·0 S·924B Q·8 +23:43:57.937500 table@build exiting +23:43:57.937480 db@close closing +23:43:57.937612 db@close done T·126.927µs +=============== Apr 29, 2016 (EDT) =============== +23:43:58.109650 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:43:58.109851 version@stat F·[4] S·924B[924B] Sc·[1.00] +23:43:58.109876 db@open opening +23:43:58.109948 journal@recovery F·1 +23:43:58.110915 journal@recovery recovering @18 +23:43:58.116332 memdb@flush created L0@20 N·1 S·190B "htt..ata,v9":"htt..ata,v9" +23:43:58.118317 version@stat F·[5] S·1KiB[1KiB] Sc·[1.25] +23:43:58.119611 db@janitor F·7 G·0 +23:43:58.119681 db@open done T·9.784011ms +23:43:58.119836 db@close closing +23:43:58.119856 table@compaction L0·5 -> L1·0 S·1KiB Q·10 +23:43:58.119872 table@build exiting +23:43:58.119894 db@close done T·57.084µs +=============== Apr 29, 2016 (EDT) =============== +23:56:56.871481 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:56:56.871853 version@stat F·[5] S·1KiB[1KiB] Sc·[1.25] +23:56:56.871877 db@open opening +23:56:56.872001 journal@recovery F·1 +23:56:56.873483 journal@recovery recovering @21 +23:56:56.876720 memdb@flush created L0@23 N·1 S·272B "htt..ata,v11":"htt..ata,v11" +23:56:56.877379 version@stat F·[6] S·1KiB[1KiB] Sc·[1.50] +23:56:56.878820 db@janitor F·8 G·0 +23:56:56.878905 db@open done T·6.998044ms +23:56:56.879728 table@compaction L0·6 -> L1·0 S·1KiB Q·12 +23:56:56.880938 db@close closing +23:56:56.884410 table@build created L1@26 N·1 S·272B "htt..ata,v11":"htt..ata,v11" +23:56:56.884434 table@build exiting +23:56:56.884444 table@build revert @26 +23:56:56.884615 db@close done T·3.667859ms +=============== Apr 29, 2016 (EDT) =============== +23:56:56.884716 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:56:56.884903 version@stat F·[6] S·1KiB[1KiB] Sc·[1.50] +23:56:56.884925 db@open opening +23:56:56.885023 journal@recovery F·1 +23:56:56.886670 journal@recovery recovering @24 +23:56:56.888161 version@stat F·[6] S·1KiB[1KiB] Sc·[1.50] +23:56:56.888611 db@janitor F·8 G·0 +23:56:56.888648 db@open done T·3.709385ms +23:56:56.889258 table@compaction L0·6 -> L1·0 S·1KiB Q·12 +23:56:56.889267 db@close closing +23:56:56.889272 table@build exiting +23:56:56.889305 db@close done T·36.664µs +=============== Apr 29, 2016 (EDT) =============== +23:56:56.993236 log@legend F·NumFile S·FileSize N·Entry C·BadEntry B·BadBlock Ke·KeyError D·DroppedEntry L·Level Q·SeqNum T·TimeElapsed +23:56:56.993379 version@stat F·[6] S·1KiB[1KiB] Sc·[1.50] +23:56:56.993392 db@open opening +23:56:56.993478 journal@recovery F·1 +23:56:56.994592 journal@recovery recovering @26 +23:56:56.999533 memdb@flush created L0@28 N·1 S·190B "htt..ata,v13":"htt..ata,v13" +23:56:57.000615 version@stat F·[7] S·1KiB[1KiB] Sc·[1.75] +23:56:57.001511 db@janitor F·9 G·0 +23:56:57.001532 db@open done T·8.13046ms +23:56:57.001590 db@close closing +23:56:57.001631 table@compaction L0·7 -> L1·0 S·1KiB Q·15 +23:56:57.001646 table@build exiting +23:56:57.001668 db@close done T·76.788µs diff --git a/auth.leveldb/MANIFEST-000030 b/auth.leveldb/MANIFEST-000030 new file mode 100644 index 0000000..2e60808 Binary files /dev/null and b/auth.leveldb/MANIFEST-000030 differ diff --git a/handlers.go b/handlers.go index ea4eb58..8318819 100644 --- a/handlers.go +++ b/handlers.go @@ -561,3 +561,41 @@ func CheckServer(w http.ResponseWriter, r *http.Request) { } } } + +func LoginUser(w http.ResponseWriter, r *http.Request) { + resp := JSONResponse{ + Success: false, + } + + w.Header().Set("Content-Type", "application/json;charset=UTF-8") + + switch r.Method { + case "GET": + log.Printf("GET not supported for login handler") + resp.Data = "Unsupported method" + resp.Success = false + if err := json.NewEncoder(w).Encode(resp); err != nil { + log.Printf("Error listing mods: %s", err) + } + case "POST": + var user User + body, err := ioutil.ReadAll(r.Body) + if err != nil { + log.Printf("Error in starting factorio server handler body: %s", err) + return + } + + log.Printf("Logging in user: %v", string(body)) + + err = json.Unmarshal(body, &user) + if err != nil { + log.Printf("Error unmarshaling server settings JSON: %s", err) + return + } + + fmt.Println(user) + + } + + //if err := Auth.aaa.Login(w, r, username, password, "/") +} diff --git a/main.go b/main.go index 6eeab7c..8a00a25 100644 --- a/main.go +++ b/main.go @@ -47,7 +47,6 @@ func loadServerConfig(f string) { decoder := json.NewDecoder(file) err = decoder.Decode(&config) - fmt.Println(config.Password) parseFlags() } @@ -78,7 +77,12 @@ func main() { FactorioServ = initFactorio() Auth = initAuth() + Auth.createAuthDb(config.DatabaseFile) Auth.createRoles() + err := Auth.createUser(config.Username, config.Password, "admin", "") + if err != nil { + log.Printf("Error creating user: %s", err) + } router := NewRouter() diff --git a/routes.go b/routes.go index f3854b3..afd1b52 100644 --- a/routes.go +++ b/routes.go @@ -31,7 +31,7 @@ func NewRouter() *mux.Router { s.Methods(route.Method). Path(route.Pattern). Name(route.Name). - Handler(CheckSession(route.HandlerFunc)) + Handler(route.HandlerFunc) } // Serves the frontend application from the app directory @@ -68,7 +68,6 @@ func NewRouter() *mux.Router { // Middleware returns a http.HandlerFunc which authenticates the users request func CheckSession(h http.Handler) http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - log.Printf("%+v", Auth.aaa) if err := Auth.aaa.Authorize(w, r, true); err != nil { log.Printf("Unauthenticated request %s %s %s", r.Method, r.Host, r.RequestURI) http.Redirect(w, r, "/login", http.StatusSeeOther) @@ -166,5 +165,10 @@ var apiRoutes = Routes{ "GET", "/server/status", CheckServer, + }, { + "LoginUser", + "POST", + "/login", + LoginUser, }, } diff --git a/ui/App/App.jsx b/ui/App/App.jsx index 4dd10f0..5d1a3df 100644 --- a/ui/App/App.jsx +++ b/ui/App/App.jsx @@ -1,4 +1,5 @@ import React from 'react'; +import {browserHistory} from 'react-router'; import Header from './components/Header.jsx'; import Sidebar from './components/Sidebar.jsx'; import Footer from './components/Footer.jsx'; @@ -15,7 +16,14 @@ class App extends React.Component { serverRunning: "stopped", serverStatus: {}, saves: [], - loggedIn: false, + loggedIn: true, + } + } + + // Check if state.loggedIn is true, if so continue, else redirect to /login page. + componentWillMount() { + if (!this.state.loggedIn) { + browserHistory.push("/login"); } } diff --git a/ui/App/components/LoginContent.jsx b/ui/App/components/LoginContent.jsx index 4035633..42fdebe 100644 --- a/ui/App/components/LoginContent.jsx +++ b/ui/App/components/LoginContent.jsx @@ -2,53 +2,86 @@ import React from 'react'; import {IndexLink} from 'react-router'; class LoginContent extends React.Component { + constructor(props) { + super(props) + this.loginUser = this.loginUser.bind(this); + } + + componentDidMount() { + console.log(this.state); + } + + loginUser(e) { + e.preventDefault(); + console.log(this) + let user = { + username: this.refs.username.value, + password: this.refs.password.value, + } + + $.ajax({ + type: "POST", + url: "/api/login", + dataType: "json", + data: JSON.stringify(user), + success: (resp) => { + console.log(resp) + } + }) + } + render() { return( -
-
-
-

- Login - Login to manage Factorio -

-
- -
+
-
-

Sign in to start your session

+
+
+
+

+ Login + Login to manage Factorio +

+
-
-
- - -
-
- - -
-
-
-
- +
+
+
+ + +
+ +
-
-
- -
-
- +
+ + +
+
+
+
+ +
+
+
+
+
+ +
+
+ - I forgot my password
-
+ I forgot my password
+
+
+
+
+
- - ) } } diff --git a/ui/App/components/ServerCtl/ServerCtl.jsx b/ui/App/components/ServerCtl/ServerCtl.jsx index bd66a6b..6e0eb9a 100644 --- a/ui/App/components/ServerCtl/ServerCtl.jsx +++ b/ui/App/components/ServerCtl/ServerCtl.jsx @@ -5,6 +5,7 @@ class ServerCtl extends React.Component { super(props); this.startServer = this.startServer.bind(this); this.stopServer = this.stopServer.bind(this); + this.incrementAutosave = this.incrementAutosave.bind(this); this.decrementAutosave = this.decrementAutosave.bind(this); @@ -214,17 +215,15 @@ class ServerCtl extends React.Component {
-
-