|
@@ -7,13 +7,13 @@ from typing import Dict, Optional, List
|
|
|
from pathlib import Path
|
|
from pathlib import Path
|
|
|
|
|
|
|
|
from rich import print
|
|
from rich import print
|
|
|
-from pydantic import Field, field_validator, computed_field
|
|
|
|
|
|
|
+from pydantic import Field, field_validator
|
|
|
from django.utils.crypto import get_random_string
|
|
from django.utils.crypto import get_random_string
|
|
|
|
|
|
|
|
from abx.archivebox.base_configset import BaseConfigSet
|
|
from abx.archivebox.base_configset import BaseConfigSet
|
|
|
|
|
|
|
|
from .constants import CONSTANTS
|
|
from .constants import CONSTANTS
|
|
|
-from .version import get_COMMIT_HASH, get_BUILD_TIME
|
|
|
|
|
|
|
+from .version import get_COMMIT_HASH, get_BUILD_TIME, VERSION
|
|
|
from .permissions import IN_DOCKER
|
|
from .permissions import IN_DOCKER
|
|
|
|
|
|
|
|
###################### Config ##########################
|
|
###################### Config ##########################
|
|
@@ -31,25 +31,22 @@ class ShellConfig(BaseConfigSet):
|
|
|
|
|
|
|
|
ANSI: Dict[str, str] = Field(default=lambda c: CONSTANTS.DEFAULT_CLI_COLORS if c.USE_COLOR else CONSTANTS.DISABLED_CLI_COLORS)
|
|
ANSI: Dict[str, str] = Field(default=lambda c: CONSTANTS.DEFAULT_CLI_COLORS if c.USE_COLOR else CONSTANTS.DISABLED_CLI_COLORS)
|
|
|
|
|
|
|
|
- VERSIONS_AVAILABLE: bool = False # .check_for_update.get_versions_available_on_github(c)},
|
|
|
|
|
- CAN_UPGRADE: bool = False # .check_for_update.can_upgrade(c)},
|
|
|
|
|
-
|
|
|
|
|
- @computed_field
|
|
|
|
|
@property
|
|
@property
|
|
|
def TERM_WIDTH(self) -> int:
|
|
def TERM_WIDTH(self) -> int:
|
|
|
if not self.IS_TTY:
|
|
if not self.IS_TTY:
|
|
|
return 200
|
|
return 200
|
|
|
return shutil.get_terminal_size((140, 10)).columns
|
|
return shutil.get_terminal_size((140, 10)).columns
|
|
|
|
|
|
|
|
- @computed_field
|
|
|
|
|
@property
|
|
@property
|
|
|
def COMMIT_HASH(self) -> Optional[str]:
|
|
def COMMIT_HASH(self) -> Optional[str]:
|
|
|
return get_COMMIT_HASH()
|
|
return get_COMMIT_HASH()
|
|
|
|
|
|
|
|
- @computed_field
|
|
|
|
|
@property
|
|
@property
|
|
|
def BUILD_TIME(self) -> str:
|
|
def BUILD_TIME(self) -> str:
|
|
|
return get_BUILD_TIME()
|
|
return get_BUILD_TIME()
|
|
|
|
|
+
|
|
|
|
|
+ # def VERSIONS_AVAILABLE() -> bool # .check_for_update.get_versions_available_on_github(c)},
|
|
|
|
|
+ # def CAN_UPGRADE() -> bool # .check_for_update.can_upgrade(c)},
|
|
|
|
|
|
|
|
SHELL_CONFIG = ShellConfig()
|
|
SHELL_CONFIG = ShellConfig()
|
|
|
|
|
|
|
@@ -79,7 +76,6 @@ STORAGE_CONFIG = StorageConfig()
|
|
|
class GeneralConfig(BaseConfigSet):
|
|
class GeneralConfig(BaseConfigSet):
|
|
|
TAG_SEPARATOR_PATTERN: str = Field(default=r'[,]')
|
|
TAG_SEPARATOR_PATTERN: str = Field(default=r'[,]')
|
|
|
|
|
|
|
|
-
|
|
|
|
|
GENERAL_CONFIG = GeneralConfig()
|
|
GENERAL_CONFIG = GeneralConfig()
|
|
|
|
|
|
|
|
|
|
|
|
@@ -90,6 +86,7 @@ class ServerConfig(BaseConfigSet):
|
|
|
CSRF_TRUSTED_ORIGINS: str = Field(default=lambda c: 'http://localhost:8000,http://127.0.0.1:8000,http://0.0.0.0:8000,http://{}'.format(c.BIND_ADDR))
|
|
CSRF_TRUSTED_ORIGINS: str = Field(default=lambda c: 'http://localhost:8000,http://127.0.0.1:8000,http://0.0.0.0:8000,http://{}'.format(c.BIND_ADDR))
|
|
|
|
|
|
|
|
SNAPSHOTS_PER_PAGE: int = Field(default=40)
|
|
SNAPSHOTS_PER_PAGE: int = Field(default=40)
|
|
|
|
|
+ PREVIEW_ORIGINALS: bool = Field(default=True)
|
|
|
FOOTER_INFO: str = Field(default='Content is hosted for personal archiving purposes only. Contact server owner for any takedown requests.')
|
|
FOOTER_INFO: str = Field(default='Content is hosted for personal archiving purposes only. Contact server owner for any takedown requests.')
|
|
|
# CUSTOM_TEMPLATES_DIR: Path = Field(default=None) # this is now a constant
|
|
# CUSTOM_TEMPLATES_DIR: Path = Field(default=None) # this is now a constant
|
|
|
|
|
|
|
@@ -99,10 +96,10 @@ class ServerConfig(BaseConfigSet):
|
|
|
|
|
|
|
|
ADMIN_USERNAME: str = Field(default=None)
|
|
ADMIN_USERNAME: str = Field(default=None)
|
|
|
ADMIN_PASSWORD: str = Field(default=None)
|
|
ADMIN_PASSWORD: str = Field(default=None)
|
|
|
|
|
+
|
|
|
REVERSE_PROXY_USER_HEADER: str = Field(default='Remote-User')
|
|
REVERSE_PROXY_USER_HEADER: str = Field(default='Remote-User')
|
|
|
REVERSE_PROXY_WHITELIST: str = Field(default='')
|
|
REVERSE_PROXY_WHITELIST: str = Field(default='')
|
|
|
LOGOUT_REDIRECT_URL: str = Field(default='/')
|
|
LOGOUT_REDIRECT_URL: str = Field(default='/')
|
|
|
- PREVIEW_ORIGINALS: bool = Field(default=True)
|
|
|
|
|
|
|
|
|
|
SERVER_CONFIG = ServerConfig()
|
|
SERVER_CONFIG = ServerConfig()
|
|
|
|
|
|
|
@@ -116,7 +113,7 @@ class ArchivingConfig(BaseConfigSet):
|
|
|
MEDIA_MAX_SIZE: str = Field(default='750m')
|
|
MEDIA_MAX_SIZE: str = Field(default='750m')
|
|
|
RESOLUTION: str = Field(default='1440,2000')
|
|
RESOLUTION: str = Field(default='1440,2000')
|
|
|
CHECK_SSL_VALIDITY: bool = Field(default=True)
|
|
CHECK_SSL_VALIDITY: bool = Field(default=True)
|
|
|
- USER_AGENT: str = Field(default='Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/128.0.0.0 Safari/537.36 ArchiveBox/{VERSION} (+https://github.com/ArchiveBox/ArchiveBox/)')
|
|
|
|
|
|
|
+ USER_AGENT: str = Field(default=f'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36 ArchiveBox/{VERSION} (+https://github.com/ArchiveBox/ArchiveBox/)')
|
|
|
COOKIES_FILE: Path | None = Field(default=None)
|
|
COOKIES_FILE: Path | None = Field(default=None)
|
|
|
|
|
|
|
|
URL_DENYLIST: str = Field(default=r'\.(css|js|otf|ttf|woff|woff2|gstatic\.com|googleapis\.com/css)(\?.*)?$', alias='URL_BLACKLIST')
|
|
URL_DENYLIST: str = Field(default=r'\.(css|js|otf|ttf|woff|woff2|gstatic\.com|googleapis\.com/css)(\?.*)?$', alias='URL_BLACKLIST')
|
|
@@ -134,17 +131,15 @@ class ArchivingConfig(BaseConfigSet):
|
|
|
# CHROME_HEADLESS: bool = Field(default=True)
|
|
# CHROME_HEADLESS: bool = Field(default=True)
|
|
|
# CHROME_SANDBOX: bool = Field(default=lambda: not SHELL_CONFIG.IN_DOCKER)
|
|
# CHROME_SANDBOX: bool = Field(default=lambda: not SHELL_CONFIG.IN_DOCKER)
|
|
|
|
|
|
|
|
- @field_validator('TIMEOUT', mode='after')
|
|
|
|
|
- def validate_timeout(cls, v):
|
|
|
|
|
- if int(v) < 5:
|
|
|
|
|
- print(f'[red][!] Warning: TIMEOUT is set too low! (currently set to TIMEOUT={v} seconds)[/red]', file=sys.stderr)
|
|
|
|
|
|
|
+ def validate(self):
|
|
|
|
|
+ if int(self.TIMEOUT) < 5:
|
|
|
|
|
+ print(f'[red][!] Warning: TIMEOUT is set too low! (currently set to TIMEOUT={self.TIMEOUT} seconds)[/red]', file=sys.stderr)
|
|
|
print(' You must allow *at least* 5 seconds for indexing and archive methods to run succesfully.', file=sys.stderr)
|
|
print(' You must allow *at least* 5 seconds for indexing and archive methods to run succesfully.', file=sys.stderr)
|
|
|
print(' (Setting it to somewhere between 30 and 3000 seconds is recommended)', file=sys.stderr)
|
|
print(' (Setting it to somewhere between 30 and 3000 seconds is recommended)', file=sys.stderr)
|
|
|
print(file=sys.stderr)
|
|
print(file=sys.stderr)
|
|
|
print(' If you want to make ArchiveBox run faster, disable specific archive methods instead:', file=sys.stderr)
|
|
print(' If you want to make ArchiveBox run faster, disable specific archive methods instead:', file=sys.stderr)
|
|
|
print(' https://github.com/ArchiveBox/ArchiveBox/wiki/Configuration#archive-method-toggles', file=sys.stderr)
|
|
print(' https://github.com/ArchiveBox/ArchiveBox/wiki/Configuration#archive-method-toggles', file=sys.stderr)
|
|
|
print(file=sys.stderr)
|
|
print(file=sys.stderr)
|
|
|
- return v
|
|
|
|
|
|
|
|
|
|
@field_validator('CHECK_SSL_VALIDITY', mode='after')
|
|
@field_validator('CHECK_SSL_VALIDITY', mode='after')
|
|
|
def validate_check_ssl_validity(cls, v):
|
|
def validate_check_ssl_validity(cls, v):
|
|
@@ -167,15 +162,17 @@ class ArchivingConfig(BaseConfigSet):
|
|
|
@property
|
|
@property
|
|
|
def SAVE_ALLOWLIST_PTNS(self) -> Dict[re.Pattern, List[str]]:
|
|
def SAVE_ALLOWLIST_PTNS(self) -> Dict[re.Pattern, List[str]]:
|
|
|
return {
|
|
return {
|
|
|
- re.compile(k, CONSTANTS.ALLOWDENYLIST_REGEX_FLAGS): v
|
|
|
|
|
- for k, v in self.SAVE_ALLOWLIST.items()
|
|
|
|
|
|
|
+ # regexp: methods list
|
|
|
|
|
+ re.compile(key, CONSTANTS.ALLOWDENYLIST_REGEX_FLAGS): val
|
|
|
|
|
+ for key, val in self.SAVE_ALLOWLIST.items()
|
|
|
} if self.SAVE_ALLOWLIST else {}
|
|
} if self.SAVE_ALLOWLIST else {}
|
|
|
|
|
|
|
|
@property
|
|
@property
|
|
|
def SAVE_DENYLIST_PTNS(self) -> Dict[re.Pattern, List[str]]:
|
|
def SAVE_DENYLIST_PTNS(self) -> Dict[re.Pattern, List[str]]:
|
|
|
return {
|
|
return {
|
|
|
- re.compile(k, CONSTANTS.ALLOWDENYLIST_REGEX_FLAGS): v
|
|
|
|
|
- for k, v in self.SAVE_DENYLIST.items()
|
|
|
|
|
|
|
+ # regexp: methods list
|
|
|
|
|
+ re.compile(key, CONSTANTS.ALLOWDENYLIST_REGEX_FLAGS): val
|
|
|
|
|
+ for key, val in self.SAVE_DENYLIST.items()
|
|
|
} if self.SAVE_DENYLIST else {}
|
|
} if self.SAVE_DENYLIST else {}
|
|
|
|
|
|
|
|
ARCHIVING_CONFIG = ArchivingConfig()
|
|
ARCHIVING_CONFIG = ArchivingConfig()
|