resourcexjs 1.7.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/arp.js +356 -62
- package/dist/arp.js.map +3 -3
- package/dist/index.js +345 -69
- package/dist/index.js.map +3 -3
- package/package.json +6 -6
package/dist/arp.js
CHANGED
|
@@ -8,6 +8,10 @@ import { join as join2 } from "node:path";
|
|
|
8
8
|
import { readFile as readFile2, writeFile as writeFile2, mkdir as mkdir2, rm as rm2, stat as stat2, readdir as readdir2 } from "node:fs/promises";
|
|
9
9
|
import { gzip as gzip2, gunzip as gunzip2 } from "node:zlib";
|
|
10
10
|
import { promisify as promisify2 } from "node:util";
|
|
11
|
+
import { homedir as homedir2 } from "node:os";
|
|
12
|
+
import { join as join22 } from "node:path";
|
|
13
|
+
import { readFile as readFile22, stat as stat22, readdir as readdir22, mkdir as mkdir22 } from "node:fs/promises";
|
|
14
|
+
import { execSync } from "node:child_process";
|
|
11
15
|
|
|
12
16
|
class ARPError extends Error {
|
|
13
17
|
constructor(message, options) {
|
|
@@ -283,6 +287,9 @@ var httpTransport = new HttpTransportHandler("http");
|
|
|
283
287
|
function isRemoteConfig(config) {
|
|
284
288
|
return config !== undefined && "endpoint" in config;
|
|
285
289
|
}
|
|
290
|
+
function isGitConfig(config) {
|
|
291
|
+
return config !== undefined && "type" in config && config.type === "git";
|
|
292
|
+
}
|
|
286
293
|
|
|
287
294
|
class ResourceXError extends Error {
|
|
288
295
|
constructor(message, options) {
|
|
@@ -1752,23 +1759,63 @@ class LocalRegistry {
|
|
|
1752
1759
|
supportType(type) {
|
|
1753
1760
|
this.typeHandler.register(type);
|
|
1754
1761
|
}
|
|
1755
|
-
buildPath(locator) {
|
|
1762
|
+
buildPath(locator, area) {
|
|
1756
1763
|
const rxl = typeof locator === "string" ? parseRXL(locator) : locator;
|
|
1757
|
-
const
|
|
1764
|
+
const resourceName = rxl.type ? `${rxl.name}.${rxl.type}` : rxl.name;
|
|
1758
1765
|
const version = rxl.version ?? "latest";
|
|
1759
|
-
|
|
1760
|
-
|
|
1761
|
-
|
|
1766
|
+
if (area === "local") {
|
|
1767
|
+
return join2(this.basePath, "local", resourceName, version);
|
|
1768
|
+
} else {
|
|
1769
|
+
const domain = rxl.domain ?? "localhost";
|
|
1770
|
+
let path = join2(this.basePath, "cache", domain);
|
|
1771
|
+
if (rxl.path) {
|
|
1772
|
+
path = join2(path, rxl.path);
|
|
1773
|
+
}
|
|
1774
|
+
return join2(path, resourceName, version);
|
|
1762
1775
|
}
|
|
1763
|
-
const resourceName = rxl.type ? `${rxl.name}.${rxl.type}` : rxl.name;
|
|
1764
|
-
return join2(path, resourceName, version);
|
|
1765
1776
|
}
|
|
1766
|
-
|
|
1767
|
-
|
|
1777
|
+
isLocalOnlyLocator(locator) {
|
|
1778
|
+
const rxl = typeof locator === "string" ? parseRXL(locator) : locator;
|
|
1779
|
+
return !rxl.domain || rxl.domain === "localhost";
|
|
1780
|
+
}
|
|
1781
|
+
async existsAt(resourcePath) {
|
|
1782
|
+
const manifestPath = join2(resourcePath, "manifest.json");
|
|
1783
|
+
try {
|
|
1784
|
+
await stat2(manifestPath);
|
|
1785
|
+
return true;
|
|
1786
|
+
} catch {
|
|
1787
|
+
return false;
|
|
1788
|
+
}
|
|
1789
|
+
}
|
|
1790
|
+
async findArea(locator) {
|
|
1791
|
+
const localPath = this.buildPath(locator, "local");
|
|
1792
|
+
if (await this.existsAt(localPath)) {
|
|
1793
|
+
return "local";
|
|
1794
|
+
}
|
|
1795
|
+
const cachePath = this.buildPath(locator, "cache");
|
|
1796
|
+
if (await this.existsAt(cachePath)) {
|
|
1797
|
+
return "cache";
|
|
1798
|
+
}
|
|
1799
|
+
return null;
|
|
1800
|
+
}
|
|
1801
|
+
async loadFrom(resourcePath) {
|
|
1802
|
+
const manifestPath = join2(resourcePath, "manifest.json");
|
|
1803
|
+
const manifestContent = await readFile2(manifestPath, "utf-8");
|
|
1804
|
+
const manifestData = JSON.parse(manifestContent);
|
|
1805
|
+
const manifest = createRXM(manifestData);
|
|
1806
|
+
const contentPath = join2(resourcePath, "content.tar.gz");
|
|
1807
|
+
const data = await readFile2(contentPath);
|
|
1808
|
+
return this.typeHandler.deserialize(data, manifest);
|
|
1809
|
+
}
|
|
1810
|
+
async pull(_locator, _options) {
|
|
1811
|
+
throw new RegistryError("Pull not implemented yet - see issue #018");
|
|
1812
|
+
}
|
|
1813
|
+
async publish(_resource, _options) {
|
|
1814
|
+
throw new RegistryError("Publish not implemented yet - see issue #018");
|
|
1768
1815
|
}
|
|
1769
1816
|
async link(resource) {
|
|
1770
1817
|
const locator = resource.manifest.toLocator();
|
|
1771
|
-
const resourcePath = this.buildPath(locator);
|
|
1818
|
+
const resourcePath = this.buildPath(locator, "local");
|
|
1772
1819
|
await mkdir2(resourcePath, { recursive: true });
|
|
1773
1820
|
const manifestPath = join2(resourcePath, "manifest.json");
|
|
1774
1821
|
await writeFile2(manifestPath, JSON.stringify(resource.manifest.toJSON(), null, 2), "utf-8");
|
|
@@ -1777,58 +1824,62 @@ class LocalRegistry {
|
|
|
1777
1824
|
await writeFile2(contentPath, serialized);
|
|
1778
1825
|
}
|
|
1779
1826
|
async get(locator) {
|
|
1780
|
-
|
|
1827
|
+
const area = await this.findArea(locator);
|
|
1828
|
+
if (!area) {
|
|
1781
1829
|
throw new RegistryError(`Resource not found: ${locator}`);
|
|
1782
1830
|
}
|
|
1783
|
-
const resourcePath = this.buildPath(locator);
|
|
1784
|
-
|
|
1785
|
-
const manifestContent = await readFile2(manifestPath, "utf-8");
|
|
1786
|
-
const manifestData = JSON.parse(manifestContent);
|
|
1787
|
-
const manifest = createRXM(manifestData);
|
|
1788
|
-
const contentPath = join2(resourcePath, "content.tar.gz");
|
|
1789
|
-
const data = await readFile2(contentPath);
|
|
1790
|
-
return this.typeHandler.deserialize(data, manifest);
|
|
1831
|
+
const resourcePath = this.buildPath(locator, area);
|
|
1832
|
+
return this.loadFrom(resourcePath);
|
|
1791
1833
|
}
|
|
1792
1834
|
async resolve(locator) {
|
|
1793
1835
|
const rxr = await this.get(locator);
|
|
1794
1836
|
return this.typeHandler.resolve(rxr);
|
|
1795
1837
|
}
|
|
1796
1838
|
async exists(locator) {
|
|
1797
|
-
const
|
|
1798
|
-
|
|
1799
|
-
try {
|
|
1800
|
-
await stat2(manifestPath);
|
|
1801
|
-
return true;
|
|
1802
|
-
} catch {
|
|
1803
|
-
return false;
|
|
1804
|
-
}
|
|
1839
|
+
const area = await this.findArea(locator);
|
|
1840
|
+
return area !== null;
|
|
1805
1841
|
}
|
|
1806
1842
|
async delete(locator) {
|
|
1807
|
-
|
|
1808
|
-
|
|
1843
|
+
const isLocal = this.isLocalOnlyLocator(locator);
|
|
1844
|
+
if (isLocal) {
|
|
1845
|
+
const localPath = this.buildPath(locator, "local");
|
|
1846
|
+
if (await this.existsAt(localPath)) {
|
|
1847
|
+
await rm2(localPath, { recursive: true, force: true });
|
|
1848
|
+
}
|
|
1849
|
+
} else {
|
|
1850
|
+
const cachePath = this.buildPath(locator, "cache");
|
|
1851
|
+
if (await this.existsAt(cachePath)) {
|
|
1852
|
+
await rm2(cachePath, { recursive: true, force: true });
|
|
1853
|
+
}
|
|
1809
1854
|
}
|
|
1810
|
-
const resourcePath = this.buildPath(locator);
|
|
1811
|
-
await rm2(resourcePath, { recursive: true, force: true });
|
|
1812
1855
|
}
|
|
1813
1856
|
async search(options) {
|
|
1814
1857
|
const { query, limit, offset = 0 } = options ?? {};
|
|
1815
|
-
let entries;
|
|
1816
|
-
try {
|
|
1817
|
-
entries = await this.listRecursive(this.basePath);
|
|
1818
|
-
} catch {
|
|
1819
|
-
return [];
|
|
1820
|
-
}
|
|
1821
1858
|
const locators = [];
|
|
1822
|
-
|
|
1823
|
-
|
|
1824
|
-
|
|
1859
|
+
const localDir = join2(this.basePath, "local");
|
|
1860
|
+
try {
|
|
1861
|
+
const localEntries = await this.listRecursive(localDir);
|
|
1862
|
+
for (const entry of localEntries) {
|
|
1863
|
+
if (!entry.endsWith("manifest.json"))
|
|
1864
|
+
continue;
|
|
1865
|
+
const relativePath = entry.slice(localDir.length + 1);
|
|
1866
|
+
const rxl = this.parseLocalEntry(relativePath);
|
|
1867
|
+
if (rxl)
|
|
1868
|
+
locators.push(rxl);
|
|
1825
1869
|
}
|
|
1826
|
-
|
|
1827
|
-
|
|
1828
|
-
|
|
1829
|
-
|
|
1870
|
+
} catch {}
|
|
1871
|
+
const cacheDir = join2(this.basePath, "cache");
|
|
1872
|
+
try {
|
|
1873
|
+
const cacheEntries = await this.listRecursive(cacheDir);
|
|
1874
|
+
for (const entry of cacheEntries) {
|
|
1875
|
+
if (!entry.endsWith("manifest.json"))
|
|
1876
|
+
continue;
|
|
1877
|
+
const relativePath = entry.slice(cacheDir.length + 1);
|
|
1878
|
+
const rxl = this.parseCacheEntry(relativePath);
|
|
1879
|
+
if (rxl)
|
|
1880
|
+
locators.push(rxl);
|
|
1830
1881
|
}
|
|
1831
|
-
}
|
|
1882
|
+
} catch {}
|
|
1832
1883
|
let filtered = locators;
|
|
1833
1884
|
if (query) {
|
|
1834
1885
|
const lowerQuery = query.toLowerCase();
|
|
@@ -1859,7 +1910,27 @@ class LocalRegistry {
|
|
|
1859
1910
|
} catch {}
|
|
1860
1911
|
return results;
|
|
1861
1912
|
}
|
|
1862
|
-
|
|
1913
|
+
parseLocalEntry(entry) {
|
|
1914
|
+
const dirPath = entry.replace(/[/\\]manifest\.json$/, "");
|
|
1915
|
+
const parts = dirPath.split(/[/\\]/);
|
|
1916
|
+
if (parts.length < 2) {
|
|
1917
|
+
return null;
|
|
1918
|
+
}
|
|
1919
|
+
const version = parts.pop();
|
|
1920
|
+
const nameTypePart = parts.shift();
|
|
1921
|
+
const { name, type } = this.parseNameType(nameTypePart);
|
|
1922
|
+
let locatorStr = name;
|
|
1923
|
+
if (type) {
|
|
1924
|
+
locatorStr += `.${type}`;
|
|
1925
|
+
}
|
|
1926
|
+
locatorStr += `@${version}`;
|
|
1927
|
+
try {
|
|
1928
|
+
return parseRXL(locatorStr);
|
|
1929
|
+
} catch {
|
|
1930
|
+
return null;
|
|
1931
|
+
}
|
|
1932
|
+
}
|
|
1933
|
+
parseCacheEntry(entry) {
|
|
1863
1934
|
const dirPath = entry.replace(/[/\\]manifest\.json$/, "");
|
|
1864
1935
|
const parts = dirPath.split(/[/\\]/);
|
|
1865
1936
|
if (parts.length < 3) {
|
|
@@ -1869,16 +1940,7 @@ class LocalRegistry {
|
|
|
1869
1940
|
const nameTypePart = parts.pop();
|
|
1870
1941
|
const domain = parts.shift();
|
|
1871
1942
|
const path = parts.length > 0 ? parts.join("/") : undefined;
|
|
1872
|
-
const
|
|
1873
|
-
let name;
|
|
1874
|
-
let type;
|
|
1875
|
-
if (dotIndex !== -1) {
|
|
1876
|
-
name = nameTypePart.substring(0, dotIndex);
|
|
1877
|
-
type = nameTypePart.substring(dotIndex + 1);
|
|
1878
|
-
} else {
|
|
1879
|
-
name = nameTypePart;
|
|
1880
|
-
type = undefined;
|
|
1881
|
-
}
|
|
1943
|
+
const { name, type } = this.parseNameType(nameTypePart);
|
|
1882
1944
|
let locatorStr = domain;
|
|
1883
1945
|
if (path) {
|
|
1884
1946
|
locatorStr += `/${path}`;
|
|
@@ -1894,6 +1956,17 @@ class LocalRegistry {
|
|
|
1894
1956
|
return null;
|
|
1895
1957
|
}
|
|
1896
1958
|
}
|
|
1959
|
+
parseNameType(nameTypePart) {
|
|
1960
|
+
const dotIndex = nameTypePart.lastIndexOf(".");
|
|
1961
|
+
if (dotIndex !== -1) {
|
|
1962
|
+
return {
|
|
1963
|
+
name: nameTypePart.substring(0, dotIndex),
|
|
1964
|
+
type: nameTypePart.substring(dotIndex + 1)
|
|
1965
|
+
};
|
|
1966
|
+
} else {
|
|
1967
|
+
return { name: nameTypePart, type: undefined };
|
|
1968
|
+
}
|
|
1969
|
+
}
|
|
1897
1970
|
}
|
|
1898
1971
|
|
|
1899
1972
|
class RemoteRegistry {
|
|
@@ -1906,7 +1979,10 @@ class RemoteRegistry {
|
|
|
1906
1979
|
supportType(type) {
|
|
1907
1980
|
this.typeHandler.register(type);
|
|
1908
1981
|
}
|
|
1909
|
-
async
|
|
1982
|
+
async pull(_locator, _options) {
|
|
1983
|
+
throw new RegistryError("Cannot pull to remote registry - use local registry for pulling");
|
|
1984
|
+
}
|
|
1985
|
+
async publish(_resource, _options) {
|
|
1910
1986
|
throw new RegistryError("Remote registry publish not implemented yet");
|
|
1911
1987
|
}
|
|
1912
1988
|
async link(_resource) {
|
|
@@ -1972,7 +2048,13 @@ async function discoverRegistry(domain) {
|
|
|
1972
2048
|
throw new RegistryError(`Well-known discovery failed for ${domain}: ${response.statusText}`);
|
|
1973
2049
|
}
|
|
1974
2050
|
const data = await response.json();
|
|
1975
|
-
|
|
2051
|
+
if (!data.registries || !Array.isArray(data.registries) || data.registries.length === 0) {
|
|
2052
|
+
throw new RegistryError(`Invalid well-known response for ${domain}: missing or empty registries`);
|
|
2053
|
+
}
|
|
2054
|
+
return {
|
|
2055
|
+
domain,
|
|
2056
|
+
registries: data.registries
|
|
2057
|
+
};
|
|
1976
2058
|
} catch (error) {
|
|
1977
2059
|
if (error instanceof RegistryError) {
|
|
1978
2060
|
throw error;
|
|
@@ -1980,10 +2062,210 @@ async function discoverRegistry(domain) {
|
|
|
1980
2062
|
throw new RegistryError(`Failed to discover registry for ${domain}: ${error.message}`);
|
|
1981
2063
|
}
|
|
1982
2064
|
}
|
|
2065
|
+
var DEFAULT_GIT_CACHE = `${homedir2()}/.resourcex/.git-cache`;
|
|
2066
|
+
|
|
2067
|
+
class GitRegistry {
|
|
2068
|
+
url;
|
|
2069
|
+
ref;
|
|
2070
|
+
basePath;
|
|
2071
|
+
cacheDir;
|
|
2072
|
+
typeHandler;
|
|
2073
|
+
trustedDomain;
|
|
2074
|
+
constructor(config) {
|
|
2075
|
+
this.url = config.url;
|
|
2076
|
+
this.ref = config.ref ?? "main";
|
|
2077
|
+
this.basePath = config.basePath ?? ".resourcex";
|
|
2078
|
+
this.typeHandler = TypeHandlerChain.create();
|
|
2079
|
+
this.trustedDomain = config.domain;
|
|
2080
|
+
if (this.isRemoteUrl(config.url) && !config.domain) {
|
|
2081
|
+
throw new RegistryError(`Remote git registry requires a trusted domain.
|
|
2082
|
+
|
|
2083
|
+
` + `Either:
|
|
2084
|
+
` + `1. Use discoverRegistry("your-domain.com") to auto-bind domain
|
|
2085
|
+
` + `2. Explicitly set domain: createRegistry({ type: "git", url: "...", domain: "your-domain.com" })
|
|
2086
|
+
|
|
2087
|
+
` + `This ensures resources from untrusted sources cannot impersonate your domain.`);
|
|
2088
|
+
}
|
|
2089
|
+
this.cacheDir = this.buildCacheDir(config.url);
|
|
2090
|
+
}
|
|
2091
|
+
isRemoteUrl(url) {
|
|
2092
|
+
return url.startsWith("git@") || url.startsWith("https://") || url.startsWith("http://");
|
|
2093
|
+
}
|
|
2094
|
+
buildCacheDir(url) {
|
|
2095
|
+
let normalized = url;
|
|
2096
|
+
if (url.startsWith("git@")) {
|
|
2097
|
+
normalized = url.slice(4).replace(":", "/");
|
|
2098
|
+
}
|
|
2099
|
+
if (normalized.endsWith(".git")) {
|
|
2100
|
+
normalized = normalized.slice(0, -4);
|
|
2101
|
+
}
|
|
2102
|
+
const dirName = normalized.replace(/\//g, "-");
|
|
2103
|
+
return join22(DEFAULT_GIT_CACHE, dirName);
|
|
2104
|
+
}
|
|
2105
|
+
supportType(type) {
|
|
2106
|
+
this.typeHandler.register(type);
|
|
2107
|
+
}
|
|
2108
|
+
async ensureCloned() {
|
|
2109
|
+
const gitDir = join22(this.cacheDir, ".git");
|
|
2110
|
+
try {
|
|
2111
|
+
await stat22(gitDir);
|
|
2112
|
+
this.gitExec(`fetch origin ${this.ref}`);
|
|
2113
|
+
this.gitExec(`checkout FETCH_HEAD`);
|
|
2114
|
+
} catch {
|
|
2115
|
+
await mkdir22(DEFAULT_GIT_CACHE, { recursive: true });
|
|
2116
|
+
execSync(`git clone --depth 1 --branch ${this.ref} ${this.url} ${this.cacheDir}`, {
|
|
2117
|
+
stdio: "pipe"
|
|
2118
|
+
});
|
|
2119
|
+
}
|
|
2120
|
+
}
|
|
2121
|
+
gitExec(command) {
|
|
2122
|
+
execSync(`git -C ${this.cacheDir} ${command}`, { stdio: "pipe" });
|
|
2123
|
+
}
|
|
2124
|
+
buildResourcePath(locator) {
|
|
2125
|
+
const rxl = parseRXL(locator);
|
|
2126
|
+
const domain = rxl.domain ?? "localhost";
|
|
2127
|
+
const version = rxl.version ?? "latest";
|
|
2128
|
+
let path = join22(this.cacheDir, this.basePath, domain);
|
|
2129
|
+
if (rxl.path) {
|
|
2130
|
+
path = join22(path, rxl.path);
|
|
2131
|
+
}
|
|
2132
|
+
const resourceName = rxl.type ? `${rxl.name}.${rxl.type}` : rxl.name;
|
|
2133
|
+
return join22(path, resourceName, version);
|
|
2134
|
+
}
|
|
2135
|
+
async get(locator) {
|
|
2136
|
+
await this.ensureCloned();
|
|
2137
|
+
const resourcePath = this.buildResourcePath(locator);
|
|
2138
|
+
const manifestPath = join22(resourcePath, "manifest.json");
|
|
2139
|
+
try {
|
|
2140
|
+
await stat22(manifestPath);
|
|
2141
|
+
} catch {
|
|
2142
|
+
throw new RegistryError(`Resource not found: ${locator}`);
|
|
2143
|
+
}
|
|
2144
|
+
const manifestContent = await readFile22(manifestPath, "utf-8");
|
|
2145
|
+
const manifestData = JSON.parse(manifestContent);
|
|
2146
|
+
const manifest = createRXM(manifestData);
|
|
2147
|
+
if (this.trustedDomain && manifest.domain !== this.trustedDomain) {
|
|
2148
|
+
throw new RegistryError(`Untrusted domain: resource claims "${manifest.domain}" but registry only trusts "${this.trustedDomain}"`);
|
|
2149
|
+
}
|
|
2150
|
+
const contentPath = join22(resourcePath, "content.tar.gz");
|
|
2151
|
+
const data = await readFile22(contentPath);
|
|
2152
|
+
return this.typeHandler.deserialize(data, manifest);
|
|
2153
|
+
}
|
|
2154
|
+
async resolve(locator) {
|
|
2155
|
+
const rxr = await this.get(locator);
|
|
2156
|
+
return this.typeHandler.resolve(rxr);
|
|
2157
|
+
}
|
|
2158
|
+
async exists(locator) {
|
|
2159
|
+
try {
|
|
2160
|
+
await this.ensureCloned();
|
|
2161
|
+
const resourcePath = this.buildResourcePath(locator);
|
|
2162
|
+
const manifestPath = join22(resourcePath, "manifest.json");
|
|
2163
|
+
await stat22(manifestPath);
|
|
2164
|
+
return true;
|
|
2165
|
+
} catch {
|
|
2166
|
+
return false;
|
|
2167
|
+
}
|
|
2168
|
+
}
|
|
2169
|
+
async search(options) {
|
|
2170
|
+
await this.ensureCloned();
|
|
2171
|
+
const { query, limit, offset = 0 } = options ?? {};
|
|
2172
|
+
const locators = [];
|
|
2173
|
+
const baseDir = join22(this.cacheDir, this.basePath);
|
|
2174
|
+
try {
|
|
2175
|
+
const entries = await this.listRecursive(baseDir);
|
|
2176
|
+
for (const entry of entries) {
|
|
2177
|
+
if (!entry.endsWith("manifest.json"))
|
|
2178
|
+
continue;
|
|
2179
|
+
const relativePath = entry.slice(baseDir.length + 1);
|
|
2180
|
+
const rxl = this.parseEntryToRXL(relativePath);
|
|
2181
|
+
if (rxl)
|
|
2182
|
+
locators.push(rxl);
|
|
2183
|
+
}
|
|
2184
|
+
} catch {
|
|
2185
|
+
return [];
|
|
2186
|
+
}
|
|
2187
|
+
let filtered = locators;
|
|
2188
|
+
if (query) {
|
|
2189
|
+
const lowerQuery = query.toLowerCase();
|
|
2190
|
+
filtered = locators.filter((rxl) => {
|
|
2191
|
+
const searchText = `${rxl.domain ?? ""} ${rxl.path ?? ""} ${rxl.name} ${rxl.type ?? ""}`.toLowerCase();
|
|
2192
|
+
return searchText.includes(lowerQuery);
|
|
2193
|
+
});
|
|
2194
|
+
}
|
|
2195
|
+
let result = filtered.slice(offset);
|
|
2196
|
+
if (limit !== undefined) {
|
|
2197
|
+
result = result.slice(0, limit);
|
|
2198
|
+
}
|
|
2199
|
+
return result;
|
|
2200
|
+
}
|
|
2201
|
+
async listRecursive(dir) {
|
|
2202
|
+
const results = [];
|
|
2203
|
+
try {
|
|
2204
|
+
const entries = await readdir22(dir, { withFileTypes: true });
|
|
2205
|
+
for (const entry of entries) {
|
|
2206
|
+
const fullPath = join22(dir, entry.name);
|
|
2207
|
+
if (entry.isDirectory()) {
|
|
2208
|
+
const subEntries = await this.listRecursive(fullPath);
|
|
2209
|
+
results.push(...subEntries);
|
|
2210
|
+
} else {
|
|
2211
|
+
results.push(fullPath);
|
|
2212
|
+
}
|
|
2213
|
+
}
|
|
2214
|
+
} catch {}
|
|
2215
|
+
return results;
|
|
2216
|
+
}
|
|
2217
|
+
parseEntryToRXL(entry) {
|
|
2218
|
+
const dirPath = entry.replace(/[/\\]manifest\.json$/, "");
|
|
2219
|
+
const parts = dirPath.split(/[/\\]/);
|
|
2220
|
+
if (parts.length < 3)
|
|
2221
|
+
return null;
|
|
2222
|
+
const version = parts.pop();
|
|
2223
|
+
const nameTypePart = parts.pop();
|
|
2224
|
+
const domain = parts.shift();
|
|
2225
|
+
const path = parts.length > 0 ? parts.join("/") : undefined;
|
|
2226
|
+
const dotIndex = nameTypePart.lastIndexOf(".");
|
|
2227
|
+
let name;
|
|
2228
|
+
let type;
|
|
2229
|
+
if (dotIndex !== -1) {
|
|
2230
|
+
name = nameTypePart.substring(0, dotIndex);
|
|
2231
|
+
type = nameTypePart.substring(dotIndex + 1);
|
|
2232
|
+
} else {
|
|
2233
|
+
name = nameTypePart;
|
|
2234
|
+
type = undefined;
|
|
2235
|
+
}
|
|
2236
|
+
let locatorStr = domain;
|
|
2237
|
+
if (path)
|
|
2238
|
+
locatorStr += `/${path}`;
|
|
2239
|
+
locatorStr += `/${name}`;
|
|
2240
|
+
if (type)
|
|
2241
|
+
locatorStr += `.${type}`;
|
|
2242
|
+
locatorStr += `@${version}`;
|
|
2243
|
+
try {
|
|
2244
|
+
return parseRXL(locatorStr);
|
|
2245
|
+
} catch {
|
|
2246
|
+
return null;
|
|
2247
|
+
}
|
|
2248
|
+
}
|
|
2249
|
+
async pull(_locator, _options) {
|
|
2250
|
+
throw new RegistryError("GitRegistry is read-only - use LocalRegistry.pull()");
|
|
2251
|
+
}
|
|
2252
|
+
async publish(_resource, _options) {
|
|
2253
|
+
throw new RegistryError("GitRegistry is read-only - use LocalRegistry.publish()");
|
|
2254
|
+
}
|
|
2255
|
+
async link(_resource) {
|
|
2256
|
+
throw new RegistryError("GitRegistry is read-only - use LocalRegistry.link()");
|
|
2257
|
+
}
|
|
2258
|
+
async delete(_locator) {
|
|
2259
|
+
throw new RegistryError("GitRegistry is read-only - use LocalRegistry.delete()");
|
|
2260
|
+
}
|
|
2261
|
+
}
|
|
1983
2262
|
function createRegistry(config) {
|
|
1984
2263
|
if (isRemoteConfig(config)) {
|
|
1985
2264
|
return new RemoteRegistry(config);
|
|
1986
2265
|
}
|
|
2266
|
+
if (isGitConfig(config)) {
|
|
2267
|
+
return new GitRegistry(config);
|
|
2268
|
+
}
|
|
1987
2269
|
return new LocalRegistry(config);
|
|
1988
2270
|
}
|
|
1989
2271
|
var registryCache = new Map;
|
|
@@ -2037,8 +2319,17 @@ class RxrTransport {
|
|
|
2037
2319
|
registry = createRegistry();
|
|
2038
2320
|
} else {
|
|
2039
2321
|
try {
|
|
2040
|
-
const
|
|
2041
|
-
|
|
2322
|
+
const discovery = await discoverRegistry(domain);
|
|
2323
|
+
const registryUrl = discovery.registries[0];
|
|
2324
|
+
if (this.isGitUrl(registryUrl)) {
|
|
2325
|
+
registry = createRegistry({
|
|
2326
|
+
type: "git",
|
|
2327
|
+
url: registryUrl,
|
|
2328
|
+
domain: discovery.domain
|
|
2329
|
+
});
|
|
2330
|
+
} else {
|
|
2331
|
+
registry = createRegistry({ endpoint: registryUrl });
|
|
2332
|
+
}
|
|
2042
2333
|
} catch (error) {
|
|
2043
2334
|
throw new TransportError(`Failed to discover registry for domain ${domain}: ${error.message}`, this.name);
|
|
2044
2335
|
}
|
|
@@ -2046,6 +2337,9 @@ class RxrTransport {
|
|
|
2046
2337
|
registryCache.set(domain, registry);
|
|
2047
2338
|
return registry;
|
|
2048
2339
|
}
|
|
2340
|
+
isGitUrl(url) {
|
|
2341
|
+
return url.startsWith("git@") || url.endsWith(".git");
|
|
2342
|
+
}
|
|
2049
2343
|
parseLocation(location) {
|
|
2050
2344
|
const atIndex = location.indexOf("@");
|
|
2051
2345
|
if (atIndex === -1) {
|
|
@@ -2263,7 +2557,7 @@ class ARP {
|
|
|
2263
2557
|
function createARP(config) {
|
|
2264
2558
|
return new ARP(config);
|
|
2265
2559
|
}
|
|
2266
|
-
var VERSION = "
|
|
2560
|
+
var VERSION = "2.0.0";
|
|
2267
2561
|
export {
|
|
2268
2562
|
textSemantic,
|
|
2269
2563
|
httpsTransport,
|
|
@@ -2285,4 +2579,4 @@ export {
|
|
|
2285
2579
|
ARP
|
|
2286
2580
|
};
|
|
2287
2581
|
|
|
2288
|
-
//# debugId=
|
|
2582
|
+
//# debugId=CFFA41D50CE0FA3A64756E2164756E21
|