diff options
-rw-r--r-- | src/ninjacloud.go | 126 |
1 files changed, 123 insertions, 3 deletions
diff --git a/src/ninjacloud.go b/src/ninjacloud.go index 2786202..4068b2d 100644 --- a/src/ninjacloud.go +++ b/src/ninjacloud.go | |||
@@ -11,6 +11,7 @@ import ( | |||
11 | "path/filepath" | 11 | "path/filepath" |
12 | "runtime" | 12 | "runtime" |
13 | "strconv" | 13 | "strconv" |
14 | "strings" | ||
14 | ) | 15 | ) |
15 | 16 | ||
16 | const APP_NAME = "Ninja Go Local Cloud" | 17 | const APP_NAME = "Ninja Go Local Cloud" |
@@ -32,6 +33,15 @@ const webPathLen = len(webPath) | |||
32 | 33 | ||
33 | //const statusPathLen = len(statusPath) | 34 | //const statusPathLen = len(statusPath) |
34 | 35 | ||
36 | func sliceContains(s []string, c string) bool { | ||
37 | for _, e := range s { | ||
38 | if c == e { | ||
39 | return true | ||
40 | } | ||
41 | } | ||
42 | return false | ||
43 | } | ||
44 | |||
35 | //////// FILESYSTEM | 45 | //////// FILESYSTEM |
36 | 46 | ||
37 | func properties(path string) (infos os.FileInfo, err error) { | 47 | func properties(path string) (infos os.FileInfo, err error) { |
@@ -133,10 +143,10 @@ func removeDir(path string) (err error) { | |||
133 | return | 143 | return |
134 | } | 144 | } |
135 | 145 | ||
136 | func listDir(path string) (list []os.FileInfo, err error) { | 146 | /*func listDir(path string) (list []os.FileInfo, err error) { |
137 | list, err = ioutil.ReadDir(path) | 147 | list, err = ioutil.ReadDir(path) |
138 | return | 148 | return |
139 | } | 149 | }*/ |
140 | 150 | ||
141 | func moveDir(source string, dest string) (err error) { | 151 | func moveDir(source string, dest string) (err error) { |
142 | err = os.Rename(source, dest) | 152 | err = os.Rename(source, dest) |
@@ -179,6 +189,65 @@ func copyDir(source string, dest string) (err error) { | |||
179 | return | 189 | return |
180 | } | 190 | } |
181 | 191 | ||
192 | type element struct { | ||
193 | Type string `json:"type"` | ||
194 | Name string `json:"name"` | ||
195 | Uri string `json:"uri"` | ||
196 | CreationDate string `json:"creationdate"` | ||
197 | ModifiedDate string `json:"modifieddate"` | ||
198 | Size string `json:"size"` | ||
199 | Writable string `json:"writable"` | ||
200 | Children []element `json:"children"` | ||
201 | } | ||
202 | |||
203 | func listDir(path string, recursive bool, filter []string, returnType string) (list []element, err error) { | ||
204 | returnAll := returnType == "all" || returnType == "" | ||
205 | returnFiles := returnType == "files" || returnAll | ||
206 | returnDirs := returnType == "directories" || returnAll | ||
207 | currentDir, err := ioutil.ReadDir(path) | ||
208 | for _, d := range currentDir { | ||
209 | if d.IsDir() && returnDirs { | ||
210 | var e element | ||
211 | modTime := strconv.FormatInt(d.ModTime().UnixNano(), 10) | ||
212 | modTime = modTime[:len(modTime)-6] | ||
213 | uri := filepath.Clean(path + "/" + d.Name()) | ||
214 | list = append(list, element{}) | ||
215 | e.Type = "directory" | ||
216 | e.Name = d.Name() | ||
217 | e.Uri = uri | ||
218 | e.CreationDate = modTime // TODO | ||
219 | e.ModifiedDate = modTime | ||
220 | e.Size = strconv.FormatInt(d.Size(), 10) | ||
221 | e.Writable = "true" // TODO | ||
222 | if recursive { | ||
223 | e.Children, err = listDir(uri, recursive, filter, returnType) | ||
224 | if err != nil { | ||
225 | return | ||
226 | } | ||
227 | } else { | ||
228 | e.Children = nil | ||
229 | } | ||
230 | list = append(list, e) | ||
231 | } else if !d.IsDir() && returnFiles { | ||
232 | if sliceContains(filter, filepath.Ext(d.Name())) { | ||
233 | var e element | ||
234 | modTime := strconv.FormatInt(d.ModTime().UnixNano(), 10) | ||
235 | modTime = modTime[:len(modTime)-6] | ||
236 | e.Type = "file" | ||
237 | e.Name = d.Name() | ||
238 | e.Uri = filepath.Clean(path + "/" + d.Name()) | ||
239 | e.CreationDate = modTime // TODO | ||
240 | e.ModifiedDate = modTime | ||
241 | e.Size = strconv.FormatInt(d.Size(), 10) | ||
242 | e.Writable = "true" // TODO | ||
243 | e.Children = nil | ||
244 | list = append(list, e) | ||
245 | } | ||
246 | } | ||
247 | } | ||
248 | return | ||
249 | } | ||
250 | |||
182 | //////// REQUEST HANDLERS | 251 | //////// REQUEST HANDLERS |
183 | 252 | ||
184 | func osPath(p string) string { | 253 | func osPath(p string) string { |
@@ -362,7 +431,58 @@ func dirHandler(w http.ResponseWriter, r *http.Request) { | |||
362 | return | 431 | return |
363 | case "GET": | 432 | case "GET": |
364 | // List the contents of an existing directory | 433 | // List the contents of an existing directory |
365 | // TODO | 434 | modSince := r.Header.Get("If-modified-since") |
435 | if p == "" { | ||
436 | w.Write([]byte(rootFlag)) | ||
437 | return | ||
438 | } else if modSince != "" && modSince != "false" && modSince != "none" { | ||
439 | if !exist(p) { | ||
440 | w.WriteHeader(http.StatusNotFound) | ||
441 | return | ||
442 | } | ||
443 | if modifiedSince(p, modSince) { | ||
444 | w.WriteHeader(http.StatusOK) | ||
445 | return | ||
446 | } else { | ||
447 | w.WriteHeader(http.StatusNotModified) | ||
448 | return | ||
449 | } | ||
450 | } else if r.Header.Get("check-existence-only") == "true" { | ||
451 | if exist(p) { | ||
452 | w.WriteHeader(http.StatusNoContent) | ||
453 | return | ||
454 | } else { | ||
455 | w.WriteHeader(http.StatusNotFound) | ||
456 | return | ||
457 | } | ||
458 | } else { | ||
459 | recursive := r.Header.Get("recursive") == "true" | ||
460 | filter := strings.Split(r.Header.Get("file-filters"), ";") | ||
461 | returnType := r.Header.Get("return-type") | ||
462 | if returnType == "" { | ||
463 | returnType = "all" | ||
464 | } | ||
465 | fileInfo, err := listDir(p, recursive, filter, returnType) | ||
466 | if err == os.ErrNotExist { | ||
467 | w.WriteHeader(http.StatusNotFound) | ||
468 | return | ||
469 | } else if err != nil { | ||
470 | w.WriteHeader(http.StatusInternalServerError) | ||
471 | return | ||
472 | } | ||
473 | var e element | ||
474 | e.Type = "directory" | ||
475 | e.Name = "root" | ||
476 | e.Uri = p + "/" | ||
477 | e.Children = fileInfo | ||
478 | j, err := json.Marshal(e) | ||
479 | if err != nil { | ||
480 | w.WriteHeader(http.StatusInternalServerError) | ||
481 | return | ||
482 | } | ||
483 | w.Write(j) | ||
484 | return | ||
485 | } | ||
366 | case "PUT": | 486 | case "PUT": |
367 | // Copy, Move of an existing directory | 487 | // Copy, Move of an existing directory |
368 | source := r.Header.Get("sourceURI") | 488 | source := r.Header.Get("sourceURI") |