Compare commits

...

4 Commits

12 changed files with 267 additions and 28 deletions
+10 -1
View File
@@ -9,7 +9,7 @@
<i :class="fileIcon(item)" />
<p class="file-name" :title="item.name">{{ item.name }}</p>
<p class="file-size">{{ fileSize(item.size) }}</p>
<i v-if="item.type !== 'dir'" class="fas fa-download download" @click="download(item)" />
<i v-if="item.type !== 'dir' && canDownload" class="fas fa-download download" @click="download(item)" />
</div>
</div>
<div class="transfer-area">
@@ -73,6 +73,7 @@
</div>
</div>
<div
v-if="canUpload"
class="upload-area"
:class="{ 'upload-area-drag': uploadAreaDrag }"
@dragover.prevent="uploadAreaDrag = true"
@@ -281,6 +282,14 @@
export default class extends Vue {
public uploadAreaDrag: boolean = false
get canDownload() {
return this.$accessor.user.admin || this.$accessor.files.userDownload
}
get canUpload() {
return this.$accessor.user.admin || this.$accessor.files.userUpload
}
get cwd() {
return this.$accessor.files.cwd
}
+11 -1
View File
@@ -94,9 +94,19 @@
},
})
export default class extends Vue {
get canDownload() {
return this.$accessor.user.admin || this.$accessor.files.userDownload
}
get canUpload() {
return this.$accessor.user.admin || this.$accessor.files.userUpload
}
get filetransferAllowed() {
return (
this.$accessor.remote.fileTransfer && (this.$accessor.user.admin || !this.$accessor.isLocked('file_transfer'))
this.$accessor.remote.fileTransfer &&
(this.$accessor.user.admin || !this.$accessor.isLocked('file_transfer')) &&
(this.canDownload || this.canUpload)
)
}
+3 -1
View File
@@ -361,9 +361,11 @@ export class NekoClient extends BaseClient implements EventEmitter<NekoEvents> {
/////////////////////////////
// File Transfer Events
/////////////////////////////
protected [EVENT.FILETRANSFER.LIST]({ cwd, files }: FileTransferListPayload) {
protected [EVENT.FILETRANSFER.LIST]({ cwd, user_download, user_upload, files }: FileTransferListPayload) {
this.$accessor.files.setCwd(cwd)
this.$accessor.files.setFileList(files)
this.$accessor.files.setUserDownload(user_download)
this.$accessor.files.setUserUpload(user_upload)
}
/////////////////////////////
+2
View File
@@ -204,6 +204,8 @@ export interface FileTransferListMessage extends WebSocketMessage, FileTransferL
export interface FileTransferListPayload {
cwd: string
user_download: boolean
user_upload: boolean
files: FileListItem[]
}
+18
View File
@@ -7,6 +7,8 @@ export const state = () => ({
cwd: '',
files: [] as FileListItem[],
transfers: [] as FileTransfer[],
userDownload: false,
userUpload: false,
})
export const getters = getterTree(state, {
@@ -22,6 +24,14 @@ export const mutations = mutationTree(state, {
state.files = files
},
_setUserDownload(state, val: boolean) {
state.userDownload = val
},
_setUserUpload(state, val: boolean) {
state.userUpload = val
},
_addTransfer(state, transfer: FileTransfer) {
state.transfers = [...state.transfers, transfer]
},
@@ -42,6 +52,14 @@ export const actions = actionTree(
accessor.files._setFileList(files)
},
setUserDownload(store, val: boolean) {
accessor.files._setUserDownload(val)
},
setUserUpload(store, val: boolean) {
accessor.files._setUserUpload(val)
},
addTransfer(store, transfer: FileTransfer) {
if (transfer.status !== 'pending') {
return
@@ -109,9 +109,11 @@ type EmoteSend struct {
}
type FileTransferList struct {
Event string `json:"event"`
Cwd string `json:"cwd"`
Files []types.FileListItem `json:"files"`
Event string `json:"event"`
Cwd string `json:"cwd"`
UserDownload bool `json:"user_download"`
UserUpload bool `json:"user_upload"`
Files []types.FileListItem `json:"files"`
}
type Admin struct {
+5 -3
View File
@@ -607,9 +607,11 @@ func (s *session) wsToClient(msg []byte) error {
}
return s.toClient(&oldMessage.FileTransferList{
Event: oldEvent.FILETRANSFER_LIST,
Cwd: request.RootDir,
Files: files,
Event: oldEvent.FILETRANSFER_LIST,
Cwd: request.RootDir,
UserDownload: request.UserDownload,
UserUpload: request.UserUpload,
Files: files,
})
// Screen Events
@@ -12,6 +12,8 @@ type Config struct {
Enabled bool
RootDir string
RefreshInterval time.Duration
UserDownload bool
UserUpload bool
}
func (Config) Init(cmd *cobra.Command) error {
@@ -30,6 +32,16 @@ func (Config) Init(cmd *cobra.Command) error {
return err
}
cmd.PersistentFlags().Bool("filetransfer.user_download", false, "allow non-admin users to download files")
if err := viper.BindPFlag("filetransfer.user_download", cmd.PersistentFlags().Lookup("filetransfer.user_download")); err != nil {
return err
}
cmd.PersistentFlags().Bool("filetransfer.user_upload", false, "allow non-admin users to upload files")
if err := viper.BindPFlag("filetransfer.user_upload", cmd.PersistentFlags().Lookup("filetransfer.user_upload")); err != nil {
return err
}
// v2 config
cmd.PersistentFlags().Bool("file_transfer_enabled", false, "enable file transfer feature")
@@ -50,6 +62,8 @@ func (s *Config) Set() {
rootDir := viper.GetString("filetransfer.dir")
s.RootDir = filepath.Clean(rootDir)
s.RefreshInterval = viper.GetDuration("filetransfer.refresh_interval")
s.UserDownload = viper.GetBool("filetransfer.user_download")
s.UserUpload = viper.GetBool("filetransfer.user_upload")
// v2 config
@@ -103,9 +103,11 @@ func (m *Manager) broadcastUpdate() {
m.mu.RUnlock()
m.sessions.Broadcast(FILETRANSFER_UPDATE, Message{
Enabled: m.config.Enabled,
RootDir: m.config.RootDir,
Files: fileList,
Enabled: m.config.Enabled,
RootDir: m.config.RootDir,
UserDownload: m.config.UserDownload,
UserUpload: m.config.UserUpload,
Files: fileList,
})
}
@@ -115,9 +117,11 @@ func (m *Manager) sendUpdate(session types.Session) {
m.mu.RUnlock()
session.Send(FILETRANSFER_UPDATE, Message{
Enabled: m.config.Enabled,
RootDir: m.config.RootDir,
Files: fileList,
Enabled: m.config.Enabled,
RootDir: m.config.RootDir,
UserDownload: m.config.UserDownload,
UserUpload: m.config.UserUpload,
Files: fileList,
})
}
@@ -208,8 +212,8 @@ func (m *Manager) Shutdown() error {
}
func (m *Manager) Route(r types.Router) {
r.With(auth.AdminsOnly).Get("/", m.downloadFileHandler)
r.With(auth.AdminsOnly).Post("/", m.uploadFileHandler)
r.Get("/", m.downloadFileHandler)
r.Post("/", m.uploadFileHandler)
}
func (m *Manager) WebSocketHandler(session types.Session, msg types.WebSocketMessage) bool {
@@ -251,6 +255,10 @@ func (m *Manager) downloadFileHandler(w http.ResponseWriter, r *http.Request) er
return utils.HttpForbidden("file transfer is disabled")
}
if !session.Profile().IsAdmin && !m.config.UserDownload {
return utils.HttpForbidden("file download is not allowed for non-admin users")
}
filename := r.URL.Query().Get("filename")
badChars, err := regexp.MatchString(`(?m)\.\.(?:\/|$)`, filename)
if filename == "" || badChars || err != nil {
@@ -285,6 +293,10 @@ func (m *Manager) uploadFileHandler(w http.ResponseWriter, r *http.Request) erro
return utils.HttpForbidden("file transfer is disabled")
}
if !session.Profile().IsAdmin && !m.config.UserUpload {
return utils.HttpForbidden("file upload is not allowed for non-admin users")
}
err = r.ParseMultipartForm(multipartFormMaxMemory)
if err != nil || r.MultipartForm == nil {
return utils.HttpBadRequest().
@@ -11,9 +11,11 @@ const (
)
type Message struct {
Enabled bool `json:"enabled"`
RootDir string `json:"root_dir"`
Files []Item `json:"files"`
Enabled bool `json:"enabled"`
RootDir string `json:"root_dir"`
UserDownload bool `json:"user_download"`
UserUpload bool `json:"user_upload"`
Files []Item `json:"files"`
}
type ItemType string
+4
View File
@@ -59,11 +59,15 @@ The file transfer plugin is a simple pre-loaded internal plugin that allows you
type: 'duration',
defaultValue: '30s',
},
'filetransfer.user_download': false,
'filetransfer.user_upload': false,
}} />
- <Def id="filetransfer.enabled" /> enables the file transfer support. If set to `false`, the file transfer is disabled.
- <Def id="filetransfer.dir" /> refers to the directory where the files are stored.
- <Def id="filetransfer.refresh_interval" /> refers to the interval at which the file list is refreshed.
- <Def id="filetransfer.user_download" /> allows non-admin users to download files. If set to `false` (default), only admins can download files.
- <Def id="filetransfer.user_upload" /> allows non-admin users to upload files. If set to `false` (default), only admins can upload files.
The file transfer plugin extends user profile and room settings by adding the following fields:
+170 -8
View File
@@ -2,16 +2,178 @@
## master {#master}
### New Features {#master-feats}
- Scroll to chat on mobile ([#496](https://github.com/m1k1o/neko/pull/496))
- Added mobile keyboard icon to open the keyboard on mobile devices ([#497](https://github.com/m1k1o/neko/pull/497))
No unreleased changes yet.
### Fixes {#master-fixes}
- Fixed various bugs related to the legacy client and migration.
- Fixed long standing issue [#279](https://github.com/m1k1o/neko/pull/279) where Google Chrome GPU acceleration did not work with Nvidia GPUs, thanks to [@TobyColeman](https://github.com/TobyColeman), [@alexbakerdev](https://github.com/alexbakerdev) and [@samstefan](https://github.com/samstefan) from [@wearewildcards](https://github.com/wearewildcards).
## [n.eko v3.1.5](https://github.com/m1k1o/neko/releases/tag/v3.1.5) {#v3.1.5}
### Misc {#master-misc}
- Added an https condition to the healthcheck ([#503](https://github.com/m1k1o/neko/pull/503), by @Garrulousbrevity).
### New Features {#v3.1.5-feats}
- Added H.265 (HEVC) video encoding support ([#648](https://github.com/m1k1o/neko/pull/648)).
- Added keyboard input via `XTestFakeDeviceKeyEvent` for improved XInput device compatibility ([#642](https://github.com/m1k1o/neko/pull/642)).
- Updated NVIDIA video encoding to use `nvautogpuh264enc` for NVIDIA driver 590+ ([#667](https://github.com/m1k1o/neko/pull/667)).
- Clipboard is now synced automatically when the browser window gains focus ([#662](https://github.com/m1k1o/neko/pull/662)).
- Display name input is now auto-focused when entering a room ([#654](https://github.com/m1k1o/neko/pull/654)).
### Fixes {#v3.1.5-fixes}
- Fixed incorrect `LegacyIsHost` boolean logic ([#675](https://github.com/m1k1o/neko/pull/675)).
- Fixed CORS handling: wildcard usage now emits a warning and CORS is disabled by default ([#674](https://github.com/m1k1o/neko/pull/674)).
- Fixed ungoogled-chromium Dockerfile to correctly fetch and extract the binary ([#676](https://github.com/m1k1o/neko/pull/676)).
- Reduced audio jitter buffer latency ([#673](https://github.com/m1k1o/neko/pull/673)).
- Fixed video pipelines being incorrectly overridden when using legacy settings ([#666](https://github.com/m1k1o/neko/pull/666)).
- Disabled `CommandLineFlagSecurityWarnings` in browser policies for Chromium-based browsers ([#668](https://github.com/m1k1o/neko/pull/668)).
### Misc {#v3.1.5-misc}
- Installed Widevine DRM support for ARM64 ([#660](https://github.com/m1k1o/neko/pull/660)).
- Upgraded Go dependencies ([#644](https://github.com/m1k1o/neko/pull/644)).
## [n.eko v3.1.4](https://github.com/m1k1o/neko/releases/tag/v3.1.4) {#v3.1.4}
### Fixes {#v3.1.4-fixes}
- Fixed regressions in GHCR workflow updates ([#639](https://github.com/m1k1o/neko/issues/639), [#638](https://github.com/m1k1o/neko/issues/638)).
### Misc {#v3.1.4-misc}
- Added latest-version check and automatic image update logic for GHCR workflows ([#637](https://github.com/m1k1o/neko/pull/637)).
## [n.eko v3.1.3](https://github.com/m1k1o/neko/releases/tag/v3.1.3) {#v3.1.3}
### Misc {#v3.1.3-misc}
- Upgraded Go to version 1.25.
- Updated Go module dependencies.
- Standardized internal constant names and improved goroutine lifecycle handling.
## [n.eko v3.1.2](https://github.com/m1k1o/neko/releases/tag/v3.1.2) {#v3.1.2}
### Fixes {#v3.1.2-fixes}
- Fixed profile API endpoint to only update the `name` field, preventing unintended changes to other profile attributes.
## [n.eko v3.1.1](https://github.com/m1k1o/neko/releases/tag/v3.1.1) {#v3.1.1}
### Misc {#v3.1.1-misc}
- Removed support for the `linux/arm/v7` platform. Supported platforms are now `linux/amd64` and `linux/arm64`.
## [n.eko v3.1.0](https://github.com/m1k1o/neko/releases/tag/v3.1.0) {#v3.1.0}
### New Features {#v3.1.0-feats}
- Upgraded base OS from Debian Bookworm (12) to Debian Trixie (13), bringing updated system packages and improved hardware support ([#581](https://github.com/m1k1o/neko/pull/581)).
- Added microphone passthrough button to the controls toolbar ([#620](https://github.com/m1k1o/neko/pull/620)).
### Fixes {#v3.1.0-fixes}
- Completed and standardized all locale translations ([#549](https://github.com/m1k1o/neko/pull/549)).
### Misc {#v3.1.0-misc}
- Added `vlc-plugin-skins2` to the VLC image ([#623](https://github.com/m1k1o/neko/pull/623)).
## [n.eko v3.0.11](https://github.com/m1k1o/neko/releases/tag/v3.0.11) {#v3.0.11}
Maintenance release for the v3.0.x series, backporting the new features from v3.1.0 while keeping Debian Bookworm (12) as the base OS.
### New Features {#v3.0.11-feats}
- Added microphone passthrough button to the controls toolbar ([#620](https://github.com/m1k1o/neko/pull/620)).
### Fixes {#v3.0.11-fixes}
- Fixed profile API endpoint to only update the `name` field, preventing unintended changes to other profile attributes.
- Completed and standardized all locale translations ([#549](https://github.com/m1k1o/neko/pull/549)).
### Misc {#v3.0.11-misc}
- Added `vlc-plugin-skins2` to the VLC image ([#623](https://github.com/m1k1o/neko/pull/623)).
## [n.eko v3.0.10](https://github.com/m1k1o/neko/releases/tag/v3.0.10) {#v3.0.10}
### Fixes {#v3.0.10-fixes}
- Fixed legacy API calls to correctly include the configured path prefix ([#615](https://github.com/m1k1o/neko/issues/615), [#618](https://github.com/m1k1o/neko/pull/618)).
- Fixed `--no-cache` flag in the build script.
## [n.eko v3.0.9](https://github.com/m1k1o/neko/releases/tag/v3.0.9) {#v3.0.9}
### Fixes {#v3.0.9-fixes}
- Fixed Opera browser Docker image build.
- Changed WebRTC heartbeat interval from 120 s to 10 s for more responsive disconnection detection ([#585](https://github.com/m1k1o/neko/issues/585)).
- Updated all Debian Bookworm-based images to the latest packages ([#580](https://github.com/m1k1o/neko/pull/580)).
### Misc {#v3.0.9-misc}
- Added Polish (`pl`) translation ([#582](https://github.com/m1k1o/neko/pull/582)).
- Removed additional Google telemetry from ungoogled-chromium.
## [n.eko v3.0.8](https://github.com/m1k1o/neko/releases/tag/v3.0.8) {#v3.0.8}
### New Features {#v3.0.8-feats}
- Added support for entering text indirectly through the virtual keyboard ([#577](https://github.com/m1k1o/neko/pull/577)).
- Hostname is now available as a broadcast template variable ([#576](https://github.com/m1k1o/neko/pull/576)).
### Fixes {#v3.0.8-fixes}
- Fixed WidevineCDM download for DRM-protected content ([#578](https://github.com/m1k1o/neko/pull/578)).
- Fixed unreliable CapsLock behavior under macOS Chrome (upstream fix from GUACAMOLE-1823).
## [n.eko v3.0.7](https://github.com/m1k1o/neko/releases/tag/v3.0.7) {#v3.0.7}
### New Features {#v3.0.7-feats}
- Implicit hosting: when a user interacts with the screen, control is automatically requested first ([#499](https://github.com/m1k1o/neko/issues/499), [#540](https://github.com/m1k1o/neko/pull/540)).
### Misc {#v3.0.7-misc}
- Added Indonesian (`id`) translation ([#552](https://github.com/m1k1o/neko/pull/552)).
- Upgraded Go to version 1.24 and updated all dependencies ([#564](https://github.com/m1k1o/neko/pull/564)).
## [n.eko v3.0.6](https://github.com/m1k1o/neko/releases/tag/v3.0.6) {#v3.0.6}
### New Features {#v3.0.6-feats}
- Added clipboard command replacement support on the desktop ([#539](https://github.com/m1k1o/neko/pull/539)).
### Fixes {#v3.0.6-fixes}
- Fixed Vivaldi browser installation in the Docker image.
### Misc {#v3.0.6-misc}
- Updated VirtualGL to a more recent version ([#538](https://github.com/m1k1o/neko/pull/538)).
## [n.eko v3.0.5](https://github.com/m1k1o/neko/releases/tag/v3.0.5) {#v3.0.5}
### Fixes {#v3.0.5-fixes}
- Fixed mobile keyboard behavior ([#522](https://github.com/m1k1o/neko/pull/522), [#523](https://github.com/m1k1o/neko/issues/523)).
- Fixed clipboard to use the `UTF8_STRING` target for better compatibility ([#517](https://github.com/m1k1o/neko/issues/517)).
- Fixed WebRTC pong message forwarding ([#510](https://github.com/m1k1o/neko/issues/510)).
- Fixed build script for Apple Silicon (macOS) ([#520](https://github.com/m1k1o/neko/pull/520)).
- Fixed Docker volume mount error in the build script ([#519](https://github.com/m1k1o/neko/pull/519)).
- Commented out Firefox `xpinstall` preferences that were causing extension issues ([#512](https://github.com/m1k1o/neko/issues/512)).
### Misc {#v3.0.5-misc}
- Added `SECURITY.md` with vulnerability reporting instructions.
- Temporarily disabled Waterfox build while the upstream download link is unavailable.
## [n.eko v3.0.4](https://github.com/m1k1o/neko/releases/tag/v3.0.4) {#v3.0.4}
### Fixes {#v3.0.4-fixes}
- Fixed HTTPS + legacy mode: a local HTTP server is now also started to handle both connection types ([#507](https://github.com/m1k1o/neko/pull/507)).
- Disabled HTTP proxy for local requests to prevent unintended request forwarding ([#509](https://github.com/m1k1o/neko/issues/509)).
- Updated Waterfox user agent to work around Cloudflare bot protection blocking downloads.
### Misc {#v3.0.4-misc}
- Added HTTPS condition to the Docker healthcheck ([#503](https://github.com/m1k1o/neko/pull/503), by [@Garrulousbrevity](https://github.com/Garrulousbrevity)).
## [n.eko v3.0.3](https://github.com/m1k1o/neko/releases/tag/v3.0.3) {#v3.0.3}
### Fixes {#v3.0.3-fixes}
- Fixed legacy WebSocket mode to correctly forward ping messages ([#506](https://github.com/m1k1o/neko/issues/506)).
- Fixed legacy handler logging and WebSocket error unwrapping.
- Fixed legacy pipeline generation when a specific codec is configured.
### Misc {#v3.0.3-misc}
- Configuration option names updated and scripts moved to a dedicated `scripts/` folder.
- Updated Docker image naming convention to include version information.
- Documentation improvements: legacy mode explanation, V2 migration guide, available encoders overview, NVIDIA GPU examples ([#502](https://github.com/m1k1o/neko/issues/502)), filetransfer migration guide.
## [n.eko v3.0.2](https://github.com/m1k1o/neko/releases/tag/v3.0.2) {#v3.0.2}
### Misc {#v3.0.2-misc}
- Added `net.m1k1o.neko.api-version` label to Docker images for easier API version detection.
- Legacy handler key/button action events are now only logged at trace level, reducing log verbosity.
## [n.eko v3.0.1](https://github.com/m1k1o/neko/releases/tag/v3.0.1) {#v3.0.1}
### New Features {#v3.0.1-feats}
- Added mobile keyboard icon for opening the on-screen keyboard on touch devices ([#497](https://github.com/m1k1o/neko/pull/497)).
- Chat now auto-scrolls to the latest message on mobile ([#496](https://github.com/m1k1o/neko/pull/496)).
### Fixes {#v3.0.1-fixes}
- Fixed ICE Lite being incorrectly enabled by default (it should be disabled).
- Fixed supervisord configuration to use the new `server.static` flag.
## [n.eko v3.0.0](https://github.com/m1k1o/neko/releases/tag/v3.0.0) {#v3.0.0}