44 Full text available at: https://opensource.org/licenses/MIT
55*/
66import { base64_decode } from "../../base/base64" ;
7- import { initiate_download } from "../../base/dom/download" ;
8- import { extension } from "../../base/paths" ;
9- import { Codeberg , GetBlobResponse , RepoContentResponse } from "./codeberg" ;
10- import { type IFileSystem } from "./vfs" ;
7+ import { based_on , normalize_join } from "../../base/paths" ;
8+ import {
9+ Codeberg ,
10+ CodebergRepoInfo ,
11+ GetBlobResponse ,
12+ RepoContentResponse ,
13+ } from "./codeberg" ;
14+ import { FileEntry , FileSystemBase } from "./vfs" ;
15+
16+ export class CodebergFileSystem extends FileSystemBase {
17+ private download_urls : Map < string , URL > = new Map ( ) ;
18+
19+ constructor ( private repo : CodebergRepoInfo ) {
20+ super ( ) ;
21+ }
1122
12- export class CodebergFileSystem implements IFileSystem {
13- static readonly kicad_extensions = [ "kicad_pcb" , "kicad_pro" , "kicad_sch" ] ;
23+ async load_file ( path : string ) : Promise < File > {
24+ const url = this . download_urls . get ( path ) ;
25+ if ( ! url ) {
26+ throw new Error ( `File ${ path } not found.` ) ;
27+ }
1428
15- async setup ( ) { }
16- constructor ( private files_to_urls : Map < string , URL > ) { }
29+ // API: https://codeberg.org/api/swagger#/repository/GetBlob
30+ const blob = await Codeberg . request_json < GetBlobResponse > ( url . pathname ) ;
1731
18- public static async fromURLs (
19- url : string | URL ,
20- ) : Promise < CodebergFileSystem | null > {
21- const files_to_urls = new Map < string , URL > ( ) ;
32+ if ( blob . content . length === 0 ) {
33+ throw new Error ( `Blob returns empty when loading file ${ path } ` ) ;
34+ }
2235
23- const info = Codeberg . parse_url ( url ) ;
24- if ( ! info ) {
25- return null ;
36+ if ( blob . encoding !== "base64" ) {
37+ throw new Error ( `Unsupported encoding: ${ blob . encoding } ` ) ;
2638 }
2739
40+ const content = base64_decode ( blob . content ) ;
41+ const file = new File ( [ content ] , path ) ;
42+
43+ return file ;
44+ }
45+
46+ async enumerate ( cur_path : string ) : Promise < FileEntry [ ] > {
2847 // API:
2948 // https://codeberg.org/api/swagger#/repository/repoGetContents
30- const api_url = `repos/${ info . owner } /${ info . repo } /contents/${ info . path } ` ;
49+ const info = this . repo ;
50+ const base_dir = info . path ;
51+ const base_api = `repos/${ info . owner } /${ info . repo } /contents` ;
52+ const api_url = normalize_join ( base_api , base_dir , cur_path ) ;
3153
3254 let files = await Codeberg . request_json <
3355 RepoContentResponse | RepoContentResponse [ ]
@@ -37,58 +59,39 @@ export class CodebergFileSystem implements IFileSystem {
3759 files = [ files ] ;
3860 }
3961
40- for ( const file of files ) {
41- if ( ! file . name || ! file . git_url || file . type !== "file" ) {
42- continue ;
43- }
44-
62+ const result : FileEntry [ ] = [ ] ;
63+ for ( const it of files ) {
4564 if (
46- ! CodebergFileSystem . kicad_extensions . includes (
47- extension ( file . name ) ,
48- )
65+ it . type === "file" &&
66+ CodebergFileSystem . is_kicad_file ( it . name )
4967 ) {
50- continue ;
68+ const file_path = based_on ( base_dir , it . path ) ;
69+
70+ this . download_urls . set ( file_path , new URL ( it . git_url ) ) ;
71+
72+ result . push ( {
73+ type : "file" ,
74+ path : file_path ,
75+ } ) ;
76+ } else if ( it . type === "dir" ) {
77+ result . push ( {
78+ type : "directory" ,
79+ path : based_on ( base_dir , it . path ) ,
80+ } ) ;
5181 }
52-
53- files_to_urls . set ( file . name , new URL ( file . git_url ) ) ;
54- }
55-
56- if ( files_to_urls . size == 0 ) {
57- // no valid URL and files, return null.
58- return null ;
5982 }
6083
61- return new CodebergFileSystem ( files_to_urls ) ;
62- }
63-
64- * list ( ) : Generator < string > {
65- yield * this . files_to_urls . keys ( ) ;
84+ return result ;
6685 }
6786
68- async get ( name : string ) {
69- const url = this . files_to_urls . get ( name ) ;
70- if ( ! url ) {
71- throw new Error ( `File ${ name } not found.` ) ;
72- }
73-
74- // API: https://codeberg.org/api/swagger#/repository/GetBlob
75- const blob = await Codeberg . request_json < GetBlobResponse > ( url . pathname ) ;
76-
77- if ( blob . encoding !== "base64" ) {
78- throw new Error ( `Unsupported encoding: ${ blob . encoding } ` ) ;
87+ public static async fromURLs (
88+ url : string | URL ,
89+ ) : Promise < CodebergFileSystem | null > {
90+ const info = Codeberg . parse_url ( url ) ;
91+ if ( ! info ) {
92+ return null ;
7993 }
8094
81- const content = base64_decode ( blob . content ) ;
82- const file = new File ( [ content ] , name ) ;
83-
84- return file ;
85- }
86-
87- async has ( name : string ) {
88- return Promise . resolve ( this . files_to_urls . has ( name ) ) ;
89- }
90-
91- async download ( name : string ) {
92- initiate_download ( await this . get ( name ) ) ;
95+ return new CodebergFileSystem ( info ) ;
9396 }
9497}
0 commit comments