InjNameService 클래스 구현
권장되는 접근 방식은 이름 서비스 기능을 캡슐화하는 자체InjNameService 클래스를 만드는 것입니다. 이렇게 하면 도메인 확인 및 역방향 조회를 위한 깔끔하고 재사용 가능한 인터페이스가 제공됩니다.
InjNameService 클래스 생성
다음은 애플리케이션에서 사용할 수 있는 완전한 구현입니다:복사
AI에게 묻기
import {
Network,
getNetworkEndpoints,
getInjNameRegistryContractForNetwork,
getInjNameReverseResolverContractForNetwork,
} from "@injectivelabs/networks";
import {
QueryInjName,
ChainGrpcWasmApi,
QueryResolverAddress,
QueryInjectiveAddress,
InjNameServiceQueryTransformer,
} from "@injectivelabs/sdk-ts/client/wasm";
import { nameToNode, normalizeName } from "@injectivelabs/sdk-ts/utils";
export class InjNameService {
private reverseResolverAddress: string;
private registryAddress: string;
private chainGrpcWasmApi: ChainGrpcWasmApi;
constructor(network: Network = Network.Mainnet) {
const endpoints = getNetworkEndpoints(network);
this.chainGrpcWasmApi = new ChainGrpcWasmApi(endpoints.grpc);
this.registryAddress = getInjNameRegistryContractForNetwork(network);
this.reverseResolverAddress =
getInjNameReverseResolverContractForNetwork(network);
}
/**
* 주어진 Injective 주소에 대한 .inj 이름을 가져옵니다 (역방향 확인)
* @param address - 확인할 Injective 주소
* @returns .inj 도메인 이름
*/
async fetchInjName(address: string): Promise<string> {
const query = new QueryInjName({ address }).toPayload();
const response = await this.chainGrpcWasmApi.fetchSmartContractState(
this.reverseResolverAddress,
query
);
const name =
InjNameServiceQueryTransformer.injectiveNameResponseToInjectiveName(
response
);
if (!name) {
throw new Error(`.inj name not found for ${address}`);
}
// 이름이 실제로 동일한 주소로 다시 확인되는지 확인하여 역방향 확인 검증
const addressFromName = await this.fetchInjAddress(name);
if (addressFromName.toLowerCase() !== address.toLowerCase()) {
throw new Error(`.inj name not found for ${address}`);
}
return name;
}
/**
* 주어진 .inj 도메인 이름에 대한 Injective 주소를 가져옵니다 (정방향 확인)
* @param name - 확인할 .inj 도메인 이름
* @returns Injective 주소
*/
async fetchInjAddress(name: string): Promise<string> {
const normalizedName = normalizeName(name);
const node = nameToNode(normalizedName);
if (!node || node.length === 0) {
throw new Error(`The ${name} can't be normalized`);
}
const resolverAddress = await this.fetchResolverAddress(node);
if (!resolverAddress) {
throw new Error(`Resolver address not found for ${name}`);
}
const query = new QueryInjectiveAddress({ node }).toPayload();
const response = await this.chainGrpcWasmApi.fetchSmartContractState(
resolverAddress,
query
);
const address =
InjNameServiceQueryTransformer.injectiveAddressResponseToInjectiveAddress(
response
);
if (!address) {
throw new Error(`Address not found for ${name}`);
}
return address;
}
/**
* 주어진 노드에 대한 resolver 주소를 가져옵니다
* @private
*/
private async fetchResolverAddress(node: number[]): Promise<string> {
const query = new QueryResolverAddress({ node }).toPayload();
const response = await this.chainGrpcWasmApi.fetchSmartContractState(
this.registryAddress,
query
);
return InjNameServiceQueryTransformer.resolverAddressResponseToResolverAddress(
response
);
}
}
InjNameService 클래스 사용
복사
AI에게 묻기
import { Network } from "@injectivelabs/networks";
// 서비스 초기화
const injNameService = new InjNameService(Network.Mainnet);
// .inj 도메인을 주소로 확인
const address = await injNameService.fetchInjAddress("ninja.inj");
console.log("Address:", address);
// 주소를 .inj 도메인으로 역방향 확인
const name = await injNameService.fetchInjName("inj1...");
console.log("Name:", name);
직접 스마트 컨트랙트 쿼리
추상화 레이어 없이 컨트랙트를 직접 쿼리해야 하거나 더 많은 제어가 필요한 경우 개별 메서드는 다음과 같습니다:도메인 확인 (정방향 조회)
.inj 도메인 이름을 Injective 주소로 확인합니다.1단계: Resolver 주소 가져오기
복사
AI에게 묻기
import {
Network,
getNetworkEndpoints,
getInjNameRegistryContractForNetwork,
} from "@injectivelabs/networks";
import { nameToNode, normalizeName } from "@injectivelabs/sdk-ts/utils";
import {
ChainGrpcWasmApi,
QueryResolverAddress,
InjNameServiceQueryTransformer,
} from "@injectivelabs/sdk-ts/client/wasm";
const endpoints = getNetworkEndpoints(Network.Mainnet);
const chainGrpcWasmApi = new ChainGrpcWasmApi(endpoints.grpc);
const registryContractAddress = getInjNameRegistryContractForNetwork(
Network.Mainnet
);
const name = "ninja.inj";
const normalizedName = normalizeName(name);
const node = nameToNode(normalizedName);
const query = new QueryResolverAddress({ node }).toPayload();
const response = await chainGrpcWasmApi.fetchSmartContractState(
registryContractAddress,
query
);
const resolverAddress =
InjNameServiceQueryTransformer.resolverAddressResponseToResolverAddress(
response
);
console.log("Resolver Address:", resolverAddress);
2단계: 도메인의 주소 가져오기
복사
AI에게 묻기
import { Network, getNetworkEndpoints } from "@injectivelabs/networks";
import { nameToNode, normalizeName } from "@injectivelabs/sdk-ts/utils";
import {
ChainGrpcWasmApi,
QueryInjectiveAddress,
InjNameServiceQueryTransformer,
} from "@injectivelabs/sdk-ts/client/wasm";
const endpoints = getNetworkEndpoints(Network.Mainnet);
const chainGrpcWasmApi = new ChainGrpcWasmApi(endpoints.grpc);
const name = "ninja.inj";
const normalizedName = normalizeName(name);
const node = nameToNode(normalizedName);
// 1단계의 resolver 주소 사용
const resolverAddress = "...";
const query = new QueryInjectiveAddress({ node }).toPayload();
const response = await chainGrpcWasmApi.fetchSmartContractState(
resolverAddress,
query
);
const injectiveAddress =
InjNameServiceQueryTransformer.injectiveAddressResponseToInjectiveAddress(
response
);
if (!injectiveAddress) {
throw new Error(`Address not found for ${name}`);
}
console.log("Injective Address:", injectiveAddress);
역방향 확인 (주소에서 도메인으로)
Injective 주소를 기본 .inj 도메인 이름으로 확인합니다.복사
AI에게 묻기
import {
Network,
getNetworkEndpoints,
getInjNameReverseResolverContractForNetwork,
} from "@injectivelabs/networks";
import {
QueryInjName,
ChainGrpcWasmApi,
InjNameServiceQueryTransformer,
} from "@injectivelabs/sdk-ts/client/wasm";
const endpoints = getNetworkEndpoints(Network.Mainnet);
const chainGrpcWasmApi = new ChainGrpcWasmApi(endpoints.grpc);
const reverseResolverContractAddress =
getInjNameReverseResolverContractForNetwork(Network.Mainnet);
const injectiveAddress = "inj1...";
const query = new QueryInjName({ address: injectiveAddress }).toPayload();
const response = await chainGrpcWasmApi.fetchSmartContractState(
reverseResolverContractAddress,
query
);
const name =
InjNameServiceQueryTransformer.injectiveNameResponseToInjectiveName(response);
if (!name) {
throw new Error(`.inj name not found for ${injectiveAddress}`);
}
console.log("INS Name:", name);
복사
AI에게 묻기
import { Network, getNetworkEndpoints, getInjNameRegistryContractForNetwork } from "@injectivelabs/networks";
import { nameToNode, normalizeName } from "@injectivelabs/sdk-ts/utils";
import {
ChainGrpcWasmApi,
QueryResolverAddress,
QueryInjectiveAddress,
InjNameServiceQueryTransformer,
} from "@injectivelabs/sdk-ts/client/wasm";
// gRPC 클라이언트 초기화
const endpoints = getNetworkEndpoints(Network.Mainnet);
const chainGrpcWasmApi = new ChainGrpcWasmApi(endpoints.grpc);
// 역방향 확인에서 이름을 얻은 후 다시 확인되는지 검증
const normalizedName = normalizeName(name);
const node = nameToNode(normalizedName);
// resolver 주소 가져오기
const registryContractAddress = getInjNameRegistryContractForNetwork(
Network.Mainnet
);
const resolverQuery = new QueryResolverAddress({ node }).toPayload();
const resolverResponse = await chainGrpcWasmApi.fetchSmartContractState(
registryContractAddress,
resolverQuery
);
const resolverAddress =
InjNameServiceQueryTransformer.resolverAddressResponseToResolverAddress(
resolverResponse
);
// 이름에서 주소 가져오기
const addressQuery = new QueryInjectiveAddress({ node }).toPayload();
const addressResponse = await chainGrpcWasmApi.fetchSmartContractState(
resolverAddress,
addressQuery
);
const addressFromName =
InjNameServiceQueryTransformer.injectiveAddressResponseToInjectiveAddress(
addressResponse
);
// 이름이 원래 주소로 다시 확인되는지 검증
if (addressFromName.toLowerCase() !== injectiveAddress.toLowerCase()) {
throw new Error(
`Verification failed: ${name} does not resolve back to ${injectiveAddress}`
);
}
참고: 앞서 보여준InjNameService클래스를 사용하는 경우 이 검증을 다음과 같이 단순화할 수 있습니다:await injNameService.fetchInjAddress(name)
모범 사례
- 처리하기 전에 항상 도메인 이름을 정규화하세요 - 일관성을 보장합니다
- 역방향 확인을 검증하세요 - 이름이 실제로 주소로 다시 확인되는지 정방향 조회를 수행하여 확인합니다
- 오류를 우아하게 처리하세요 - 모든 주소에 .inj 이름이 있는 것은 아니며 모든 이름이 등록된 것도 아닙니다
- 적절한 네트워크 구성을 사용하세요 - 올바른 네트워크(메인넷 vs 테스트넷)를 쿼리하는지 확인하세요
- 적절한 경우 결과를 캐시하세요 - 불필요한 컨트랙트 쿼리를 줄입니다
종속성
Injective Name Service를 사용하려면 다음 패키지가 필요합니다:복사
AI에게 묻기
{
"dependencies": {
"@injectivelabs/sdk-ts": "latest",
"@injectivelabs/networks": "latest"
}
}
