Coverage for sources/librovore/structures/sphinx/detection.py: 25%
42 statements
« prev ^ index » next coverage.py v7.10.4, created at 2025-08-17 23:43 +0000
« prev ^ index » next coverage.py v7.10.4, created at 2025-08-17 23:43 +0000
1# vim: set filetype=python fileencoding=utf-8:
2# -*- coding: utf-8 -*-
4#============================================================================#
5# #
6# Licensed under the Apache License, Version 2.0 (the "License"); #
7# you may not use this file except in compliance with the License. #
8# You may obtain a copy of the License at #
9# #
10# http://www.apache.org/licenses/LICENSE-2.0 #
11# #
12# Unless required by applicable law or agreed to in writing, software #
13# distributed under the License is distributed on an "AS IS" BASIS, #
14# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. #
15# See the License for the specific language governing permissions and #
16# limitations under the License. #
17# #
18#============================================================================#
21''' Sphinx detection and metadata extraction. '''
24from urllib.parse import ParseResult as _Url
26from . import __
27from . import extraction as _extraction
28from . import urls as _urls
31_scribe = __.acquire_scribe( __name__ )
34class SphinxDetection( __.StructureDetection ):
35 ''' Detection result for Sphinx documentation sources. '''
37 source: str
38 has_searchindex: bool = False
39 normalized_source: str = ''
40 theme: __.typx.Optional[ str ] = None
42 @classmethod
43 async def from_source(
44 selfclass,
45 auxdata: __.ApplicationGlobals,
46 processor: __.Processor,
47 source: str,
48 ) -> __.typx.Self:
49 ''' Constructs detection from source location. '''
50 detection = await processor.detect( auxdata, source )
51 return __.typx.cast( __.typx.Self, detection )
53 async def extract_contents(
54 self,
55 auxdata: __.ApplicationGlobals,
56 source: str,
57 objects: __.cabc.Sequence[ __.cabc.Mapping[ str, __.typx.Any ] ], /, *,
58 include_snippets: bool = True,
59 ) -> list[ dict[ str, __.typx.Any ] ]:
60 ''' Extracts documentation content for specified objects. '''
61 theme = self.theme if self.theme is not None else __.absent
62 return await _extraction.extract_contents(
63 auxdata, source, objects,
64 theme = theme, include_snippets = include_snippets )
68async def check_searchindex(
69 auxdata: __.ApplicationGlobals, source: _Url
70) -> bool:
71 ''' Checks if searchindex.js exists (indicates full Sphinx site). '''
72 url = _urls.derive_searchindex_url( source )
73 return await __.probe_url( auxdata.probe_cache, url )
76async def detect_theme(
77 auxdata: __.ApplicationGlobals, source: _Url
78) -> dict[ str, __.typx.Any ]:
79 ''' Detects Sphinx theme and other metadata. '''
80 theme_metadata: dict[ str, __.typx.Any ] = { }
81 html_url = _urls.derive_html_url( source )
82 try:
83 # TODO: Use probe_url instead of `try`.
84 html_content = await __.retrieve_url_as_text(
85 auxdata.content_cache,
86 html_url, duration_max = 10.0 )
87 except __.DocumentationInaccessibility: pass
88 else:
89 html_content_lower = html_content.lower( )
90 if ( 'furo' in html_content_lower
91 or 'css/furo.css' in html_content_lower
92 ): theme_metadata[ 'theme' ] = 'furo'
93 elif ( 'sphinx_rtd_theme' in html_content_lower
94 or 'css/theme.css' in html_content_lower
95 ): theme_metadata[ 'theme' ] = 'sphinx_rtd_theme'
96 elif ( 'alabaster' in html_content_lower
97 or 'css/alabaster.css' in html_content_lower
98 ): theme_metadata[ 'theme' ] = 'alabaster'
99 elif ( 'pydoctheme.css' in html_content_lower
100 or 'classic.css' in html_content_lower
101 ): theme_metadata[ 'theme' ] = 'pydoctheme'
102 elif 'flask.css' in html_content_lower:
103 theme_metadata[ 'theme' ] = 'flask'
104 elif 'css/nature.css' in html_content_lower:
105 theme_metadata[ 'theme' ] = 'nature'
106 elif 'css/default.css' in html_content_lower:
107 theme_metadata[ 'theme' ] = 'classic'
108 elif 'sphinx_book_theme' in html_content_lower:
109 theme_metadata[ 'theme' ] = 'sphinx_book_theme'
110 elif 'pydata_sphinx_theme' in html_content_lower:
111 theme_metadata[ 'theme' ] = 'pydata_sphinx_theme'
112 # If no theme detected, don't set theme key (returns None)
113 return theme_metadata