Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 9 additions & 9 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,7 @@
"version": "0.2.0",
"configurations": [
{
"name": "Python: Current File",
"type": "debugpy",
"request": "launch",
"program": "${file}",
"console": "integratedTerminal"
},
{
"name": "Debug API",
"name": "API",
"type": "debugpy",
"request": "launch",
"module": "makemkv_headless.__main__",
Expand All @@ -19,10 +12,17 @@
},
{
"type": "node-terminal",
"name": "Launch Web",
"name": "Web",
"request": "launch",
"command": "npm run dev",
"cwd": "${workspaceFolder}/web"
}
],
"compounds": [
{
"name": "API + Web",
"configurations": ["API", "Web"],
"stopAll": true
}
]
}
4 changes: 4 additions & 0 deletions api/src/makemkv_headless/api/state.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

from makemkv_headless.models.socket import CurrentProgressMessage, ProgressValueMessage, TotalProgressMessage
from makemkv_headless.models.state import ProgressStateModel, StateModel
from makemkv_headless.models.toc import TocStateModel

logger = logging.getLogger(__name__)

Expand All @@ -20,6 +21,9 @@ def reset_all(self):
setattr(self, field, default_value)

self.model_fields_set.clear()

def reset_toc(self):
self.toc = TocStateModel()

def reset_socket(self):
for field, field_info in type(self.socket.rip).model_fields.items():
Expand Down
2 changes: 1 addition & 1 deletion api/src/makemkv_headless/api/v1/state.py
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ def get_state_by_path(path: str, page=None, page_size=None, filter_keys: list[st
@router.get('')
@router.get('/')
def get_state():
return STATE
return APIResponse(status="success", data=STATE)

@router.get('/{state_path:path}')
def get_state_select(state_path: str):
Expand Down
52 changes: 22 additions & 30 deletions api/src/makemkv_headless/api/v1/toc.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,37 +23,40 @@ class TocError(Exception): ...

router = APIRouter(prefix="/toc")

# @lru_cache
async def get_toc_from_disc(source):
async def get_toc_from_disc(source = CONFIG.source):
with LOCK:
toc = Toc()
# STATE.reset_rip_indexes() # Reset which indexes are selected
STATE.reset_toc()
STATE.reset_rip_indexes() # Reset which indexes are selected
STATE.reset_socket() # Reset which indexes are complete
logger.info('Getting TOC...')
await cancellable_async(toc.get_from_disc(source), CANCEL)
STATE.toc = toc
STATE.toc.source = toc.source
get_interface().send(TocStatusMessage(state="complete"))
return toc

@router.get('')
@router.get('/')
@router.get('.async') # Deprecated
async def get_toc_async(background_tasks: BackgroundTasks):
try:
if LOCK.locked():
return APIResponse("in progress")
async def get_toc():
if LOCK.locked():
return APIResponse("in progress")
else:
if STATE.toc.source is not None:
return APIResponse(status='success', data=STATE.toc)
else:
background_tasks.add_task(get_toc_from_disc, CONFIG.source)
return APIResponse("started")
except TocError as ex:
logger.error(ex.args[0])
except Exception as ex:
logger.error(format_exc())
raise APIException(500, GenericAPIError("error", ex))
return APIResponse(status='stopped')


@router.get('.start')
async def get_toc_start(background_tasks: BackgroundTasks):
if LOCK.locked():
return APIResponse("in progress")
else:
background_tasks.add_task(get_toc_from_disc)
return APIResponse("started")

@router.get('.status')
@router.get('.async.status') # Deprecated
async def get_toc_async_status():
async def get_toc_status():
if LOCK.locked():
return APIResponse("in progress")
else:
Expand All @@ -65,15 +68,4 @@ async def toc_get_stop():
CANCEL.set()
return APIResponse("in progress")
else:
return APIResponse("done")

@router.get('.cache.clear')
async def toc_clear_cache():
try:
get_toc_from_disc.cache_clear()
except Exception as ex:
raise APIException(500, GenericAPIError("error", ex))

@router.get('.cache.info')
async def toc_clear_cache():
return get_toc_from_disc.cache_info()
return APIResponse("done")
26 changes: 13 additions & 13 deletions api/src/makemkv_headless/models/state.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,26 +19,26 @@
]

class RipDestinationModel(BaseModel):
library: str = None
media: str = None
content: str = None
library: str | None = None
media: str | None = None
content: str | None = None

class RipSortInfoModel(BaseModel):
name: str = None
id: str = None
main_indexes: list[int] = None
extra_indexes: list[int] = None
split_segments: list[int] = []
name: str | None = None
id: str | None = None
main_indexes: list[int] | None = None
extra_indexes: list[int] | None = None
split_segments: list[int] | None = []
id_db: str = "tmdbid"

class RipShowInfoModel(RipSortInfoModel):
first_episode: int = None
season_number: int = None
first_episode: int | None = None
season_number: int | None = None

class RipStateModel(BaseModel):
destination: RipDestinationModel = None
sort_info: RipSortInfoModel | RipShowInfoModel = None
rip_all: bool = None
destination: RipDestinationModel | None = None
sort_info: RipSortInfoModel | RipShowInfoModel | None = None
rip_all: bool | None = None
tmdb_selection: TMDBShowSearchResultModel | TMDBMovieSearchResultModel | None = None

class ProgressStateModel(BaseModel):
Expand Down
7 changes: 0 additions & 7 deletions attach.sh

This file was deleted.

3 changes: 0 additions & 3 deletions run.sh

This file was deleted.

42 changes: 0 additions & 42 deletions start.sh

This file was deleted.

6 changes: 0 additions & 6 deletions stop.sh

This file was deleted.

48 changes: 15 additions & 33 deletions web/src/api/endpoints.ts
Original file line number Diff line number Diff line change
@@ -1,23 +1,10 @@
import type { TmdbConfiguration } from "./v1/tmdb/store"
import type { Toc as TocV1 } from "./v1/toc/types"
import type { Response as ResponseV1 } from "./v1"
import { BACKEND, type Response as ResponseV1 } from "./v1"
import type { State as StateV1 } from "./v1/state/types"
import type { TmdbSearchResultMovie, TmdbSearchResultShow } from "./v1/tmdb/types"
import type { TmdbConfiguration, TmdbSearchResultMovie, TmdbSearchResultShow } from "./v1/tmdb/types"
import type { Config } from "./v1/config/types"
import type { ApiError } from "./v1/error/types"

let backend_port = window.location.port;

if (import.meta.env.DEV) {
backend_port = import.meta.env.BACKEND_PORT ?? 4000
console.info(`Setting backend port to ${backend_port}`)
}

export const BACKEND_HOST_PORT = `${window.location.hostname}:${backend_port}`
export const BACKEND = `${window.location.protocol}//${BACKEND_HOST_PORT}`

// export const BACKEND = `${window.location.protocol}//${window.location.hostname}:${window.location.port}`

export const endpoints = {
disc: {
eject: () => `${BACKEND}/api/v1/disc/eject`,
Expand All @@ -43,34 +30,29 @@ export const endpoints = {

export const endpointsV1 = {
disc: {
eject: () => `/api/v1/disc/eject`,
eject: () => `/disc/eject`,
},
toc: () => `/api/v1/toc`,
toc: () => `/toc`,
state: {
get: (path?: string) => `/api/v1/state${path ? "/" + path : ""}`,
resetSocket: () => `/api/v1/state.reset/socket`,
get: (path: string | void) => `/state${path ? "/" + path : ""}`,
resetSocket: () => `/state.reset/socket`,
},
rip: {
start: () => `/api/v1/rip`,
stop: () => `/api/v1/rip.stop`
start: () => `/rip`,
stop: () => `/rip.stop`
},
tmdb: {
show: (query: string) => `/api/v1/tmdb/show?${new URLSearchParams({q: query})}`,
movie: (query: string) => `/api/v1/tmdb/movie?${new URLSearchParams({q: query})}`,
configuration: () => `/api/v1/tmdb/configuration`
show: (query: string) => `/tmdb/show?${new URLSearchParams({q: query})}`,
movie: (query: string) => `/tmdb/movie?${new URLSearchParams({q: query})}`,
configuration: () => `/tmdb/configuration`
},
config: {
get: () => `/api/v1/config`,
put: () => (body: Partial<Config>) => ({
url: '/api/v1/config',
method: 'PUT',
body
}),
reload: () => () => `/api/v1/config.reload`
get: () => `/config`,
reload: () => () => `/config.reload`
},
error: {
get: () => `/api/v1/error`,
clear: () => `/api/v1/error.clear`
get: () => `/error`,
clear: () => `/error.clear`
}
}

Expand Down
Loading