108 lines
2.7 KiB
Vue
108 lines
2.7 KiB
Vue
<template>
|
|
<div :class="['address', { identified: Boolean(inferredId) }]" ref="root">
|
|
<hash-badge :address="address" class="hash-badge" />
|
|
<router-link v-if="isFile" :to="{ name: 'file', params: { address } }">
|
|
{{ address }}
|
|
</router-link>
|
|
<template v-else>
|
|
<router-link v-if="link" :to="{ name: 'inspect', params: { address } }">
|
|
{{ inferredId || address }}
|
|
</router-link>
|
|
<template v-else>{{ inferredId || address }}</template>
|
|
</template>
|
|
</div>
|
|
</template>
|
|
|
|
<script lang="ts">
|
|
import { ListingResult } from "@/types/base";
|
|
import { fetcher } from "@/utils";
|
|
import useSWRV from "swrv";
|
|
import { computed, defineComponent, onMounted, ref } from "vue";
|
|
import HashBadge from "./HashBadge.vue";
|
|
|
|
export default defineComponent({
|
|
components: { HashBadge },
|
|
name: "Address",
|
|
props: {
|
|
address: {
|
|
type: String,
|
|
required: true,
|
|
},
|
|
link: {
|
|
type: Boolean,
|
|
default: false,
|
|
},
|
|
isFile: {
|
|
type: Boolean,
|
|
default: false,
|
|
},
|
|
resolve: {
|
|
type: Boolean,
|
|
default: true,
|
|
},
|
|
},
|
|
setup(props) {
|
|
const rootEl = ref<HTMLElement | undefined>();
|
|
const visible = ref(false);
|
|
const observer = new IntersectionObserver((entries) => {
|
|
visible.value = entries.some((entry) => entry.isIntersecting);
|
|
});
|
|
onMounted(() => {
|
|
if (rootEl.value) {
|
|
observer.observe(rootEl.value);
|
|
}
|
|
});
|
|
|
|
const { data: addressEntries } = useSWRV<ListingResult, unknown>(
|
|
() => (visible.value && `/api/obj/${props.address}`) || null,
|
|
fetcher
|
|
);
|
|
|
|
const { data: typeId } = useSWRV<ListingResult, unknown>(() => {
|
|
if (!props.isFile && props.resolve) {
|
|
const entries = Object.values(addressEntries?.value || {});
|
|
const isEntry = entries.find(
|
|
(entry) => entry.entity === props.address && entry.attribute === "IS"
|
|
);
|
|
if (isEntry) {
|
|
return `/api/obj?query=(matches "${isEntry.value.c}" "TYPE_ID" ?)`;
|
|
}
|
|
}
|
|
return null;
|
|
}, fetcher);
|
|
|
|
const inferredId = computed(() => {
|
|
const typeIdValue = Object.values(typeId?.value || {})[0];
|
|
if (typeIdValue) {
|
|
return Object.values(addressEntries?.value || []).find(
|
|
(entry) =>
|
|
entry.entity === props.address &&
|
|
entry.attribute === typeIdValue.value.c
|
|
)?.value.c;
|
|
}
|
|
});
|
|
|
|
return {
|
|
root: rootEl,
|
|
inferredId,
|
|
};
|
|
},
|
|
});
|
|
</script>
|
|
|
|
<style scoped>
|
|
.address {
|
|
font-family: var(--monospace-font);
|
|
display: flex;
|
|
}
|
|
|
|
.address.identified {
|
|
font-family: var(--default-font);
|
|
font-size: 0.95em;
|
|
}
|
|
|
|
.hash-badge {
|
|
margin-right: 0.5em;
|
|
}
|
|
</style>
|