Skip to content

Commit

Permalink
refactor: renamed field action to resolver
Browse files Browse the repository at this point in the history
  • Loading branch information
Akryum committed Sep 2, 2024
1 parent 4598bf2 commit 0c1b6fd
Show file tree
Hide file tree
Showing 29 changed files with 309 additions and 182 deletions.
4 changes: 2 additions & 2 deletions packages/app/components/AppNav.vue
Original file line number Diff line number Diff line change
Expand Up @@ -99,9 +99,9 @@ const colorMode = useColorMode()
/>

<AppNavItem
to="/db/fieldActions"
to="/db/resolvers"
icon="i-ph-lightning"
title="Field actions"
title="Resolvers"
/>

<AppNavItem
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,8 +61,8 @@ const routes = computed(() => [
shortcuts: [metaSymbol.value, '', 'P'],
},
{
id: '_route.db.fieldActions',
to: '/db/fieldActions',
id: '_route.db.resolvers',
to: '/db/resolvers',
icon: 'i-ph-lightning',
label: 'Database > Field actions',
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ const props = defineProps<{
resourceName: string
}>()
const { data, refresh } = await useFetch('/api/fieldActions', {
const { data, refresh } = await useFetch('/api/resolvers', {
query: {
resourceName: props.resourceName,
getCode: true,
Expand All @@ -13,7 +13,7 @@ onWindowFocus(refresh)
const filter = ref('')
const actions = computed(() => {
const resolvers = computed(() => {
const filtered = (data.value ?? []).filter((item) => {
return item.fieldName.toLowerCase().includes(filter.value)
})
Expand All @@ -28,16 +28,16 @@ const actions = computed(() => {
<div class="p-4">
<UInput
v-model="filter"
placeholder="Filter actions by name..."
placeholder="Resolvers by name..."
icon="i-ph-magnifying-glass"
autofocus
class="max-w-[400px]"
/>
</div>

<div class="flex-1 overflow-auto">
<FieldActionListItem
v-for="(item, index) in actions"
<ResolverListItem
v-for="(item, index) in resolvers"
:key="index"
:resource-name="props.resourceName"
:field-name="item.fieldName"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<script lang="ts" setup>
const { data, refresh } = await useFetch('/api/fieldActions/counts')
const { data, refresh } = await useFetch('/api/resolvers/counts')
onWindowFocus(refresh)
interface Item {
Expand All @@ -26,7 +26,7 @@ const router = useRouter()
function openResource(item: Item) {
router.push({
name: 'db-fieldActions-resourceName',
name: 'db-resolvers-resourceName',
params: {
resourceName: item.name,
},
Expand Down Expand Up @@ -64,7 +64,7 @@ defineShortcuts({
@select="openResource"
>
<template #default="{ item, ...props }">
<FieldActionResourceListItem
<ResolverResourceListItem
:name="item.name"
:count="item.count"
v-bind="props"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ const icon = computed(() => {
<template>
<LinkListItem
:to="{
name: 'db-fieldActions-resourceName',
name: 'db-resolvers-resourceName',
params: {
resourceName: name,
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ const props = defineProps<{
field: ResourceSchemaField
}>()
const { data, refresh } = await useFetch(`/api/fieldActions/preview`, {
const { data, refresh } = await useFetch(`/api/resolvers/preview`, {
method: 'POST',
body: {
resourceName: props.resourceName,
Expand Down
6 changes: 3 additions & 3 deletions packages/app/components/resource/ResourceTable.vue
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ onWindowFocus(refreshResourceType)
// Field actions
const { data: fieldActions, refresh: refreshFieldActions } = await useFetch(`/api/fieldActions`, {
const { data: resolvers, refresh: refreshFieldActions } = await useFetch(`/api/resolvers`, {
query: {
resourceName: props.resourceName,
},
Expand All @@ -58,11 +58,11 @@ const cols = computed(() => {
for (const field in resourceType.value.fields) {
const data = colsData[field]
const fieldData = resourceType.value.fields[field]
const fieldAction = fieldActions.value?.find(fa => fa.fieldName === field)
const resolver = resolvers.value?.find(fa => fa.fieldName === field)
cols.push({
field,
fieldData,
fieldAction,
resolver,
label: field,
size: data?.size ?? fieldData ? getDefaultColSize(fieldData) : 200,
childResourceType: fieldData.type === 'resource' ? resourceTypeStore.getResourceType(fieldData.resourceName) : undefined,
Expand Down
16 changes: 8 additions & 8 deletions packages/app/components/resource/ResourceTableRow.vue
Original file line number Diff line number Diff line change
Expand Up @@ -47,11 +47,11 @@ async function toggleActive() {
// Open field action file
async function openFieldActionFile(col: Col) {
if (col.fieldAction) {
async function openResolverFile(col: Col) {
if (col.resolver) {
$fetch('/api/openInEditor', {
params: {
file: col.fieldAction.file,
file: col.resolver.file,
},
})
}
Expand Down Expand Up @@ -186,7 +186,7 @@ async function openFieldActionFile(col: Col) {
width: `${col.size}px`,
}"
>
<template v-if="col.fieldAction && col.fieldData">
<template v-if="col.resolver && col.fieldData">
<Menu
placement="top"
:delay="500"
Expand Down Expand Up @@ -214,23 +214,23 @@ async function openFieldActionFile(col: Col) {

<div class="mb-2 flex items-center gap-2">
<div>
Field action
Resolver
</div>

<UButton
v-tooltip="`Open ${col.fieldAction.file}`"
v-tooltip="`Open ${col.resolver.file}`"
icon="i-ph-file-arrow-up"
variant="link"
:padded="false"
@click="openFieldActionFile(col)"
@click="openResolverFile(col)"
/>
</div>

<div
v-if="instance.active"
class="flex mt-4"
>
<ResourceFieldActionPreview
<ResourceResolverPreview
:resource-name="resourceType.name"
:instance-id="instance.id"
:field="col.fieldData"
Expand Down
2 changes: 1 addition & 1 deletion packages/app/components/resource/tableTypes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ export interface Col {
label: string
field: string
size: number
fieldAction?: { file: string }
resolver?: { file: string }
fieldData?: ResourceSchemaField
childResourceType?: ResourceSchemaType
}
Expand Down
7 changes: 0 additions & 7 deletions packages/app/pages/db/fieldActions/index.vue

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,26 +1,26 @@
<script lang="ts" setup>
useSaveRoute({
key: 'db.fieldActions.lastRoute',
basePath: '/db/fieldActions',
key: 'db.resolvers.lastRoute',
basePath: '/db/resolvers',
defaultRoute: {
name: 'db-fieldActions-resourceName',
name: 'db-resolvers-resourceName',
},
})
useHead({
title: 'Field actions',
title: 'Resolvers',
})
</script>

<template>
<SplitPane
save-id="db.fieldActions"
save-id="db.resolvers"
:min="8"
:max="40"
:default-split="12"
>
<template #first>
<FieldActionResourceList />
<ResolverResourceList />
</template>

<template #last>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ const route = useRoute()
</script>

<template>
<FieldActionList
<ResolverList
:resource-name="String(route.params.resourceName)"
/>
</template>
7 changes: 7 additions & 0 deletions packages/app/pages/db/resolvers/index.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<template>
<ExplanationView
icon="i-ph-lightning"
>
Resolvers are functions called when a field is accessed on a resource. For example, you can mock a GraphQL mutation with a resolver on the `Mutation` resource.
</ExplanationView>
</template>
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
export default defineEventHandler(async () => {
const mq = getMq()
const ctx = await mq.getResolvedContext()
const actions = ctx.fieldActions.items.map(fa => ({
const actions = [...ctx.fieldActions.items, ...ctx.resolvers.items].map(fa => ({
resourceName: fa.resourceName,
fieldName: fa.fieldName,
file: fa.file,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ export default defineEventHandler(async (event) => {

const mq = getMq()
const ctx = await mq.getResolvedContext()
let result = ctx.fieldActions.items.map(fa => ({
let result = [...ctx.fieldActions.items, ...ctx.resolvers.items].map(fa => ({
resourceName: fa.resourceName,
fieldName: fa.fieldName,
file: fa.file,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,8 @@ export default defineEventHandler(async (event) => {
const mq = getMq()
const ctx = await mq.getResolvedContext()

const fieldAction = ctx.fieldActions.items.find(fa => fa.resourceName === resourceName && fa.fieldName === fieldName)
const fieldAction = ctx.resolvers.items.find(fa => fa.resourceName === resourceName && fa.fieldName === fieldName)
?? ctx.fieldActions.items.find(fa => fa.resourceName === resourceName && fa.fieldName === fieldName)
if (!fieldAction) {
throw new Error(`Field action not found for resource ${resourceName} and field ${fieldName}`)
}
Expand Down
18 changes: 17 additions & 1 deletion packages/core/src/context.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import { createServer } from './server.js'
import type { ResolvedGraphQLSchema } from './graphql/schema.js'
import { type QueryManagerProxy, createQueryManagerProxy } from './resource/queryManagerProxy.js'
import { MockFileWatcher } from './mock/index.js'
import { FieldActionStore } from './fieldActions/index.js'
import { FieldActionStore, ResolverStore } from './resolvers/index.js'
import { type SettingsManager, createSettingsManager } from './settings/settingsManager.js'
import { type PubSubs, createPubSubs } from './pubsub/createPubSub.js'
import type { MoquerieInstance } from './instance.js'
Expand Down Expand Up @@ -137,7 +137,11 @@ export interface ResolvedContext {
graphqlSchema?: ResolvedGraphQLSchema
server: Server
mockFiles: MockFileWatcher
/**
* @deprecated use `resolvers` instead
*/
fieldActions: FieldActionStore
resolvers: ResolverStore
schemaTransforms: SchemaTransformStore
scripts: ScriptStore
apiRoutes: ApiRouteStore
Expand Down Expand Up @@ -173,6 +177,17 @@ async function createResolvedContext(mq: MoquerieInstance): Promise<ResolvedCont
mq.onDestroy(() => fieldActions?.destroy())
}

// Resolvers

let resolvers = mq.data.resolvedContext?.resolvers

if (!resolvers) {
resolvers = new ResolverStore()
mockFileWatcher.onUpdate(resolvers.handleMockFile.bind(resolvers))
mockFileWatcher.onRemove(resolvers.handleMockFileRemoved.bind(resolvers))
mq.onDestroy(() => resolvers?.destroy())
}

// Schema transforms

let schemaTransforms = mq.data.resolvedContext?.schemaTransforms
Expand Down Expand Up @@ -255,6 +270,7 @@ async function createResolvedContext(mq: MoquerieInstance): Promise<ResolvedCont
server,
mockFiles: mockFileWatcher,
fieldActions,
resolvers,
schemaTransforms,
scripts,
apiRoutes,
Expand Down
28 changes: 0 additions & 28 deletions packages/core/src/fieldActions/fieldActionStore.ts

This file was deleted.

1 change: 0 additions & 1 deletion packages/core/src/fieldActions/index.ts

This file was deleted.

16 changes: 16 additions & 0 deletions packages/core/src/graphql/resolvers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -66,5 +66,21 @@ export async function createGraphQLResolvers(mq: MoquerieInstance): Promise<IRes
})
}

// Resolvers
for (const resolver of ctx.resolvers.items) {
const { resourceName, fieldName, action } = resolver
if (!resolvers[resourceName]) {
resolvers[resourceName] = {}
}
const r = resolvers[resourceName] as Record<string, ISchemaLevelResolver<any, any>>
r[fieldName] = (parent, input) => action({
parent,
input,
db: ctx.db,
pubsub: ctx.pubSubs,
generateId: nanoid,
})
}

return resolvers
}
1 change: 1 addition & 0 deletions packages/core/src/resolvers/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export * from './resolverStore.js'
Loading

0 comments on commit 0c1b6fd

Please sign in to comment.