generic entity identification
parent
415450ccae
commit
699335243f
|
@ -1,25 +1,23 @@
|
||||||
<template>
|
<template>
|
||||||
<div :class="['address', { identified: Boolean(inferredId) }]" ref="root">
|
<div :class="['address', { identified: Boolean(inferredIds) }]" ref="root">
|
||||||
<hash-badge :address="address" class="hash-badge" />
|
<hash-badge :address="address" class="hash-badge" />
|
||||||
<router-link v-if="isFile" :to="{ name: 'file', params: { address } }">
|
<router-link v-if="isFile" :to="{ name: 'file', params: { address } }">
|
||||||
{{ address }}
|
{{ address }}
|
||||||
</router-link>
|
</router-link>
|
||||||
<template v-else>
|
<template v-else>
|
||||||
<router-link v-if="link" :to="{ name: 'inspect', params: { address } }">
|
<router-link v-if="link" :to="{ name: 'inspect', params: { address } }">
|
||||||
{{ inferredId || address }}
|
{{ inferredIds.join(" | ") || address }}
|
||||||
</router-link>
|
</router-link>
|
||||||
<template v-else>
|
<template v-else>
|
||||||
{{ inferredId || address }}
|
{{ inferredIds.join(" | ") || address }}
|
||||||
</template>
|
</template>
|
||||||
</template>
|
</template>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts">
|
<script lang="ts">
|
||||||
import { ListingResult } from "@/types/base";
|
import { identify, useEntity } from "@/lib/entity";
|
||||||
import { fetcher } from "@/utils";
|
import { computed, ComputedRef, defineComponent, onMounted, ref } from "vue";
|
||||||
import useSWRV from "swrv";
|
|
||||||
import { computed, defineComponent, onMounted, ref } from "vue";
|
|
||||||
import HashBadge from "./HashBadge.vue";
|
import HashBadge from "./HashBadge.vue";
|
||||||
|
|
||||||
export default defineComponent({
|
export default defineComponent({
|
||||||
|
@ -56,41 +54,15 @@ export default defineComponent({
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
// Set up resolving; retrieve all entries of address
|
// Identification
|
||||||
const { data: addressEntries } = useSWRV<ListingResult, unknown>(
|
const { attributes } = useEntity(props.address);
|
||||||
() => (visible.value && `/api/obj/${props.address}`) || null,
|
const inferredIds: ComputedRef<string[]> = computed(() => {
|
||||||
fetcher
|
return identify(attributes).value.map((eid) => eid.value);
|
||||||
);
|
|
||||||
|
|
||||||
// Out of those, pick out and retrieve those that are referred to as TYPE_ID
|
|
||||||
const { data: typeId } = useSWRV<ListingResult, unknown>(() => {
|
|
||||||
if (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);
|
|
||||||
|
|
||||||
// Return Values of TYPE_ID entries
|
|
||||||
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 {
|
return {
|
||||||
root: rootEl,
|
root: rootEl,
|
||||||
inferredId,
|
inferredIds,
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import { IEntry, ListingResult } from "@/types/base";
|
import { IEntry, ListingResult } from "@/types/base";
|
||||||
import { fetcher } from "@/utils";
|
import { fetcher } from "@/utils";
|
||||||
import useSWRV from "swrv";
|
import useSWRV from "swrv";
|
||||||
import { computed, Ref } from "vue";
|
import { computed, ComputedRef, Ref } from "vue";
|
||||||
|
|
||||||
|
|
||||||
export function useEntity(address: string | (() => string)) {
|
export function useEntity(address: string | (() => string)) {
|
||||||
|
@ -40,4 +40,46 @@ export function useEntity(address: string | (() => string)) {
|
||||||
error,
|
error,
|
||||||
mutate
|
mutate
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
interface EntityIdentification {
|
||||||
|
type: string;
|
||||||
|
value: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function identify(attributes: ComputedRef<[string, IEntry][]>): ComputedRef<EntityIdentification[]> {
|
||||||
|
// Get all identities of the object
|
||||||
|
const isEntries = attributes.value
|
||||||
|
.filter(
|
||||||
|
([_, entry]) => entry.attribute === "IS"
|
||||||
|
).map(([_, entry]) => entry.value.c);
|
||||||
|
|
||||||
|
// Out of those, retrieve their TYPE_ID entries
|
||||||
|
const idAttributes: [string, Ref<ListingResult | undefined>][] = isEntries.map((type) => {
|
||||||
|
const { data: listing } = useSWRV<ListingResult, unknown>(() => {
|
||||||
|
return `/api/obj?query=(matches "${type}" "TYPE_ID" ?)`;
|
||||||
|
}, fetcher);
|
||||||
|
return [type, listing];
|
||||||
|
});
|
||||||
|
|
||||||
|
// Finally, filter own object's attributes according to TYPE_IDs
|
||||||
|
return computed(() => {
|
||||||
|
// For each identity
|
||||||
|
return idAttributes
|
||||||
|
.filter(([_, listing]) => Boolean(listing.value))
|
||||||
|
.map(([type, listing]) => {
|
||||||
|
// And each associated TYPE_ID attribute...
|
||||||
|
return Object.values(listing.value || {}).map((idEntry) => {
|
||||||
|
// return own matchin attributes
|
||||||
|
return attributes.value
|
||||||
|
.filter(([_, e]) => e.attribute === idEntry.value.c)
|
||||||
|
.map(([_, attr]) => {
|
||||||
|
return {
|
||||||
|
type,
|
||||||
|
value: attr.value.c
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}).flat();
|
||||||
|
}).flat();
|
||||||
|
});
|
||||||
}
|
}
|
Loading…
Reference in New Issue