mirror of https://github.com/Qortal/Q-Apps-Utils
Qortal Dev
2 months ago
22 changed files with 524 additions and 49 deletions
@ -0,0 +1,51 @@
|
||||
// returns {error: "Cannot find requested data"} if data isn't found
|
||||
import { ProfileCoinType } from "./Utils/Types.ts"; |
||||
|
||||
export const getProfileData = async (property: string) => { |
||||
return (await qortalRequest({ |
||||
action: "GET_PROFILE_DATA", |
||||
property, |
||||
})) as string | object; |
||||
}; |
||||
|
||||
export const setProfileData = async ( |
||||
property: string, |
||||
data: object, |
||||
encrypt = false |
||||
) => { |
||||
if (encrypt) property += "-private"; |
||||
return (await qortalRequest({ |
||||
action: "SET_PROFILE_DATA", |
||||
property, |
||||
data: { customData: data }, |
||||
})) as string; |
||||
}; |
||||
|
||||
export const setDefaultProfileData = async ( |
||||
property: string, |
||||
data: object, |
||||
encrypt = false |
||||
) => { |
||||
if (encrypt) property += "-private"; |
||||
return (await qortalRequest({ |
||||
action: "SET_PROFILE_DATA", |
||||
property, |
||||
data, |
||||
})) as string; |
||||
}; |
||||
|
||||
export const getProfileWallet = async (coin: ProfileCoinType) => { |
||||
return await getProfileData("wallets")[coin]; |
||||
}; |
||||
|
||||
export const setProfileWallet = async (wallet: object) => { |
||||
return await setProfileData("wallets", wallet); |
||||
}; |
||||
|
||||
export const summonProfileModal = async () => { |
||||
return (await qortalRequest({ |
||||
action: "SET_PROFILE_DATA", |
||||
property: "wallets", |
||||
data: {}, |
||||
})) as string; |
||||
}; |
@ -0,0 +1,62 @@
|
||||
export const hasQFundEnded = async (atAddress: string) => { |
||||
try { |
||||
const url = `/at/${atAddress}`; |
||||
const response = await fetch(url, { |
||||
method: "GET", |
||||
headers: { |
||||
"Content-Type": "application/json", |
||||
}, |
||||
}); |
||||
if (response.status === 200) { |
||||
const responseDataSearch = await response.json(); |
||||
if ( |
||||
Object.keys(responseDataSearch).length > 0 && |
||||
responseDataSearch?.isFinished |
||||
) { |
||||
return true; |
||||
} else { |
||||
return false; |
||||
} |
||||
} |
||||
} catch (error) { |
||||
console.log(error); |
||||
} |
||||
}; |
||||
|
||||
export const getATAmount = async crowdfundLink => { |
||||
const crowdfund = await getCrowdfund(crowdfundLink); |
||||
const atAddress = crowdfund?.deployedAT?.aTAddress; |
||||
if (!atAddress) return 0; |
||||
try { |
||||
const res = await qortalRequest({ |
||||
action: "SEARCH_TRANSACTIONS", |
||||
txType: ["PAYMENT"], |
||||
confirmationStatus: "CONFIRMED", |
||||
address: atAddress, |
||||
limit: 0, |
||||
reverse: true, |
||||
}); |
||||
if (res?.length > 0) { |
||||
const totalAmount: number = res.reduce( |
||||
(total: number, transaction) => total + parseFloat(transaction.amount), |
||||
0 |
||||
); |
||||
return totalAmount; |
||||
} |
||||
} catch (e) { |
||||
console.log(e); |
||||
return 0; |
||||
} |
||||
}; |
||||
|
||||
export const getCrowdfund = async (crowdfundLink: string) => { |
||||
const splitLink = crowdfundLink.split("/"); |
||||
const name = splitLink[5]; |
||||
const identifier = splitLink[6]; |
||||
return await qortalRequest({ |
||||
action: "FETCH_QDN_RESOURCE", |
||||
service: "DOCUMENT", |
||||
name, |
||||
identifier, |
||||
}); |
||||
}; |
@ -0,0 +1,28 @@
|
||||
import { SearchResourcesResponse } from "./Utils/Interfaces/Responses.ts"; |
||||
|
||||
export const fetchResourcesByIdentifier = async <T>( |
||||
service: string, |
||||
identifier: string |
||||
) => { |
||||
const names: SearchResourcesResponse[] = await qortalRequest({ |
||||
action: "SEARCH_QDN_RESOURCES", |
||||
service, |
||||
identifier, |
||||
includeMetadata: false, |
||||
}); |
||||
const distinctNames = names.filter( |
||||
(searchResponse, index) => names.indexOf(searchResponse) === index |
||||
); |
||||
|
||||
const promises: Promise<T>[] = []; |
||||
distinctNames.map(response => { |
||||
const resource: Promise<T> = qortalRequest({ |
||||
action: "FETCH_QDN_RESOURCE", |
||||
name: response.name, |
||||
service, |
||||
identifier, |
||||
}); |
||||
promises.push(resource); |
||||
}); |
||||
return (await Promise.all(promises)) as T[]; |
||||
}; |
@ -0,0 +1,8 @@
|
||||
export const getAvatarFromName = async (name: string) => { |
||||
return await qortalRequest({ |
||||
action: "GET_QDN_RESOURCE_URL", |
||||
name, |
||||
service: "THUMBNAIL", |
||||
identifier: "qortal_avatar", |
||||
}); |
||||
}; |
@ -1,12 +0,0 @@
|
||||
export const setProfileData = async ( |
||||
property: string, |
||||
data: object, |
||||
encrypt = false |
||||
) => { |
||||
if (encrypt) property += "-private"; |
||||
return (await qortalRequest({ |
||||
action: "SET_PROFILE_DATA", |
||||
property, |
||||
data: { customData: data }, |
||||
})) as string; |
||||
}; |
@ -0,0 +1,184 @@
|
||||
export const publishFormatter = ( |
||||
file: File |
||||
): Promise<string | ArrayBuffer | null> => |
||||
new Promise((resolve, reject) => { |
||||
const reader = new FileReader(); |
||||
reader.readAsDataURL(file); |
||||
|
||||
reader.onload = () => { |
||||
const result = reader.result; |
||||
reader.onload = null; // remove onload handler
|
||||
reader.onerror = null; // remove onerror handler
|
||||
resolve(result); |
||||
}; |
||||
|
||||
reader.onerror = error => { |
||||
reader.onload = null; // remove onload handler
|
||||
reader.onerror = null; // remove onerror handler
|
||||
reject(error); |
||||
}; |
||||
}); |
||||
|
||||
export function objectToBase64(obj: any) { |
||||
// Step 1: Convert the object to a JSON string
|
||||
const jsonString = JSON.stringify(obj); |
||||
|
||||
// Step 2: Create a Blob from the JSON string
|
||||
const blob = new Blob([jsonString], { type: "application/json" }); |
||||
|
||||
// Step 3: Create a FileReader to read the Blob as a base64-encoded string
|
||||
return new Promise<string>((resolve, reject) => { |
||||
const reader = new FileReader(); |
||||
reader.onloadend = () => { |
||||
if (typeof reader.result === "string") { |
||||
// Remove 'data:application/json;base64,' prefix
|
||||
const base64 = reader.result.replace( |
||||
"data:application/json;base64,", |
||||
"" |
||||
); |
||||
resolve(base64); |
||||
} else { |
||||
reject(new Error("Failed to read the Blob as a base64-encoded string")); |
||||
} |
||||
}; |
||||
reader.onerror = () => { |
||||
reject(reader.error); |
||||
}; |
||||
reader.readAsDataURL(blob); |
||||
}); |
||||
} |
||||
|
||||
export function objectToFile(obj: any) { |
||||
// Step 1: Convert the object to a JSON string
|
||||
const jsonString = JSON.stringify(obj); |
||||
|
||||
// Step 2: Create a Blob from the JSON string
|
||||
return new Blob([jsonString], { type: "application/json" }); |
||||
} |
||||
|
||||
export function objectToUint8Array(obj: any) { |
||||
// Convert the object to a JSON string
|
||||
const jsonString = JSON.stringify(obj); |
||||
|
||||
// Encode the JSON string as a byte array using TextEncoder
|
||||
const encoder = new TextEncoder(); |
||||
const byteArray = encoder.encode(jsonString); |
||||
|
||||
// Create a new Uint8Array and set its content to the encoded byte array
|
||||
const uint8Array = new Uint8Array(byteArray); |
||||
|
||||
return uint8Array; |
||||
} |
||||
|
||||
export function uint8ArrayToBase64(uint8Array: Uint8Array): string { |
||||
const length = uint8Array.length; |
||||
let binaryString = ""; |
||||
const chunkSize = 1024 * 1024; // Process 1MB at a time
|
||||
|
||||
for (let i = 0; i < length; i += chunkSize) { |
||||
const chunkEnd = Math.min(i + chunkSize, length); |
||||
const chunk = uint8Array.subarray(i, chunkEnd); |
||||
binaryString += Array.from(chunk, byte => String.fromCharCode(byte)).join( |
||||
"" |
||||
); |
||||
} |
||||
|
||||
return btoa(binaryString); |
||||
} |
||||
|
||||
export function objectToUint8ArrayFromResponse(obj: any) { |
||||
const len = Object.keys(obj).length; |
||||
const result = new Uint8Array(len); |
||||
|
||||
for (let i = 0; i < len; i++) { |
||||
result[i] = obj[i]; |
||||
} |
||||
|
||||
return result; |
||||
} |
||||
// export function uint8ArrayToBase64(arrayBuffer: Uint8Array): string {
|
||||
// let binary = ''
|
||||
// const bytes = new Uint8Array(arrayBuffer)
|
||||
// const len = bytes.length
|
||||
|
||||
// for (let i = 0; i < len; i++) {
|
||||
// binary += String.fromCharCode(bytes[i])
|
||||
// }
|
||||
|
||||
// return btoa(binary)
|
||||
// }
|
||||
|
||||
export function base64ToUint8Array(base64: string) { |
||||
const binaryString = atob(base64); |
||||
const len = binaryString.length; |
||||
const bytes = new Uint8Array(len); |
||||
|
||||
for (let i = 0; i < len; i++) { |
||||
bytes[i] = binaryString.charCodeAt(i); |
||||
} |
||||
|
||||
return bytes; |
||||
} |
||||
|
||||
export function uint8ArrayToObject(uint8Array: Uint8Array) { |
||||
// Decode the byte array using TextDecoder
|
||||
const decoder = new TextDecoder(); |
||||
const jsonString = decoder.decode(uint8Array); |
||||
|
||||
// Convert the JSON string back into an object
|
||||
const obj = JSON.parse(jsonString); |
||||
|
||||
return obj; |
||||
} |
||||
|
||||
export function processFileInChunks(file: File): Promise<Uint8Array> { |
||||
return new Promise( |
||||
(resolve: (value: Uint8Array) => void, reject: (reason?: any) => void) => { |
||||
const reader = new FileReader(); |
||||
|
||||
reader.onload = function (event: ProgressEvent<FileReader>) { |
||||
const arrayBuffer = event.target?.result as ArrayBuffer; |
||||
const uint8Array = new Uint8Array(arrayBuffer); |
||||
resolve(uint8Array); |
||||
}; |
||||
|
||||
reader.onerror = function (error: ProgressEvent<FileReader>) { |
||||
reject(error); |
||||
}; |
||||
|
||||
reader.readAsArrayBuffer(file); |
||||
} |
||||
); |
||||
} |
||||
|
||||
// export async function processFileInChunks(file: File, chunkSize = 1024 * 1024): Promise<Uint8Array> {
|
||||
// const fileStream = file.stream();
|
||||
// const reader = fileStream.getReader();
|
||||
// const totalLength = file.size;
|
||||
|
||||
// if (totalLength <= 0 || isNaN(totalLength)) {
|
||||
// throw new Error('Invalid file size');
|
||||
// }
|
||||
|
||||
// const combinedArray = new Uint8Array(totalLength);
|
||||
// let offset = 0;
|
||||
|
||||
// while (offset < totalLength) {
|
||||
// const { value, done } = await reader.read();
|
||||
|
||||
// if (done) {
|
||||
// break;
|
||||
// }
|
||||
|
||||
// const chunk = new Uint8Array(value.buffer, value.byteOffset, value.byteLength);
|
||||
|
||||
// // Set elements one by one instead of using combinedArray.set(chunk, offset)
|
||||
// for (let i = 0; i < chunk.length; i++) {
|
||||
// combinedArray[offset + i] = chunk[i];
|
||||
// }
|
||||
|
||||
// offset += chunk.length;
|
||||
// }
|
||||
|
||||
// return combinedArray;
|
||||
// }
|
@ -0,0 +1,13 @@
|
||||
export const getFileExtensionIndex = (s: string) => { |
||||
const lastIndex = s.lastIndexOf("."); |
||||
return lastIndex > 0 ? lastIndex : s.length - 1; |
||||
}; |
||||
|
||||
export const getFileName = (s: string) => { |
||||
return s.substring(0, getFileExtensionIndex(s)); |
||||
}; |
||||
|
||||
export const isNumber = (input: string) => { |
||||
const num = Number(input); |
||||
return !isNaN(num); |
||||
}; |
Loading…
Reference in new issue