diff --git a/.github/workflows/docker.yml b/.github/workflows/docker.yml
index 2199b52b..087c76cc 100644
--- a/.github/workflows/docker.yml
+++ b/.github/workflows/docker.yml
@@ -3,6 +3,9 @@ name: docker-build
on:
workflow_dispatch:
push:
+ paths-ignore:
+ - 'docs/**'
+ - 'README.md'
branches:
- 'master'
- 'staging'
diff --git a/docs/config.md b/docs/config.md
index b4cdd8e6..26e6b4fd 100644
--- a/docs/config.md
+++ b/docs/config.md
@@ -219,7 +219,6 @@ Exercise caution with this recipe - the app is designed not to allow unsafe
paths by default. If you are happy to disable this check, then go ahead.
```javascript
-const dayjs = require('dayjs');
module.exports = {
afterConfig(config) {
// Set your path here
@@ -230,3 +229,17 @@ module.exports = {
}
}
```
+
+### Only show ISO paper sizes
+
+You can use a filter to include only the paper sizes you want. To only show ISO
+sizes do something like the following. You can obviously extend or reverse the
+filter as required.
+
+```javascript
+module.exports = {
+ afterConfig(config) {
+ config.paperSizes = config.paperSizes.filter(p => /[AB]\d/.test(p.name));
+ }
+}
+```
\ No newline at end of file
diff --git a/docs/development.md b/docs/development.md
index 6dbcb631..b9622882 100644
--- a/docs/development.md
+++ b/docs/development.md
@@ -1,33 +1,60 @@
# Development
-## Steps
+## Install and setup
-* Install Node
-* Clone the repo
-* Navigate to the repo directory
- ```
- sudo npm install -g @vue/cli @vue/cli-service-global gulp-cli
- npm run install
- ```
+```shell
+# Install dependencies
+sudo apt-get install curl nodejs npm imagemagick sane-utils tesseract-ocr
-## Run for development
+# Ideally set the npm version
+sudo npm install npm@7.11.2 -g
-```
+# Enable PDF (required for execution and unit tests)
+sudo sed -i 's/policy domain="coder" rights="none" pattern="PDF"/policy domain="coder" rights="read | write" pattern="PDF"'/ /etc/ImageMagick-6/policy.xml
+
+# Clone the repo
+git clone https://github.com/sbs20/scanservjs.git
+
+# Install all packages
+cd scanservjs && npm run install
+
+# Run (from the scanservjs directory)
npm run serve
```
-This will hook the server component into webpack (see vue.config.js) and
-references below.
+`npm run serve` will hook the development server into webpack (see
+vue.config.js).
+
+If you run into the following error, then you may need to increase your inotify
+limit:
+
+```
+[nodemon] Internal watch failed: ENOSPC: System limit for number of file watchers reached, watch '/.../scanservjs/packages/server/src'
+```
+
+To incease it temporarily:
+
+```
+sudo sysctl fs.inotify.max_user_watches=131072
+```
+
+To update it permanently will depend on your distribution - but this will work
+with Debian:
+
+```
+echo fs.inotify.max_user_watches=131072 | sudo tee -a /etc/sysctl.d/50-default.conf; sudo sysctl -p
+```
## Build
Before committing please verify and build
+
```
-npm run verify
-npm run build
+npm run verify && npm run build
```
-Create a local release package
+Alternatively, create a local release package
+
```
npm run release
```
diff --git a/docs/install.md b/docs/install.md
index dc3f766a..6da197cd 100644
--- a/docs/install.md
+++ b/docs/install.md
@@ -50,6 +50,12 @@ debug where the problem is:
[here](./sane.md)) to allow certain groups access to the hardware - but it's
also worth verifying that the `scanservjs` user is a member of the `scanner`
group (or the group specified in your udev rule): `groups scanservjs`.
+* If everything so far has worked, then also try running a scan as the
+ scanservjs user with
+ `sudo su - scanservjs -c 'scanimage --format tiff > test.tif'` - this should
+ output a tif file in the scanservjs home directory (probably
+ `/home/scanservjs/`). If you can get this to work then scanservjs should be
+ working fine.
* Getting logs: use `journalctl`. See the journalctl manpage for details but
`sudo journalctl -e -u scanservjs` should be enough to get you started.
diff --git a/docs/troubleshooting.md b/docs/troubleshooting.md
index a2e91037..52b1cab0 100644
--- a/docs/troubleshooting.md
+++ b/docs/troubleshooting.md
@@ -1,5 +1,19 @@
# Troubleshooting
+## scanimage: sane_read: Invalid argument
+
+This is a problem with SANE rather than scanservjs. It usually signifies a
+[problem with the driver](https://askubuntu.com/a/447283). Your best bet is
+going back to first principles with SANE itself. Follow the steps
+[here](./install.md#troubleshooting)
+
+## Cropping results in incorrect positioning
+
+Some scanners mis-report their size - don't know why, but they do. This means
+that when the app attempts to crop things the maths is all wrong. The best way
+around this is to override the reported scanner dimensions. See
+[this recipe](./config.md#override-scanner-dimensions) for more.
+
## JSON.parse error
This happens when the browser received a string from the server which is not a
diff --git a/package-lock.json b/package-lock.json
index d8f15d7b..be7ed200 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -1,12 +1,12 @@
{
"name": "scanservjs",
- "version": "2.17.0",
+ "version": "2.17.1",
"lockfileVersion": 2,
"requires": true,
"packages": {
"": {
"name": "scanservjs",
- "version": "2.17.0",
+ "version": "2.17.1",
"hasInstallScript": true,
"license": "GPL-2.0"
}
diff --git a/package.json b/package.json
index ab2e550d..8bc045e0 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "scanservjs",
- "version": "2.17.0",
+ "version": "2.17.1",
"description": "scanservjs is a simple web-based UI for SANE which allows you to share a scanner on a network without the need for drivers or complicated installation.",
"scripts": {
"clean": "rm -rf ./dist",
diff --git a/packages/client/package-lock.json b/packages/client/package-lock.json
index 425aab2b..d889a6db 100644
--- a/packages/client/package-lock.json
+++ b/packages/client/package-lock.json
@@ -1,12 +1,12 @@
{
"name": "scanservjs",
- "version": "2.17.0",
+ "version": "2.17.1",
"lockfileVersion": 2,
"requires": true,
"packages": {
"": {
"name": "scanservjs",
- "version": "2.17.0",
+ "version": "2.17.1",
"license": "GPL-2.0",
"dependencies": {
"@mdi/font": "^5.9.55",
diff --git a/packages/client/package.json b/packages/client/package.json
index 2f9fa654..6ec9a97d 100644
--- a/packages/client/package.json
+++ b/packages/client/package.json
@@ -1,6 +1,6 @@
{
"name": "scanservjs",
- "version": "2.17.0",
+ "version": "2.17.1",
"description": "scanservjs is a simple web-based UI for SANE which allows you to share a scanner on a network without the need for drivers or complicated installation.",
"author": "Sam Strachan",
"scripts": {
diff --git a/packages/client/src/components/BatchDialog.vue b/packages/client/src/components/BatchDialog.vue
index deeb2941..8001e637 100644
--- a/packages/client/src/components/BatchDialog.vue
+++ b/packages/client/src/components/BatchDialog.vue
@@ -1,15 +1,16 @@
-
+
{{ message }}
-
- {{ $t('batch-dialog.btn-cancel') }}
- {{ $t('batch-dialog.btn-finish') }}
- {{ $t('batch-dialog.btn-rescan') }}
- {{ $t('batch-dialog.btn-next') }}
+
+ {{ $t('batch-dialog.btn-next') }}
+ {{ $t('batch-dialog.btn-finish') }}
+ {{ $t('batch-dialog.btn-rescan') }}
+ {{ $t('batch-dialog.btn-cancel') }}
+
diff --git a/packages/client/src/components/Files.vue b/packages/client/src/components/Files.vue
index 4bc70a23..3d9cfa60 100644
--- a/packages/client/src/components/Files.vue
+++ b/packages/client/src/components/Files.vue
@@ -4,6 +4,10 @@
:items="files"
v-model="selectedFiles"
item-key="name"
+ :footer-props="{
+ 'items-per-page-text': $t('files.items-per-page'),
+ 'items-per-page-all-text': $t('files.items-per-page-all')
+ }"
show-select>
@@ -20,10 +24,10 @@
-
+
{{ $t('files.dialog:rename-cancel') }}
-
+
{{ $t('files.dialog:rename-save') }}
@@ -45,6 +49,9 @@
mdi-delete
+
+ {{ items.pageStart }} - {{ items.pageStop }} / {{ items.itemsLength }}
+
@@ -117,7 +124,7 @@ export default {
Common.fetch(`files/${file.name}`, {
method: 'DELETE'
}).then(data => {
- this.$emit('notify', {type: 'i', message: `${this.$t('files.message:deleted')} ${data.name}`});
+ this.$emit('notify', {type: 'i', message: `${this.$t('files.message:deleted', [data.name])}`});
this.fileList();
this.$emit('mask', -1);
}).catch(error => {
@@ -169,7 +176,7 @@ export default {
const name = this.selectedFiles[0].name;
try {
await Common.fetch(`files/${name}`, {method: 'DELETE'});
- this.$emit('notify', {type: 'i', message: `${this.$t('files.message:deleted')} ${name}`});
+ this.$emit('notify', {type: 'i', message: `${this.$t('files.message:deleted', [name])}`});
} catch (error) {
this.$emit('notify', {type: 'e', message: error});
}
diff --git a/packages/client/src/components/Scan.vue b/packages/client/src/components/Scan.vue
index 03092791..987878b2 100644
--- a/packages/client/src/components/Scan.vue
+++ b/packages/client/src/components/Scan.vue
@@ -9,7 +9,7 @@
v-if="context.devices.length > 0"
:label="$t('scan.device')" v-model="device"
:items="context.devices" return-object item-text="name" @change="clear">
- mdi-refresh
+ mdi-refresh
+ {{ $t('scan.btn-scan') }} mdi-camera
{{ $t('scan.btn-preview') }} mdi-magnify
{{ $t('scan.btn-clear') }} mdi-delete
- {{ $t('scan.btn-scan') }} mdi-camera
@@ -64,10 +64,10 @@
-
-
-
-
+
+
+
+
diff --git a/packages/client/src/locales/cs.json b/packages/client/src/locales/cs.json
index 0c54f35e..c2dc49e4 100644
--- a/packages/client/src/locales/cs.json
+++ b/packages/client/src/locales/cs.json
@@ -33,9 +33,9 @@
},
"batch-dialog": {
- "btn-cancel": "Zrušení",
+ "btn-cancel": "Zrušit",
"btn-finish": "Dokončit",
- "btn-rescan": "Oskenovat znovu",
+ "btn-rescan": "Znovu oskenovat stranu",
"btn-next": "Další"
},
@@ -43,7 +43,9 @@
"filename": "Název souboru",
"date": "Datum",
"size": "Velikost",
- "message:deleted": "Odstraněno",
+ "items-per-page": "Počet souborů na stránku",
+ "items-per-page-all": "Všechny",
+ "message:deleted": "Soubor {0} byl odstraněn",
"message:renamed": "Soubor byl přejmenován",
"button:delete-selected": "Odstranit vybrané",
"dialog:rename": "Změnit název souboru",
@@ -111,7 +113,7 @@
"lzw-compressed": "S kompresí LZW",
"ocr": "OCR",
"text-file": "Textový soubor"
- },
+ },
"paper-size": {
"letter": "Letter",
@@ -149,7 +151,7 @@
"message:no-devices": "Nebyla nalezena žádná zařízení",
"message:deleted-preview": "Odstranit náhled",
"message:turn-documents": "Obrátit dokumenty",
- "message:preview-of-page": "Náhled stránky"
+ "message:preview-of-page": "Náhled strany"
},
"settings": {
diff --git a/packages/client/src/locales/de.json b/packages/client/src/locales/de.json
index 10733b57..f60752ce 100644
--- a/packages/client/src/locales/de.json
+++ b/packages/client/src/locales/de.json
@@ -43,7 +43,9 @@
"filename": "Dateiname",
"date": "Datum",
"size": "Größe",
- "message:deleted": "Gelöscht",
+ "items-per-page": "Files per page",
+ "items-per-page-all": "All",
+ "message:deleted": "Gelöscht {0}",
"message:renamed": "Datei umbenannt",
"button:delete-selected": "Auswahl löschen",
"dialog:rename": "Datei umbennen",
diff --git a/packages/client/src/locales/en.json b/packages/client/src/locales/en.json
index 4a57aa2f..ecb2f2d2 100644
--- a/packages/client/src/locales/en.json
+++ b/packages/client/src/locales/en.json
@@ -43,7 +43,9 @@
"filename": "Filename",
"date": "Date",
"size": "Size",
- "message:deleted": "Deleted",
+ "items-per-page": "Files per page",
+ "items-per-page-all": "All",
+ "message:deleted": "Deleted {0}",
"message:renamed": "File renamed",
"button:delete-selected": "Delete Selected",
"dialog:rename": "Change file name",
diff --git a/packages/client/src/locales/es.json b/packages/client/src/locales/es.json
index c9bbaf20..31651520 100644
--- a/packages/client/src/locales/es.json
+++ b/packages/client/src/locales/es.json
@@ -43,7 +43,9 @@
"filename": "Nombre de fichero",
"date": "Fecha",
"size": "Tamaño",
- "message:deleted": "Borrado",
+ "items-per-page": "Files per page",
+ "items-per-page-all": "All",
+ "message:deleted": "Borrado {0}",
"message:renamed": "File renamed",
"button:delete-selected": "Delete Selected",
"dialog:rename": "Change file name",
diff --git a/packages/client/src/locales/fr.json b/packages/client/src/locales/fr.json
index f68706b5..62d19408 100644
--- a/packages/client/src/locales/fr.json
+++ b/packages/client/src/locales/fr.json
@@ -43,7 +43,9 @@
"filename": "Nom de fichier",
"date": "Date",
"size": "Taille",
- "message:deleted": "Supprimé",
+ "items-per-page": "Files per page",
+ "items-per-page-all": "All",
+ "message:deleted": "Supprimé {0}",
"message:renamed": "File renamed",
"button:delete-selected": "Delete Selected",
"dialog:rename": "Change file name",
diff --git a/packages/client/src/locales/it.json b/packages/client/src/locales/it.json
index 74ac8f93..9c35ace3 100644
--- a/packages/client/src/locales/it.json
+++ b/packages/client/src/locales/it.json
@@ -43,7 +43,9 @@
"filename": "Nome file",
"date": "Data",
"size": "Dimensione",
- "message:deleted": "Eliminato",
+ "items-per-page": "File per pagina",
+ "items-per-page-all": "Tutti",
+ "message:deleted": "Eliminato {0}",
"message:renamed": "File rinominato",
"button:delete-selected": "Elimina selezionati",
"dialog:rename": "Rinomina file",
diff --git a/packages/client/src/locales/pl.json b/packages/client/src/locales/pl.json
index bac20ea1..36545a2f 100644
--- a/packages/client/src/locales/pl.json
+++ b/packages/client/src/locales/pl.json
@@ -43,7 +43,9 @@
"filename": "Nazwa pliku",
"date": "Data",
"size": "Rozmiar",
- "message:deleted": "Usunięto",
+ "items-per-page": "Files per page",
+ "items-per-page-all": "All",
+ "message:deleted": "Usunięto {0}",
"message:renamed": "File renamed",
"button:delete-selected": "Delete Selected",
"dialog:rename": "Change file name",
diff --git a/packages/client/src/locales/pt-BR.json b/packages/client/src/locales/pt-BR.json
index ea8fd9e5..e9373351 100644
--- a/packages/client/src/locales/pt-BR.json
+++ b/packages/client/src/locales/pt-BR.json
@@ -43,7 +43,9 @@
"filename": "Nome do arquivo",
"date": "Data",
"size": "Tamanho",
- "message:deleted": "Excluído",
+ "items-per-page": "Files per page",
+ "items-per-page-all": "All",
+ "message:deleted": "Excluído {0}",
"message:renamed": "File renamed",
"button:delete-selected": "Delete Selected",
"dialog:rename": "Change file name",
diff --git a/packages/client/src/locales/ru.json b/packages/client/src/locales/ru.json
index 3030badd..00ca4794 100644
--- a/packages/client/src/locales/ru.json
+++ b/packages/client/src/locales/ru.json
@@ -43,7 +43,9 @@
"filename": "Имя файла",
"date": "Дата",
"size": "Размер",
- "message:deleted": "Удален",
+ "items-per-page": "Файлов на страницу",
+ "items-per-page-all": "Все",
+ "message:deleted": "Удален {0}",
"message:renamed": "Файл переименован",
"button:delete-selected": "Удалить выбранное",
"dialog:rename": "Переименовать",
diff --git a/packages/client/src/locales/test.json b/packages/client/src/locales/test.json
index b9cf38db..210709e3 100644
--- a/packages/client/src/locales/test.json
+++ b/packages/client/src/locales/test.json
@@ -43,7 +43,9 @@
"filename": "##FILENAME",
"date": "##DATE",
"size": "##SIZE",
- "message:deleted": "##MESSAGE:DELETED",
+ "items-per-page": "##ITEMS-PER-PAGE",
+ "items-per-page-all": "##ALL",
+ "message:deleted": "##MESSAGE:DELETED {0}",
"message:renamed": "##FILE-RENAMED",
"button:delete-selected": "##DELETE-SELECTED",
"dialog:rename": "##RENAME",
diff --git a/packages/client/src/locales/zh.json b/packages/client/src/locales/zh.json
index f5b6ebca..f73f63f2 100644
--- a/packages/client/src/locales/zh.json
+++ b/packages/client/src/locales/zh.json
@@ -43,7 +43,9 @@
"filename": "文件名",
"date": "日期",
"size": "大小",
- "message:deleted": "已删除",
+ "items-per-page": "Files per page",
+ "items-per-page-all": "All",
+ "message:deleted": "已删除 {0}",
"message:renamed": "File renamed",
"button:delete-selected": "Delete Selected",
"dialog:rename": "Change file name",
diff --git a/packages/client/vue.config.js b/packages/client/vue.config.js
index 235831e1..0c3793e0 100644
--- a/packages/client/vue.config.js
+++ b/packages/client/vue.config.js
@@ -16,7 +16,8 @@ module.exports = {
devServer: {
before: app => {
configure(app, '../server/');
- }
+ },
+ disableHostCheck: true
},
pages: {
diff --git a/packages/server/package-lock.json b/packages/server/package-lock.json
index 7634417c..99152825 100644
--- a/packages/server/package-lock.json
+++ b/packages/server/package-lock.json
@@ -1,12 +1,12 @@
{
"name": "scanservjs-server",
- "version": "2.17.0",
+ "version": "2.17.1",
"lockfileVersion": 2,
"requires": true,
"packages": {
"": {
"name": "scanservjs-server",
- "version": "2.17.0",
+ "version": "2.17.1",
"license": "GPL-2.0",
"dependencies": {
"adm-zip": "^0.5.5",
diff --git a/packages/server/package.json b/packages/server/package.json
index 9ac0410b..d1a268ac 100644
--- a/packages/server/package.json
+++ b/packages/server/package.json
@@ -1,6 +1,6 @@
{
"name": "scanservjs-server",
- "version": "2.17.0",
+ "version": "2.17.1",
"description": "scanservjs is a simple web-based UI for SANE which allows you to share a scanner on a network without the need for drivers or complicated installation.",
"scripts": {
"lint": "gulp lint",
diff --git a/packages/server/src/config.js b/packages/server/src/config.js
index c2084814..97302224 100644
--- a/packages/server/src/config.js
+++ b/packages/server/src/config.js
@@ -79,30 +79,30 @@ class Config {
],
paperSizes: [
- { name: 'A3 @:paper-size.portrait', dimensions: { x: 297, y: 420 } },
- { name: 'A4 @:paper-size.portrait', dimensions: { x: 210, y: 297 } },
- { name: 'A5 @:paper-size.portrait', dimensions: { x: 148, y: 210 } },
- { name: 'A5 @:paper-size.landscape', dimensions: { x: 210, y: 148 } },
- { name: 'A6 @:paper-size.portrait', dimensions: { x: 105, y: 148 } },
- { name: 'A6 @:paper-size.landscape', dimensions: { x: 148, y: 105 } },
- { name: 'B3 @:paper-size.portrait', dimensions: { x: 353, y: 500 } },
- { name: 'B4 @:paper-size.portrait', dimensions: { x: 250, y: 353 } },
- { name: 'B5 @:paper-size.portrait', dimensions: { x: 176, y: 250 } },
- { name: 'B5 @:paper-size.landscape', dimensions: { x: 250, y: 176 } },
- { name: 'B6 @:paper-size.portrait', dimensions: { x: 125, y: 176 } },
- { name: 'B6 @:paper-size.landscape', dimensions: { x: 176, y: 125 } },
- { name: 'DIN D3 @:paper-size.portrait', dimensions: { x: 272, y: 385 } },
- { name: 'DIN D4 @:paper-size.portrait', dimensions: { x: 192, y: 272 } },
- { name: 'DIN D5 @:paper-size.portrait', dimensions: { x: 136, y: 192 } },
- { name: 'DIN D5 @:paper-size.landscape', dimensions: { x: 192, y: 136 } },
- { name: 'DIN D6 @:paper-size.portrait', dimensions: { x: 96, y: 136 } },
- { name: 'DIN D6 @:paper-size.landscape', dimensions: { x: 136, y: 96 } },
- { name: '@:paper-size.letter @:paper-size.portrait', dimensions: { x: 216, y: 279 } },
- { name: '@:paper-size.legal @:paper-size.portrait', dimensions: { x: 216, y: 356 } },
- { name: '@:paper-size.tabloid @:paper-size.portrait', dimensions: { x: 279, y: 432 } },
- { name: '@:paper-size.ledger @:paper-size.portrait', dimensions: { x: 432, y: 279 } },
- { name: '@:paper-size.junior-legal @:paper-size.portrait', dimensions: { x: 127, y: 203 } },
- { name: '@:paper-size.half-letter @:paper-size.portrait', dimensions: { x: 140, y: 216 } }
+ { name: 'A3 (@:paper-size.portrait)', dimensions: { x: 297, y: 420 } },
+ { name: 'A4 (@:paper-size.portrait)', dimensions: { x: 210, y: 297 } },
+ { name: 'A5 (@:paper-size.portrait)', dimensions: { x: 148, y: 210 } },
+ { name: 'A5 (@:paper-size.landscape)', dimensions: { x: 210, y: 148 } },
+ { name: 'A6 (@:paper-size.portrait)', dimensions: { x: 105, y: 148 } },
+ { name: 'A6 (@:paper-size.landscape)', dimensions: { x: 148, y: 105 } },
+ { name: 'B3 (@:paper-size.portrait)', dimensions: { x: 353, y: 500 } },
+ { name: 'B4 (@:paper-size.portrait)', dimensions: { x: 250, y: 353 } },
+ { name: 'B5 (@:paper-size.portrait)', dimensions: { x: 176, y: 250 } },
+ { name: 'B5 (@:paper-size.landscape)', dimensions: { x: 250, y: 176 } },
+ { name: 'B6 (@:paper-size.portrait)', dimensions: { x: 125, y: 176 } },
+ { name: 'B6 (@:paper-size.landscape)', dimensions: { x: 176, y: 125 } },
+ { name: 'DIN D3 (@:paper-size.portrait)', dimensions: { x: 272, y: 385 } },
+ { name: 'DIN D4 (@:paper-size.portrait)', dimensions: { x: 192, y: 272 } },
+ { name: 'DIN D5 (@:paper-size.portrait)', dimensions: { x: 136, y: 192 } },
+ { name: 'DIN D5 (@:paper-size.landscape)', dimensions: { x: 192, y: 136 } },
+ { name: 'DIN D6 (@:paper-size.portrait)', dimensions: { x: 96, y: 136 } },
+ { name: 'DIN D6 (@:paper-size.landscape)', dimensions: { x: 136, y: 96 } },
+ { name: '@:paper-size.letter (@:paper-size.portrait)', dimensions: { x: 216, y: 279 } },
+ { name: '@:paper-size.legal (@:paper-size.portrait)', dimensions: { x: 216, y: 356 } },
+ { name: '@:paper-size.tabloid (@:paper-size.portrait)', dimensions: { x: 279, y: 432 } },
+ { name: '@:paper-size.ledger (@:paper-size.portrait)', dimensions: { x: 432, y: 279 } },
+ { name: '@:paper-size.junior-legal (@:paper-size.portrait)', dimensions: { x: 127, y: 203 } },
+ { name: '@:paper-size.half-letter (@:paper-size.portrait)', dimensions: { x: 140, y: 216 } }
],
});