Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
72 commits
Select commit Hold shift + click to select a range
574bfb5
wip
gmolki Nov 21, 2025
53b62e5
wip
gmolki Nov 24, 2025
76d24a1
wip
gmolki Nov 24, 2025
3a9d15d
wip: action button
gmolki Nov 24, 2025
59bf145
wip: table content
gmolki Nov 24, 2025
710dd7d
rows content
gmolki Nov 24, 2025
f245e7c
refactor: styles and component reusability
gmolki Nov 25, 2025
de48d43
wip: detail
gmolki Nov 26, 2025
fb8d245
wip
gmolki Nov 26, 2025
a78b23c
wip: refactor
gmolki Nov 26, 2025
2e0cf75
finish refactor of api - domain
gmolki Nov 26, 2025
a7b0d3d
wip
gmolki Nov 27, 2025
5d6ecdd
wip: refactor styled table
gmolki Nov 27, 2025
3384b66
wip: refactor styled table
gmolki Nov 27, 2025
ee14a9e
refactor: table styles
gmolki Nov 27, 2025
3a74b99
wip: form
gmolki Nov 27, 2025
c0779ef
wip: side panel footer style
gmolki Nov 27, 2025
d536c14
wip: change handling
gmolki Nov 27, 2025
4940dd6
wip: form state handling
gmolki Nov 27, 2025
4fb2a48
refactor: form
gmolki Nov 28, 2025
a9540b1
wip: form button handling
gmolki Nov 28, 2025
8bf02da
wip: confirm modal
gmolki Nov 28, 2025
6d48841
wip: confirm modal handling
gmolki Nov 28, 2025
cfbaeab
refactor
gmolki Nov 28, 2025
091d607
wip: form management
gmolki Nov 28, 2025
2ff078e
wip
gmolki Nov 30, 2025
3cc5a55
wip
gmolki Dec 2, 2025
dbea0d6
wip
gmolki Dec 2, 2025
f59e3c7
wip
gmolki Dec 2, 2025
ea96009
main flow working
gmolki Dec 3, 2025
e551ab8
post & aggregate filters designs
gmolki Dec 3, 2025
c5ce49f
channels filters designs
gmolki Dec 3, 2025
8a4e240
wip: fetch account messages data for permissiong
gmolki Dec 11, 2025
8bf7768
wip: fetch account posted channels
gmolki Dec 11, 2025
63db01d
fix: channels and post types displayed
gmolki Dec 11, 2025
c2d50af
wip: side panel inside detail
gmolki Dec 11, 2025
6ee3e5f
scrollable side content
gmolki Dec 11, 2025
c104341
fix: backdrop size
gmolki Dec 11, 2025
10c1246
fix: remove duplicated content
gmolki Dec 11, 2025
320a3e0
working channels changing
gmolki Dec 11, 2025
da23276
fix: channels text ellipsis
gmolki Dec 11, 2025
1358f26
wip: new permissions
gmolki Dec 11, 2025
189ad2f
new permissions
gmolki Dec 12, 2025
f520764
fix detail
gmolki Dec 12, 2025
b72e15c
feat: fetch aggregate keys
gmolki Dec 12, 2025
3637787
refactor: loader action button
gmolki Dec 12, 2025
2b68a75
wip: revoke
gmolki Dec 12, 2025
9d874ff
wip: revoke & restore
gmolki Dec 12, 2025
37f8820
wip: lint
gmolki Dec 12, 2025
31e824a
wip
gmolki Dec 12, 2025
50e9ec8
request logic
gmolki Dec 12, 2025
4f22a7b
wip: update multiple
gmolki Dec 12, 2025
e4d0236
standard update
gmolki Dec 12, 2025
835bcad
checkout notification
gmolki Dec 12, 2025
24f98f6
validate schema on creation
gmolki Dec 12, 2025
aeda8e0
wip: show footer on pending changes
gmolki Dec 15, 2025
543b911
refactor: save changes pops in only on changes pending
gmolki Dec 15, 2025
b47b069
refactor: refresh data on new permissions
gmolki Dec 15, 2025
f52085e
refactor: refresh logic improved
gmolki Dec 15, 2025
babd49c
refactor: useLocalReqeust for channels and post types
gmolki Dec 15, 2025
600a398
fix: build
gmolki Dec 15, 2025
5d3d4f0
fix: select and clear all buttons size
gmolki Dec 15, 2025
eefac9f
refactor: refresh on save all changes
gmolki Dec 15, 2025
04e7560
refactor: slide in footer on new permissions
gmolki Dec 15, 2025
a325c57
fix/refactor: routing navigation
gmolki Dec 16, 2025
0629c37
refactor: select all logic
gmolki Dec 16, 2025
0884083
wip: channels select all
gmolki Dec 16, 2025
e53978a
select all transitions
gmolki Dec 16, 2025
aa0dbc1
refactor: side panel footer
gmolki Dec 16, 2025
127963e
refactor: side panel footer
gmolki Dec 16, 2025
47834b1
refactor: sidepanel width and height
gmolki Dec 17, 2025
c5cbc93
Merge branch 'main' into feat/delegation-panel
gmolki Dec 23, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
"lint:fix": "next lint --fix"
},
"dependencies": {
"@aleph-front/core": "^1.32.0",
"@aleph-front/core": "^1.32.1",
"@aleph-sdk/account": "^1.2.0",
"@aleph-sdk/avalanche": "^1.5.0",
"@aleph-sdk/base": "^1.5.0",
Expand Down
22 changes: 22 additions & 0 deletions src/components/common/CopyToClipboard/cmp.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import { memo } from 'react'
import { useCopyToClipboardAndNotify } from '@aleph-front/core'
import { StyledCopytoClipboard, StyledIcon } from './styles'
import { CopyToClipboardProps } from './types'

export const CopytoClipboard = ({
text,
textToCopy,
iconColor = 'purple3',
}: CopyToClipboardProps) => {
const handleCopy = useCopyToClipboardAndNotify(textToCopy || '')

return (
<StyledCopytoClipboard onClick={handleCopy}>
{text}
<StyledIcon name="copy" $color={iconColor} size="0.8em" />
</StyledCopytoClipboard>
)
}
CopytoClipboard.displayName = 'CopytoClipboard'

export default memo(CopytoClipboard)
1 change: 1 addition & 0 deletions src/components/common/CopyToClipboard/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { default } from './cmp'
23 changes: 23 additions & 0 deletions src/components/common/CopyToClipboard/styles.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import { Icon } from '@aleph-front/core'
import styled, { css } from 'styled-components'
import tw from 'twin.macro'

export const StyledCopytoClipboard = styled.div`
${({ theme }) => css`
${tw`cursor-pointer flex gap-x-2 items-center`}

&:hover ${StyledIcon} {
color: ${theme.color.main0};
}
`}
`

export const StyledIcon = styled(Icon)<{ $color: string }>`
${({ theme, $color }) => css`
color: ${theme.color[$color]};

transition-property: color;
transition-duration: ${theme.transition.duration.fast}ms;
transition-timing-function: ${theme.transition.timing};
`}
`
7 changes: 7 additions & 0 deletions src/components/common/CopyToClipboard/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import { ReactNode } from 'react'

export type CopyToClipboardProps = {
text?: ReactNode
iconColor?: string
textToCopy?: string
}
17 changes: 17 additions & 0 deletions src/components/common/CountBadge/cmp.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import React, { memo } from 'react'
import { CountBadgeProps } from './types'

export const CountBadge = ({ count }: CountBadgeProps) => {
return (
<div
tw="flex items-center min-w-4 min-h-4 w-fit py-1 px-1.5 rounded-md"
className="bg-purple4 fs-10 tp-info"
>
{count}
</div>
)
}

CountBadge.displayName = 'CountBadge'

export default memo(CountBadge) as typeof CountBadge
2 changes: 2 additions & 0 deletions src/components/common/CountBadge/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
export { default } from './cmp'
export * from './types'
3 changes: 3 additions & 0 deletions src/components/common/CountBadge/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export type CountBadgeProps = {
count: number
}
2 changes: 1 addition & 1 deletion src/components/common/DashboardCardWithSideImage/cmp.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ export const DashboardCardWithSideImage = ({
<TextGradient as="h2" type="h3">
{title}
</TextGradient>
{description}
<div className="tp-body1">{description}</div>
</div>
{(withButton || externalLinkUrl) && (
<div tw="mt-6 flex flex-wrap items-center justify-between gap-6">
Expand Down
4 changes: 3 additions & 1 deletion src/components/common/DashboardCardWithSideImage/types.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
import { ReactNode } from 'react'

export type DashboardCardWithSideImageProps = {
info: string
title: string
description: string
description: ReactNode
imageSrc: string
imageAlt: string
withButton?: boolean
Expand Down
84 changes: 84 additions & 0 deletions src/components/common/PermissionsDetail/cmp.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
import React, { memo } from 'react'
import { PermissionsDetailProps } from './types'
import { NoisyContainer, ObjectImg } from '@aleph-front/core'
import CopyToClipboard from '../CopyToClipboard'
import Form from '@/components/form/Form'
import { usePermissionsDetailForm } from './hook'
import PermissionsConfiguration from '@/components/form/PermissionsConfiguration'

export const PermissionsDetail = ({
permissions,
onSubmit,
onUpdate,
channelsPanelOrder = 1,
}: PermissionsDetailProps) => {
const { handleSubmit, errors, control } = usePermissionsDetailForm({
permissions,
onSubmitSuccess: onSubmit,
onUpdate,
})

return (
<>
<Form
tw="overflow-y-auto"
id="permissions-detail-form"
onSubmit={handleSubmit}
errors={errors}
>
<div tw="flex flex-col gap-y-12">
<div tw="flex flex-col gap-y-2">
<div className="tp-info fs-14">Recipient details</div>
<NoisyContainer>
<div tw="flex gap-x-4">
<div>
<ObjectImg id="Object12" size={90} color="main0" />
</div>
<div tw="flex flex-col gap-y-2">
{/* <div>
<div className="tp-info fs-10 text-main0">Created at</div>
<div className="tp-body2">
{permissions.created_at || 'Unknown'}
</div>
</div> */}
<div>
<div className="tp-info fs-10 text-main0">
Recipient account address
</div>
<div>
<CopyToClipboard
text={
<span className="tp-body1 fs-12">
{permissions.id}
</span>
}
textToCopy={permissions.id}
/>
</div>
</div>
<div>
<div className="tp-info fs-10 text-main0">
Recipient alias
</div>
<div className="tp-body2">{permissions.alias || '-'}</div>
</div>
</div>
</div>
</NoisyContainer>
</div>
<div tw="flex flex-col gap-y-2">
<div className="tp-info fs-14">Permissions details</div>
<PermissionsConfiguration
control={control}
name=""
channelsPanelOrder={channelsPanelOrder}
/>
</div>
</div>
</Form>
</>
)
}
PermissionsDetail.displayName = 'PermissionsDetail'

export default memo(PermissionsDetail) as typeof PermissionsDetail
88 changes: 88 additions & 0 deletions src/components/common/PermissionsDetail/hook.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
import { useCallback, useEffect } from 'react'
import { useWatch } from 'react-hook-form'
import { useForm } from '@/hooks/common/useForm'
import {
AccountPermissions,
MessageTypePermissions,
} from '@/domain/permissions'

export type PermissionsDetailFormState = {
channels: string[]
messageTypes: MessageTypePermissions[]
revoked: boolean
}

export type UsePermissionsDetailFormProps = {
permissions: AccountPermissions
onSubmitSuccess?: (updatedPermission: AccountPermissions) => void
onUpdate?: (updatedPermission: AccountPermissions) => void
}

export function usePermissionsDetailForm({
permissions,
onSubmitSuccess,
onUpdate,
}: UsePermissionsDetailFormProps) {
const defaultValues: PermissionsDetailFormState = {
channels: permissions.channels,
messageTypes: permissions.messageTypes,
revoked: permissions.revoked,
}

const onSubmit = useCallback(
async (state: PermissionsDetailFormState) => {
const updatedPermission: AccountPermissions = {
id: permissions.id,
alias: permissions.alias,
...state,
}
console.log('Updated permissions:', updatedPermission)

onSubmitSuccess?.(updatedPermission)
},
[permissions.id, permissions.alias, onSubmitSuccess],
)

const {
control,
handleSubmit,
formState: { errors, isDirty },
} = useForm({
defaultValues,
onSubmit,
onSuccess: () => Promise.resolve(),
})

// Watch form values for real-time updates
const watchedValues = useWatch({ control })

useEffect(() => {
if (onUpdate) {
const updatedPermission: AccountPermissions = {
id: permissions.id,
alias: permissions.alias,
channels: watchedValues.channels ?? permissions.channels,
messageTypes:
(watchedValues.messageTypes as MessageTypePermissions[]) ??
permissions.messageTypes,
revoked: permissions.revoked,
}
onUpdate(updatedPermission)
}
}, [
watchedValues,
permissions.id,
permissions.alias,
permissions.channels,
permissions.messageTypes,
permissions.revoked,
onUpdate,
])

return {
control,
handleSubmit,
errors,
isDirty,
}
}
1 change: 1 addition & 0 deletions src/components/common/PermissionsDetail/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { default } from './cmp'
9 changes: 9 additions & 0 deletions src/components/common/PermissionsDetail/types.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import { AccountPermissions } from '@/domain/permissions'

export type PermissionsDetailProps = {
permissions: AccountPermissions
onSubmit?: (updatedPermission: AccountPermissions) => void
onUpdate?: (updatedPermission: AccountPermissions) => void
channelsPanelOrder?: number
onCancel?: () => void
}
22 changes: 22 additions & 0 deletions src/components/common/Portal/cmp.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import { memo, useEffect, useState } from 'react'
import { createPortal } from 'react-dom'
import { PortalProps } from './types'

export const Portal = ({ children, containerRef }: PortalProps) => {
const [SSR, setSSR] = useState(true)
const container = containerRef?.current

const shouldRender = container || !SSR

useEffect(() => {
if (container) return
setSSR(false)
}, [container])

return shouldRender
? createPortal(children, container || window.document.body)
: null
}
Portal.displayName = 'Portal'

export default memo(Portal) as typeof Portal
2 changes: 2 additions & 0 deletions src/components/common/Portal/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
export { default as Portal } from './cmp'
export type { PortalProps } from './types'
6 changes: 6 additions & 0 deletions src/components/common/Portal/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import { ReactNode, RefObject } from 'react'

export type PortalProps = {
containerRef?: RefObject<HTMLElement>
children: ReactNode
}
Loading