/ src / renderer / store / resource.ts
resource.ts
  1  import { defineStore } from 'pinia'
  2  import { useMcpStore } from '@/renderer/store/mcp'
  3  
  4  import { ListResourcesResult, ListResourceTemplatesResult } from '@modelcontextprotocol/sdk/types'
  5  
  6  type ResourceTemplatesType = ListResourceTemplatesResult['resourceTemplates']
  7  
  8  type ResourcesType = ListResourcesResult['resources']
  9  
 10  type CursorType = ListResourcesResult['nextCursor']
 11  
 12  type ResourceRecordType = {
 13    resource: ResourceItemType
 14    template: ResourceTemplateType
 15  }
 16  
 17  type ResourceItemType = {
 18    perPage: number
 19    cursor: CursorType
 20    list: ResourcesType
 21  }
 22  
 23  type ResourceTemplateType = {
 24    perPage: number
 25    cursor: CursorType
 26    list: ResourceTemplatesType
 27  }
 28  
 29  export const emptyItem: ResourceItemType | ResourceTemplateType = {
 30    perPage: -1,
 31    cursor: undefined,
 32    list: []
 33  }
 34  
 35  export const useResourceStore = defineStore('resourceStore', {
 36    state: () => ({
 37      data: {} as Record<string, ResourceRecordType>,
 38      loadingTemplates: false,
 39      loadingResources: false
 40    }),
 41    actions: {
 42      loadTemplates: function (serverName: string) {
 43        this.loadingTemplates = true
 44        const mcpStore = useMcpStore()
 45        const resourceFunction = mcpStore.getServerFunction({
 46          serverName,
 47          primitiveName: 'resources',
 48          methodName: 'templates/list'
 49        })
 50        try {
 51          resourceFunction().then((result: ListResourceTemplatesResult) => {
 52            console.log(result)
 53            this.data[serverName] = this.data[serverName] || {}
 54            this.data[serverName].template = {
 55              perPage: -1,
 56              cursor: result.nextCursor,
 57              list: result.resourceTemplates
 58            }
 59          })
 60        } catch (error) {
 61          console.error('Failed to load resource templates:', error)
 62        } finally {
 63          this.loadingTemplates = false
 64        }
 65      },
 66      loadResources: async function (serverName: string) {
 67        // Already loaded
 68        if (this.data[serverName] && 'resource' in this.data[serverName]) return
 69  
 70        this.loadingResources = true
 71        const mcpStore = useMcpStore()
 72        const resourceFunction = mcpStore.getServerFunction({
 73          serverName,
 74          primitiveName: 'resources',
 75          methodName: 'list'
 76        })
 77  
 78        try {
 79          const result: ListResourcesResult = await resourceFunction()
 80          console.log(result)
 81          const resources: ResourcesType = result.resources
 82          this.data[serverName] = this.data[serverName] || {}
 83          this.data[serverName].resource = {
 84            perPage: resources.length,
 85            cursor: result.nextCursor,
 86            list: resources
 87          }
 88        } catch (error) {
 89          console.error('Failed to load resources:', error)
 90        } finally {
 91          this.loadingResources = false
 92        }
 93      },
 94      getNextpage: async function (serverName: string) {
 95        if (!this.data[serverName]?.resource?.cursor) {
 96          return
 97        }
 98        this.loadingResources = true
 99        const currentResource = this.data[serverName].resource
100  
101        try {
102          const mcpStore = useMcpStore()
103          const resourceFunction = mcpStore.getServerFunction({
104            serverName,
105            primitiveName: 'resources',
106            methodName: 'list'
107          })
108  
109          const result: ListResourcesResult = await resourceFunction({
110            method: 'resources/list',
111            params: {
112              cursor: currentResource.cursor
113            }
114          })
115  
116          console.log(result)
117          const resources: ResourcesType = result.resources
118  
119          currentResource.list = [...currentResource.list, ...resources]
120          currentResource.cursor = result.nextCursor
121        } catch (error) {
122          console.error('Failed to load resources:', error)
123        } finally {
124          this.loadingResources = false
125        }
126      }
127    }
128  })