julien-c's picture
julien-c HF staff
Working PoC
f8b5fef verified
raw
history blame
3.24 kB
const c = console;
const ENDPOINT = "https://huggingface.co";
async function whoami(token: string): Promise<{ name: string }> {
const path = `${ENDPOINT}/api/whoami-v2`;
const res = await fetch(path, {
headers: {
Authorization: `Bearer ${token}`,
}
});
return await res.json();
}
/**
* @returns `str`: full URL to the newly created repo.
*/
async function createRepo(
token: string,
repoName: string,
repoType: "model" | "dataset" | "space",
): Promise<string> {
const path = `${ENDPOINT}/api/repos/create`;
const res = await fetch(path, {
method: "POST",
headers: {
Authorization: `Bearer ${token}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
name: repoName,
type: repoType,
})
});
const output = await res.json();
if (!res.ok) {
throw new Error(`Error ${res.status}: ${output.error ?? output}`);
}
return output.url;
}
/**
* @returns `str`: URL to the newly uploaded blob.
*/
async function uploadFile(
token: string,
repoId: string,
repoType: "model" | "dataset" | "space",
filename: string,
blob: Blob,
): Promise<string> {
const prefix = (repoType === "dataset") ? "/datasets"
: (repoType === "space") ? "/spaces"
: "";
const path = `${ENDPOINT}/api${prefix}/${repoId}/upload/main/${filename}`;
const res = await fetch(path, {
method: "POST",
headers: {
Authorization: `Bearer ${token}`,
},
body: blob
});
const output = await res.json();
if (!res.ok) {
throw new Error(`Error ${res.status}: ${output.error ?? output}`);
}
return output.url;
}
const FILES_TO_UPLOAD = [
"./mobilenet/model.json",
"./mobilenet/group1-shard1of2",
"./mobilenet/group1-shard2of2",
"./mobilenet/coffee.jpg",
"./mobilenet/README.md",
];
function filenameFromURL(url: string): string {
return url.substring(url.lastIndexOf("/") + 1);
}
window.addEventListener("load", function () {
const tokenEl = document.querySelector<HTMLInputElement>("#token")!;
const repoNameEl = document.querySelector<HTMLInputElement>("#repo_name")!;
const button = document.querySelector("#submit")!;
const output = document.querySelector("#logs")!;
const storedToken = window.localStorage.getItem("hf_token");
if (storedToken) {
tokenEl.value = storedToken;
/// ^to help in dev.
}
repoNameEl.value = `tfjs-mobilenet-${Date.now() % 1_000}`;
/// "random" repo name
button.addEventListener("click", async function () {
const token = tokenEl.value;
const repoName = repoNameEl.value;
if (!token || !repoName) {
alert("You need a token and a repo name");
return;
}
button.setAttribute("disabled", "disabled");
try {
const fullUrl = await createRepo(token, repoName, "model");
const repoId = fullUrl.replace(ENDPOINT, "").replace(/^\//, "");
for (const file of FILES_TO_UPLOAD) {
const blob = await (await fetch(file)).blob();
await uploadFile(token, repoId, "model", filenameFromURL(file), blob);
}
button.insertAdjacentHTML(
"afterend",
`<div class="text-green-500 mb-6">πŸŽ‰ Upload complete! Model page is <a target="_blank" class="text-bold underline" href="${fullUrl}">${fullUrl}</a></div>`
);
} catch (err) {
output.append("\n"+err);
}
button.removeAttribute("disabled");
});
});