early implementation of Browser, but somehow minio broke
parent
6f9c0c176d
commit
a4dea3b8ca
|
@ -96,7 +96,7 @@ func stringPrompt(prompt string, viperKey string) {
|
|||
}
|
||||
|
||||
func intPrompt(prompt string, viperKey string) {
|
||||
defaultValue := viper.GetString(viperKey)
|
||||
defaultValue := viper.GetInt(viperKey)
|
||||
var str string
|
||||
r := bufio.NewReader(os.Stdin)
|
||||
for {
|
||||
|
|
10
cmd/root.go
10
cmd/root.go
|
@ -13,8 +13,7 @@ GNU General Public License for more details.
|
|||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package cmd
|
||||
*/package cmd
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
@ -67,8 +66,10 @@ func init() {
|
|||
// Cobra supports persistent flags, which, if defined here,
|
||||
// will be global for your application.
|
||||
|
||||
rootCmd.PersistentFlags().StringVar(&cfgFile, "config", "", "config file (default is /etc/filegate.yaml)")
|
||||
rootCmd.PersistentFlags().BoolVarP(&production, "production", "p", true, "Toggle production use")
|
||||
rootCmd.PersistentFlags().
|
||||
StringVar(&cfgFile, "config", "", "config file (default is /etc/filegate.yaml)")
|
||||
rootCmd.PersistentFlags().
|
||||
BoolVarP(&production, "production", "p", true, "Toggle production use")
|
||||
|
||||
// Cobra also supports local flags, which will only run
|
||||
// when this action is called directly.
|
||||
|
@ -108,6 +109,7 @@ func initConfig() {
|
|||
viper.SetDefault("db.password", "dbpw")
|
||||
viper.SetDefault("db.port", 5432)
|
||||
viper.SetDefault("db.sslmode", "disable")
|
||||
// Minio (S3 Object Storage)
|
||||
viper.SetDefault("minio.accessKeyID", "MINIO_ACCESS_KEY")
|
||||
viper.SetDefault("minio.accessKeySecret", "MINIO_ACCESS_SECRET")
|
||||
viper.SetDefault("minio.hostname", "s3.example.com")
|
||||
|
|
|
@ -11,3 +11,11 @@ web:
|
|||
sessionkey: 8Zpj3QEifL036QxxCjM0-MVsuYmt6UPbNYLSC3ljAio1AdctpXMwMaVi5SFbqSu9
|
||||
trustedproxies:
|
||||
- 127.0.0.1
|
||||
minio:
|
||||
accesskeyid: lZvkgrfXNbEMye6BSf6s
|
||||
accesskeysecret: U109MtkE1jcc6qm3SIGk3IEZsq1cl8vTxqIRr3ZH
|
||||
hostname: 127.0.0.1
|
||||
port: 9000
|
||||
bucket: filegate
|
||||
usessl: false
|
||||
location: filegate-local
|
|
@ -55,6 +55,6 @@ func DownloadFile(rawURL string, blob string, id uint) (uint, error) {
|
|||
log.Println(err)
|
||||
return 0, err
|
||||
}
|
||||
go RunStaticAnalysis(id)
|
||||
// go RunStaticAnalysis(id)
|
||||
return 0, nil
|
||||
}
|
||||
|
|
|
@ -34,7 +34,7 @@ func UploadFile(file *multipart.FileHeader, name string, url string, comment str
|
|||
return fileID, err
|
||||
}
|
||||
log.Printf("Successfully uploaded %s of size %d\n", blob, objectInfo.Size)
|
||||
go RunStaticAnalysis(fileID)
|
||||
// go service.RunStaticAnalysis(fileID)
|
||||
return fileID, nil
|
||||
}
|
||||
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package auth
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net/http"
|
||||
|
||||
"github.com/gin-contrib/sessions"
|
||||
|
@ -25,9 +26,13 @@ func AuthMiddleware(requiredLevel int) gin.HandlerFunc {
|
|||
if accessLevelValue, ok := accessLevel.(int); ok {
|
||||
if accessLevelValue < requiredLevel {
|
||||
metaContent := utils.GenMetaContent(c)
|
||||
err := &AuthenticationError{
|
||||
Code: http.StatusForbidden,
|
||||
Message: "You are not authorized to do this Action",
|
||||
}
|
||||
metaContent.ErrorTitle = "Not Authorized"
|
||||
metaContent.ErrorText = "You are not authorized to do this Action"
|
||||
c.HTML(http.StatusUnauthorized, "", templates.Index(metaContent))
|
||||
c.HTML(http.StatusUnauthorized, "", templates.Index(metaContent, err))
|
||||
c.Abort()
|
||||
return
|
||||
}
|
||||
|
@ -36,3 +41,12 @@ func AuthMiddleware(requiredLevel int) gin.HandlerFunc {
|
|||
c.Next()
|
||||
}
|
||||
}
|
||||
|
||||
type AuthenticationError struct {
|
||||
Code int
|
||||
Message string
|
||||
}
|
||||
|
||||
func (e *AuthenticationError) Error() string {
|
||||
return fmt.Sprintf("Error %d: %s", e.Code, e.Message)
|
||||
}
|
||||
|
|
|
@ -1,22 +0,0 @@
|
|||
package web
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
"net/http/httputil"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
func reverseProxy(c *gin.Context, target string) {
|
||||
director := func(req *http.Request) {
|
||||
//r := c.Request
|
||||
|
||||
req.URL.Scheme = "http"
|
||||
req.URL.Host = target
|
||||
//req.Header["my-header"] = []string{r.Header.Get("my-header")}
|
||||
//// Golang camelcases headers
|
||||
//delete(req.Header, "My-Header")
|
||||
}
|
||||
proxy := &httputil.ReverseProxy{Director: director}
|
||||
proxy.ServeHTTP(c.Writer, c.Request)
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
package templates
|
||||
|
||||
import "fmt"
|
||||
|
||||
templ BrowserFileDiv() {
|
||||
<div class="section is-medium" id="browser-div">
|
||||
<div class="columns is-centered">
|
||||
<div class="column is-two-thirds">
|
||||
<div class="container">
|
||||
@uploadForm()
|
||||
</div>
|
||||
</div>
|
||||
<div class="column is-one-third">
|
||||
@BrowserFilePicker()
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
}
|
||||
|
||||
templ BrowserFilePicker() {
|
||||
<div class="container" id="file-picker"></div>
|
||||
}
|
||||
|
||||
templ BrowserIframe(browserUUID string) {
|
||||
<div class="container" id="browser">
|
||||
<iframe
|
||||
src={ fmt.Sprintf("/browser/%s", browserUUID) }
|
||||
title="Browser"
|
||||
allow="fullscreen"
|
||||
sandbox
|
||||
style="object-fit: fill"
|
||||
></iframe>
|
||||
</div>
|
||||
}
|
|
@ -0,0 +1,109 @@
|
|||
// Code generated by templ - DO NOT EDIT.
|
||||
|
||||
// templ: version: 0.2.476
|
||||
package templates
|
||||
|
||||
//lint:file-ignore SA4006 This context is only used if a nested component is present.
|
||||
|
||||
import "github.com/a-h/templ"
|
||||
import "context"
|
||||
import "io"
|
||||
import "bytes"
|
||||
|
||||
import "fmt"
|
||||
|
||||
func BrowserFileDiv() templ.Component {
|
||||
return templ.ComponentFunc(func(ctx context.Context, templ_7745c5c3_W io.Writer) (templ_7745c5c3_Err error) {
|
||||
templ_7745c5c3_Buffer, templ_7745c5c3_IsBuffer := templ_7745c5c3_W.(*bytes.Buffer)
|
||||
if !templ_7745c5c3_IsBuffer {
|
||||
templ_7745c5c3_Buffer = templ.GetBuffer()
|
||||
defer templ.ReleaseBuffer(templ_7745c5c3_Buffer)
|
||||
}
|
||||
ctx = templ.InitializeContext(ctx)
|
||||
templ_7745c5c3_Var1 := templ.GetChildren(ctx)
|
||||
if templ_7745c5c3_Var1 == nil {
|
||||
templ_7745c5c3_Var1 = templ.NopComponent
|
||||
}
|
||||
ctx = templ.ClearChildren(ctx)
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("<div class=\"section is-medium\" id=\"browser-div\"><div class=\"columns is-centered\"><div class=\"column is-two-thirds\"><div class=\"container\">")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
templ_7745c5c3_Err = uploadForm().Render(ctx, templ_7745c5c3_Buffer)
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("</div></div><div class=\"column is-one-third\">")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
templ_7745c5c3_Err = BrowserFilePicker().Render(ctx, templ_7745c5c3_Buffer)
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("</div></div></div>")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
if !templ_7745c5c3_IsBuffer {
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteTo(templ_7745c5c3_W)
|
||||
}
|
||||
return templ_7745c5c3_Err
|
||||
})
|
||||
}
|
||||
|
||||
func BrowserFilePicker() templ.Component {
|
||||
return templ.ComponentFunc(func(ctx context.Context, templ_7745c5c3_W io.Writer) (templ_7745c5c3_Err error) {
|
||||
templ_7745c5c3_Buffer, templ_7745c5c3_IsBuffer := templ_7745c5c3_W.(*bytes.Buffer)
|
||||
if !templ_7745c5c3_IsBuffer {
|
||||
templ_7745c5c3_Buffer = templ.GetBuffer()
|
||||
defer templ.ReleaseBuffer(templ_7745c5c3_Buffer)
|
||||
}
|
||||
ctx = templ.InitializeContext(ctx)
|
||||
templ_7745c5c3_Var2 := templ.GetChildren(ctx)
|
||||
if templ_7745c5c3_Var2 == nil {
|
||||
templ_7745c5c3_Var2 = templ.NopComponent
|
||||
}
|
||||
ctx = templ.ClearChildren(ctx)
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("<div class=\"container\" id=\"file-picker\"></div>")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
if !templ_7745c5c3_IsBuffer {
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteTo(templ_7745c5c3_W)
|
||||
}
|
||||
return templ_7745c5c3_Err
|
||||
})
|
||||
}
|
||||
|
||||
func BrowserIframe(browserUUID string) templ.Component {
|
||||
return templ.ComponentFunc(func(ctx context.Context, templ_7745c5c3_W io.Writer) (templ_7745c5c3_Err error) {
|
||||
templ_7745c5c3_Buffer, templ_7745c5c3_IsBuffer := templ_7745c5c3_W.(*bytes.Buffer)
|
||||
if !templ_7745c5c3_IsBuffer {
|
||||
templ_7745c5c3_Buffer = templ.GetBuffer()
|
||||
defer templ.ReleaseBuffer(templ_7745c5c3_Buffer)
|
||||
}
|
||||
ctx = templ.InitializeContext(ctx)
|
||||
templ_7745c5c3_Var3 := templ.GetChildren(ctx)
|
||||
if templ_7745c5c3_Var3 == nil {
|
||||
templ_7745c5c3_Var3 = templ.NopComponent
|
||||
}
|
||||
ctx = templ.ClearChildren(ctx)
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("<div class=\"container\" id=\"browser\"><iframe src=\"")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString(templ.EscapeString(fmt.Sprintf("/browser/%s", browserUUID)))
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("\" title=\"Browser\" allow=\"fullscreen\" sandbox style=\"object-fit: fill\"></iframe></div>")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
if !templ_7745c5c3_IsBuffer {
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteTo(templ_7745c5c3_W)
|
||||
}
|
||||
return templ_7745c5c3_Err
|
||||
})
|
||||
}
|
|
@ -75,7 +75,7 @@ templ urlDownloadForm() {
|
|||
}
|
||||
|
||||
templ browserDownloadForm() {
|
||||
<form id="urldownload" name="urldownload" action="/file/new/browser" method="POST" hx-post="/file/new/browser">
|
||||
<form id="urldownload" name="urldownload" action="/file/new/browser" method="POST" hx-post="/file/new/browser" hx-target="#upload-options" hx-swap="outerHTML">
|
||||
<h3 class="subtitle">Opens a Browser inside a container to download a suspicious file.</h3>
|
||||
<div class="field">
|
||||
<label class="label">File Name</label>
|
||||
|
|
|
@ -221,7 +221,7 @@ func browserDownloadForm() templ.Component {
|
|||
templ_7745c5c3_Var18 = templ.NopComponent
|
||||
}
|
||||
ctx = templ.ClearChildren(ctx)
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("<form id=\"urldownload\" name=\"urldownload\" action=\"/file/new/browser\" method=\"POST\" hx-post=\"/file/new/browser\"><h3 class=\"subtitle\">")
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("<form id=\"urldownload\" name=\"urldownload\" action=\"/file/new/browser\" method=\"POST\" hx-post=\"/file/new/browser\" hx-target=\"#upload-options\" hx-swap=\"outerHTML\"><h3 class=\"subtitle\">")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
|
|
|
@ -72,7 +72,7 @@ templ FileViewPage(metaContent utils.MetaContent, title string, file db.File, er
|
|||
|
||||
templ NewFilePage(metaContent utils.MetaContent, title string, err error) {
|
||||
@wrapBase(metaContent, title, err) {
|
||||
<div class="section is-medium">
|
||||
<div class="section is-medium" id="upload-options">
|
||||
<div class="columns is-centered">
|
||||
<div class="column">
|
||||
<div class="container">
|
||||
|
|
|
@ -305,7 +305,7 @@ func NewFilePage(metaContent utils.MetaContent, title string, err error) templ.C
|
|||
templ_7745c5c3_Buffer = templ.GetBuffer()
|
||||
defer templ.ReleaseBuffer(templ_7745c5c3_Buffer)
|
||||
}
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("<div class=\"section is-medium\"><div class=\"columns is-centered\"><div class=\"column\"><div class=\"container\">")
|
||||
_, templ_7745c5c3_Err = templ_7745c5c3_Buffer.WriteString("<div class=\"section is-medium\" id=\"upload-options\"><div class=\"columns is-centered\"><div class=\"column\"><div class=\"container\">")
|
||||
if templ_7745c5c3_Err != nil {
|
||||
return templ_7745c5c3_Err
|
||||
}
|
||||
|
|
|
@ -1,14 +1,31 @@
|
|||
package ui
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"log"
|
||||
"net/http"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
|
||||
"git.jmbit.de/filegate/filegate/db"
|
||||
"git.jmbit.de/filegate/filegate/utils"
|
||||
"git.jmbit.de/filegate/filegate/web/templates"
|
||||
)
|
||||
|
||||
func getBrowser(c *gin.Context) {
|
||||
c.HTML(http.StatusOK, "", templates.Index(utils.GenMetaContent(c), nil))
|
||||
id := c.Param("id")
|
||||
//TODO: save to session instead of hitting DB for this
|
||||
container, err := db.ContainerByFolder(id)
|
||||
port := container.Port
|
||||
if err != nil {
|
||||
log.Printf("could not get container from Folder UUID: %v", err)
|
||||
c.HTML(http.StatusNotFound, "", templates.Index(utils.GenMetaContent(c), err))
|
||||
}
|
||||
targetURL := fmt.Sprintf("http://localhost:%d/", port)
|
||||
proxy, err := createReverseProxy(targetURL)
|
||||
if err != nil {
|
||||
log.Printf("could not get container from Folder UUID: %v", err)
|
||||
c.HTML(http.StatusNotFound, "", templates.Index(utils.GenMetaContent(c), err))
|
||||
}
|
||||
proxy.ServeHTTP(c.Writer, c.Request)
|
||||
}
|
||||
|
|
|
@ -29,13 +29,13 @@ func getFileListPage(c *gin.Context) {
|
|||
highestEntry := page * count
|
||||
fileListPage := fileList[lowestEntry:highestEntry]
|
||||
|
||||
content := gin.H{
|
||||
"fileList": fileListPage,
|
||||
"error": err,
|
||||
"page": page,
|
||||
"count": count,
|
||||
"totalEntries": len(fileList),
|
||||
}
|
||||
//content := gin.H{
|
||||
// "fileList": fileListPage,
|
||||
// "error": err,
|
||||
// "page": page,
|
||||
// "count": count,
|
||||
// "totalEntries": len(fileList),
|
||||
//}
|
||||
c.HTML(
|
||||
http.StatusOK,
|
||||
"",
|
||||
|
|
|
@ -0,0 +1,20 @@
|
|||
package ui
|
||||
|
||||
import (
|
||||
"log"
|
||||
"net/http/httputil"
|
||||
"net/url"
|
||||
)
|
||||
|
||||
func createReverseProxy(backendService string) (*httputil.ReverseProxy, error) {
|
||||
var err error
|
||||
|
||||
backendURL, err := url.Parse(backendService)
|
||||
if err != nil {
|
||||
log.Printf("Could not parees backend URL: %v", err)
|
||||
}
|
||||
|
||||
proxy := httputil.NewSingleHostReverseProxy(backendURL)
|
||||
|
||||
return proxy, err
|
||||
}
|
|
@ -16,7 +16,7 @@ func GroupWeb(router *gin.Engine) *gin.Engine {
|
|||
file.POST("/new/upload", postNewFileUpload)
|
||||
file.POST("/new/download", postNewFileDownload)
|
||||
file.POST("/new/browser", postNewFileBrowser)
|
||||
router.GET("/browser/:id", getBrowser)
|
||||
router.Any("/browser/:id/*any", getBrowser)
|
||||
|
||||
return router
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue